Search Unity

How do I force mediump default float precision when compiling GLES shaders?

Discussion in 'Shaders' started by SamBigosES, Jul 1, 2021.

  1. SamBigosES

    SamBigosES

    Joined:
    Jul 8, 2020
    Posts:
    1
    When compiling shaders for a mobile GLES platform, all output GLSL fragment shader code includes this at the top:

    Code (GLSL):
    1. precision highp float;
    This is a problem because it causes all floats/vecs to be highp unless otherwise defined using half/fixed types.

    I have replaced all instances of float with half in my shaders, but there are still some variables which are compiled without the mediump tag in the output GLSL and thus use the default highp precision.

    These variables lacking the mediump tag are either variables which the shader compiler adds as optimisations, or built-in variables such as unity_FogParams which I'm unable to change to a lower precision.

    Profiling the difference between precision highp float and precision mediump float shows a fairly significant performance gain, so my question is why does Unity set the default precision to highp, and how do I change it?

    Thank you.
     
  2. aleksandrk

    aleksandrk

    Unity Technologies

    Joined:
    Jul 3, 2017
    Posts:
    2,176
    Hi!

    The default precision is set to highp because it's the safest option. If it were mediump, it would be very easy to get visual artifacts that are terrible to debug.
    There are certain quantities that are nearly guaranteed to produce incorrect rendering. These include world position, texture UVs, depth, and some others.
    We provide control over the precision of texture data, uniforms and temporaries that you create in HLSL code. If the operands match in precision, the result will have the same precision. If the operands' precisions do not match, they get upgraded to the highest precision, and the result gets the same precision as well. The compiler is not allowed to lower the precision.
    If you want to force fp16, you need to cast the operands to fp16 if they use fp32. Or you need to cast the result to fp16, this depends on whether you want the calculation be performed in fp16 or fp32.
     
unityunity