📄 interpreter.java
字号:
import java.util.Vector;import javax.media.j3d.*;import javax.vecmath.*;import com.sun.j3d.utils.geometry.*;/** * This class walks through an L-system rule, as a Logo turtle would. * The turtle draws line segments (cylinders) behind it. * (called by: Lsystem.java, Interpreter.java) * * @author: Scott Teresi, April 1999, www.teresi.us */public class Interpreter { State s = new State(); Vector stateStack = new Vector(); Appearance branchApp = new Appearance(); Appearance leafApp = new Appearance(); int depth; String rule; int cylEdges = 3; double cylRadius = 0.1; double mult = 0.01; boolean debug = false;; public Interpreter () { // set the default Appearances Material mat1 = new Material(); mat1.setDiffuseColor(.9f, .2f, .05f); mat1.setAmbientColor(.18f, .05f, 0f); branchApp.setMaterial(mat1); Material mat2 = new Material(); mat2.setDiffuseColor(0f, .7f, .05f); mat2.setAmbientColor(0f, .3f, 0f); leafApp.setMaterial(mat2); } public void setState (State state) { s = state; } public void setAppearance (Appearance app1, Appearance app2) { branchApp = app1; leafApp = app2; } public void initDraw (double rad, double m, int edges, boolean dbg) { cylRadius = rad; mult = m; cylEdges = edges; debug = dbg; } public BranchGroup execute(int d, String r) { depth = d; rule = r; BranchGroup bg = new BranchGroup(); if (depth == 0) return bg; if (debug) { for (int i = 0; i < (8-depth); i ++) System.out.print(" "); System.out.println("Interpreting: " + rule); } int i = 0; while (i < rule.length()) { // System.out.println(rule.charAt(i) + " " + new Point3f(s.curPos) + // " " + s.angle); switch (rule.charAt(i)) { case ' ': case '=': break; case '+': // turn the cursor left if (!s.swapDirections) s.angle += s.angleInc; // turn left else s.angle -= s.angleInc; // turn right if (s.angle > 360.0) s.angle -= 360.0; if (s.angle < -360.0) s.angle += 360.0; break; case '-': // turn the cursor right if (!s.swapDirections) s.angle -= s.angleInc; // turn right else s.angle += s.angleInc; // turn left if (s.angle > 360.0) s.angle -= 360.0; if (s.angle < -360.0) s.angle += 360.0; break; case '!': // swap directions of all following cursor turns s.swapDirections = !s.swapDirections; break; case 'f': // move forward one line length (actually DRAW something!) double x = s.lineLength*Math.cos(Math.PI * s.angle/180.0) + s.curPos.x; double y = s.lineLength * Math.sin(Math.PI * s.angle/180.0) + s.curPos.y; double z = s.curPos.z; CylinderCreator cylinder = new CylinderCreator(); cylinder.setResolution(cylEdges); Appearance app; if (depth > 1) app = branchApp; else app = leafApp; // make a branch bg.addChild(cylinder.create(s.curPos, new Point3d(x, y, z), cylRadius + mult * s.lineLength, app)); // cap the end of the branch Transform3D transMatrix = new Transform3D(); transMatrix.setTranslation(new Vector3d(x, y, z)); TransformGroup tg = new TransformGroup(transMatrix); Sphere sphere = new Sphere((float) (cylRadius + mult*s.lineLength), Sphere.GENERATE_NORMALS, app); tg.addChild(sphere); bg.addChild(tg); s.curPos = new Point3d(x, y, z); break; case '@': // scale the line length up or down i = readScaleValue(i+1); break; case 'z': case 'y': case 'x': case 'w': case 'v': // interpret the rule for the variable encountered Interpreter interpreter = new Interpreter(); interpreter.setState(s); interpreter.setAppearance(branchApp, leafApp); interpreter.initDraw (cylRadius, mult, cylEdges, debug); bg.addChild(interpreter.execute(depth - 1, Rules.getRule(rule.charAt(i)))); break; case '[': // remember the current graphics state stateStack.addElement(new State(s)); break; case ']': // recall the previous graphics state if (stateStack.size() > 0) s = (State) stateStack.remove(stateStack.size() - 1); else System.out.println("Missing ] in line: " + rule); break; default: break; } i ++; } bg.compile(); return bg; } int readScaleValue(int i) { StringBuffer valString = new StringBuffer(); while (i < rule.length()) { switch (rule.charAt(i)) { case '.': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': case '0': valString.append(rule.charAt(i)); break; default: double scale = 0; try { scale = (new Double(valString.toString())).doubleValue(); } catch (Exception ex) { System.out.println("Bad line length scale value, position " + i); System.out.println("Line: " + rule); System.exit(1); } s.lineLength *= scale; // if (debug) // System.out.println("new line length: " + s.lineLength); return i-1; } i ++; } return i; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -