Beispiel #1
0
    def testparam(self):
        p = (normpath([
            normsubpath([
                normline_pt(0, 0, 10, 0),
                normline_pt(10, 0, 10, 20),
                normline_pt(10, 20, 0, 20),
                normline_pt(0, 20, 0, 0)
            ],
                        closed=1)
        ]) + circle_pt(0, 0, 10) + line_pt(0, 0, 2, 0))

        param = normpathparam(p, 0, 1.5)
        param = param + 0
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 1.5)
        param = param + 15 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 2.5)
        param += 24.9 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 3.995)
        param = 0.1 * unit.t_pt + param
        self.assertEqual(param.normsubpathindex, 1)
        self.assertAlmostEqual(param.normsubpathparam, 0)
        param = param + 0.5 * circle_pt(0, 0, 10).arclen()
        circlerange = len(p.normsubpaths[1])
        self.assertEqual(param.normsubpathindex, 1)
        self.assertAlmostEqual(param.normsubpathparam, 0.5 * circlerange, 4)
        param = param + 0.5 * circle_pt(0, 0, 10).arclen()
        param = param + 2 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 2)
        self.assertAlmostEqual(param.normsubpathparam, 1, 4)
        param = param + 1 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 2)
        self.assertAlmostEqual(param.normsubpathparam, 1.5, 4)

        param = normpathparam(p, 0, 1.5)
        param = param - 15 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 0.5)
        param -= 10 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, -0.5)

        param = normpathparam(p, 0, 1.2)
        param2 = 2 * param
        param += param
        self.assertEqual(param.normsubpathindex, param2.normsubpathindex)
        self.assertEqual(param.normsubpathparam, param2.normsubpathparam)

        param = normpathparam(p, 0, 1.2)
        self.assertTrue(param < 15 * unit.t_pt)
        self.assertTrue(15 * unit.t_pt > param)
        self.assertTrue(param > 12 * unit.t_pt)
        self.assertTrue(12 * unit.t_pt < param)
        self.assertTrue(param < 1)
        self.assertTrue(1 > param)
Beispiel #2
0
    def testparam(self):
        p = ( normpath([normsubpath([normline_pt(0, 0, 10, 0),
                                   normline_pt(10, 0, 10, 20),
                                   normline_pt(10, 20, 0, 20),
                                   normline_pt(0, 20, 0, 0)], closed=1)]) +
              circle_pt(0, 0, 10) +
              line_pt(0, 0, 2, 0))

        param = normpathparam(p, 0, 1.5)
        param = param + 0
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 1.5)
        param = param + 15 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 2.5)
        param += 24.9 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 3.995)
        param = 0.1 * unit.t_pt + param
        self.assertEqual(param.normsubpathindex, 1)
        self.assertAlmostEqual(param.normsubpathparam, 0)
        param = param + 0.5*circle_pt(0, 0, 10).arclen()
        circlerange = len(p.normsubpaths[1])
        self.assertEqual(param.normsubpathindex, 1)
        self.assertAlmostEqual(param.normsubpathparam, 0.5*circlerange, 4)
        param = param + 0.5*circle_pt(0, 0, 10).arclen()
        param = param + 2 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 2)
        self.assertAlmostEqual(param.normsubpathparam, 1, 4)
        param = param + 1 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 2)
        self.assertAlmostEqual(param.normsubpathparam, 1.5, 4)

        param = normpathparam(p, 0, 1.5)
        param = param - 15 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, 0.5)
        param -= 10 * unit.t_pt
        self.assertEqual(param.normsubpathindex, 0)
        self.assertAlmostEqual(param.normsubpathparam, -0.5)
        
        param = normpathparam(p, 0, 1.2)
        param2 = 2*param
        param += param
        self.assertEqual(param.normsubpathindex, param2.normsubpathindex)
        self.assertEqual(param.normsubpathparam, param2.normsubpathparam)

        param = normpathparam(p, 0, 1.2)
        self.assertTrue(param < 15 * unit.t_pt)
        self.assertTrue(15 * unit.t_pt > param)
        self.assertTrue(param > 12 * unit.t_pt)
        self.assertTrue(12 * unit.t_pt < param)
        self.assertTrue(param < 1)
        self.assertTrue(1 > param)
Beispiel #3
0
    def testsplit(self):
        p = normline_pt(0, 0, 10, 0)
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.2])
        s = p.segments([0.2, 0.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(s[0], normline_pt(2, 0, 8, 0))
        s = p.segments([-0.2, 1.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(s[0], normline_pt(-2, 0, 18, 0))

        p = normcurve_pt(0, 0, 10, 0, 20, 0, 30, 0)
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.2])
        s = p.segments([0.2, 0.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(s[0], normcurve_pt(6, 0, 12, 0, 18, 0, 24, 0))
        s = p.segments([-0.2, 1.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(s[0], normcurve_pt(-6, 0, 14, 0, 34, 0, 54, 0))

        p = normsubpath([normline_pt(0, 0, 1, 0),
                         normline_pt(1, 0, 1, 1),
                         normline_pt(1, 1, 0, 1),
                         normline_pt(0, 1, 0, 0)])
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.2])
        s = p.segments([0.5, 2.5])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0.5, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0.5, 1)]))
        s = p.segments([4.5, -1])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0, -0.5, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, -1, 0)]))
        s = p.segments([0, 0.1, 1.2, 1.3, 3.4, 0.5, 4])
        self.assertEqual(len(s), 6)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0, 0, 0.1, 0)]))
        self.assertAlmostEqualNormsubpath(s[1], normsubpath([normline_pt(0.1, 0, 1, 0), normline_pt(1, 0, 1, 0.2)]))
        self.assertAlmostEqualNormsubpath(s[2], normsubpath([normline_pt(1, 0.2, 1, 0.3)]))
        self.assertAlmostEqualNormsubpath(s[3], normsubpath([normline_pt(1, 0.3, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.6)]))
        self.assertAlmostEqualNormsubpath(s[4], normsubpath([normline_pt(0, 0.6, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, 0.5, 0)]))
        self.assertAlmostEqualNormsubpath(s[5], normsubpath([normline_pt(0.5, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0)]))

        p = normsubpath([normline_pt(0, 0, 1, 0),
                         normline_pt(1, 0, 1, 1),
                         normline_pt(1, 1, 0, 1)], closed=1)
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.5])
        s = p.segments([0.5, 2.5])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0.5, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0.5, 1)]))
        s = p.segments([4.5, -1])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0, -0.5, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, -1, 0)]))
        s = p.segments([0, 0.1, 1.2, 1.3, 3.4, 0.5, 4])
        self.assertEqual(len(s), 5)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0.5, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0), normline_pt(0, 0, 0.1, 0)]))
        self.assertAlmostEqualNormsubpath(s[1], normsubpath([normline_pt(0.1, 0, 1, 0), normline_pt(1, 0, 1, 0.2)]))
        self.assertAlmostEqualNormsubpath(s[2], normsubpath([normline_pt(1, 0.2, 1, 0.3)]))
        self.assertAlmostEqualNormsubpath(s[3], normsubpath([normline_pt(1, 0.3, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.6)]))
        self.assertAlmostEqualNormsubpath(s[4], normsubpath([normline_pt(0, 0.6, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, 0.5, 0)]))
        s = p.segments([4, 0.1, 1.2, 1.3, 3.4, 0.5, 0])
        self.assertEqual(len(s), 5)
        self.assertAlmostEqualNormsubpath(s[0], normsubpath([normline_pt(0.5, 0, 0, 0), normline_pt(0, 0, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, 0.1, 0)]))
        self.assertAlmostEqualNormsubpath(s[1], normsubpath([normline_pt(0.1, 0, 1, 0), normline_pt(1, 0, 1, 0.2)]))
        self.assertAlmostEqualNormsubpath(s[2], normsubpath([normline_pt(1, 0.2, 1, 0.3)]))
        self.assertAlmostEqualNormsubpath(s[3], normsubpath([normline_pt(1, 0.3, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.6)]))
        self.assertAlmostEqualNormsubpath(s[4], normsubpath([normline_pt(0, 0.6, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, 0.5, 0)]))

        p = normpath([normsubpath([normline_pt(0, 0, 1, 0), normline_pt(1, 0, 2, 0), normline_pt(2, 0, 3, 0), normline_pt(3, 0, 4, 0)]),
                      normsubpath([normline_pt(0, 1, 1, 1), normline_pt(1, 1, 2, 1), normline_pt(2, 1, 3, 1), normline_pt(3, 1, 4, 1)]),
                      normsubpath([normline_pt(0, 2, 1, 2), normline_pt(1, 2, 2, 2), normline_pt(2, 2, 3, 2), normline_pt(3, 2, 4, 2)]),
                      normsubpath([normline_pt(0, 3, 1, 3), normline_pt(1, 3, 2, 3), normline_pt(2, 3, 3, 3), normline_pt(3, 3, 4, 3)]),
                      normsubpath([normline_pt(0, 4, 1, 4), normline_pt(1, 4, 2, 4), normline_pt(2, 4, 3, 4), normline_pt(3, 4, 4, 4)])])
        s = p.split([normpathparam(p, 3, 0.1),
                     normpathparam(p, 4, 1.2),
                     normpathparam(p, 2, 2.3),
                     normpathparam(p, 0, 3.4),
                     normpathparam(p, 1, 0.5)])
        self.assertEqual(len(s), 6)
        self.assertAlmostEqualNormpath(s[0], normpath([normsubpath([normline_pt(0, 0, 1, 0), normline_pt(1, 0, 2, 0), normline_pt(2, 0, 3, 0), normline_pt(3, 0, 4, 0)]),
                                                           normsubpath([normline_pt(0, 1, 1, 1), normline_pt(1, 1, 2, 1), normline_pt(2, 1, 3, 1), normline_pt(3, 1, 4, 1)]),
                                                           normsubpath([normline_pt(0, 2, 1, 2), normline_pt(1, 2, 2, 2), normline_pt(2, 2, 3, 2), normline_pt(3, 2, 4, 2)]),
                                                           normsubpath([normline_pt(0, 3, 0.1, 3)])]))
        self.assertAlmostEqualNormpath(s[1], normpath([normsubpath([normline_pt(0.1, 3, 1, 3), normline_pt(1, 3, 2, 3), normline_pt(2, 3, 3, 3), normline_pt(3, 3, 4, 3)]),
                                                           normsubpath([normline_pt(0, 4, 1, 4), normline_pt(1, 4, 1.2, 4)])]))
        self.assertAlmostEqualNormpath(s[2], normpath([normsubpath([normline_pt(1.2, 4, 1, 4), normline_pt(1, 4, 0, 4)]),
                                                           normsubpath([normline_pt(4, 3, 3, 3), normline_pt(3, 3, 2, 3), normline_pt(2, 3, 1, 3), normline_pt(1, 3, 0, 3)]),
                                                           normsubpath([normline_pt(4, 2, 3, 2), normline_pt(3, 2, 2.3, 2)])]))
        self.assertAlmostEqualNormpath(s[3], normpath([normsubpath([normline_pt(2.3, 2, 2, 2), normline_pt(2, 2, 1, 2), normline_pt(1, 2, 0, 2)]),
                                                           normsubpath([normline_pt(4, 1, 3, 1), normline_pt(3, 1, 2, 1), normline_pt(2, 1, 1, 1), normline_pt(1, 1, 0, 1)]),
                                                           normsubpath([normline_pt(4, 0, 3.4, 0)])]))
        self.assertAlmostEqualNormpath(s[4], normpath([normsubpath([normline_pt(3.4, 0, 4, 0)]),
                                                           normsubpath([normline_pt(0, 1, 0.5, 1)])]))
        self.assertAlmostEqualNormpath(s[5], normpath([normsubpath([normline_pt(0.5, 1, 1, 1), normline_pt(1, 1, 2, 1), normline_pt(2, 1, 3, 1), normline_pt(3, 1, 4, 1)]),
                                                           normsubpath([normline_pt(0, 2, 1, 2), normline_pt(1, 2, 2, 2), normline_pt(2, 2, 3, 2), normline_pt(3, 2, 4, 2)]),
                                                           normsubpath([normline_pt(0, 3, 1, 3), normline_pt(1, 3, 2, 3), normline_pt(2, 3, 3, 3), normline_pt(3, 3, 4, 3)]),
                                                           normsubpath([normline_pt(0, 4, 1, 4), normline_pt(1, 4, 2, 4), normline_pt(2, 4, 3, 4), normline_pt(3, 4, 4, 4)])]))

        p = normpath([normsubpath([normline_pt(0, -5, 1, -5)]),
                      normsubpath([normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1)], closed=1),
                      normsubpath([normline_pt(0, 5, 1, 5)])])
        s = p.split([normpathparam(p, 1, 3.5)])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormpath(s[0], normpath([normsubpath([normline_pt(0, -5, 1, -5)]),
                                                           normsubpath([normline_pt(0, 0.5, 0, 0), normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.5)]),
                                                           normsubpath([normline_pt(0, 5, 1, 5)])]))

        p = normpath([normsubpath([normline_pt(0, -5, 1, -5)]),
                      normsubpath([normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1)], closed=1),
                      normsubpath([normline_pt(0, 5, 1, 5)])])
        s = p.split([normpathparam(p, 0, 0.5),
                     normpathparam(p, 1, 3.5),
                     normpathparam(p, 0, 0.5),
                     normpathparam(p, 2, 0.5)])
        self.assertEqual(len(s), 5)
        self.assertAlmostEqualNormpath(s[0], normpath([normsubpath([normline_pt(0, -5, 0.5, -5)])]))
        self.assertAlmostEqualNormpath(s[1], normpath([normsubpath([normline_pt(0.5, -5, 1, -5)]),
                                                           normsubpath([normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.5)])]))
        # XXX should we do ???: normsubpath([normline_pt(0, 0.5, 0, 0), normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.5)])]))
        # same question in the next line ...
        self.assertAlmostEqualNormpath(s[2], normpath([normsubpath([normline_pt(0, 0.5, 0, 1), normline_pt(0, 1, 1, 1), normline_pt(1, 1, 1, 0), normline_pt(1, 0, 0, 0)]),
                                                           normsubpath([normline_pt(1, -5, 0.5, -5)])]))
        self.assertAlmostEqualNormpath(s[3], normpath([normsubpath([normline_pt(0.5, -5, 1, -5)]),
                                                           normsubpath([normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0)], closed=1),
                                                           normsubpath([normline_pt(0, 5, 0.5, 5)])]))
        self.assertAlmostEqualNormpath(s[4], normpath([normsubpath([normline_pt(0.5, 5, 1, 5)])]))
Beispiel #4
0
def testparallel_1(c):

    # HARD TESTS of elementary geometry:
    #
    # test for correct skipping of short ugly pieces:
    move = (-2, 0)
    p = path.path(path.moveto(0, 1), path.lineto(10, 0.3), path.lineto(12, 0),
                  path.lineto(0, 0))
    p.append(path.closepath())
    hard_test(c,
              p,
              0.1,
              parallel(0.0),
              move,
              "A",
              checklens=[[15], [15], [4], [4]])
    hard_test(c,
              p,
              0.25,
              parallel(0.0, sharpoutercorners=True),
              move,
              "A",
              checklens=[[12], [12], [3], [3]])
    hard_test(c,
              p,
              0.55,
              parallel(0.0),
              move,
              "A",
              checklens=[[15], [15], [], []])

    # test non-intersecting/too short neighbouring pathels
    move = (0, 4)
    p = path.curve(0, 0, 0, 1, 1, 2, 2, 0)
    p.append(path.lineto(2.1, 0.1))
    p.append(path.lineto(1.6, -2))
    p.append(path.lineto(2.1, -2))
    p.append(path.lineto(-0.15, 0))
    p.append(path.closepath())
    hard_test(c,
              p,
              0.02,
              parallel(0.0, sharpoutercorners=1),
              move,
              "B",
              checklens=[[3], [3], [11], [11]])
    hard_test(c,
              p,
              0.06,
              parallel(0.0),
              move,
              "B",
              checklens=[[3], [3], [10], [
                  9
              ]])  # difference is due to rounding in path._arctobeziers
    hard_test(c,
              p,
              0.3,
              parallel(0.0),
              move,
              "B",
              checklens=[[25], [25], [5], [5]])
    hard_test(c,
              p,
              0.3,
              parallel(0.0, sharpoutercorners=1),
              move,
              "B",
              checklens=[[22], [22], [5], [5]])

    # test extreme precision:
    move = (3.5, 2)
    p = path.curve(0, 0, 0, 1, 1, 1, 1, 0)
    p.append(path.closepath())
    hard_test(c,
              p,
              0.1,
              parallel(0.0),
              move,
              "C",
              checklens=[[8], [8], [2], [2]])
    hard_test(c,
              p,
              0.1,
              parallel(0.0, relerr=1e-15, checkdistanceparams=[0.5]),
              move,
              "C",
              checklens=[[23], [23], [15], [15]])

    # test for numeric instabilities:
    move = (6, 2)
    p = path.curve(0, 0, 1, 1, 1, 1, 2, 0)
    p.append(path.closepath())
    hard_test(c,
              p,
              0.1,
              parallel(0.0, relerr=0.15, checkdistanceparams=[0.5]),
              move,
              "D",
              checklens=[[11], [11], [3], [3]])
    hard_test(c,
              p,
              0.3,
              parallel(0.0),
              move,
              "D",
              checklens=[[11], [11], [3], [3]])

    # test for an empty parallel path:
    move = (5, 5)
    p = path.circle(0, 0, 0.5).normpath()
    nspitems = [
        nspitem for nspitem in p[0]
        if isinstance(nspitem, normpath.normcurve_pt)
    ]
    nspitems[-1] = nspitems[-1].modifiedend_pt(*nspitems[0].atbegin_pt())
    p = normpath.normpath([normpath.normsubpath(nspitems, closed=True)])
    hard_test(c,
              p,
              0.55,
              parallel(0.0),
              move,
              "E",
              checklens=[[], [], [9], [9]])
    hard_test(c,
              p,
              0.4999,
              parallel(0.0, relerr=1.0e-15),
              move,
              "E",
              checklens=[[1, 14, 8], [1, 14], [17], [17]])

    # a degenerate path:
    move = (13, 3)
    p = path.curve(0, 0, 0, -5, 0, 1, 0, 0.5)
    hard_test(c,
              p,
              0.10,
              parallel(0.0, dointersection=False),
              move,
              "F",
              dotests=[True, True, False, False],
              checklens=[[13], [12], [13], [12]])
    hard_test(c,
              p,
              0.13,
              parallel(0.0, dointersection=False),
              move,
              "F",
              dotests=[False, False, True, True],
              checklens=[[13], [12], [13], [12]])

    # test for too big curvatures in the middle:
    move = (9, 2.5)
    p = path.curve(0, 0, 1, 1, 1, 1, 2, 0)
    hard_test(c,
              p,
              0.4,
              parallel(0.0, relerr=1.0e-2),
              move,
              "G",
              checklens=[[2], [2], [4], [4]])
    hard_test(c,
              p,
              0.6,
              parallel(0.0, relerr=1.0e-2),
              move,
              "G",
              checklens=[[2], [2], [4], [4]])
    hard_test(c,
              p,
              0.8,
              parallel(0.0, relerr=1.0e-2),
              move,
              "G",
              checklens=[[2], [2], [4], [4]])
    hard_test(c,
              p,
              1.7,
              parallel(0.0, relerr=1.0e-2),
              move,
              "G",
              checklens=[[2], [2], [1, 1], [1, 1]])

    # deformation of the deformation:
    move = (11, 6)
    p = path.curve(-1, 0, 0, 1, 0, 1, 1, 0).normpath()
    c.stroke(p, [trafo.translate(*move), color.gray(0.8)])
    dist = unit.u_pt / p.curvature_pt([normpath.normpathparam(p, 0, 0.5)])[0]
    p = parallel(dist, relerr=1.0e-2, dointersection=0).deform(p)
    assert len(p) == 2
    assert len(p[0]) == len(p[1]) == 2
    c.stroke(p, [trafo.translate(*move), color.gray(0.8)])
    hard_test(c,
              p,
              -dist,
              parallel(0.0),
              move,
              "H",
              checklens=[[4], [4], [2], [2]])

    # test for infinite curvature in the middle:
    move = (11, 8.5)
    p = path.curve(0, 0, 1, 1, 0, 1, 1, 0).normpath()
    hard_test(c,
              p,
              0.2,
              parallel(0.0),
              move,
              "I",
              checklens=[[1, 1], [1, 1], [2], [2]])
    hard_test(c,
              p,
              1.5,
              parallel(0.0),
              move,
              "I",
              checklens=[[1, 1], [1, 1], [7], [7]])
    #ard_test(c, p, 5.0, parallel(0.0), move, "I", checklens=[[],[],[7],[7]])

    # test for infinite curvature at the end:
    move = (-2, 13)
    p = path.curve(0, 0, 0.5, 0.5, 0.75, 0.5, 0.75, 0.5)
    hard_test(c,
              p,
              0.1,
              parallel(0.0, relerr=1.0e-4),
              move,
              "J",
              checklens=[[5], [5], [5], [5]])
    # test for infinite curvature when the path goes on
    # XXX this is not correctly detected if rlineto(1,0). Expect two nsp
    p.append(path.rlineto(0, 1))
    hard_test(c,
              p,
              0.22,
              parallel(0.0, relerr=1.0e-4),
              move,
              "J",
              checklens=[[4], [4], [3, 1], [1, 3]])

    # test for too big curvature in the middle, the non-intersecting case
    move = (0, 8)
    p = path.curve(-1, -1, 4, 4, -4, 4, 1, -1).normpath()
    dist = unit.u_pt * (1.0 /
                        p.curvature_pt([normpath.normpathparam(p, 0, 0.5)])[0])
    hard_test(c,
              p,
              1.5 * dist,
              parallel(0.0, dointersection=False),
              move,
              "K",
              checklens=[[1, 1], [1, 1], [2], [2]])
    hard_test(c,
              p,
              dist + normpath._epsilon,
              parallel(0.0, dointersection=False, relerr=1.0e-5),
              move,
              "K",
              checklens=[[11, 11], [11, 11], [16], [16]])
    hard_test(c,
              p,
              dist + 0 * normpath._epsilon,
              parallel(0.0, dointersection=False, relerr=1.0e-5),
              move,
              "K",
              checklens=[[22], [22], [16], [16]])

    # what is to be done with the arcs running around corners?
    # for dist=1.1 they do not even intersect with the original path:
    # TODO
    move = (8, 14)
    p = path.rect(0, 0, 1, 1).normpath()
    hard_test(c,
              p,
              1.1,
              parallel(0.0),
              move,
              "L",
              dotests=[True, True, False, False],
              checklens=[[20], [20], None, None])
    hard_test(c,
              p,
              0.55,
              parallel(0.0),
              move,
              "L",
              dotests=[True, True, False, False],
              checklens=[[28], [28], None, None])

    # very small lines approximating a curve
    # make sure that there is no "dust" remaining from the many intersections
    move = (3, 9)
    N = 12
    angle = 0.5 * math.pi / (N - 1.0)
    p = path.path(path.moveto(0, 0))
    for n in range(N):
        p.append(path.lineto(2 + math.sin(n * angle), 1 - math.cos(n * angle)))
    p.append(path.rlineto(0, 1))
    p.append(path.rlineto(2, 0))
    p.append(path.rlineto(0, -2))
    p = p.transformed(trafo.translate(0, 0.05))
    p = p << p.transformed(trafo.scale(1, -1)).reversed()
    hard_test(c,
              p,
              0.6,
              parallel(0.0),
              move,
              "M",
              checklens=[[43], [43], [29], [29]])

    # intersections where paths are parallel (in the middle of a nsp-item)
    move = (4, 15)
    c.text(move[0], move[1] + 0.2, "N")
    tr = trafo.translate(*move)
    par = parallel(0.1)
    par.dist_pt = unit.topt(par.distance)
    c1 = path.curve(-2, -1, -2, 1, 2, -1, 2, 1).transformed(tr).normpath()
    c2 = path.curve(-2, -1, -2, 1 / 3.0, 2, 1 / 3.0, 2,
                    -1).transformed(tr).normpath()
    l = path.line(-2, 0, 2, 0).transformed(tr).normpath()
    for p in [c1, c2, l]:
        c.stroke(p)
    p = (c1 + l).normpath()
    try:
        par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                          mynormpathparam(p, 1, 0, 0.5))
    except IntersectionError as e:
        assert str(
            e
        ) == "Cannot determine whether curves intersect (parallel and equally curved)"
    p = c2 + l
    assert par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                             mynormpathparam(p, 1, 0, 0.5))
    p = c2 + l.reversed()
    assert par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                             mynormpathparam(p, 1, 0, 0.5))
    p = c2.reversed() + l
    assert not par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                                 mynormpathparam(p, 1, 0, 0.5))
    p = c2.reversed() + l.reversed()
    assert not par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                                 mynormpathparam(p, 1, 0, 0.5))
    p = c1 + c2
    assert not par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                                 mynormpathparam(p, 1, 0, 0.5))
    p = c2 + c1
    assert par._can_continue(mynormpathparam(p, 0, 0, 0.5),
                             mynormpathparam(p, 1, 0, 0.5))
    # intersections where paths are parallel (between nsp-items)
    c11, c12 = c1.split([normpath.normpathparam(c1, 0, 0.5)])
    c21, c22 = c2.split([normpath.normpathparam(c2, 0, 0.5)])
    l1, l2 = l.split([normpath.normpathparam(l, 0, 0.5)])
    p = (c21 << l2 + l1 << c22).normpath()  # curve-line + line-curve
    assert par._can_continue(mynormpathparam(p, 1, 0, 1),
                             mynormpathparam(p, 0, 1, 0))  # line -> line
    assert not par._can_continue(mynormpathparam(p, 0, 0, 1),
                                 mynormpathparam(p, 1, 1, 0))  # curve -> curve

    # intersections where paths are parallel (in the middle of a nsp-item)
    move = (12, 13)
    p1 = path.path(path.moveto(0, 0), path.curveto(0, 3, 1, 5, 1,
                                                   0)).normpath()
    params1, params2 = p1.intersect(path.line(0.5, -1, 0.5, 5))
    p11, p12 = p1.split(params1)
    p11.append(path.rlineto(0, -2))
    p = p11 << p12
    p.append(path.closepath())
    hard_test(c,
              p,
              0.55,
              parallel(0.0),
              move,
              "O",
              dotests=[True, True, False, False],
              checklens=[[10], [10], None, None])

    # jump to too large curvature between nspitems
    move = (-2, 17)
    p = path.path(path.moveto(0, 0), path.arc(2, 0.5, 0.5, -90, 90),
                  path.lineto(0, 1)).normpath()
    hard_test(c,
              p,
              0.55,
              parallel(0.0),
              move,
              "P",
              dotests=[True, True, True, True],
              checklens=[[1, 1], [1, 1], [7], [7]])
Beispiel #5
0
import sys, math
sys.path[:0] = [".."]
from pyx import *
from pyx.normpath import normpathparam

def mark(c, t, phi, x, y):
    c.stroke(path.line(x-0.1, y, x+0.1, y))
    c.stroke(path.line(x, y-0.1, x, y+0.1))
    t = text.text(x, y, t, [text.halign.center, text.vshift.mathaxis])
    t.circlealign(0.2, math.cos(phi*math.pi/180), math.sin(phi*math.pi/180))
    c.insert(t)
c = canvas.canvas()
b = path.curve(0, 0, 0, 0.5, 0, 1, 4, 4).normpath()
l = path.line(*(b.atbegin() + b.atend()))
c.draw(l, [deco.shownormpath()])
c.draw(b, [deco.shownormpath()])
mark(c, "A", 180, 0, 0)
mark(c, "B", 180, 0, 0.5)
mark(c, "C", 180, 0, 1)
mark(c, "D", 0, 4, 4)
mark(c, "Y", -45, 2, 2)
mark(c, "X", 90, *b.at(normpathparam(b, 0, 0.5)))
mark(c, "X'", 135, *b.at(0.5*b.arclen()))
c.writeEPSfile("beziertoline")
c.writePDFfile("beziertoline")
Beispiel #6
0
import sys, math
sys.path[:0] = [".."]
from pyx import *
from pyx.normpath import normpathparam


def mark(c, t, phi, x, y):
    c.stroke(path.line(x - 0.1, y, x + 0.1, y))
    c.stroke(path.line(x, y - 0.1, x, y + 0.1))
    t = text.text(x, y, t, [text.halign.center, text.vshift.mathaxis])
    t.circlealign(0.2, math.cos(phi * math.pi / 180),
                  math.sin(phi * math.pi / 180))
    c.insert(t)


c = canvas.canvas()
b = path.curve(0, 0, 0, 0.5, 0, 1, 4, 4).normpath()
l = path.line(*(b.atbegin() + b.atend()))
c.draw(l, [deco.shownormpath()])
c.draw(b, [deco.shownormpath()])
mark(c, "A", 180, 0, 0)
mark(c, "B", 180, 0, 0.5)
mark(c, "C", 180, 0, 1)
mark(c, "D", 0, 4, 4)
mark(c, "Y", -45, 2, 2)
mark(c, "X", 90, *b.at(normpathparam(b, 0, 0.5)))
mark(c, "X'", 135, *b.at(0.5 * b.arclen()))
c.writeEPSfile("beziertoline")
c.writePDFfile("beziertoline")
Beispiel #7
0
def testparallel_1(c):

    # HARD TESTS of elementary geometry:
    #
    # test for correct skipping of short ugly pieces:
    move = (-2, 0)
    p = path.path(
        path.moveto(0, 1), path.lineto(10, 0.3), path.lineto(12, 0),
        path.lineto(0, 0))
    p.append(path.closepath())
    hard_test(
        c, p, 0.1, parallel(0.0), move, "A", checklens=[[15], [15], [4], [4]])
    hard_test(
        c,
        p,
        0.25,
        parallel(0.0, sharpoutercorners=True),
        move,
        "A",
        checklens=[[12], [12], [3], [3]])
    hard_test(
        c, p, 0.55, parallel(0.0), move, "A", checklens=[[15], [15], [], []])

    # test non-intersecting/too short neighbouring pathels
    move = (0, 4)
    p = path.curve(0, 0, 0, 1, 1, 2, 2, 0)
    p.append(path.lineto(2.1, 0.1))
    p.append(path.lineto(1.6, -2))
    p.append(path.lineto(2.1, -2))
    p.append(path.lineto(-0.15, 0))
    p.append(path.closepath())
    hard_test(
        c,
        p,
        0.02,
        parallel(0.0, sharpoutercorners=1),
        move,
        "B",
        checklens=[[3], [3], [11], [11]])
    hard_test(
        c, p, 0.06, parallel(0.0), move, "B",
        checklens=[[3], [3], [10],
                   [9]])  # difference is due to rounding in path._arctobeziers
    hard_test(
        c, p, 0.3, parallel(0.0), move, "B", checklens=[[25], [25], [5], [5]])
    hard_test(
        c,
        p,
        0.3,
        parallel(0.0, sharpoutercorners=1),
        move,
        "B",
        checklens=[[22], [22], [5], [5]])

    # test extreme precision:
    move = (3.5, 2)
    p = path.curve(0, 0, 0, 1, 1, 1, 1, 0)
    p.append(path.closepath())
    hard_test(
        c, p, 0.1, parallel(0.0), move, "C", checklens=[[8], [8], [2], [2]])
    hard_test(
        c,
        p,
        0.1,
        parallel(0.0, relerr=1e-15, checkdistanceparams=[0.5]),
        move,
        "C",
        checklens=[[23], [23], [15], [15]])

    # test for numeric instabilities:
    move = (6, 2)
    p = path.curve(0, 0, 1, 1, 1, 1, 2, 0)
    p.append(path.closepath())
    hard_test(
        c,
        p,
        0.1,
        parallel(0.0, relerr=0.15, checkdistanceparams=[0.5]),
        move,
        "D",
        checklens=[[11], [11], [3], [3]])
    hard_test(
        c, p, 0.3, parallel(0.0), move, "D", checklens=[[11], [11], [3], [3]])

    # test for an empty parallel path:
    move = (5, 5)
    p = path.circle(0, 0, 0.5).normpath()
    nspitems = [
        nspitem for nspitem in p[0]
        if isinstance(nspitem, normpath.normcurve_pt)
    ]
    nspitems[-1] = nspitems[-1].modifiedend_pt(*nspitems[0].atbegin_pt())
    p = normpath.normpath([normpath.normsubpath(nspitems, closed=True)])
    hard_test(
        c, p, 0.55, parallel(0.0), move, "E", checklens=[[], [], [9], [9]])
    hard_test(
        c,
        p,
        0.4999,
        parallel(0.0, relerr=1.0e-15),
        move,
        "E",
        checklens=[[1, 14, 8], [1, 14], [17], [17]])

    # a degenerate path:
    move = (13, 3)
    p = path.curve(0, 0, 0, -5, 0, 1, 0, 0.5)
    hard_test(
        c,
        p,
        0.10,
        parallel(0.0, dointersection=False),
        move,
        "F",
        dotests=[True, True, False, False],
        checklens=[[13], [12], [13], [12]])
    hard_test(
        c,
        p,
        0.13,
        parallel(0.0, dointersection=False),
        move,
        "F",
        dotests=[False, False, True, True],
        checklens=[[13], [12], [13], [12]])

    # test for too big curvatures in the middle:
    move = (9, 2.5)
    p = path.curve(0, 0, 1, 1, 1, 1, 2, 0)
    hard_test(
        c,
        p,
        0.4,
        parallel(0.0, relerr=1.0e-2),
        move,
        "G",
        checklens=[[2], [2], [4], [4]])
    hard_test(
        c,
        p,
        0.6,
        parallel(0.0, relerr=1.0e-2),
        move,
        "G",
        checklens=[[2], [2], [4], [4]])
    hard_test(
        c,
        p,
        0.8,
        parallel(0.0, relerr=1.0e-2),
        move,
        "G",
        checklens=[[2], [2], [4], [4]])
    hard_test(
        c,
        p,
        1.7,
        parallel(0.0, relerr=1.0e-2),
        move,
        "G",
        checklens=[[2], [2], [1, 1], [1, 1]])

    # deformation of the deformation:
    move = (11, 6)
    p = path.curve(-1, 0, 0, 1, 0, 1, 1, 0).normpath()
    c.stroke(p, [trafo.translate(*move), color.gray(0.8)])
    dist = unit.u_pt / p.curvature_pt([normpath.normpathparam(p, 0, 0.5)])[0]
    p = parallel(dist, relerr=1.0e-2, dointersection=0).deform(p)
    assert len(p) == 2
    assert len(p[0]) == len(p[1]) == 2
    c.stroke(p, [trafo.translate(*move), color.gray(0.8)])
    hard_test(
        c, p, -dist, parallel(0.0), move, "H", checklens=[[4], [4], [2], [2]])

    # test for infinite curvature in the middle:
    move = (11, 8.5)
    p = path.curve(0, 0, 1, 1, 0, 1, 1, 0).normpath()
    hard_test(
        c,
        p,
        0.2,
        parallel(0.0),
        move,
        "I",
        checklens=[[1, 1], [1, 1], [2], [2]])
    hard_test(
        c,
        p,
        1.5,
        parallel(0.0),
        move,
        "I",
        checklens=[[1, 1], [1, 1], [7], [7]])
    #ard_test(c, p, 5.0, parallel(0.0), move, "I", checklens=[[],[],[7],[7]])

    # test for infinite curvature at the end:
    move = (-2, 13)
    p = path.curve(0, 0, 0.5, 0.5, 0.75, 0.5, 0.75, 0.5)
    hard_test(
        c,
        p,
        0.1,
        parallel(0.0, relerr=1.0e-4),
        move,
        "J",
        checklens=[[5], [5], [5], [5]])
    # test for infinite curvature when the path goes on
    # XXX this is not correctly detected if rlineto(1,0). Expect two nsp
    p.append(path.rlineto(0, 1))
    hard_test(
        c,
        p,
        0.22,
        parallel(0.0, relerr=1.0e-4),
        move,
        "J",
        checklens=[[4], [4], [3, 1], [1, 3]])

    # test for too big curvature in the middle, the non-intersecting case
    move = (0, 8)
    p = path.curve(-1, -1, 4, 4, -4, 4, 1, -1).normpath()
    dist = unit.u_pt * (
        1.0 / p.curvature_pt([normpath.normpathparam(p, 0, 0.5)])[0])
    hard_test(
        c,
        p,
        1.5 * dist,
        parallel(0.0, dointersection=False),
        move,
        "K",
        checklens=[[1, 1], [1, 1], [2], [2]])
    hard_test(
        c,
        p,
        dist + normpath._epsilon,
        parallel(0.0, dointersection=False, relerr=1.0e-5),
        move,
        "K",
        checklens=[[11, 11], [11, 11], [16], [16]])
    hard_test(
        c,
        p,
        dist + 0 * normpath._epsilon,
        parallel(0.0, dointersection=False, relerr=1.0e-5),
        move,
        "K",
        checklens=[[22], [22], [16], [16]])

    # what is to be done with the arcs running around corners?
    # for dist=1.1 they do not even intersect with the original path:
    # TODO
    move = (8, 14)
    p = path.rect(0, 0, 1, 1).normpath()
    hard_test(
        c,
        p,
        1.1,
        parallel(0.0),
        move,
        "L",
        dotests=[True, True, False, False],
        checklens=[[20], [20], None, None])
    hard_test(
        c,
        p,
        0.55,
        parallel(0.0),
        move,
        "L",
        dotests=[True, True, False, False],
        checklens=[[28], [28], None, None])

    # very small lines approximating a curve
    # make sure that there is no "dust" remaining from the many intersections
    move = (3, 9)
    N = 12
    angle = 0.5 * math.pi / (N - 1.0)
    p = path.path(path.moveto(0, 0))
    for n in range(N):
        p.append(path.lineto(2 + math.sin(n * angle), 1 - math.cos(n * angle)))
    p.append(path.rlineto(0, 1))
    p.append(path.rlineto(2, 0))
    p.append(path.rlineto(0, -2))
    p = p.transformed(trafo.translate(0, 0.05))
    p = p << p.transformed(trafo.scale(1, -1)).reversed()
    hard_test(
        c,
        p,
        0.6,
        parallel(0.0),
        move,
        "M",
        checklens=[[43], [43], [29], [29]])

    # intersections where paths are parallel (in the middle of a nsp-item)
    move = (4, 15)
    c.text(move[0], move[1] + 0.2, "N")
    tr = trafo.translate(*move)
    par = parallel(0.1)
    par.dist_pt = unit.topt(par.distance)
    c1 = path.curve(-2, -1, -2, 1, 2, -1, 2, 1).transformed(tr).normpath()
    c2 = path.curve(-2, -1, -2, 1 / 3.0, 2, 1 / 3.0, 2,
                    -1).transformed(tr).normpath()
    l = path.line(-2, 0, 2, 0).transformed(tr).normpath()
    for p in [c1, c2, l]:
        c.stroke(p)
    p = (c1 + l).normpath()
    try:
        par._can_continue(
            mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    except IntersectionError as e:
        assert str(
            e
        ) == "Cannot determine whether curves intersect (parallel and equally curved)"
    p = c2 + l
    assert par._can_continue(
        mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    p = c2 + l.reversed()
    assert par._can_continue(
        mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    p = c2.reversed() + l
    assert not par._can_continue(
        mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    p = c2.reversed() + l.reversed()
    assert not par._can_continue(
        mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    p = c1 + c2
    assert not par._can_continue(
        mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    p = c2 + c1
    assert par._can_continue(
        mynormpathparam(p, 0, 0, 0.5), mynormpathparam(p, 1, 0, 0.5))
    # intersections where paths are parallel (between nsp-items)
    c11, c12 = c1.split([normpath.normpathparam(c1, 0, 0.5)])
    c21, c22 = c2.split([normpath.normpathparam(c2, 0, 0.5)])
    l1, l2 = l.split([normpath.normpathparam(l, 0, 0.5)])
    p = (c21 << l2 + l1 << c22).normpath()  # curve-line + line-curve
    assert par._can_continue(
        mynormpathparam(p, 1, 0, 1), mynormpathparam(p, 0, 1,
                                                     0))  # line -> line
    assert not par._can_continue(
        mynormpathparam(p, 0, 0, 1), mynormpathparam(p, 1, 1,
                                                     0))  # curve -> curve

    # intersections where paths are parallel (in the middle of a nsp-item)
    move = (12, 13)
    p1 = path.path(path.moveto(0, 0), path.curveto(0, 3, 1, 5, 1,
                                                   0)).normpath()
    params1, params2 = p1.intersect(path.line(0.5, -1, 0.5, 5))
    p11, p12 = p1.split(params1)
    p11.append(path.rlineto(0, -2))
    p = p11 << p12
    p.append(path.closepath())
    hard_test(
        c,
        p,
        0.55,
        parallel(0.0),
        move,
        "O",
        dotests=[True, True, False, False],
        checklens=[[10], [10], None, None])

    # jump to too large curvature between nspitems
    move = (-2, 17)
    p = path.path(
        path.moveto(0, 0), path.arc(2, 0.5, 0.5, -90, 90),
        path.lineto(0, 1)).normpath()
    hard_test(
        c,
        p,
        0.55,
        parallel(0.0),
        move,
        "P",
        dotests=[True, True, True, True],
        checklens=[[1, 1], [1, 1], [7], [7]])
Beispiel #8
0
    def testsplit(self):
        p = normline_pt(0, 0, 10, 0)
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.2])
        s = p.segments([0.2, 0.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(s[0], normline_pt(2, 0, 8, 0))
        s = p.segments([-0.2, 1.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(s[0], normline_pt(-2, 0, 18, 0))

        p = normcurve_pt(0, 0, 10, 0, 20, 0, 30, 0)
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.2])
        s = p.segments([0.2, 0.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(
            s[0], normcurve_pt(6, 0, 12, 0, 18, 0, 24, 0))
        s = p.segments([-0.2, 1.8])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpathitem(
            s[0], normcurve_pt(-6, 0, 14, 0, 34, 0, 54, 0))

        p = normsubpath([
            normline_pt(0, 0, 1, 0),
            normline_pt(1, 0, 1, 1),
            normline_pt(1, 1, 0, 1),
            normline_pt(0, 1, 0, 0)
        ])
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.2])
        s = p.segments([0.5, 2.5])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(
            s[0],
            normsubpath([
                normline_pt(0.5, 0, 1, 0),
                normline_pt(1, 0, 1, 1),
                normline_pt(1, 1, 0.5, 1)
            ]))
        s = p.segments([4.5, -1])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(
            s[0],
            normsubpath([
                normline_pt(0, -0.5, 0, 1),
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 1, 0),
                normline_pt(1, 0, -1, 0)
            ]))
        s = p.segments([0, 0.1, 1.2, 1.3, 3.4, 0.5, 4])
        self.assertEqual(len(s), 6)
        self.assertAlmostEqualNormsubpath(
            s[0], normsubpath([normline_pt(0, 0, 0.1, 0)]))
        self.assertAlmostEqualNormsubpath(
            s[1],
            normsubpath([normline_pt(0.1, 0, 1, 0),
                         normline_pt(1, 0, 1, 0.2)]))
        self.assertAlmostEqualNormsubpath(
            s[2], normsubpath([normline_pt(1, 0.2, 1, 0.3)]))
        self.assertAlmostEqualNormsubpath(
            s[3],
            normsubpath([
                normline_pt(1, 0.3, 1, 1),
                normline_pt(1, 1, 0, 1),
                normline_pt(0, 1, 0, 0.6)
            ]))
        self.assertAlmostEqualNormsubpath(
            s[4],
            normsubpath([
                normline_pt(0, 0.6, 0, 1),
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 1, 0),
                normline_pt(1, 0, 0.5, 0)
            ]))
        self.assertAlmostEqualNormsubpath(
            s[5],
            normsubpath([
                normline_pt(0.5, 0, 1, 0),
                normline_pt(1, 0, 1, 1),
                normline_pt(1, 1, 0, 1),
                normline_pt(0, 1, 0, 0)
            ]))

        p = normsubpath([
            normline_pt(0, 0, 1, 0),
            normline_pt(1, 0, 1, 1),
            normline_pt(1, 1, 0, 1)
        ],
                        closed=1)
        self.assertRaises(ValueError, p.segments, [])
        self.assertRaises(ValueError, p.segments, [0.5])
        s = p.segments([0.5, 2.5])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(
            s[0],
            normsubpath([
                normline_pt(0.5, 0, 1, 0),
                normline_pt(1, 0, 1, 1),
                normline_pt(1, 1, 0.5, 1)
            ]))
        s = p.segments([4.5, -1])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormsubpath(
            s[0],
            normsubpath([
                normline_pt(0, -0.5, 0, 1),
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 1, 0),
                normline_pt(1, 0, -1, 0)
            ]))
        s = p.segments([0, 0.1, 1.2, 1.3, 3.4, 0.5, 4])
        self.assertEqual(len(s), 5)
        self.assertAlmostEqualNormsubpath(
            s[0],
            normsubpath([
                normline_pt(0.5, 0, 1, 0),
                normline_pt(1, 0, 1, 1),
                normline_pt(1, 1, 0, 1),
                normline_pt(0, 1, 0, 0),
                normline_pt(0, 0, 0.1, 0)
            ]))
        self.assertAlmostEqualNormsubpath(
            s[1],
            normsubpath([normline_pt(0.1, 0, 1, 0),
                         normline_pt(1, 0, 1, 0.2)]))
        self.assertAlmostEqualNormsubpath(
            s[2], normsubpath([normline_pt(1, 0.2, 1, 0.3)]))
        self.assertAlmostEqualNormsubpath(
            s[3],
            normsubpath([
                normline_pt(1, 0.3, 1, 1),
                normline_pt(1, 1, 0, 1),
                normline_pt(0, 1, 0, 0.6)
            ]))
        self.assertAlmostEqualNormsubpath(
            s[4],
            normsubpath([
                normline_pt(0, 0.6, 0, 1),
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 1, 0),
                normline_pt(1, 0, 0.5, 0)
            ]))
        s = p.segments([4, 0.1, 1.2, 1.3, 3.4, 0.5, 0])
        self.assertEqual(len(s), 5)
        self.assertAlmostEqualNormsubpath(
            s[0],
            normsubpath([
                normline_pt(0.5, 0, 0, 0),
                normline_pt(0, 0, 0, 1),
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 1, 0),
                normline_pt(1, 0, 0.1, 0)
            ]))
        self.assertAlmostEqualNormsubpath(
            s[1],
            normsubpath([normline_pt(0.1, 0, 1, 0),
                         normline_pt(1, 0, 1, 0.2)]))
        self.assertAlmostEqualNormsubpath(
            s[2], normsubpath([normline_pt(1, 0.2, 1, 0.3)]))
        self.assertAlmostEqualNormsubpath(
            s[3],
            normsubpath([
                normline_pt(1, 0.3, 1, 1),
                normline_pt(1, 1, 0, 1),
                normline_pt(0, 1, 0, 0.6)
            ]))
        self.assertAlmostEqualNormsubpath(
            s[4],
            normsubpath([
                normline_pt(0, 0.6, 0, 1),
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 1, 0),
                normline_pt(1, 0, 0.5, 0)
            ]))

        p = normpath([
            normsubpath([
                normline_pt(0, 0, 1, 0),
                normline_pt(1, 0, 2, 0),
                normline_pt(2, 0, 3, 0),
                normline_pt(3, 0, 4, 0)
            ]),
            normsubpath([
                normline_pt(0, 1, 1, 1),
                normline_pt(1, 1, 2, 1),
                normline_pt(2, 1, 3, 1),
                normline_pt(3, 1, 4, 1)
            ]),
            normsubpath([
                normline_pt(0, 2, 1, 2),
                normline_pt(1, 2, 2, 2),
                normline_pt(2, 2, 3, 2),
                normline_pt(3, 2, 4, 2)
            ]),
            normsubpath([
                normline_pt(0, 3, 1, 3),
                normline_pt(1, 3, 2, 3),
                normline_pt(2, 3, 3, 3),
                normline_pt(3, 3, 4, 3)
            ]),
            normsubpath([
                normline_pt(0, 4, 1, 4),
                normline_pt(1, 4, 2, 4),
                normline_pt(2, 4, 3, 4),
                normline_pt(3, 4, 4, 4)
            ])
        ])
        s = p.split([
            normpathparam(p, 3, 0.1),
            normpathparam(p, 4, 1.2),
            normpathparam(p, 2, 2.3),
            normpathparam(p, 0, 3.4),
            normpathparam(p, 1, 0.5)
        ])
        self.assertEqual(len(s), 6)
        self.assertAlmostEqualNormpath(
            s[0],
            normpath([
                normsubpath([
                    normline_pt(0, 0, 1, 0),
                    normline_pt(1, 0, 2, 0),
                    normline_pt(2, 0, 3, 0),
                    normline_pt(3, 0, 4, 0)
                ]),
                normsubpath([
                    normline_pt(0, 1, 1, 1),
                    normline_pt(1, 1, 2, 1),
                    normline_pt(2, 1, 3, 1),
                    normline_pt(3, 1, 4, 1)
                ]),
                normsubpath([
                    normline_pt(0, 2, 1, 2),
                    normline_pt(1, 2, 2, 2),
                    normline_pt(2, 2, 3, 2),
                    normline_pt(3, 2, 4, 2)
                ]),
                normsubpath([normline_pt(0, 3, 0.1, 3)])
            ]))
        self.assertAlmostEqualNormpath(
            s[1],
            normpath([
                normsubpath([
                    normline_pt(0.1, 3, 1, 3),
                    normline_pt(1, 3, 2, 3),
                    normline_pt(2, 3, 3, 3),
                    normline_pt(3, 3, 4, 3)
                ]),
                normsubpath(
                    [normline_pt(0, 4, 1, 4),
                     normline_pt(1, 4, 1.2, 4)])
            ]))
        self.assertAlmostEqualNormpath(
            s[2],
            normpath([
                normsubpath(
                    [normline_pt(1.2, 4, 1, 4),
                     normline_pt(1, 4, 0, 4)]),
                normsubpath([
                    normline_pt(4, 3, 3, 3),
                    normline_pt(3, 3, 2, 3),
                    normline_pt(2, 3, 1, 3),
                    normline_pt(1, 3, 0, 3)
                ]),
                normsubpath(
                    [normline_pt(4, 2, 3, 2),
                     normline_pt(3, 2, 2.3, 2)])
            ]))
        self.assertAlmostEqualNormpath(
            s[3],
            normpath([
                normsubpath([
                    normline_pt(2.3, 2, 2, 2),
                    normline_pt(2, 2, 1, 2),
                    normline_pt(1, 2, 0, 2)
                ]),
                normsubpath([
                    normline_pt(4, 1, 3, 1),
                    normline_pt(3, 1, 2, 1),
                    normline_pt(2, 1, 1, 1),
                    normline_pt(1, 1, 0, 1)
                ]),
                normsubpath([normline_pt(4, 0, 3.4, 0)])
            ]))
        self.assertAlmostEqualNormpath(
            s[4],
            normpath([
                normsubpath([normline_pt(3.4, 0, 4, 0)]),
                normsubpath([normline_pt(0, 1, 0.5, 1)])
            ]))
        self.assertAlmostEqualNormpath(
            s[5],
            normpath([
                normsubpath([
                    normline_pt(0.5, 1, 1, 1),
                    normline_pt(1, 1, 2, 1),
                    normline_pt(2, 1, 3, 1),
                    normline_pt(3, 1, 4, 1)
                ]),
                normsubpath([
                    normline_pt(0, 2, 1, 2),
                    normline_pt(1, 2, 2, 2),
                    normline_pt(2, 2, 3, 2),
                    normline_pt(3, 2, 4, 2)
                ]),
                normsubpath([
                    normline_pt(0, 3, 1, 3),
                    normline_pt(1, 3, 2, 3),
                    normline_pt(2, 3, 3, 3),
                    normline_pt(3, 3, 4, 3)
                ]),
                normsubpath([
                    normline_pt(0, 4, 1, 4),
                    normline_pt(1, 4, 2, 4),
                    normline_pt(2, 4, 3, 4),
                    normline_pt(3, 4, 4, 4)
                ])
            ]))

        p = normpath([
            normsubpath([normline_pt(0, -5, 1, -5)]),
            normsubpath([
                normline_pt(0, 0, 1, 0),
                normline_pt(1, 0, 1, 1),
                normline_pt(1, 1, 0, 1)
            ],
                        closed=1),
            normsubpath([normline_pt(0, 5, 1, 5)])
        ])
        s = p.split([normpathparam(p, 1, 3.5)])
        self.assertEqual(len(s), 1)
        self.assertAlmostEqualNormpath(
            s[0],
            normpath([
                normsubpath([normline_pt(0, -5, 1, -5)]),
                normsubpath([
                    normline_pt(0, 0.5, 0, 0),
                    normline_pt(0, 0, 1, 0),
                    normline_pt(1, 0, 1, 1),
                    normline_pt(1, 1, 0, 1),
                    normline_pt(0, 1, 0, 0.5)
                ]),
                normsubpath([normline_pt(0, 5, 1, 5)])
            ]))

        p = normpath([
            normsubpath([normline_pt(0, -5, 1, -5)]),
            normsubpath([
                normline_pt(0, 0, 1, 0),
                normline_pt(1, 0, 1, 1),
                normline_pt(1, 1, 0, 1)
            ],
                        closed=1),
            normsubpath([normline_pt(0, 5, 1, 5)])
        ])
        s = p.split([
            normpathparam(p, 0, 0.5),
            normpathparam(p, 1, 3.5),
            normpathparam(p, 0, 0.5),
            normpathparam(p, 2, 0.5)
        ])
        self.assertEqual(len(s), 5)
        self.assertAlmostEqualNormpath(
            s[0], normpath([normsubpath([normline_pt(0, -5, 0.5, -5)])]))
        self.assertAlmostEqualNormpath(
            s[1],
            normpath([
                normsubpath([normline_pt(0.5, -5, 1, -5)]),
                normsubpath([
                    normline_pt(0, 0, 1, 0),
                    normline_pt(1, 0, 1, 1),
                    normline_pt(1, 1, 0, 1),
                    normline_pt(0, 1, 0, 0.5)
                ])
            ]))
        # XXX should we do ???: normsubpath([normline_pt(0, 0.5, 0, 0), normline_pt(0, 0, 1, 0), normline_pt(1, 0, 1, 1), normline_pt(1, 1, 0, 1), normline_pt(0, 1, 0, 0.5)])]))
        # same question in the next line ...
        self.assertAlmostEqualNormpath(
            s[2],
            normpath([
                normsubpath([
                    normline_pt(0, 0.5, 0, 1),
                    normline_pt(0, 1, 1, 1),
                    normline_pt(1, 1, 1, 0),
                    normline_pt(1, 0, 0, 0)
                ]),
                normsubpath([normline_pt(1, -5, 0.5, -5)])
            ]))
        self.assertAlmostEqualNormpath(
            s[3],
            normpath([
                normsubpath([normline_pt(0.5, -5, 1, -5)]),
                normsubpath([
                    normline_pt(0, 0, 1, 0),
                    normline_pt(1, 0, 1, 1),
                    normline_pt(1, 1, 0, 1),
                    normline_pt(0, 1, 0, 0)
                ],
                            closed=1),
                normsubpath([normline_pt(0, 5, 0.5, 5)])
            ]))
        self.assertAlmostEqualNormpath(
            s[4], normpath([normsubpath([normline_pt(0.5, 5, 1, 5)])]))