Search Unity

Question I have to disable a keyword before enabling another one, why?

Discussion in 'Shaders' started by jjiangweilan, Feb 24, 2021.

  1. jjiangweilan

    jjiangweilan

    Joined:
    Mar 31, 2018
    Posts:
    19
    Can anyone help me with this one? I know there is scoring system behind how Unity select matching shaders, but I really can't figure out myself how that works under this situation.

    Here is my key words set: _EMISSION _FOGENABLE _REALTIME_LIGHT_ENABLE _REFLECT_OFF _SOFTOUTLINE_ON _MY_FEATURE

    To enable the keyword _MY_FEATURE at runtime in a build, I have to disable _FOGENABLE. Why is this happening? (I don't have to disable _FOGENABLE in editor mode tho)
     
    Last edited: Feb 24, 2021
  2. aleksandrk

    aleksandrk

    Unity Technologies

    Joined:
    Jul 3, 2017
    Posts:
    3,014
    How do you declare those keywords in the shader?
     
  3. jjiangweilan

    jjiangweilan

    Joined:
    Mar 31, 2018
    Posts:
    19
    Sure. The effect of _MY_FEATURE is enabled if I manually disable _FOGENABLE

    Working:
    Code (CSharp):
    1.             var mat = GetComponent<MeshRenderer>().sharedMaterial;
    2.             mat.EnableKeyword("_MY_FEATURE");
    3.             mat.DisableKeyword("_FOGENABLE");
    Not Working:
    Code (CSharp):
    1.             var mat = GetComponent<MeshRenderer>().sharedMaterial;
    2.             mat.EnableKeyword("_MY_FEATURE");
    Shader looks like this:
    Code (CSharp):
    1.             HLSLPROGRAM
    2.             #include "../Library/Assets.hlsl"
    3.             #pragma target 3.5
    4.             #pragma prefer_hlslcc gles
    5.             #pragma exclude_renderers d3d11_9x
    6.             #pragma fragmentoption ARB_precision_hint_fastest
    7.             #pragma skip_variants POINT POINT_COOKIE SHADOWS_SCREEN VERTEXLIGHT_ON LIGHTPROBE_SH SHADOWS_CUBE LINEAR_FOG
    8.          
    9.             #pragma multi_compile __ _DISABLE_FOG
    10.             #pragma multi_compile __ LIGHTMAP_ON
    11.             #pragma multi_compile __ _HEIGHTFOG_ON
    12.             #pragma multi_compile _SOFT_SHADOW_16
    13.             #pragma multi_compile __ _CASCADE_SHADOWMAP_ON _STANDARD_SHADOWMAP_ON
    14.  
    15.             #pragma shader_feature _REFLECT_OFF _REFLECT_CUBE _REFLECT_MIRROR
    16.             #pragma shader_feature _RECEIVE_SHADOWS
    17.             #pragma shader_feature _NORMALMAP
    18.             #pragma shader_feature _RAMPMAP
    19.             #pragma shader_feature _EMISSION
    20.             #pragma shader_feature _FOGENABLE
    21.             #pragma shader_feature _REALTIME_LIGHT_ENABLE
    22.             #pragma shader_feature METALLIC_SPECGLOSS_MAP
    23. #pragma shader_feature _ _MY_FEATURE
    24.             #pragma vertex AssetsPassVertex
    25.             #pragma fragment AssetsPassFragment
    26.             ENDHLSL
     
    Last edited: Feb 24, 2021
  4. aleksandrk

    aleksandrk

    Unity Technologies

    Joined:
    Jul 3, 2017
    Posts:
    3,014
    Do you have any material that has this setup (both _FOGENABLE and _MY_FEATURE enabled)?
    Shader features provide a way to reduce the amount of variants compiled for the player that is based on material usage. If there is no material that has both enabled referenced in the scenes that go to the build, the variants will not be there, so it won't work.
    You need to either include such a material or change to use multi_compile. The latter will include all possible variant combinations, but this means it has more variants to compile.
    Check https://docs.unity3d.com/Manual/SL-MultipleProgramVariants.html for more info.