-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathLSystems2.py
133 lines (109 loc) · 4.4 KB
/
LSystems2.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
import turtle
# --------------------------------------------------------------------------
# These functions take a string-based L-System and create a string by applying
# the rewriting rules
def createLSystem(numIters, axiom, rules):
"""Takes in the number of iterations of the rewriting process, the starting
axiom, and a list of rules. Each rule is a sublist with the symbol on the lefthand side
first, followed by a string for the righthand side. Returns the final string."""
currString = axiom
nextString = ""
for i in range(numIters):
nextString = processString(currString, rules)
currString = nextString
return nextString
def processString(oldStr, rules):
"""Processes the current string by going through character by character and
replacing each character by the application of a rule, if any. Returns the
new string. This performs one step of the rewriting process."""
newstr = ""
for ch in oldStr:
newstr = newstr + applyRules(ch, rules)
return newstr
def applyRules(ch, rules):
"""Takes in a character and the list of rules, and finds the first rule that applies
to the character and returns the righthand side. If no rules apply the character is
returned unchanged."""
newstr = ""
for rule in rules:
lhs = rule[0]
rhs = rule[1]
if ch == lhs:
return rhs
return ch
# --------------------------------------------------------------------------
# These functions take a string giving instructions for an L-system, and a list
# that decodes the characters in the string to tell what to do with them, and
# it has a turtle trace the shape given by the instructions
def drawLSystem(aTurtle, instructions, angle, distance):
"""Takes in a turtle, a string of instructions, plus the
angle to turn when told to turn, and the distance forward to go.
It loops over the instructions, and does the correct action for
each. F means go forward distance while drawing, f means go forward
distance without drawing, + means turn left by angle, - means turn right
by angle, and | means turn 180 degrees."""
savedInfoList = []
for cmd in instructions:
if cmd == 'F':
aTurtle.forward(distance)
elif cmd == 'f':
aTurtle.up()
aTurtle.forward(distance)
aTurtle.down()
elif cmd == '-':
aTurtle.right(angle)
elif cmd == '+':
aTurtle.left(angle)
elif cmd == '|':
aTurtle.left(180)
elif cmd == '[':
currLoc = [aTurtle.heading(), aTurtle.xcor(), aTurtle.ycor()]
savedInfoList.append(currLoc)
elif cmd == ']':
oldLoc = savedInfoList.pop()
[head, x, y] = oldLoc
aTurtle.up()
aTurtle.setheading(head)
aTurtle.setposition(x, y)
aTurtle.down()
else:
# ignore any other characters in the instructions
pass
def displayFractal(instructs, angle, dist, startPos=(-400, 0), startHead=0):
"""Takes in the string of instructions, the turn angle, the distance for
moving forward, and then two optional arguments: a starting position for
the turtle to start the fractal, and a starting heading. If no input is
given for these, then they are assigned the value in the def line above.
This function """
# Make screen and turtle
wn = turtle.Screen()
t = turtle.Turtle()
# Move turtle to starting position and heading and set it up otherwise
t.hideturtle()
t.up()
t.goto(startPos)
t.setheading(startHead)
t.down()
t.speed(0)
# draw the picture
drawLSystem(t, instructs, angle, dist) # make sure to check angle here
wn.exitonclick()
def main():
# first defines a few L-systems for fractals
kochAxiom = "F"
kochRules = [['F', 'F+F--F+F']]
kochAngle = 60
hilbertAxiom = "L"
hilbertRules = [['L', '+RF-LFL-FR+'], ['R', '-LF+RFR+FL-']]
hilbertAngle = 90
islandLakeAxiom = "F+F+F+F"
islandLakeRules = [['F', 'F+f-FF+F+FF+Ff+FF-f+FF-F-FF-Ff-FFF'], ['f', 'ffffff']]
islandLakeAngle = 90
pythagAxiom = "X"
pythagRules = [['X', 'F[-X]+X'], ['F', 'FF']]
pythagAngle = 60
# Build instructions with L-system
instructs1 = createLSystem(5, pythagAxiom, pythagRules)
displayFractal(instructs1, pythagAngle, 10, (0, -300), 90)
if __name__ == "__main__":
main()