Search Unity

Question shader warning with no reason

Discussion in 'Shaders' started by grobonom, May 2, 2021.

  1. grobonom

    grobonom

    Joined:
    Jun 23, 2018
    Posts:
    335
    Hi all :)

    I'm sure there's a reason for a shader warning but i'm too noob for finding it :/

    I got an Shader warning in 'My_shaders/test_geom': Output value 'vertex_program' is not completely initialized at line 104 (on d3d11)

    on this shader:
    Code (CSharp):
    1. Shader "My_shaders/test_geom"
    2. {
    3.     Properties {
    4.         [NoScaleOffset] _MainTex ("Diffuse Texture", 2D) = "white" {}
    5.         [NoScaleOffset] _DirtLMTex ("Dirt/AO-LM (RGB-A)", 2D) = "(RGBA: .98,.98,.98,1)" {}
    6.         _NightLightColor ("Lightmap color", Color) = (1,1,1,1)
    7.         [NoScaleOffset] _BumpMap ("Normal Texture", 2D) = "bump" {}
    8.  
    9.     }
    10.     SubShader {
    11.         Pass{
    12.             Tags { "LightMode" = "ForwardBase" }
    13.             CGPROGRAM
    14.  
    15.          // my variants....
    16.          #pragma multi_compile_local ___ WITH_CITY_NIGHTLIGHTS
    17.  
    18.             #pragma vertex vertex_program
    19.          #pragma geometry geometry_program
    20.          #pragma fragment fragment_program
    21.  
    22.          #pragma multi_compile_fog
    23.  
    24.          #pragma multi_compile_fwdbase nolightmap nodirlightmap nodynlightmap novertexlight
    25.  
    26.  
    27.          #include "Lighting.cginc"
    28.          #include "AutoLight.cginc"
    29.          
    30.             // My vars
    31.             sampler2D _MainTex;
    32.             sampler2D _BumpMap;
    33.             sampler2D _DirtLMTex;
    34.          static const half _BumpDistFade=20;
    35.          static const half _BumpLengthFade=5;
    36.  
    37.      
    38. #if defined(WITH_CITY_NIGHTLIGHTS)
    39.          fixed4 _NightLightColor;
    40. #endif
    41.  
    42.  
    43.             // Base Input Structs
    44.             struct APP2V {
    45.                 float4 vertex: POSITION;
    46.                 half3 normal: NORMAL;
    47.                 half4 UV0: TEXCOORD0;
    48.                 half4 UV1: TEXCOORD1;
    49.                 half4 UVdissolve: TEXCOORD2;
    50.                 half4 tangent: TANGENT;
    51.             };
    52.      
    53.             struct V2G {
    54.                 float4 pos: SV_POSITION;
    55.                 half4 UV0: TEXCOORD0;
    56.                 half4 UV1: TEXCOORD1;
    57.                 half4 posWorld: TEXCOORD2;
    58.                 half3 normalWorld: TEXCOORD3;
    59.                 half3 tangentWorld: TEXCOORD4;
    60.                 half3 binormalWorld: TEXCOORD5;
    61.             UNITY_FOG_COORDS(6) // fog in 6
    62. //#if defined (SHADOWS_SCREEN)
    63. //            SHADOW_COORDS(7) // shadows data into TEXCOORD7
    64.             unityShadowCoord4 _ShadowCoord : TEXCOORD7;
    65. //#endif
    66.  
    67.             };
    68.  
    69.             struct G2F {
    70.                 float4 pos: SV_POSITION;
    71.                 half4 UV0: TEXCOORD0;
    72.                 half4 UV1: TEXCOORD1;
    73.                 half4 posWorld: TEXCOORD2;
    74.                 half3 normalWorld: TEXCOORD3;
    75.                 half3 tangentWorld: TEXCOORD4;
    76.                 half3 binormalWorld: TEXCOORD5;
    77.             UNITY_FOG_COORDS(6) // fog in 6
    78.             unityShadowCoord4 _ShadowCoord : TEXCOORD7;
    79.             half fade_factor: COLOR0;
    80.             };
    81.  
    82.  
    83.  
    84.          //========================================================================
    85.  
    86.          
    87.             // Vertex program
    88.             V2G vertex_program( APP2V v )
    89.          {
    90.                 V2G o;
    91.              
    92.                 o.normalWorld = normalize( mul( float4( v.normal, 0.0 ), unity_WorldToObject ).xyz );    
    93.                 o.tangentWorld = normalize( mul( unity_ObjectToWorld, v.tangent ).xyz );
    94.                 o.binormalWorld = normalize( cross( o.normalWorld, o.tangentWorld )* v.tangent.w);
    95.                      
    96.  
    97.                 o.posWorld = mul( unity_ObjectToWorld, v.vertex);
    98.                 o.pos = v.vertex;//UnityObjectToClipPos( v.vertex);
    99.                 o.UV0 = v.UV0;
    100.                 o.UV1 = v.UV1;
    101.  
    102. #if defined (UNITY_NO_SCREENSPACE_SHADOWS)
    103.             TRANSFER_SHADOW(o)
    104. #else
    105.             o._ShadowCoord = ComputeScreenPos(UnityObjectToClipPos( v.vertex));
    106. #endif
    107.  
    108.             UNITY_TRANSFER_FOG(o,o.pos);
    109.  
    110.                 return o;
    111.             }
    112.      
    113.      
    114.          [maxvertexcount(3)]
    115.          void geometry_program(triangle V2G IN[3], inout TriangleStream<G2F> triStream)
    116.          {
    117.             G2F o;
    118.  
    119.             for(int i = 0; i < 3; i++)
    120.             {
    121.                o.posWorld=IN[i].posWorld;
    122.                o.normalWorld=IN[i].normalWorld;
    123.                o.tangentWorld=IN[i].tangentWorld;
    124.                o.binormalWorld=IN[i].binormalWorld;
    125.  
    126.                o.pos = UnityObjectToClipPos(IN[i].pos);
    127.  
    128.                o._ShadowCoord = IN[i]._ShadowCoord; // transfer as is shadows coming from vertex program
    129.            
    130.                UNITY_TRANSFER_FOG(o,o.pos);
    131.            
    132.                o.UV0 = IN[i].UV0;
    133.                o.UV1 = IN[i].UV1;
    134.            
    135.                o.fade_factor = 1;
    136.            
    137.                triStream.Append(o);
    138.             }
    139.  
    140.             triStream.RestartStrip();
    141.          }      
    142.      
    143.          
    144.             // Fragment program
    145.             float4 fragment_program( G2F i ): COLOR
    146.          {
    147.             half3 pixel_in_cam = _WorldSpaceCameraPos.xyz - i.posWorld.xyz;
    148.             half pixel_dist = length(pixel_in_cam);
    149.  
    150.  
    151.                 half3 lightDirection = normalize( _WorldSpaceLightPos0.xyz );
    152.  
    153.                 // Texture Maps
    154.             //--------------
    155.             // diffuse
    156.                 fixed4 diffuse = tex2D( _MainTex, i.UV0);
    157.  
    158.             // if diffuse texture have some alpha then clip under 0.5
    159.             clip(diffuse.a-0.5);
    160.      
    161.             // dirt-AO
    162.                 fixed4 dirt = tex2D( _DirtLMTex, i.UV1);// dirt and AO texture
    163.          
    164.             fixed3 diff = diffuse * dirt.rgb * 1.5; // *1.5 for less dark walls
    165.  
    166.             fixed3 normalDirection;
    167.          
    168.          
    169.             // fading bumps with distance ( far walls do not need bumpmaps )
    170.             //---------------------------------------------------------------
    171.             if(pixel_dist < _BumpDistFade)
    172.             {
    173.                // bump
    174.                fixed3 bump =  UnpackNormal (tex2D (_BumpMap,  i.UV0));
    175.            
    176.                // a revoir sur un vecteur plutot que sur des valeurs X et Y independantes
    177.                fixed delta=saturate((pixel_dist-(_BumpDistFade-_BumpLengthFade))/_BumpLengthFade);
    178.            
    179.                // small interpolation to make bump coming less visible...
    180.                bump = fixed3(lerp(bump.x,0,delta),lerp(bump.y,0,delta),1);
    181.  
    182.                // Normal Transpose Matrix ( i still do not get why this is here 8*(  )
    183.                half3x3 local2WorldTranspose = half3x3(
    184.                   i.tangentWorld,
    185.                   i.binormalWorld,
    186.                   i.normalWorld
    187.                );
    188.            
    189.                // Calculate Normal Direction from normal and bumpies
    190.                normalDirection = normalize( mul( bump, local2WorldTranspose ) );
    191.             }
    192.             else
    193.             {
    194.                normalDirection = i.normalWorld; // with no bumps
    195.             }
    196.            
    197.            
    198.             fixed3 outputColor;
    199.            
    200.            
    201. #if defined(WITH_CITY_NIGHTLIGHTS)
    202.             // Night lightmap and its color and its intensity
    203.             fixed lm =  dirt.a;
    204.             fixed3 emiss = lm * _NightLightColor.rgb;// * _NightLightFactor;
    205.          
    206.             // night city wall lightings with less dirt/AO....
    207.             outputColor = diff * UNITY_LIGHTMODEL_AMBIENT.rgb + diffuse*(1-(dirt.rgb*lm-(lm-1)))*emiss*2;
    208. #else
    209.             // Lighting
    210.             fixed3 diffuseReflection = _LightColor0.rgb * saturate( dot( normalDirection, lightDirection ) );
    211.          
    212.                 outputColor = diff * (diffuseReflection * SHADOW_ATTENUATION(i) + UNITY_LIGHTMODEL_AMBIENT.rgb);
    213.              
    214. #endif            
    215.  
    216.             // coming IN and OUT color setting
    217.             outputColor = lerp(outputColor,UNITY_LIGHTMODEL_AMBIENT.rgb,i.fade_factor);
    218.      
    219.          
    220.             UNITY_APPLY_FOG(i.fogCoord,outputColor);
    221.          
    222.                 return half4(outputColor, 1.0);
    223.          
    224.             // show grey normals+bumps
    225. //                return half4(saturate( dot( normalDirection, lightDirection )),saturate( dot( normalDirection, lightDirection )),saturate( dot( normalDirection, lightDirection )), 1.0);
    226.          
    227.             }
    228.          
    229.             ENDCG
    230.         }
    231.    
    232.       // shadow caster rendering pass, implemented manually
    233.       // using macros from UnityCG.cginc
    234.       Pass
    235.       {
    236.          Tags {"LightMode"="ShadowCaster"}
    237.  
    238.          CGPROGRAM
    239.          #pragma vertex vert
    240.          #pragma fragment frag
    241.          #pragma multi_compile_shadowcaster
    242.          #include "UnityCG.cginc"
    243.  
    244.          struct v2f {
    245.              V2F_SHADOW_CASTER;
    246.          };
    247.  
    248.          v2f vert(appdata_base v)
    249.          {
    250.              v2f o;
    251.              TRANSFER_SHADOW_CASTER_NORMALOFFSET(o)
    252.              return o;
    253.          }
    254.  
    255.          float4 frag(v2f i) : SV_Target
    256.          {
    257.              SHADOW_CASTER_FRAGMENT(i)
    258.          }
    259.          ENDCG
    260.       }
    261.    }
    262. }
    As you can see, the V2G struct is completely initialized and i really don't know what is the problem here.

    This shader works like a charm on win, lin and android, even with this warning.

    I'd be curious of experts advices ;)

    Happy unitying !
     
  2. bgolus

    bgolus

    Joined:
    Dec 7, 2012
    Posts:
    12,352
    In some cases this macro is empty, which means your
    o._ShadowCoord
    isn’t being initialized. The error should list out what keywords are enabled. I suspect you’ll see
    UNITY_NO_SCREENSPACE_SHADOWS
    with no other shadow related keywords, meaning no shadows at all.
     
  3. grobonom

    grobonom

    Joined:
    Jun 23, 2018
    Posts:
    335
    The thing is here, in vertex program:
    Code (CSharp):
    1. #if defined (UNITY_NO_SCREENSPACE_SHADOWS)
    2.             TRANSFER_SHADOW(o)
    3. #else
    4.             o._ShadowCoord = ComputeScreenPos(UnityObjectToClipPos( v.vertex));
    5. #endif
    6.  
    If i always use the TRANSFER_SHADOW(o) shadows work on windows PC target but not on android target.
    if i always use the ComputeScreenPos, shadows work on android target but not on PC win target.
    This is the reason why i used this things.

    However i confess i don't know the reason why one work on a platform and not other and vice-versa.

    If you got any idea @bgolus or anyone else, i'd be pleased to hear of it ;)

    Happy unitying !
     
  4. bgolus

    bgolus

    Joined:
    Dec 7, 2012
    Posts:
    12,352
    Is there a reason you don't just use
    TRANSFER_SHADOW(o)
    and
    SHADOW_COORDS(7)
    for both?
     
  5. grobonom

    grobonom

    Joined:
    Jun 23, 2018
    Posts:
    335
    I wish i could but for some reason when i use the U3D standard macros, shadows work properly on windows target but do not work ( they do some weird result ) for android target :/

    I dig on this for some hours and found no reason, and using the hand-initialized ShadowCoord is the only way i found ( till now ) for making shadows work on both target platforms.

    Hmmm i'll be back soon with more accurate info about this ;-)
     
  6. pitibonom

    pitibonom

    Joined:
    Aug 17, 2010
    Posts:
    220
    Back there with more info....

    I simply made a short simple project with few things and 2 shaders.
    * my strange shader that works fine with the
    1. #if defined (UNITY_NO_SCREENSPACE_SHADOWS)
    2. TRANSFER_SHADOW(o)
    3. #else
    4. o._ShadowCoord = ComputeScreenPos(UnityObjectToClipPos( v.vertex));
    5. #endif
    * a base shader using standard unity SHADOWS macros and variables.

    Here's the rar of the whole project ( minus the library folder ) in the linked files...

    and a screenshot:
    upload_2021-5-4_16-10-55.png

    On the right the result of my shader with the strange #if defined

    On the left the shader using macros that do not even compile for android target.
    Here's a copy of this shader with some comments in code for making it work like i did:

    Code (CSharp):
    1. Shader "My_shaders/buggy_my_mat"
    2. {
    3.     Properties {
    4.         [NoScaleOffset] _MainTex ("Diffuse Texture", 2D) = "white" {}
    5.     }
    6.     SubShader {
    7.         Pass{
    8.             Tags { "LightMode" = "ForwardBase" }
    9.             CGPROGRAM
    10.  
    11.  
    12.             #pragma vertex vertex_program
    13.          #pragma geometry geometry_program
    14.          #pragma fragment fragment_program
    15.  
    16.          #pragma multi_compile_fog
    17.  
    18.          #pragma multi_compile_fwdbase nolightmap nodirlightmap nodynlightmap novertexlight
    19.  
    20.  
    21.          #include "Lighting.cginc"
    22.          #include "AutoLight.cginc"
    23.          
    24.             // My vars
    25.             sampler2D _MainTex;
    26.  
    27.  
    28. // as is, using SHADOW_COORDS(x) in structs and TRANSFER_SHADOW macro,
    29. // the shader do not compile at all for android target.
    30. // the error is: Shader error in 'My_shaders/buggy_my_mat': undeclared identifier 'v'
    31. // at line 116 (on d3d11)
    32. // however, it compiles with no error and works fine for win target.
    33. // this means U3D macros seem to have a problem :-/
    34. //
    35. // TRY1: in G2F replace  SHADOW_COORDS(7) with unityShadowCoord4 _ShadowCoord
    36. // : TEXCOORD7; so that i can still use the SHADOW_ATTENUATION(i)
    37. // in fragment, and so that the shadow data calculated in vertex program passes through
    38. // the geometry shader without a change
    39. // ----> this works properly for android target but when switching to win target, shadows
    40. // exist but are inconsistent....
    41. //
    42. // TRY2: in V2G replace  SHADOW_COORDS(7) with unityShadowCoord4
    43. // _ShadowCoord : TEXCOORD7; so that i can still use the SHADOW_ATTENUATION(i)
    44. // and in vertex program, uncomment the #if thingie. you got the same shader as the one
    45. // that works for me for both win and android target...
    46.        
    47.  
    48.  
    49.             // Base Input Structs
    50.             struct APP2V {
    51.                 float4 vertex: POSITION;
    52.                 half4 UV0: TEXCOORD0;
    53.             };
    54.        
    55.             struct V2G {
    56.                 float4 pos: SV_POSITION;
    57.                 half4 UV0: TEXCOORD0;
    58.             UNITY_FOG_COORDS(6) // fog in 6
    59. //#if defined (SHADOWS_SCREEN)
    60.             SHADOW_COORDS(7) // shadows data into TEXCOORD7
    61. //            unityShadowCoord4 _ShadowCoord : TEXCOORD7;
    62. //#endif  
    63.  
    64.             };
    65.  
    66.             struct G2F {
    67.                 float4 pos: SV_POSITION;
    68.                 half4 UV0: TEXCOORD0;
    69.  
    70.             UNITY_FOG_COORDS(6) // fog in 6
    71.          
    72.             SHADOW_COORDS(7) // shadows data into TEXCOORD7
    73. //            unityShadowCoord4 _ShadowCoord : TEXCOORD7;
    74.             };
    75.  
    76.  
    77.  
    78.  
    79.  
    80.          inline float random11(float p)
    81.          {
    82.              p = frac(p * .1031);
    83.              p *= p + 33.33;
    84.              p *= p + p;
    85.              return((frac(p)-0.5)*2); //-1 to +1
    86.          }
    87.          inline half2 random21(float p)
    88.          {
    89.             half3 p3 = frac(float3(p,p,p) * half3(.1031, .1030, .0973));
    90.             p3 += dot(p3, p3.yzx + 33.33);
    91.             return frac((p3.xx+p3.yz)*p3.zy);
    92.          }
    93.          //========================================================================
    94.  
    95.          
    96.             // Vertex program
    97.             V2G vertex_program( APP2V v )
    98.          {
    99.                 V2G o;
    100.              
    101.                 o.pos = v.vertex;//UnityObjectToClipPos( v.vertex); // done in geom for triangle spreading
    102.                 o.UV0 = v.UV0;
    103.  
    104. //#if defined (UNITY_NO_SCREENSPACE_SHADOWS)
    105.             TRANSFER_SHADOW(o)
    106. //#else
    107. //            o._ShadowCoord = ComputeScreenPos(UnityObjectToClipPos( v.vertex));
    108. //#endif
    109.  
    110.             UNITY_TRANSFER_FOG(o,o.pos);
    111.  
    112.                 return o;
    113.             }
    114.        
    115.        
    116.          [maxvertexcount(3)]
    117.          void geometry_program(triangle V2G IN[3], inout TriangleStream<G2F> triStream)
    118.          {
    119.             G2F o;
    120.  
    121.  
    122.             for(int i = 0; i < 3; i++)
    123.             {
    124.  
    125.                o.pos = UnityObjectToClipPos(IN[i].pos);
    126.  
    127.  
    128. // TRY1: comment the macro and uncomment the o.__ShadowCoord so that shadow
    129. // info coming from VP passes through here
    130. // this gives a proper result in android platform but in windows, resulting shadows are
    131. //kinda fu*ked-up
    132.  
    133.                //o._ShadowCoord = IN[i]._ShadowCoord; // transfer as is shadows coming from vertex program
    134.                TRANSFER_SHADOW(o)
    135.              
    136.                UNITY_TRANSFER_FOG(o,o.pos);
    137.              
    138.                o.UV0 = IN[i].UV0;
    139.              
    140.                triStream.Append(o);
    141.             }
    142.  
    143.             triStream.RestartStrip();
    144.          }      
    145.        
    146.          
    147.             // Fragment program
    148.             float4 fragment_program( G2F i ): SV_Target
    149.          {
    150.  
    151.  
    152.                 half3 lightDirection = normalize( _WorldSpaceLightPos0.xyz );
    153.  
    154.                 // Texture Maps
    155.             //--------------
    156.             // diffuse
    157.                 fixed4 diffuse = tex2D( _MainTex, i.UV0);
    158.  
    159.             // if diffuse texture have some alpha then clip under 0.5
    160.             clip(diffuse.a-0.5);
    161.  
    162.              
    163.             fixed3 outputColor=diffuse * SHADOW_ATTENUATION(i) + UNITY_LIGHTMODEL_AMBIENT.rgb;
    164.              
    165.          
    166.             UNITY_APPLY_FOG(i.fogCoord,outputColor);
    167.          
    168.                 return half4(outputColor, 1.0);
    169.                    
    170.             }
    171.          
    172.             ENDCG
    173.         }
    174.    
    175.       // shadow caster rendering pass, implemented manually
    176.       // using macros from UnityCG.cginc
    177.       Pass
    178.       {
    179.          Tags {"LightMode"="ShadowCaster"}
    180.  
    181.          CGPROGRAM
    182.          #pragma vertex vert
    183.          #pragma fragment frag
    184.          #pragma multi_compile_shadowcaster
    185.          #include "UnityCG.cginc"
    186.  
    187.          struct v2f {
    188.              V2F_SHADOW_CASTER;
    189.          };
    190.  
    191.          v2f vert(appdata_base v)
    192.          {
    193.              v2f o;
    194.              TRANSFER_SHADOW_CASTER_NORMALOFFSET(o)
    195.              return o;
    196.          }
    197.  
    198.          float4 frag(v2f i) : SV_Target
    199.          {
    200.              SHADOW_CASTER_FRAGMENT(i)
    201.          }
    202.          ENDCG
    203.       }
    204.    }
    205. }
    What do you think i'm doing wrong @bgolus ?

    Thanks again for your kind help and your patience :)

    regards !

    Happy unitying !
     

    Attached Files:

  7. bgolus

    bgolus

    Joined:
    Dec 7, 2012
    Posts:
    12,352
    Ah, yeah, I missed the geometry shader aspect of this. That changes things.

    The shadow macros assume they're being called in a vertex shader and that there is a
    appdata_full v
    struct variable, specifically a
    v.vertex
    that's in object space.

    For a different setup, though one with a similar issue of no longer having an object space
    v.vertex
    , I wrote a bit of code in my sphere impostor article that handled getting working shadow receiving that should work on desktop and mobile.

    If your geometry shader is modifying the vertex positions in world space, you can look at the code example in the above article to get an idea of what to do. You don't need to the dummy struct because you are actually passing the data from the geometry shader to the fragment, where as in the above article's example it's all happening in the fragment shader.

    The option would be to do all of your object to world & world to clip space transforms in the geometry shader. If you're manipulating the vertices in the geometry shader, that'll be what you'll need to do. Don't bother with any of the fog or shadow calculations in the vertex shader at all. Really the main change you'll want to make is change the
    V2G
    struct to use
    float4 vertex
    instead of
    float4 pos
    . Then do something like this:
    Code (csharp):
    1. struct V2G {
    2.   float4 vertex: SV_POSITION;
    3.   float2 UV0: TEXCOORD0;
    4. };
    5.  
    6. // in the geometry shader
    7. for(int i = 0; i < 3; i++)
    8. {
    9.   // make a v variable for the macros to use
    10.   V2G v = IN[i];
    11.   o.pos = UnityObjectToClipPos(v.vertex);
    12.  
    13.   // this function sometimes expects a v.vertex, which now exists
    14.   TRANSFER_SHADOW(o)
    15.  
    16.   UNITY_TRANSFER_FOG(o,o.pos);
    17.   o.UV0 = IN[i].UV0;
    18.   triStream.Append(o);
    19. }
     
    pitibonom and grobonom like this.