复杂的延迟渲染,配合上一篇一起使用

Shader "Unlit/Shader_deffer"
{
    Properties
    {
        
    }
    SubShader
    {   
       
        Pass
        {	 ZWrite Off
			//LDR Blend DstColor Zero    HDR : Blend One One
			Blend [_SrcBlend] [_DstBlend] //计算光照 叠加
            CGPROGRAM
            //Shader3.0;
            #pragma target 3.0 
            #pragma vertex vert
            #pragma fragment frag
            // make fog work
            // 后处理
            #pragma multi_compile_lightpass
            //不支持MRT
            #pragma exclude_renderers norm
			//高动态开启
			#pragma multi_compile __ UNITY_HDR_ON
            #include "UnityCG.cginc"
            //延迟渲染相关的库文件
            #include "UnityDeferredLibrary.cginc"
            #include "UnityGBuffer.cginc"

           	sampler2D _CameraGBufferTexture0;
			sampler2D _CameraGBufferTexture1;
			sampler2D _CameraGBufferTexture2;

            struct  a2v
            {
                float4 vertex:POSITION;
                float3 normal:NORMAL;
            };
          	unity_v2f_deferred vert(a2v i)
			{
				unity_v2f_deferred o;
				o.pos = UnityObjectToClipPos(i.vertex);
				o.uv = ComputeScreenPos(o.pos);
				o.ray = UnityObjectToViewPos(i.vertex) * float3(-1,-1,1);
				//_LightAsQuad  当在处理四边形时,也就是直射光时返回1,否则返回0
				o.ray = lerp(o.ray, i.normal, _LightAsQuad);
				return o;
			};
			#ifdef	UNITY_HDR_ON
			half4
			#else
			fixed4
			#endif
             frag(unity_v2f_deferred i):SV_TARGET
            {
                //float2 uv =i.uv.xy/i.uv.w;//算出真正uv的值
                通过深度和方向重新构建世界坐标
                //float depth=SAMPLE_DEPTH_TEXTURE(_CameraDepthTexture,uv);//_CameraDepthTexture unity自动返回
                //depth=Linear01Depth(depth);//计算成为线性深度值
                /ray 只能表示方向,长度不一定   _ProjectionParams.z是远平面, 因为xyz都是等比例,所以 _ProjectionParams.z/i.ray.z就是 rayToFraPlane向量和ray向量的比值
                //float3 raytoPlane=i.ray*(_ProjectionParams.z/i.ray.z);//ray的长度
                //float4 viewPos=float4(raytoPlane*depth,1);//视角空间位置
                //float3 worldPos=mul(unity_CameraToWorld,viewPos).xyz;
                //float fadeDist=UnityComputeShadowFadeDistance(worldPos,viewPos.z);
				float3 worldPos;
				float2 uv;
				half3 lightDir;
				float atten;
				float fadeDist;
				UnityDeferredCalculateLightParams(i,worldPos,uv,lightDir, atten,fadeDist);
    //            //对光衰减的计算
    //            //如果是区域光
    //            #if defined(SPOT)
				//	float3 toLight = _LightPos.xyz-worldPos;
				//	half3 lightDir = normalize(toLight);

				//	float4 uvCookie = mul(unity_WorldToLight, float4(worldPos,1));
    //                //计算衰减  _LightTexture0无cookie衰减的采样
				//	float atten = tex2Dbias(_LightTexture0, float4(uvCookie.xy/uvCookie.w,0,-8)).w;
                    
				//	atten *= uvCookie < 0;
    //                //使用cookie _LightTextureB0采样
				//	atten *= tex2D(_LightTextureB0, dot(toLight,toLight) * _LightPos.w).r;

				//	atten *= UnityDeferredComputeShadow(worldPos, fadeDist, uv);
    //                //定义方向光
				//#elif defined(DIRECTIONAL) || defined(DIRECTIONAL_COOKIE)
				//	half3 lightDir = -_LightDir.xyz;//可以直接获取到
				//	float atten = 1.0;

				//	atten *= UnityDeferredComputeShadow(worldPos, fadeDist, uv);
    //                //定义了方向光的cookie 
				//	#if defined(DIRECTIONAL_COOKIE)
				//	float4 uvCookie = mul(unity_WorldToLight, float4(worldPos,1));
				//	atten *= tex2Dbias(_LightTexture0, float4(uvCookie.xy,0,-8)).w;//方向光不是透视不需要除w
				//	#endif
    //                 //点光
				//#elif defined(POINT) || defined(POINT_COOKIE)
				//	float3 toLight = _LightPos.xyz-worldPos;
				//	half3 lightDir = normalize(toLight);

				//	float atten = tex2D(_LightTextureB0, dot(toLight,toLight) * _LightPos.w).r;

				//	atten *= UnityDeferredComputeShadow(worldPos, fadeDist, uv);

				//	#if defined(POINT_COOKIE)
				//	float4 uvCookie = mul(unity_WorldToLight, float4(worldPos,1));
				//	atten *= texCUBEbias(_LightTexture0, float4(uvCookie.xyz, -8)).w;//采样的是cubemap
				//	#endif
				//#else
				// half3 lightDir = 0;
				// float atten = 0;
				//#endif
                half3 lightColor = _LightColor.rgb * atten;

				half4 gbuffer0 = tex2D(_CameraGBufferTexture0, uv);//漫反射
				half4 gbuffer1 = tex2D(_CameraGBufferTexture1, uv);//高光
				half4 gbuffer2 = tex2D(_CameraGBufferTexture2, uv);//法线

				half3 diffuseColor = gbuffer0.rgb;
				half3 specularColor = gbuffer1.rgb;
				float gloss = gbuffer1.a * 50;
				float3 worldNormal = normalize(gbuffer2.xyz * 2 - 1);

				fixed3 viewDir = normalize(_WorldSpaceCameraPos - worldPos);
				fixed3 halfDir = normalize(lightDir + viewDir);
                 
				half3 diffuse = lightColor * diffuseColor * max(0,dot(worldNormal,lightDir));
				half3 specular = lightColor * specularColor * pow(max(0,dot(worldNormal,halfDir)),gloss);

				half4 color = float4(diffuse + specular,1);
				#ifdef UNITY_HDR_ON
				return color;
				#else 
				return exp2(-color);//LDR
				#endif
            }
           
            ENDCG
        }
		//转码pass,主要是对于LDR转码
        Pass 
		{
			ZTest Always
			Cull Off
			ZWrite Off
			Stencil
			{
				ref[_StencilNonBackground]
				readMask[_StencilNonBackground]

				compback equal
				compfront equal
			}

			CGPROGRAM
			#pragma target 3.0
			#pragma vertex vert
			#pragma fragment frag
			#pragma exclude_renderers nomrt

			#include "UnityCG.cginc"

			sampler2D _LightBuffer;
			struct v2f
			{
				float4 vertex:SV_POSITION;
				float2 texcoord: TEXCOORD0;
			};

			v2f vert(float4 vertex:POSITION,float2 texcoord :TEXCOORD0)
			{
				v2f o;
				o.vertex = UnityObjectToClipPos(vertex);
				o.texcoord = texcoord.xy;
				#ifdef UNITY_SINGLE_PASS_STEREO
				o.texcoord = TransformStereoScreenSpaceTex(o.texcoord,1.0);
				#endif
				return o;
			}

			fixed4 frag(v2f i) :SV_Target
			{
				return -log2(tex2D(_LightBuffer,i.texcoord));
			}
			ENDCG
		}
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值