SSAO showing through objects with custom shader

Hello,

My problem is that the SSAO from objects is rendered in front of objects using my custom shader. I can set the Render Queue of these custom objects to Transparent to stop the SSAO being rendered on top off them from other objects, but this also stops the SSAO rendering from the object itself.

107544-ao.png ^ Current setup. Object behind is rendering its SSAO on top of front object.

107545-ao-nop.png ^ If I set front objects Render Queue to Transparent, but no SSAO on front object either. Turning off SSAO gives similar results.

Basically, I want SSAO to be rendered on the object but not from objects behind it, so just turning off SSAO is not the way to go. Here’s my shader:

Shader "Custom/FoliageDoublesided" {
	Properties {
		_Color ("Color", Color) = (1,1,1,1)
		_MainTex ("Albedo (RGB)", 2D) = "white" {}
		_NormalMap("Normalmap", 2D) = "bump" {}
		_Cutoff ("Alpha cutoff", Range(0,1)) = 0.5
	}
	SubShader {
		Tags { 
			"RenderType"="TransparentCutout" 
			"Queue"="AlphaTest"
			"IgnoreProjector"="True"		
			}
		LOD 200
		Cull Off

		CGPROGRAM
		#pragma surface surf TwoSided fullforwardshadows alphatest:_Cutoff
		#pragma target 3.0

		sampler2D _MainTex;
		sampler2D _NormalMap;

		struct Input {
			float2 uv_MainTex;
		};

		fixed4 _Color;

		 #pragma instancing_options assumeuniformscaling
		UNITY_INSTANCING_CBUFFER_START(Props)
		UNITY_INSTANCING_CBUFFER_END

		half4 LightingTwoSided(SurfaceOutput s, half3 lightDir, half atten) {
             half NdotL = dot (s.Normal, lightDir);
             half INdotL = dot (-s.Normal, lightDir);
             half diff = (NdotL < 0) ? INdotL : NdotL;

             half4 c;
             c.rgb = s.Albedo * _LightColor0.rgb * (diff * atten) ;
			 c.a = s.Alpha;

             return c;
         }

		void surf (Input IN, inout SurfaceOutput o) {
			fixed4 c = tex2D (_MainTex, IN.uv_MainTex) * _Color;
			o.Albedo = c.rgb;
			o.Normal = UnpackNormal (tex2D (_NormalMap, IN.uv_MainTex));
			o.Specular = 1;

			o.Alpha = c.a;
		}
		ENDCG
	}
	FallBack "StandardDoubleSided"
}

Any help is appreciated

It seems that as soon as you use any lighting other than Standard in your shader, ambient occlusion (from the Post Processing Stack) is rendered on top of your mesh. Even if you invoke the standard lighting function, it still messes up the AO.

What magic inside “#pragma surface surf Standard” am I missing? How can I use my own lighting functions and have the AO work properly?

i see it’s a cutoff shader. i think adding “FallBack “Standard”” should work. if not, you can also try adding a shadowcaster pass:

         Pass {
        Name "Caster"
        Tags { "LightMode" = "ShadowCaster" }

			CGPROGRAM
			#pragma vertex vert
			#pragma fragment frag
			#pragma target 2.0
			#pragma multi_compile_shadowcaster
			#pragma multi_compile_instancing // allow instanced shadow pass for most of the shaders
			#include "UnityCG.cginc"

			struct v2f {
			    V2F_SHADOW_CASTER;
			    float2  uv : TEXCOORD1;
			    UNITY_VERTEX_OUTPUT_STEREO
			};

			uniform float4 _MainTex_ST;

			v2f vert( appdata_base v )
			{
			    v2f o;
			    UNITY_SETUP_INSTANCE_ID(v);
			    UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(o);
			    TRANSFER_SHADOW_CASTER_NORMALOFFSET(o)
			    o.uv = TRANSFORM_TEX(v.texcoord, _MainTex);
			    return o;
			}

			uniform sampler2D _MainTex;
			uniform fixed _Cutoff;
			uniform fixed4 _Color;

			float4 frag( v2f i ) : SV_Target
			{
			    fixed4 texcol = tex2D( _MainTex, i.uv );
			    clip( texcol.a*_Color.a - _Cutoff );

			    SHADOW_CASTER_FRAGMENT(i)
			}
			ENDCG

			    

		}

PS: i haven’t fully tested so not sure it will. but i hope it gives you some direction