Creating retro graphics using Substance and shaders
Last weekend I took some time out to practise some asset production. I often find myself creating or learning something useful along the way when I do.
What started out as a curiosity about using Substance Designer to create pixel art, ended up as a homage to Guild Wars 2’s April Fool’s gag: the Super Adventure Box (SAB).
As such, the art direction is based on its aesthetics. Which provided a useful frame of reference.
A playable demo can be downloaded at the end of this post.
To create the materials, I heavily relied on Nicolas Wirrmann’s (Product manager at Allegorithmic) Pixelate Filter, which is freely available on Substance Share.
The base, prior to pixelation, across many of the materials, is made out of some pattern or noise map. Which is clamped to 0.1 values and subsequently run through the pixelation filter. Aside from the last step, this workflow does not deviate much from how you’d normally create a heightmap.
The result is a mask which I use to lerp between two colors. I utilize one primary color and use a HSL node to create a brighter and darker variation. This way I can change the main color without having to fiddle with the variations.
Finally, the normal map is created by converting the final color into grayscale and normalizing the result to 0-1 values. Which is then converted into a normal map using the Normal node.
The resulting earth material, in several seeds:
The same workflow was applied to the creation of the vegetation:
Most, if not all, of the animations of the surroundings and the characters in SAB are stepped rather than interpolated. So I wanted to recreate that lo-fi feeling.
I achieved this in a shader by modifying the vertex positions using a sine wave and a ceil function, which rounds its input up to the highest integer number. To avoid a monotonous look, I utilized the object’s positional values to add an offset to the sine wave. This way every flower would bob up and down at a slightly different speed.
The same method is used for the tree bushes, except it does not use the vertex color masking.
The water materials are also animated in their own way, using Substance’s built-in $time parameter. Like any exposed parameter this can be modified using the ProceduralMaterial API. By hooking up parameters in Substance Designer to the $time parameter and piping in Unity’s
Time.deltaTime as a value, it is increased as time progresses.
I have a readily available script which handles this, as I’ve used this method before.AnimatedSubstance
It includes an example Substance which uses the $time parameter.
You can of course apply this to any Substance you’ve created yourself by grabbing the $time value in your function graph.
You can learn more about parameter functions through the Substance documentation.
Do keep in mind that the graph complexity and the output resolution is to remain extremely low, as the graph has to be constantly re-generated. It is also extremely taxing on the CPU. However, since I only regenerate 3 times per second (for that stepped animation effect) the performance impact was negligible!
The SAB is characterized by its 3D interpretation of retro graphics and a wink at oldskool adventure platformers. Its most prominent feature are the blocks of earth covered by grass, which are kit-bashed together to form the terrain.
I opted to create a single cube with a shader that projects and the tiles the earth material on the sides, and the grass material on top. This way I could freely scale the objects without having to worry about tiling. The shader was made using the Amplify Shader Editor, which made it possible to quickly iterate on this shader.
The grass edge uses the cube’s UV’s so it remains at the top. Unfortunately that also means it is affected by the object’s scale and will stretch. Ideally, I would create a variety of pre-scaled earth cube, aligning the UV’s so the scale remains uniform. However, since these assets are not meant for a full production, and I only had an afternoon, I decided to skim on it and use the time for rest of the project.
Thanks for reading!
You can download a playable demo here:
[Press ENTER to active the camera flythrough]
[Press ‘F’ to toggle retro mode]