Stylized Water Shader
Stylized Water Shader
Thank you for purchasing the Stylized Water Shader!
Your feedback is instrumental to the future of this package!
Feedback and suggestions can be made in the forum thread:
This manual is intended to clarify the use of the package and should be consulted for troubleshooting.
Please refer to our refund policy
The minimum hardware requirement is a GPU compatible with OpenGL ES 3.0. Devices released after 2012 support this.
The shaders offer different lighting methods, the “Unlit” and “Simple” lighting methods are best suited for mobile.
Compatible with both OpenGL and Metal
Users have reported to have no issues on Playstation 4 and Nintendo Switch. The shaders are “surface shaders”, which means they use Unity’s internal lighting system rather than a custom one. This leads to assume the chance of any graphical or compiling issues are minimal.
I do not have access to any dev kits. So if you find yourself having any such issues, please get in touch as I’d be happy to work towards a solution!
The shaders have been tested using an Oculus Rift where no issues have been encountered. Planar reflections do not work in Single-Pass Stereo Rendering and are automatically disabled.
Version 2.0 adds support for orthographic camera’s, making it compatible with AR applications like Vuforia.
The minimum supported version is 5.4, up to 2018.2. Beta versions may work but will not be supported, due to the frequent changes.
With the lighting mode set to “Advanced” the shader supports Skybox reflections and Reflection Probes.
Point lights and spot light are not supported, which is a limitation of transparent surface shaders.
Objects using shaders that render to the “Transparent” render queue cannot be reflected.
DirectX 9 is not supported, a minimum of Shader Model 3.5 is required. Any graphics card newer than a Radeon X1000 or GeForce 6 will support this.
- Drag one of the prefabs found under Assets/StylizedWaterShader/Prefabs/ into your scene.
- Use the
StylizedWaterscript component to start modifying it to your liking.
- Create and assign a material to your water mesh and assign a shader found under /StylizedWater.
- Add the
When using Forward Rendering, be sure to add the
EnableDepthBuffer script to your camera. This ensures the depth and intersection effects work.
Note: It is advised to create your own materials, so your settings are not accidentally overridden when updating the package.
If you’re uncertain what a parameter is for, click the help icon to toggle descriptions for that section
Should you run into any issues or have questions/feedback, please do not hesitate to reach out! I will do my best to respond as soon as I can.
Unity forums thread: http://forum.unity3d.com/threads/stylized-water-shader-desktop-mobile.430118/
If you’d like to have separate water bodies in your scene, each with a (slightly) different appearance, you will need to create a unique material instance for these meshes.
- Create and assign a new material to your water mesh and assign a shader found under /StylizedWater.
- Add the StylizedWater script component.
Make sure only one object has Planar Reflections enabled, otherwise this will incur a huge performance hit.
All the shaders in the package are one-sided. Meaning, if you move the camera beneath the water surface, it will appear invisible.
If this is an issue for you, duplicate your water object and flip it 180 degrees. It’s recommended to create a separate material for this object, so you can fine-tune it’s visual appearance.
Triggering post processing effects, such as screen waving and blurring, is possible through SC Post Effects, which includes an “Underwater” example profile.
|8 different normal maps||√||√|
|Vertex color support||√||√|
Assertion failed on expression: ‘(srcInfo.GetChannelMask() & copyChannels) == copyChannels’
These errors are only thrown in the demo scene in Unit 2018.1+. This has been fixed in version 2.0.1.
Waves aren’t high enough, even with the highest “Wave height” value
In this case, your water mesh must be very big. If you need higher waves than the shader value allows for, increase the scale of your mesh on the Y-axis to the same effect
Waves look very pointy, triangular
This is an indication that the vertex-density/polycount of your water mesh is too low. Add subdivisions to your mesh to increase the wave fidelity.
Much like a pin-art toy; the more pins it has, the more detailed the cast becomes.
Water depth and intersection effect do not appear
If you’re using Forward rendering, check if your camera has the “EnableDepthBuffer” script attached to it. In many cases this will fix any issues.
Additionally, objects using an Unlit shader that are underneath the water, or intersect with it, will not contribute to these effects.
If using shaders other than Unlit shaders is not viable for your project, you can use vertex painting to paint the intersection effect instead.
Some objects do not receive depth and intersection effects
Objects intersecting with the water must use a shader that writes to the depth buffer, otherwise there is no way to tell where it is positioned in 3D space. For instance, Unlit shaders do not write to the depth buffer.
Transparency is set to 0, but water still has a faint bright color
This only applies to the Desktop shader. The transparency parameter doesn’t actually control the shader’s opacity, but rather controls the amount of visibility of the objects rendered underneath the water. This is known as a GrabPass. The water shader is built on the PBR model, so it inherits some shading properties such as fresnel, which explains the faint brightness.
This behaviour is by design, so it’s still possible to have crystal clear water, while retaining the refraction capabilities. Otherwise the water would simply turn invisible. When the “Unlit” toggle is checked, this is not an issue, since all lighting is overridden.
Refraction shows artifacts along edges
This is actually correct behavior, and is a common limitation of using a GrabPass. Essentially objects above the water are also refracted.
A way around this is to render the geometry underneath the water into a separate refraction buffer. However, the performance trade-off for such a technique is generally not worth the small visual improvement, which is why it is not implemented.
Water material looks black
If there is no Directional Light in your scene this may be the case. Most mobile setups do not use any lighting, for performance. In which case you should set the lighting method to “Unlit” in the Lighting tab.
(Mobile) After a few minutes, the water animation becomes stepped and the textures pixellated
Since some mobile devices don’t support high precision values, artifacts may occur the longer the shader runs. This greatly varies between devices. Disabling “World-space tiling” uses overall lower values, and will prevent these artifacts.
This issue is resolved completely in version 2.0.
Water surface flickers white and the intersection effects disappears
This is usually caused if there is no light source in the scene, or your scene-view has lighting switched off.
Water shows banding artifacts
Some of the shader features rely on the rendered depth buffer. If your device does not render this accurately banding artifacts will show. This appears to happen on some devices using a Mali-450MP4 GPU.
It has been fixed in version 1.24. Should it still occur, a potentially solution is to set the display buffer to 32-bit as some users reported this fixed the issue.
Objects show a pixelated white outline
This occurs when using Unity’s built-in MSAA and can be remedied by using an Anti-Aliasing image effect instead.
Surfaces looks jagged
This is due to compression of the shader textures. You can override this compression in the inspector under the “Advanced” tab.
This will impair a slightly larger memory cost as the two textures will be larger in file size.
(iOS) Black dots appear on the water
You can elevate this issue by doing taking the following steps:
- Unset the Sun object in the Lighting tab, if set
- Raise the Shadow Bias value on your Directional Light
`System.IO.File’ does not contain a definition for `WriteAllBytes’ error
The “WebPlayer” target platform does not support writing files to disk and is thus not supported. The WebPlayer functionality was officially deprecated since Unity 5.4.
The lighting method makes the biggest difference in performance, at least between “Simple” and “Advanced. As does enabling the normal map. For example, this is how a rather old Samsung Galaxy S4 Mini performs in comparison:
To achieve reflections, all objects above the water are rendered using a secondary camera (for every camera). This means your polycount and drawcalls can essentially be doubled.
In order to minimize the performance impact, it is recommend to make use of the “Reflect Layers” dropdown. Small objects like grass or VFX could be ignored in this way. Make sure to always ignore the layer the water object is on, by default this is the “Water” layer. This avoids recursive reflections.
Alternatively, disable reflections entirely and use a Reflection Probe. In order to use this, the lighting method must be set to “Advanced”.
When splitting up your water into tiles, planar reflections should be disabled to avoid re-rendering reflections for every individual tile.
Vertex colors can be painted using Polybrush or other vertex tools.
You can sample the mesh’s vertex colors to denote where the intersection effect should show, or where the water should be transparent.
If you’d like to show the intersection effect based on vertex colors, under the “Intersection” tab the solver must be set to “Vertex color”.
The “Enable Vertex Colors” checkbox under the Advanced tab must be checked in order to use this.
By painting the following colors, the weight is painted for: