Home | History | Annotate | Download | only in turtledemo
      1 #!/usr/bin/env python3
      2 """      turtle-example-suite:
      3 
      4         tdemo_fractalCurves.py
      5 
      6 This program draws two fractal-curve-designs:
      7 (1) A hilbert curve (in a box)
      8 (2) A combination of Koch-curves.
      9 
     10 The CurvesTurtle class and the fractal-curve-
     11 methods are taken from the PythonCard example
     12 scripts for turtle-graphics.
     13 """
     14 from turtle import *
     15 from time import sleep, clock
     16 
     17 class CurvesTurtle(Pen):
     18     # example derived from
     19     # Turtle Geometry: The Computer as a Medium for Exploring Mathematics
     20     # by Harold Abelson and Andrea diSessa
     21     # p. 96-98
     22     def hilbert(self, size, level, parity):
     23         if level == 0:
     24             return
     25         # rotate and draw first subcurve with opposite parity to big curve
     26         self.left(parity * 90)
     27         self.hilbert(size, level - 1, -parity)
     28         # interface to and draw second subcurve with same parity as big curve
     29         self.forward(size)
     30         self.right(parity * 90)
     31         self.hilbert(size, level - 1, parity)
     32         # third subcurve
     33         self.forward(size)
     34         self.hilbert(size, level - 1, parity)
     35         # fourth subcurve
     36         self.right(parity * 90)
     37         self.forward(size)
     38         self.hilbert(size, level - 1, -parity)
     39         # a final turn is needed to make the turtle
     40         # end up facing outward from the large square
     41         self.left(parity * 90)
     42 
     43     # Visual Modeling with Logo: A Structural Approach to Seeing
     44     # by James Clayson
     45     # Koch curve, after Helge von Koch who introduced this geometric figure in 1904
     46     # p. 146
     47     def fractalgon(self, n, rad, lev, dir):
     48         import math
     49 
     50         # if dir = 1 turn outward
     51         # if dir = -1 turn inward
     52         edge = 2 * rad * math.sin(math.pi / n)
     53         self.pu()
     54         self.fd(rad)
     55         self.pd()
     56         self.rt(180 - (90 * (n - 2) / n))
     57         for i in range(n):
     58             self.fractal(edge, lev, dir)
     59             self.rt(360 / n)
     60         self.lt(180 - (90 * (n - 2) / n))
     61         self.pu()
     62         self.bk(rad)
     63         self.pd()
     64 
     65     # p. 146
     66     def fractal(self, dist, depth, dir):
     67         if depth < 1:
     68             self.fd(dist)
     69             return
     70         self.fractal(dist / 3, depth - 1, dir)
     71         self.lt(60 * dir)
     72         self.fractal(dist / 3, depth - 1, dir)
     73         self.rt(120 * dir)
     74         self.fractal(dist / 3, depth - 1, dir)
     75         self.lt(60 * dir)
     76         self.fractal(dist / 3, depth - 1, dir)
     77 
     78 def main():
     79     ft = CurvesTurtle()
     80 
     81     ft.reset()
     82     ft.speed(0)
     83     ft.ht()
     84     ft.getscreen().tracer(1,0)
     85     ft.pu()
     86 
     87     size = 6
     88     ft.setpos(-33*size, -32*size)
     89     ft.pd()
     90 
     91     ta=clock()
     92     ft.fillcolor("red")
     93     ft.begin_fill()
     94     ft.fd(size)
     95 
     96     ft.hilbert(size, 6, 1)
     97 
     98     # frame
     99     ft.fd(size)
    100     for i in range(3):
    101         ft.lt(90)
    102         ft.fd(size*(64+i%2))
    103     ft.pu()
    104     for i in range(2):
    105         ft.fd(size)
    106         ft.rt(90)
    107     ft.pd()
    108     for i in range(4):
    109         ft.fd(size*(66+i%2))
    110         ft.rt(90)
    111     ft.end_fill()
    112     tb=clock()
    113     res =  "Hilbert: %.2fsec. " % (tb-ta)
    114 
    115     sleep(3)
    116 
    117     ft.reset()
    118     ft.speed(0)
    119     ft.ht()
    120     ft.getscreen().tracer(1,0)
    121 
    122     ta=clock()
    123     ft.color("black", "blue")
    124     ft.begin_fill()
    125     ft.fractalgon(3, 250, 4, 1)
    126     ft.end_fill()
    127     ft.begin_fill()
    128     ft.color("red")
    129     ft.fractalgon(3, 200, 4, -1)
    130     ft.end_fill()
    131     tb=clock()
    132     res +=  "Koch: %.2fsec." % (tb-ta)
    133     return res
    134 
    135 if __name__  == '__main__':
    136     msg = main()
    137     print(msg)
    138     mainloop()
    139