Nature of Code / GLArt Final Project:
Three Dimensional Forces Applied to Recursive Systems
Inspired by the complex structural beauty created by recursive algorithms and the natural movement simulated by applying dynamic three-dimensional vectors, I wanted to create natural-looking three-dimensional structure that moved in natural ways when an invisible forces like “wind” was applied to them.
I first investigated the use of Perlin Noise to generate a three-dimensional force that, like wind, seemed both random and smooth. I created a dynamic three-dimensional vector force by setting the X, Y, and Z fields of a Vector3D class to three different offsets of Perlin Noise. I then added that vector to the velocity of each particle in a particle system. The result was a group of particles that seemed to blow in the wind.
Next I investigated creating a three-dimensional tree-like structure using a recursive branching algorithm. Different styles of trees could be rendered by slightly changing the branch lengths and angles.
I then tried adding the “Perlin Wind” vector force to the angles and lengths of the recursion tree. Rather than blow gently in the wind however, the trees seemed to swing and dance, blow apart, and contort.
The difficulty was that a recursive system is based on relative locations. Each point in the tree is placed relative to the point before it in the branching algorithm taking no consideration for its actual place in three-dimensional space. For instance one branch is just a rotation and length away from the last branch, it doesn’t know its actual X,Y,Z location. The trick seemed to be in finding the actual locations of each point in three-dimensional space and applying the “Perlin Wind” to each point accordingly.
Diverging from recursion trees I began looking at L-Systems and their production strings to derive actual coordinates for each point in the system and store them in an array. An L-System, like a recursive algorithm, is usually created using points with locations relative to the last point in the production string. In an L-System however, the positions of each point is set by a specific rule, keeping track of where the point occurs in the production string can tell us the actual location coordinate of each point. Rather than using higher level programming functions such translate(), and rotate() to move the points of the system and pushMatrix() and popMatrix() to store and recall relative branching positions in an internal stack array I used simple trigonometry to move the coordinates and my own stack array to store and recall actual branching positions, an array was used to then store the exact location of each point in the L-System. A significant increase in performance was found by calculating the L-System at the beginning of program and storing the locations in an array, rendering only the array each frame rather than recalculating the L-System on each frame. I was able to easily apply the “Perlin Wind” force to the array of two-dimensional L-System coordinates.
After creating an array of two-dimensional L-system coordinates using the simple rule systems, I found it more difficult to implement those simple rules to create a “natural-looking” three-dimensional tree structure. Unlike an L-System, a recursive branching algorithm doesn’t follow a strict rule and recursively calls itself, almost like falling in on itself. Because of this it is more complicated to keep track of the different locations of each branching node. Also, knowing the only then location of each point in the recursion tree does not take into account how a force applied to those points would affect the other branches connected above and below those points. Further investigation into parent/child relationships between nodes and branches would be required to apply a force that would naturally flow through the tree, rather than just blow it apart.
Although, by the project deadline I was neither able to derive the actual locations of each point of the recursion tree or keep track of the parent/child relationship between each branch and node, I was able create a natural looking tree structure that seemed to blow in the wind using recursive branching algorithm and Perlin Noise. I used the aspects of the tree that I did know: the initial rotations of each branch and how far through the branching algorithm each branch was created. I then applied the “Perlin Wind” force to the rotation of each branch. Depending on which direction the branch was rotated the force was applied accordingly. For example, a branch that was rotated towards the direction of the wind would rotate away from the wind, a branch rotated away from the direction of the wind would rotate with the wind, and the branches perpendicular to the wind would rotate with the wind, but on a different axis. Also, depending on where the branch was created the amount that the wind force affected its rotation would change; smaller branches at the top of the tree would rotate more in the wind than the longer branches closer to the base.