Home | History | Annotate | Download | only in turtledemo
      1 #!/usr/bin/env python3
      2 """       xturtle-example-suite:
      3 
      4           xtx_kites_and_darts.py
      5 
      6 Constructs two aperiodic penrose-tilings,
      7 consisting of kites and darts, by the method
      8 of inflation in six steps.
      9 
     10 Starting points are the patterns "sun"
     11 consisting of five kites and "star"
     12 consisting of five darts.
     13 
     14 For more information see:
     15  http://en.wikipedia.org/wiki/Penrose_tiling
     16  -------------------------------------------
     17 """
     18 from turtle import *
     19 from math import cos, pi
     20 from time import clock, sleep
     21 
     22 f = (5**0.5-1)/2.0   # (sqrt(5)-1)/2 -- golden ratio
     23 d = 2 * cos(3*pi/10)
     24 
     25 def kite(l):
     26     fl = f * l
     27     lt(36)
     28     fd(l)
     29     rt(108)
     30     fd(fl)
     31     rt(36)
     32     fd(fl)
     33     rt(108)
     34     fd(l)
     35     rt(144)
     36 
     37 def dart(l):
     38     fl = f * l
     39     lt(36)
     40     fd(l)
     41     rt(144)
     42     fd(fl)
     43     lt(36)
     44     fd(fl)
     45     rt(144)
     46     fd(l)
     47     rt(144)
     48 
     49 def inflatekite(l, n):
     50     if n == 0:
     51         px, py = pos()
     52         h, x, y = int(heading()), round(px,3), round(py,3)
     53         tiledict[(h,x,y)] = True
     54         return
     55     fl = f * l
     56     lt(36)
     57     inflatedart(fl, n-1)
     58     fd(l)
     59     rt(144)
     60     inflatekite(fl, n-1)
     61     lt(18)
     62     fd(l*d)
     63     rt(162)
     64     inflatekite(fl, n-1)
     65     lt(36)
     66     fd(l)
     67     rt(180)
     68     inflatedart(fl, n-1)
     69     lt(36)
     70 
     71 def inflatedart(l, n):
     72     if n == 0:
     73         px, py = pos()
     74         h, x, y = int(heading()), round(px,3), round(py,3)
     75         tiledict[(h,x,y)] = False
     76         return
     77     fl = f * l
     78     inflatekite(fl, n-1)
     79     lt(36)
     80     fd(l)
     81     rt(180)
     82     inflatedart(fl, n-1)
     83     lt(54)
     84     fd(l*d)
     85     rt(126)
     86     inflatedart(fl, n-1)
     87     fd(l)
     88     rt(144)
     89 
     90 def draw(l, n, th=2):
     91     clear()
     92     l = l * f**n
     93     shapesize(l/100.0, l/100.0, th)
     94     for k in tiledict:
     95         h, x, y = k
     96         setpos(x, y)
     97         setheading(h)
     98         if tiledict[k]:
     99             shape("kite")
    100             color("black", (0, 0.75, 0))
    101         else:
    102             shape("dart")
    103             color("black", (0.75, 0, 0))
    104         stamp()
    105 
    106 def sun(l, n):
    107     for i in range(5):
    108         inflatekite(l, n)
    109         lt(72)
    110 
    111 def star(l,n):
    112     for i in range(5):
    113         inflatedart(l, n)
    114         lt(72)
    115 
    116 def makeshapes():
    117     tracer(0)
    118     begin_poly()
    119     kite(100)
    120     end_poly()
    121     register_shape("kite", get_poly())
    122     begin_poly()
    123     dart(100)
    124     end_poly()
    125     register_shape("dart", get_poly())
    126     tracer(1)
    127 
    128 def start():
    129     reset()
    130     ht()
    131     pu()
    132     makeshapes()
    133     resizemode("user")
    134 
    135 def test(l=200, n=4, fun=sun, startpos=(0,0), th=2):
    136     global tiledict
    137     goto(startpos)
    138     setheading(0)
    139     tiledict = {}
    140     a = clock()
    141     tracer(0)
    142     fun(l, n)
    143     b = clock()
    144     draw(l, n, th)
    145     tracer(1)
    146     c = clock()
    147     print("Calculation:   %7.4f s" % (b - a))
    148     print("Drawing:  %7.4f s" % (c - b))
    149     print("Together: %7.4f s" % (c - a))
    150     nk = len([x for x in tiledict if tiledict[x]])
    151     nd = len([x for x in tiledict if not tiledict[x]])
    152     print("%d kites and %d darts = %d pieces." % (nk, nd, nk+nd))
    153 
    154 def demo(fun=sun):
    155     start()
    156     for i in range(8):
    157         a = clock()
    158         test(300, i, fun)
    159         b = clock()
    160         t = b - a
    161         if t < 2:
    162             sleep(2 - t)
    163 
    164 def main():
    165     #title("Penrose-tiling with kites and darts.")
    166     mode("logo")
    167     bgcolor(0.3, 0.3, 0)
    168     demo(sun)
    169     sleep(2)
    170     demo(star)
    171     pencolor("black")
    172     goto(0,-200)
    173     pencolor(0.7,0.7,1)
    174     write("Please wait...",
    175           align="center", font=('Arial Black', 36, 'bold'))
    176     test(600, 8, startpos=(70, 117))
    177     return "Done"
    178 
    179 if __name__ == "__main__":
    180     msg = main()
    181     mainloop()
    182