SNOWY TERRAIN

Thank you for purchasing snow asset! If you have any questions do write to maidnmate@gmail.com

GENERAL INFO {#general-info}

This asset consists of shaders, materials and c# classes for interaction with snow. After purchasing this asset you are free to make any change to any part of the asset to your liking.

Demo scene contains terrain with snow material applied and a character that has all necessary components to interact with snow. Just hit play and walk around;

TABLE OF CONTENTS

GENERAL INFO 2

Terrain 3

Layer Specific Settings 5

Global Material Settings 6

Tessellation options 8

Mesh with splatmaps 12

MeshSnow 15

Scripting API 17

SnowInteractionController 18

CharacterSnowInteractor 19

CharacterFootprint 21

Adding Custom Components 22

Roadmap 24

Terrain {#terrain}

To use Snow material on terrain:

  1. Create or Select existing terrain on Scene
  2. Go to Terrain Settings
  3. Apply ‘Terrain Snow’ material to your terrain
Warnings may appear. Just ignore them
  1. Select ‘Paint terrain’ tab
  2. Select or create/add any layer

    Setting up layer

Once you select a layer to work with you will see a slightly different setting from what you used to. We’ll go through them next;

Layer Specific Settings {#layer-specific-settings}


As the name suggests, these settings are applied to each specific layer meaning each of those settings can be set separately so your terrain doesn’t all have to be snowy or some layers might have different snow height than the others.

Albedo, Normal and Mask Map are the base textures of your layer. If snowness is set to zero you will see Albedo texture with it’s normal map applied.

Tile size and offset are used to change scale and offset of a texture;

Tile size and offset are also applied to snow texture
**Ground normal scale** controls ‘bumpiness’ of a texture. It’s range is set to *\-1010* just in case ;)  

**Snowiness** controls the amount of snow set on a selected layer. You can set it to value between 0 and 1 to give an effect of slightly snow-covered land.  

Snow normal scale controls ‘bumpiness’ of a Snow texture. With a value of 10 (based on your snow texture) it can give an effect of ‘icy’ terrain;
Snow emission controls the power of color that the snow is emitting. Values [1 – 2] give a normal snow-emitting effect, but you are free to change it to your liking.
Snow height changes the height of a snow. It uses a simple vertex displacement technique. You can gradually change its value via code in runtime as will be discussed in the API section.
Smoothness refers to the smoothness of a surface and is applied both to snow and albedo texture

Global Material Settings {#global-material-settings}

This settings are applied to each layer on your terrain so you can change it from any layer

![][image8]

Snow texture, Snow normal and Footprint are the textures you will use to set up snow. Footprint here is a texture that will be used to leave a footprint on a snow where your character walks. You can leave it empty and still have a nice footprint (we’ll discuss it later)

**Footstep width and height** determine the size of the footprint your character leaves on snow.  
**Noise scale and Noise strength** adds noise to the footprint to make it look more ‘blended’ into terrain.
Noise strength and scale are zero Noise scale \= 1, Noise strength \= 0.6

Tessellation options {#tessellation-options}

Tessellation is the art of cutting things into smaller parts.

Tessellation is one of the most important parts of this asset as it allows us to increase the amount of vertices on the mesh to make displacement nice and smooth, but it’s also expensive. That’s why you are presented with several options to control it.

Player radius is the radius around your character (or any object/npc) in which tessellation will take place. The higher the radius value the more space will be subdivided into smaller triangles.

Player radius \= 8

Player radius \= 22
As you can see on the pictures above, the player radius increases the amount of vertices being tessellated. Primarily it is used to remove holes between vertices that are being tessellated and once that are not.

Player radius \= 3. Holes around the player are caused by rapid change in height of vertices. To fix it increase Player radius

Tessellation factor controls the amount of triangles each vertice will be subdivided into.

Tessellation factor \= 8

Tessellation factor \= 64

Tessellation gets exponentially more expensive the higher the factor is. As a general rule of thumb try to keep it under 10.
To visualize tessellation choose “Shaded wireframe” on unity control panel

Cull edges that are out of camera frustum is an optimisation technique allowing to cull vertices that are not visible in camera frustum. Set tessellation tolerance factor based on distance from camera to player, view angle, etc.

Quality options allows you to choose between 3 different rendering options. High Quality renders everything at full resolution, High Performance uses lods and calculates a lot of data in vertex shader making it work faster. Configurable lets you choose the distance beyond which everything will be rendered as High Performance.

Configurable options works a lot like terrain’s base map distance, but if you need to improve performance you should use both of them

Gloss adds a layer of ‘glistening’ for a snow and has a lot of configurable parts. We will not discuss in details each one of them, just try it out and see what happens ;)

If performance is an issue avoid using gloss. Simply uncheck it in the settings
Terrain layers five and higher are not self-shadowed correctly because of unity internal bug. If this is an issue you can check Draw Instanced in Terrain Settings (or just use less layers)
**Calculate binormal per fragment and Use detail normals** are just additional settings to improve the general look of layers on terrain. If you don’t notice a significant difference just leave it unchecked.

Mesh with splatmaps {#mesh-with-splatmaps}

If you don’t want to use terrain or want to convert your terrain to snow and still use this asset you can do so with a little bit of work

To use TerrainToMeshSnow material on terrain:

  1. Select your mesh
  2. Add TerrainToMeshSnow material to it

TerrainToMeshSnow settings

As a material name suggests it is used for meshes that are generated from terrain, but you can use it with any mesh you want if you have more than one texture assigned to your mesh

A lot of its settings are the same as terrain mesh so we will only discuss the new ones.

Splatmap texture is a texture that defines which texture layer will be visible at any given point of a mesh. This is a system that terrain uses under the hood and if you generate your mesh from terrain you can simply take terrain’s splatmap(s)

Pass blend is a failsafe parameter that acts like a cutout shader and allows you to control the blending between different splats. It is useful if your splatmap has weird artifacts or several splatmaps overlap each other. If you don’t see any artifacts on your mesh just leave it at zero

If you don’t see any artifacts on your mesh just leave Pass blend at zero

Texture block contains all the parameters for the layer and acts like Layer Specific Settings terrain’s block. Click on a layer block and set up albedo texture, normals and all the snowness parameters there. For more info on what each parameter does check Layer Specific Settings

To use more than 4 textures in TerrainToMeshSnow just duplicate material and assign it to the mesh as a second, third and so on material. For each duplicate select a new Splat Map texture and assign textures. You can have limitless amount of textures this way, but it will impact performance

MeshSnow {#meshsnow}

In case your mesh consists of one texture or you want to make snowy prop mesh this is a material for you

To use MeshSnow material on terrain:

  1. Select your mesh
  2. Add MeshSnow material to it

MeshSnow settings

It acts just like Mesh with splatmaps material, but without splat maps or blending because it only allows one texture on an object. This is particularly useful when you have simple terrain or want to add snowness to your rooftop or any prop in a scene.


MeshSnow material settings

For detailed information on what each property does head to Layer Specific Settings section;

If you're going to change snow height on mesh (not terrain) make sure that your mesh has enough initial polygons for tessellation to look good, otherwise there will be visible holes in a mesh.


Every object here uses a variation of MeshSnow material. Edges between vertices are visible because of low polycount mesh

Scripting API {#scripting-api}

In this section we will discuss the intricacies of character interaction with snow.

You are free to change/optimize everything to your needs in scripts and/or shaders, just make sure you have a back up. In case of any questions ask for support at maidnmate@gmail.com

In the Demo scene hierarchy you will find SnowInteractionController object. This component is required for material initialization and proper passing of parameters.

SnowInteractionController {#snowinteractioncontroller}

**Snow Draw Map** is a debug checkmark that controls visibility of GUI texture in the top left corner of your screen. It is a simple tool to visualize your character passed track and helps you debug at what stage things might have broke;

**Use tessellation** checkmark toggles between using tessellation and simple vertex displacement. It is useful when you want to deploy on a lower-end devices that do not support tessellation and see if the game is still playable.
Not every graphics card supports tessellation. For example GLES 3.1 (GLES 3.1 AEP supports tessellation) and lower do not support tessellation and will fallback to vertex displacement. You can uncheck support of such devices in Project Settings >> Player >> Other Settings >> Uncheck “Auto Graphics API” >> Add supported APIs
**Update Track Properties In Runtime** checkmark allows you to finetune other properties in runtime.  
**Test text** shows the current state of tessellation (ON or OFF). You can add anything here.  
**Snow Planes** is a list of game objects that has any of the snow materials on it. It is used to correctly apply tessellation around player. Simply drag and drop any game object with a snow material here.
If you use snow material on a prop mesh that is not walkable on such as rock or rooftop you don’t need to add it to the Snow Planes list.
**Characters** is a list of characters that will be tracked by [**SnowInteractionController**](\#snowinteractioncontroller) to apply tessellation around them. 
Characters are required to have a CharacterSnowInteractor component on them to interact with snow
**Brush Size and Brush Strength** controls the radius and strength of brush that draws track for characters on scene. 
The way this works is each character sends its position to SnowInteractionController which writes this data to a texture. Snow shaders then sample the texture and apply corresponding snow height.

CharacterSnowInteractor {#charactersnowinteractor}

Is used for setting footprints and other interaction with a snowy plane.

CharacterSnowInteractor component must be added to each character (or prop) that interacts with a snow

**Max Height** property controls at which height the character stops interacting with snow. This is useful if your character jumps and you don’t want snow to fall under them. It uses **Physics.Raycast** to check whether a character touches the plane.
If checking for raycast every frame is too expensive you can change the way the character checks if it is grounded. For example, you can add a conditional expression to only do raycast if the character's speed is beyond some threshold or only if the character is grounded.
**Can Leave Footprint** checkmark controls whether a character leaves footprints on snow material. You can uncheck it if you don’t need footprints or if you use this component on a static prop such as tree or a rock;  
**Footsteps Amount** controls the maximum amount of footprints visible on a snow material. When reaching the threshold older footprints will disappear.  
**Snow Material Layer** is a physics layer of a game object. It must correspond to the Layer the snow meshes are set to. Basically it acts like a mask for a Raycast from your character to snow.
You can leave Snow Material Layer as default, but it will be bad for performance as Raycast will check every default layer it hits.

CharacterFootprint {#characterfootprint}

Detects footprints and passes data to CharacterSnowInteractor

Another component you will find on a player is CharacterFootprint.

For good timing of a footprint we use Animation events that are called from Walk, Run and Landing animation. For your character you can add other events and call them from other animation clips or invoke it in some other way altogether.

Character Snow Interactor is a reference to a component set on the same character. We discussed it above.
Data is a list of objects that holds data necessary to correctly render footprint on a snow. Each element of Data is wrapped into CharacterFootprintCheckData class and consists of two fields.
Collision Position Type is an enum that holds different positions for a footprint. On a screen above you can see all the possible position for a footprint (Right foot, Left foot and Both).
Position is a reference to a character mesh specific bone. It defines where the footprint will be rendered on a XZ plane. You don’t have to define all of it and can have only one element in the list. This way footprint will always be rendered at the same place relative to the player position. Alternatively you can add more Collision Position Types and define their positions if your character is an animal with four legs.

You must have noticed that we only have one footprint for a character with. This is because of shader’s limitation on textures it can hold. To correctly draw right and left footprint it is set that Right foot is correct footprint and Left footprint is just mirrored version of it.

#

Adding Custom Components {#adding-custom-components}

This section discusses how you can add your own effects to a snow materials with example of dynamic height change

Select SnowInteractionController component in hierarchy on Demo scene and enable DynamicHeightChangeExample. Press Play and adjust Height Change Value. You can add such dynamic effects yourself. Let’s open the scripts to take a closer look.

private void Update() { float deltaHeight \= heightChangeValue * Time.deltaTime; UpdateTerrain(deltaHeight); UpdateMeshWithManyLayers(deltaHeight); UpdateSingleLayerMesh(deltaHeight); } private void UpdateSingleLayerMesh(float value) { if (singleLayerMesh \== null) return; float newHeight \= singleLayerMeshMat.GetFloat(MaterialKeywordLib.SnowHeightStr) + value; singleLayerMeshMat.SetFloat(MaterialKeywordLib.SnowHeightStr, newHeight); } private void UpdateMeshWithManyLayers(float value) { if (meshWitnManyLayers \== null) return; foreach (var mat in meshWitnManyLayersMat) { for (int i \= 0; i \< MAX_LAYERS; i++) { float newHeight \= mat.GetFloat($"{MaterialKeywordLib.SnowHeightStr}{i}") + value; mat.SetFloat($"{MaterialKeywordLib.SnowHeightStr}{i}", newHeight); } } } private void UpdateTerrain(float value) { if (terrain \== null) return; foreach (var layer in terrain.terrainData.terrainLayers) { float newHeight \= MaterialKeywordLib.GetTerrainSnowHeight(layer) + value; MaterialKeywordLib.SetTerrainSnowHeight(layer, newHeight); } }

In the Update call we calculate new delta height and then call methods for each type of material (TerrainSnow, TerrainToMeshSnow and MeshSnow).
Each material has its own method to apply data. We tried to systematize it by creating a MaterialKeywordLib class which has most of the properties neatly organized so you can easily access them.
For meshes you just get property that you want by using Unity’s API material.GetFloat and apply new value with material.SetFloat.
For terrain you can change properties of each layer by selecting a layer and accessing its properties directly.

Keep in mind that some terrain properties such as snow height are not directly accessed through the terrain layer. To change Snow Height, Snowness and so on you can use MaterialKeywordLib methods

Roadmap {#roadmap}

In future releases we will add support for URP and HDRP. We are also implementing some other cool features that will make snow interaction even more fun.

Thank you for purchasing snow asset! If you have any questions do write to maidnmate@gmail.com