| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185 | Shader "Custom/ParallaxCloud"{    Properties    {        _MainTex ("BaseMap:基础贴图", 2D) = "white" {}//        _TurbulenceTex ("turbulence:扰动图", 2D) = "white" {}        _Color ("Color:颜色", Color) = (0.0, 0.0, 0.0, 1.0)        _ParallaxSize ("ParallaxSize:视差映射强度", Range(0.0, 0.1)) = 0.0        _ParallaxLayers ("ParallaxLayers:视差映射层数", Range(1.0, 50.0)) = 20        _MoveSpeed ("MoveSpeed:移动速度", Range(-0.5, 0.5)) = 0.1        _Alpha ("Alpha:透明度", Range(0, 1)) = 0.5        _AlphaExtent ("AlphaExtent:透明对比度", Range(0.0, 5.0)) = 5.0//      _worldDis("云的最远距离", float) = 0        _ruiHua("虚化距离", float) = 300    }    SubShader    {        Tags        {            "RenderPipeline"="UniversalPipeline"            "Queue"="Transparent"            "RenderType"="Transparent"        }        Pass        {            Blend SrcAlpha OneMinusSrcAlpha            Cull off            ZWrite off            HLSLPROGRAM            #pragma vertex vert            #pragma fragment frag            #include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Color.hlsl"            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl"            struct Attributes            {                float4 positionOS : POSITION;                float3 normalOS : NORMAL;                float2 uv : TEXCOORD0;                float4 tangent : TANGENT;            };            struct Varyings            {                float4 positionCS : SV_POSITION;                float3 positionWS : TEXCOORD0;                float4 uv : TEXCOORD1;                float3 nDirWS : TEXCOORD2;                float3 tDirWS : TEXCOORD3;                float3 bDirWS : TEXCOORD4;                float4 screenPos : TEXCOORD5;            };            CBUFFER_START(UnityPerMaterial)                half4 _MainTex_ST;                half4 _Color;                half _ParallaxSize;                half _ParallaxLayers;                half _MoveSpeed;                half _Alpha;                half _AlphaExtent;            // float _worldDis;            float _ruiHua;            CBUFFER_END            TEXTURE2D(_MainTex);            SAMPLER(sampler_MainTex);            TEXTURE2D(_NormalTex);            SAMPLER(sampler_NormalTex);            TEXTURE2D(_ParallaxTex);            SAMPLER(sampler_ParallaxTex);            sampler2D _CameraDepthTexture;            // TEXTURE2D(_TurbulenceTex);            // SAMPLER(sampler_TurbulenceTex);            Varyings vert(Attributes v)            {                Varyings o;                o.positionCS = TransformObjectToHClip(v.positionOS.xyz);                o.positionWS = TransformObjectToWorld(v.positionOS.xyz);                o.nDirWS = TransformObjectToWorldNormal(v.normalOS);                o.tDirWS = normalize(TransformObjectToWorld(v.tangent.xyz));                o.bDirWS = normalize(cross(o.nDirWS, o.tDirWS) * v.tangent.w);                                // o.uv.xy = TRANSFORM_TEX(v.uv, _MainTex) + float2(frac(_Time.y * _MoveSpeed), 0.0);                float2 newUV=o.positionWS.xz*0.06;                o.uv.xy =TRANSFORM_TEX( newUV, _MainTex)  + float2(frac(_Time.y * _MoveSpeed), 0.0);                o.uv.zw =  o.positionWS.xz * 0.02;                o.screenPos = ComputeScreenPos(o.positionCS);                return o;            }            // 从深度值重建世界坐标            float3 ReconstructWorldPosition(float2 uv, float depth)            {                // 1. 将 UV 转换为 NDC 空间 (Normalized Device Coordinates)                float4 ndc = float4(uv * 2.0 - 1.0, depth, 1.0);                // 2. 从 NDC 转换到裁剪空间                float4 clipPos = ndc;                clipPos.z = depth * 2.0 - 1.0; // 将深度从 [0,1] 转换为 [-1,1]                // 3. 应用逆投影矩阵,转换到视图空间                float4 viewPos = mul(unity_CameraInvProjection, clipPos); // 使用 Unity 内置的逆投影矩阵                viewPos /= viewPos.w; // 透视除法                // 4. 应用逆视图矩阵,转换到世界空间                float4 worldPos = mul(UNITY_MATRIX_I_V, viewPos); // 使用 Unity 内置的逆视图矩阵                return worldPos.xyz;            }            half4 frag(Varyings i) : SV_Target            {                float2 positionSS = i.positionCS.xy * (_ScreenParams.zw - 1);                float depth = tex2D(_CameraDepthTexture, positionSS).r;                float3 positionNDC = float3(positionSS * 2 - 1, depth);                #if UNITY_UV_STARTS_AT_TOP                positionNDC.y = -positionNDC.y;                #endif                #if REQUIRE_POSITION_VS        float4 positionVS = mul(UNITY_MATRIX_I_P, float4(positionNDC, 1));        positionVS /= positionVS.w;        float4 positionWS = mul(UNITY_MATRIX_I_V, positionVS);                #else                float4 positionWS = mul(UNITY_MATRIX_I_VP, float4(positionNDC, 1));                positionWS /= positionWS.w;                #endif                float dist = length(positionWS - i.positionWS);                // return half4(dist * 0.1, 0, 0, 1.0);                dist = dist * 0.2;                dist = clamp(dist, 0, 1);                float ptcpos = length(i.positionWS - _WorldSpaceCameraPos);                ptcpos = 1 - (ptcpos - 0) / _ruiHua;                ptcpos = clamp(ptcpos, 0, 1);                //Light mylight = GetMainLight();                //half3 light = mylight.color;                float3x3 TBN = float3x3(i.tDirWS, i.bDirWS, i.nDirWS);                float3 vDir = normalize(i.positionWS - _WorldSpaceCameraPos.xyz);                float3 vDirTS = mul(TBN, vDir);                // float2 raoDongUv = SAMPLE_TEXTURE2D(_TurbulenceTex, sampler_TurbulenceTex,i.positionWS.xz * 0.06).r*0.1;                // i.uv.xy += raoDongUv;                // i.uv.zw += raoDongUv;                float3 var_MainTex = SAMPLE_TEXTURE2D(_MainTex, sampler_MainTex, i.uv.zw).rgb;                half2 offset = 0.0;                half currentDepth = 0.0;                half parallaxDepth = 0.0;                half preParallaxDepth = 0.0;                half heightStep = 1.0 / _ParallaxLayers;                half2 offsetTemp = vDirTS.xy / -vDirTS.z * _ParallaxSize;                for (int j = 0; j < _ParallaxLayers; j++)                {                    parallaxDepth = 1.0 - SAMPLE_TEXTURE2D_LOD(_MainTex, sampler_MainTex, i.uv.xy + offset, 0).r *                        var_MainTex.r;                    if (currentDepth > parallaxDepth) break;                    preParallaxDepth = parallaxDepth;                    currentDepth += heightStep;                    offset = offsetTemp * currentDepth;                }                half preDepth = currentDepth - heightStep;                half A_C = preDepth - preParallaxDepth;                half D_B = parallaxDepth - currentDepth;                half t = A_C / (D_B + A_C);                half height = lerp(preDepth, currentDepth, t);                offset += offsetTemp * height;                i.uv.xy += offset;                half3 finalColor = SAMPLE_TEXTURE2D(_MainTex, sampler_MainTex, i.uv.xy).rgb * var_MainTex.rgb;                float alphaTex = max(var_MainTex.r * finalColor.r, 0.0);                half alpha = max(pow(abs(lerp(alphaTex, 1.0, _Alpha)), _AlphaExtent), 0.0) * _Alpha * dist * ptcpos;                return half4(finalColor * _Color.rgb, alpha);            }            ENDHLSL        }    }}
 |