File: lsystem.py

package info (click to toggle)
minetest-mod-pycraft 0.22-5
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 2,744 kB
  • sloc: python: 79,282; makefile: 10
file content (123 lines) | stat: -rwxr-xr-x 2,907 bytes parent folder | download | duplicates (3)
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
#
# Code under the MIT license by Alexander Pruss
#
# L-system with turtle graphics
#

import collections
import random
import mcpi.settings
from mcturtle import *

def playProgram(s, dictionary):
    for c in s:
        if c in dictionary:
            dictionary[c]()


def transform(c, t):
    if isinstance(t, basestring):
        return t
    else:
        r = random.random()
        for p,out in t:
            if r<p:
                 return out
            r -= p
        return c

def evolveGenerator(axiom,rules):
    for c in axiom:
        if c in rules:
            yield transform(c, rules[c])
        else:
            yield c

def evolve(axiom, rules, levelCount):
    for i in range(levelCount):
        axiom = ''.join(evolveGenerator(axiom,rules))
    return axiom


def lsystem(axiom, rules, dictionary, levelCount):
    out = evolve(axiom, rules, levelCount)
    playProgram(out, dictionary)

if __name__ == "__main__":
    t = Turtle()
    t.pendelay(0)
    t.penup()
    t.turtle(None)
    t.go(10)
    t.verticalangle(90)
    t.pendown()
    t.penblock(WOOD)

# a fairly simple example with rules from http://www.nbb.cornell.edu/neurobio/land/OldStudentProjects/cs490-94to95/hwchen/
#    rules = {'F':'F[-&<F][<++&F]||F[--&>F][+&F]'}
#
#    angle = 22.5
#
#    dictionary = {
#        '[': t.push,
#        ']': t.pop,
#        'F': lambda: t.go(5),
#        '-': lambda: t.yaw(-angle),
#        '+': lambda: t.yaw(angle),
#        '&': lambda: t.pitch(angle),
#        '^': lambda: t.pitch(-angle),
#        '<': lambda: t.roll(-angle),
#        '>': lambda: t.roll(angle),
#        '|': lambda: t.pitch(180)
#        }
#
#    lsystem('F', rules, dictionary, 3)


#
# A more complex example with
# rules based on http://www.geekyblogger.com/2008/04/tree-and-l-system.html
#
    rules = {'A': '^f[^^f>>>>>>A]>>>[^^f>>>>>>A]>>>>>[^^f>>>>>>A]'}

#randomized version:
#    rules = {'A': [(0.75,'^f[^^f>>>>>>A]>>>[^^f>>>>>>A]>>>>>[^^f>>>>>>A]'),
#          (0.25,'^f>>[^^f>>>>>>A]>>>[^^f>>>>>>A]')]}

    axiom = 'fA'
    angle = 15
    thickness = 8
    length = 10 if mcpi.settings.isPE else 15;
    material = WOOD
    t.penwidth(thickness)
    t.penblock(material)

    stack = []
    def push():
        global length
        global thickness
        stack.append((length,thickness))
        t.push()
        thickness = thickness * 0.6
        length = length * 0.75
        if thickness < 1:
            thickness = 1
        if length <= 1:
            t.penblock(LEAVES_OAK_PERMANENT)
        t.penwidth(thickness)

    def pop():
        global length
        global thickness
        length,thickness = stack.pop()
        t.pop()

    dictionary = {
        '[': push,
        ']': pop,
        '^': lambda: t.pitch(angle),
        '>': lambda: t.roll(angle),
        'f': lambda: t.go(length)
    }

    lsystem(axiom, rules, dictionary, 9 if mcpi.settings.isPE else 11)