Example #1
0
    def test_rotate(self):
        R = Rotate()
        S = Rotate(pi / 3)
        T = Rotate(Point(1, 1))
        U = Rotate(-1, 1)

        self.assertTrue(S.vector(), Point(cos(pi / 3), sin(pi / 3)))
        self.assertEqual(Point(T[0], T[1]), T.vector())
        self.assertTrue(Affine.are_near(Rotate.from_degrees(60), S))
        self.assertEqual(R, Rotate.identity())
        self.assertTrue(
            Point.are_near((S * T).vector(),
                           Point(cos(pi / 3 + pi / 4), sin(pi / 3 + pi / 4))))

        self.affine(Affine(R), Affine(S))
        self.affine(Affine(S), Affine(T))
        self.affine(Affine(T), Affine(U))
        self.affine(Affine(U), Affine(R))
Example #2
0
 def test_hLineSegment(self):
     H = HLineSegment(Point(3, 9), Point(9, 9))
     I = HLineSegment(Point(1, 3), Point(92, 3))
     J = HLineSegment.from_point_length( Point(2, 4), 1)
     self.curve( H )
     self.curve( I )
     self.curve( J )
     self.curve( H.portion(0, .25) )
     self.curve( H.derivative() )
     self.curve( H.transformed(Rotate(20)) )
     self.curve( HLineSegment() )
     self.curve( I.reverse() )
     map(self.curve, I.subdivide(0.8))
     
     self.assertAlmostEqual(I.get_Y(), 3)
     J.set_Y(2)
     J.set_initial_X(0)
     J.set_final_X(1)
     self.assertAlmostEqual( J(0), Point(0, 2) )
     self.assertAlmostEqual( J(1), Point(1, 2) )
Example #3
0
    def test_rotate(self):
        R = Rotate()
        S = Rotate(pi/3)
        T = Rotate(Point( 1, 1 ))
        U = Rotate( -1, 1 )

        self.assertTrue(S.vector(), Point(cos(pi/3), sin(pi/3)) )
        self.assertEqual( Point(T[0], T[1]), T.vector() )
        self.assertTrue( Affine.are_near( Rotate.from_degrees(60), S ) )
        self.assertEqual(R, Rotate.identity())
        self.assertTrue( Point.are_near(  ( S * T ).vector(),
        Point( cos( pi/3 + pi/4 ), sin( pi/3 + pi/4 ) ) ) )

        self.affine( Affine(R), Affine(S))
        self.affine( Affine(S), Affine(T))
        self.affine( Affine(T), Affine(U))
        self.affine( Affine(U), Affine(R))
Example #4
0
    def path(self, P):
        for curve in P:
            self.assertIsInstance(curve, Curve)

        self.assertAlmostEqual(P(0), P.front()(0))
        self.curves_equal(P.front(), P[0])

        self.curves_equal(P.back_default(), P[P.size_default() - 1])
        self.curves_equal(P.back_open(), P.back())
        self.assertEqual(P.size_open(), P.size())

        self.assertFalse(P.empty() ^ (P.size() == 0))

        exact = P.bounds_exact().Rect
        exact.expand_by(1e-5)

        fast = P.bounds_fast().Rect
        fast.expand_by(1e-5)
        A1 = Affine(3, 1, 8, 3, 9, 9)
        A2 = Rotate(0.231)

        for i in range(100 * P.size_open() + 1):
            t = i / 100.0
            self.assertTrue(exact.contains(P(t)))
            self.assertTrue(fast.contains(P(t)))
            self.assertAlmostEqual((P * A1)(t), P(t) * A1)
            self.assertAlmostEqual((P * A2)(t), P(t) * A2)

            self.assertAlmostEqual(P(t), P.point_at(t))
            self.assertAlmostEqual(P(t).x, P.value_at(t, 0))
            self.assertAlmostEqual(P(t).y, P.value_at(t, 1))

        if P.closed():
            self.curves_equal(P.back_default(), P.back_closed())
            self.assertEqual(P.size_default(), P.size_closed())
        else:
            self.curves_equal(P.back_default(), P.back_open())
            self.assertEqual(P.size_default(), P.size_open())

        for i in range(10):
            for root in P.roots(i, 0):
                if root < P.size_default():
                    self.assertAlmostEqual(P.value_at(root, 0), i)
            for root in P.roots(i, 1):
                if root < P.size_default():
                    self.assertAlmostEqual(P.value_at(root, 1), i)

        for t in P.all_nearest_times(P(0)):
            self.assertAlmostEqual(P(t), P(0))
        self.assertAlmostEqual(min(P.all_nearest_times(P(0))), 0)
        self.assertAlmostEqual(P.nearest_time(P(0), 0, 0.2), 0)
        self.assertEqual(len(P.nearest_time_per_curve(Point())),
                         P.size_default())

        t, distSq = P.nearest_time_and_dist_sq(Point(-1, -1), 0, P.size())
        self.assertAlmostEqual(distSq**0.5, abs(P(t) - Point(-1, -1)))

        self.assertAlmostEqual(P.portion(0.3, 0.4)(0), P(0.3))
        self.assertAlmostEqual(
            P.portion(interval=Interval(P.size(),
                                        P.size() * 2) / 3)(0),
            P(P.size() / 3.0))

        self.assertAlmostEqual(P(0.23), P.reverse()(P.size() - 0.23))

        self.assertAlmostEqual(P.initial_point(), P(0))
        self.assertAlmostEqual(P.final_point(), P(P.size()))
Example #5
0
    def test_path(self):
        a = Path()
        a.append_curve(
            CubicBezier(Point(-7, -3), Point(2, 8), Point(2, 1), Point(-2, 0)))

        self.assertEqual(a.size(), 1)
        self.assertFalse(a.closed())
        self.path(a)

        a.close(True)
        self.assertTrue(a.closed())
        self.path(a)

        a.close(False)
        a.append_curve(LineSegment(a.final_point(), Point(3, 5)))
        self.assertEqual(a.size(), 2)
        self.path(a)

        a.append_SBasis(SBasis(3, 6) * SBasis(1, 0), SBasis(5, 2))
        self.path(a)

        a.append_curve(
            EllipticalArc(Point(), 1, 2, math.pi / 6, True, True, Point(1, 1)),
            Path.STITCH_DISCONTINUOUS)
        #Stitching adds new segment
        self.assertEqual(a.size(), 5)

        b = Path()
        for c in a:
            b.append_curve(c)

        #TODO: This fails with STITCH_DISCONTINUOUS, but also does so in C++, so
        #it's either correct behaviour or bug in 2geom
        #~ self.path(b)

        b.insert(2, LineSegment(b[2 - 1](1),
                                b[2](0)))  #, Path.STITCH_DISCONTINUOUS)
        self.curves_equal(LineSegment(b[2 - 1](1), b[2](0)), b[2])
        #TODO! fails on root finding
        #self.path(b)

        b.set_initial(a[2](1))
        b.set_final(a[3](0))

        a.insert_slice(3, b, 0, b.size())
        self.assertEqual(a.size(), b.size() * 2 - 1)

        for i in range(b.size()):
            self.curves_equal(a[3 + i], b[i])

        #Looks like bug:


#        A = Path()
#        A.append_curve( CubicBezier( Point(-7, -3), Point(2, 8), Point(2, 1), Point(-2, 0) ) )
#        A.append_curve(EllipticalArc(Point(), 1, 2, math.pi/6, True, True, Point(1, 1)), Path.STITCH_DISCONTINUOUS)
#        print A.roots(0, 1)

#Roots are [1.0, 2.768305708350847, 3.25], Point at second root is
#Point (2.32, -0.48)
#and third root is > 3 - it corresponds to root on closing segment, but A is open,
#and computing A(3.25) results in RangeError - this might be bug or feature.

        self.path(a.portion(0.232, 3.12))
        self.path(a.portion(interval=Interval(0.1, 4.7)))
        self.path(a.portion(0.232, 3.12).reverse())

        b.clear()
        self.assertTrue(b.empty())

        aa = Path()
        for c in a:
            aa.append_curve(c)

        a.erase(0)
        self.assertEqual(a.size(), aa.size() - 1)
        self.assertAlmostEqual(a(0), aa(1))

        a.erase_last()
        self.assertEqual(a.size(), aa.size() - 2)
        self.assertAlmostEqual(a.final_point(), aa[aa.size() - 2](1))

        a.replace(3, QuadraticBezier(a(3), Point(), a(4)))
        self.assertEqual(a.size(), aa.size() - 2)

        cs = [
            LineSegment(Point(-0.5, 0), Point(0.5, 0)).transformed(
                Rotate(-math.pi / 3 * i) * Translate(
                    Point(0,
                          math.sqrt(3) / 2) * Rotate(-math.pi / 3 * i)))
            for i in range(6)
        ]

        hexagon = Path.fromList(cs,
                                stitching=Path.STITCH_DISCONTINUOUS,
                                closed=True)

        if draw:
            utils.draw(hexagon, scale=100)

        #to = 5 because each corner contains one stitching segment
        half_hexagon = Path.fromPath(hexagon, fr=0, to=5)
        if draw:
            utils.draw(half_hexagon, scale=100)

        half_hexagon.replace_slice(
            1, 5, LineSegment(half_hexagon(1), half_hexagon(5)))
        self.assertEqual(half_hexagon.size(), 2)
        self.assertAlmostEqual(half_hexagon(1.5), Point(0.5, 0))

        half_hexagon.stitch_to(half_hexagon(0))
        self.assertAlmostEqual(half_hexagon(2.5), Point())

        a.start(Point(2, 2))
        a.append_SBasis(SBasis(2, 6), SBasis(1, 5) * SBasis(2, 9))
        self.assertAlmostEqual(a(1), Point(6, 5 * 9))

        l = Path.fromList(
            [QuadraticBezier(Point(6, 5 * 9), Point(1, 2), Point(-2, .21))])
        a.append_path(l)
        self.assertAlmostEqual(a.final_point(), l.final_point())

        k = Path.fromList(
            [QuadraticBezier(Point(), Point(2, 1), Point(-2, .21)).reverse()])
        k.append_portion_to(l, 0, 0.3)
        self.assertAlmostEqual(l.final_point(), k(0.3))
Example #6
0
 def get_curve(ellipse):
     p = Point(ellipse.ray(0), 0) * Rotate(ellipse.rot_angle())
     return ellipse.arc(ellipse.center() + p,
                        ellipse.center() - p,
                        ellipse.center() + p * (1 - 1e-7))
Example #7
0
    def test_ellipse(self):
        #TODO: maybe a bug in arc? get_curve(F) returns different ellipse than F
        def get_curve(ellipse):
            p = Point(ellipse.ray(0), 0) * Rotate(ellipse.rot_angle())
            return ellipse.arc(ellipse.center() + p,
                               ellipse.center() - p,
                               ellipse.center() + p * (1 - 1e-7))

        E = Ellipse()
        self.assertAlmostEqual(E.center(), Point())
        self.assertAlmostEqual(E.ray(0), 0)
        self.assertAlmostEqual(E.ray(1), 0)

        F = Ellipse(Point(), 3, 2, 0)
        self.assertAlmostEqual(F.center(), Point())
        self.assertAlmostEqual(F.ray(0), 3)
        self.assertAlmostEqual(F.ray(1), 2)
        self.assertAlmostEqual(F.rot_angle(), 0)
        # x**2/9 + y**2/4 = 1
        self.assertAlmostEqual(F.implicit_form_coefficients()[0], 1 / 9.0)
        self.assertAlmostEqual(F.implicit_form_coefficients()[2], 1 / 4.0)
        self.assertAlmostEqual(F.implicit_form_coefficients()[5], -1)

        coeffs = (1 / 3.0, 0, 1 / 16.0, 1, 0, -1 / 4.0)
        G = Ellipse.from_coefficients(*coeffs)
        self.assertAlmostEqual(G.center(), Point(-3 / 2.0, 0))
        self.assertAlmostEqual(G.ray(0), math.sqrt(3))
        self.assertAlmostEqual(G.ray(1), 4)
        self.assertAlmostEqual(G.rot_angle(), 0)

        points = [
            Point(1, 2),
            Point(2, 9),
            Point(0, 3),
            Point(-3, 8),
            Point(5, 8)
        ]
        G.set_points(points)
        coeffs_G = tuple(G.implicit_form_coefficients())

        def paramG(x, y):
            A, B, C, D, E, F = coeffs_G
            return A * x**2 + B * x * y + C * y**2 + D * x + E * y + F

        for p in points:
            self.assertAlmostEqual(paramG(p.x, p.y), 0)

        G2 = Ellipse.from_points(points)
        coeffs_G2 = tuple(G.implicit_form_coefficients())

        def paramG2(x, y):
            A, B, C, D, E, F = coeffs_G2
            return A * x**2 + B * x * y + C * y**2 + D * x + E * y + F

        for p in points:
            self.assertAlmostEqual(paramG2(p.x, p.y), 0)

        E.set_coefficients(*coeffs_G2)
        for a1, a2 in zip(E.implicit_form_coefficients(),
                          G2.implicit_form_coefficients()):
            self.assertAlmostEqual(a1, a2)

        H = Ellipse.from_circle(Circle(Point(2, 8), 5))
        self.assertAlmostEqual(H.center(), Point(2, 8))
        self.assertAlmostEqual(H.ray(0), 5)
        self.assertAlmostEqual(H.ray(1), 5)

        Ft = F.transformed(Rotate(math.pi / 2))
        self.assertAlmostEqual(F.ray(0), Ft.ray(1))
        self.assertAlmostEqual(F.ray(1), Ft.ray(0))