private static void DoCubicForwardDifferencing(Point[] controlPoints, double leftParameter, double rightParameter, double inverseErrorTolerance, List <Point> resultPolyline, List <double> resultParameters)
        {
            double num1   = controlPoints[1].X - controlPoints[0].X;
            double num2   = controlPoints[1].Y - controlPoints[0].Y;
            double num3   = controlPoints[2].X - controlPoints[1].X;
            double num4   = controlPoints[2].Y - controlPoints[1].Y;
            double num5   = controlPoints[3].X - controlPoints[2].X;
            double num6   = controlPoints[3].Y - controlPoints[2].Y;
            double num7   = num3 - num1;
            double num8   = num4 - num2;
            double num9   = num5 - num3;
            double num10  = num6 - num4;
            double num11  = num9 - num7;
            double num12  = num10 - num8;
            Vector vector = controlPoints[3] - controlPoints[0];
            double length = vector.Length;
            double num13  = length < FloatingPointArithmetic.DistanceTolerance ? Math.Max(0.0, Math.Max(VectorUtilities.Distance(controlPoints[1], controlPoints[0]), VectorUtilities.Distance(controlPoints[2], controlPoints[0]))) : Math.Max(0.0, Math.Max(Math.Abs((num7 * vector.Y - num8 * vector.X) / length), Math.Abs((num9 * vector.Y - num10 * vector.X) / length)));
            uint   num14  = 0U;

            if (num13 > 0.0)
            {
                double d = num13 * inverseErrorTolerance;
                num14 = d < (double)int.MaxValue ? BezierCurveFlattener.Log4UnsignedInt32((uint)(d + 0.5)) : BezierCurveFlattener.Log4Double(d);
            }
            int    exp1  = -(int)num14;
            int    exp2  = exp1 + exp1;
            int    exp3  = exp2 + exp1;
            double num15 = FloatingPointArithmetic.DoubleFromMantissaAndExponent(3.0 * num7, exp2);
            double num16 = FloatingPointArithmetic.DoubleFromMantissaAndExponent(3.0 * num8, exp2);
            double num17 = FloatingPointArithmetic.DoubleFromMantissaAndExponent(6.0 * num11, exp3);
            double num18 = FloatingPointArithmetic.DoubleFromMantissaAndExponent(6.0 * num12, exp3);
            double num19 = FloatingPointArithmetic.DoubleFromMantissaAndExponent(3.0 * num1, exp1) + num15 + 1.0 / 6.0 * num17;
            double num20 = FloatingPointArithmetic.DoubleFromMantissaAndExponent(3.0 * num2, exp1) + num16 + 1.0 / 6.0 * num18;
            double num21 = 2.0 * num15 + num17;
            double num22 = 2.0 * num16 + num18;
            double x     = controlPoints[0].X;
            double y     = controlPoints[0].Y;
            Point  point = new Point(0.0, 0.0);
            int    num23 = 1 << (int)num14;
            double num24 = num23 > 0 ? (rightParameter - leftParameter) / (double)num23 : 0.0;
            double num25 = leftParameter;

            for (int index = 1; index < num23; ++index)
            {
                x      += num19;
                y      += num20;
                point.X = x;
                point.Y = y;
                resultPolyline.Add(point);
                num25 += num24;
                resultParameters.Add(num25);
                num19 += num21;
                num20 += num22;
                num21 += num17;
                num22 += num18;
            }
        }
Example #2
0
        private static bool Solve2By2LinearSystem(double[][] m, double[] v)
        {
            double k = m[0][0] * m[1][1] - m[0][1] * m[1][0];

            if (FloatingPointArithmetic.IsVerySmall(k))
            {
                return(false);
            }
            double num1 = v[0];
            double num2 = v[1];

            v[0] = (num1 * m[1][1] - m[0][1] * num2) / k;
            v[1] = (m[0][0] * num2 - num1 * m[1][0]) / k;
            return(true);
        }
        public static bool CompareAlgorithmsOnChordMonotoneCubic(Point[] controlPoints, double errorTolerance)
        {
            if (!BezierCurveFlattener.IsCubicChordMonotone(controlPoints, errorTolerance * errorTolerance))
            {
                return(false);
            }
            List <Point> list1 = new List <Point>(16);
            List <Point> list2 = new List <Point>(16);

            list1.Add(controlPoints[0]);
            list2.Add(controlPoints[0]);
            double x     = controlPoints[3].X - controlPoints[2].X + controlPoints[1].X - controlPoints[0].X;
            double y     = controlPoints[3].Y - controlPoints[2].Y + controlPoints[1].Y - controlPoints[0].Y;
            double num   = 1.0 / errorTolerance;
            uint   depth = BezierCurveFlattener.Log8UnsignedInt32((uint)(FloatingPointArithmetic.Hypotenuse(x, y) * num + 0.5));

            if (depth > 0U)
            {
                --depth;
            }
            if (depth > 0U)
            {
                BezierCurveFlattener.DoCubicMidpointSubdivision(controlPoints, depth, 0.75 * num, list1);
            }
            else
            {
                BezierCurveFlattener.DoCubicForwardDifferencing(controlPoints, 0.75 * num, list1);
            }
            BezierCurveFlattener.AdaptiveForwardDifferencingCubicFlattener differencingCubicFlattener = new BezierCurveFlattener.AdaptiveForwardDifferencingCubicFlattener(controlPoints, errorTolerance, errorTolerance, false);
            Point p = new Point();

            while (differencingCubicFlattener.Next(ref p))
            {
                list2.Add(p);
            }
            list1.Add(controlPoints[3]);
            list2.Add(controlPoints[3]);
            double[] cumulatedChordLength1 = VectorUtilities.GetCumulatedChordLength(list1, 0, list1.Count - 1);
            double[] cumulatedChordLength2 = VectorUtilities.GetCumulatedChordLength(list2, 0, list2.Count - 1);
            int      firstBadVertexInQ     = 0;

            return(VectorUtilities.ArePolylinesClose(list1, cumulatedChordLength1, 0, list1.Count - 1, list2, cumulatedChordLength2, 0, list2.Count - 1, errorTolerance, ref firstBadVertexInQ));
        }
 public static void FlattenCubic(Point[] controlPoints, double errorTolerance, List <Point> resultPolyline, bool connect, List <double> resultParameters)
 {
     if (!connect || resultPolyline.Count == 0)
     {
         resultPolyline.Add(controlPoints[0]);
         resultParameters.Add(0.0);
     }
     if (BezierCurveFlattener.IsCubicChordMonotone(controlPoints, errorTolerance * errorTolerance))
     {
         BezierCurveFlattener.AdaptiveForwardDifferencingCubicFlattener differencingCubicFlattener = new BezierCurveFlattener.AdaptiveForwardDifferencingCubicFlattener(controlPoints, errorTolerance, errorTolerance, true);
         Point  p = new Point();
         double u = 0.0;
         while (differencingCubicFlattener.Next(ref p, ref u))
         {
             resultPolyline.Add(p);
             resultParameters.Add(u);
         }
     }
     else
     {
         double x     = controlPoints[3].X - controlPoints[2].X + controlPoints[1].X - controlPoints[0].X;
         double y     = controlPoints[3].Y - controlPoints[2].Y + controlPoints[1].Y - controlPoints[0].Y;
         double num   = 1.0 / errorTolerance;
         uint   depth = BezierCurveFlattener.Log8UnsignedInt32((uint)(FloatingPointArithmetic.Hypotenuse(x, y) * num + 0.5));
         if (depth > 0U)
         {
             --depth;
         }
         if (depth > 0U)
         {
             BezierCurveFlattener.DoCubicMidpointSubdivision(controlPoints, depth, 0.0, 1.0, 0.75 * num, resultPolyline, resultParameters);
         }
         else
         {
             BezierCurveFlattener.DoCubicForwardDifferencing(controlPoints, 0.0, 1.0, 0.75 * num, resultPolyline, resultParameters);
         }
     }
     resultPolyline.Add(controlPoints[3]);
     resultParameters.Add(1.0);
 }