Up to this point, environmental objects such as trees and rocks were being spawned in random positions. Doing this allowed me to focus on being able to get objects to spawn on uneven objects and I had achieved this with the downfall of using random positioning being a chance of the same point being chosen multiple times and objects with spawn within each other. My options were to try to fix this by adding checks to see if something is already spawned there or to use this as an opportunity to add a second procedural generation algorithm to choose the points before instantiating any objects. I chose the latter with the use of Poisson disc sampling.
Poisson disc sampling is an algorithm used to populate an area by picking a random point and checking whether this is a valid placement by working out the distance the current point is from the already confirmed points. Once a point is accepted or discarded, a new point is randomly chosen out of the range of the previously confirmed point, this also acts as the way to end the loop as it will return the confirmed points once no more points can be placed.
The algorithm takes in the following parameters:
Area size (this is sometimes split as X and Y/Z sizes if not square area) - How much room there is to spawn in objects
Attempt amount - Iterates through the for a loop this many times before discarding the current point valid point
Radius - Minimum distance two points can be from each other
Radius and Attempt amount also control how dense the population is (how many objects can be spawned). Lowering the radius between objects controls the density more as having the objects closer together makes room to squeeze in more objects.
Attempt amount doesn't have as much control but increases the chance of spawning in more objects by trying more points before giving up, however, the increase in attempts means having to run the for loop more times and can therefore decrease performance. When looping into the algorithm the most common attempt amount used was 30, I decided that for mine there will be 10 attempts before discarding.
Random Generation vs Poisson Disc Sampling
Trees only
Rocks only
Rocks and Trees
Implementing Poisson Disc Sampling
I made the algorithm modular by creating a separate static class that can be called any time it is needed, this also allows me to use it for future projects and all I have to do is add the script to the assets folder and call the 'GeneratePoints' method. To create variety between chunks, I have set the radius to be randomly chosen between 10-15 units which creates different tree population densities.
With the use of the algorithm, I was able to alter my code so it runs the program twice, once for each environment item without the risk of items being placed within the same place, this was done by creating an extra parameter that takes in an enum value, currently, there is only tree and rock but the use of the enum allows more objects to be added without too many alterations to the code.
I plan for my next task to work on adding Fractal noise to remove the smoothness of the terrain and add some realism to it.
Comments