Spaces:
Running
Running
| <html> | |
| <head> | |
| <meta charset="utf-8"> | |
| <title>Babylon.js L-system Fractal Example</title> | |
| <script src="https://cdn.babylonjs.com/babylon.js"></script> | |
| <style> | |
| canvas { width: 100%; height: 100%; touch-action: none; } | |
| </style> | |
| </head> | |
| <body> | |
| <canvas id="renderCanvas"></canvas> | |
| <script> | |
| const canvas = document.getElementById('renderCanvas'); | |
| const engine = new BABYLON.Engine(canvas, true); | |
| const createScene = () => { | |
| const scene = new BABYLON.Scene(engine); | |
| const camera = new BABYLON.ArcRotateCamera("Camera", 0, 0, 10, BABYLON.Vector3.Zero(), scene); | |
| const light = new BABYLON.HemisphericLight("light1", new BABYLON.Vector3(0, 1, 0), scene); | |
| const texture = new BABYLON.Texture("https://www.babylonjs-playground.com/textures/floor.png", scene); | |
| const bumpMap = new BABYLON.Texture("https://www.babylonjs-playground.com/textures/floor_n.jpg", scene); | |
| const rules = {F: "F+F-F-F+F"}; | |
| const axiom = "F-F-F-F"; | |
| const angle = Math.PI / 2, length = 1, iterations = 3; | |
| let lSystemString = axiom, position = BABYLON.Vector3.Zero(), direction = BABYLON.Vector3.Forward(); | |
| for (let i = 0; i < iterations; i++) { | |
| let newString = ""; | |
| for (let j = 0; j < lSystemString.length; j++) { | |
| const char = lSystemString.charAt(j); | |
| newString += rules[char] || char; | |
| } | |
| lSystemString = newString; | |
| } | |
| for (let i = 0; i < lSystemString.length; i++) { | |
| const char = lSystemString.charAt(i); | |
| if (char === "F") { | |
| const sphere = BABYLON.MeshBuilder.CreateSphere("sphere", { diameter: length, segments: 16 }, scene); | |
| sphere.position = position.clone(); | |
| sphere.material = new BABYLON.StandardMaterial("texture", scene); | |
| sphere.material.diffuseTexture = texture; | |
| sphere.material.bumpTexture = bumpMap; | |
| const textureAnimation = new BABYLON.Animation("textureAnimation", "material.diffuseTexture.uOffset", 60, BABYLON.Animation.ANIMATIONTYPE_FLOAT, BABYLON.Animation.ANIMATIONLOOPMODE_CYCLE, true); | |
| textureAnimation.setKeys([{ frame: 0, value: 0 }, { frame: 100, value: 1 }]); | |
| sphere.material.diffuseTexture.wrapU = sphere.material.diffuseTexture.wrapV = BABYLON.Texture.WRAP_ADDRESSMODE; | |
| sphere.material.diffuseTexture.uScale = sphere.material.diffuseTexture.vScale = 10; | |
| sphere.animations.push(textureAnimation); | |
| scene.beginAnimation(sphere, 0, 100, true); | |
| const animation = new BABYLON.Animation("myAnimation", "position", 30, BABYLON.Animation.ANIMATIONTYPE_VECTOR3, BABYLON.Animation.ANIMATIONLOOPMODE_CYCLE, true); | |
| animation.setKeys([{ frame: 0, value: position.clone() }, { frame: 100, value: position.addInPlace(direction.scale(length)).clone() }]); | |
| sphere.animations.push(animation); | |
| scene.beginAnimation(sphere, 0, 100, true); | |
| } else if (char === "+") { | |
| direction.rotateByQuaternionToRef(BABYLON.Quaternion.RotationAxis(BABYLON.Vector3.Up(), -angle), direction); | |
| } else if (char === "-") { | |
| direction.rotateByQuaternionToRef(BABYLON.Quaternion.RotationAxis(BABYLON.Vector3.Up(), angle), direction); | |
| } | |
| } | |
| return scene; | |
| }; | |
| const scene = createScene(); | |
| engine.runRenderLoop(() => scene.render()); | |
| window.addEventListener('resize', () => engine.resize()); | |
| </script> | |
| </body> | |
| </html> | |