星鸿阁

 找回密码
 立即注册
搜索
热搜: 活动 交友 动画
查看: 1636|回复: 2

Amplify Occlusion

[复制链接]

2254

主题

2764

帖子

9644

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
9644
发表于 2022-7-28 00:37:25 | 显示全部楼层 |阅读模式
  1. Shader "Hidden/Amplify Occlusion/Copy" {
  2.         Properties { }
  3.         CGINCLUDE
  4.                 #pragma vertex vert
  5.                 #pragma fragment frag
  6.                 #pragma target 3.0
  7.                 #include "UnityCG.cginc"

  8.                 float4x4 _AO_CameraProj;

  9.                 sampler2D _AO_Source;
  10.                 float4 _AO_Source_TexelSize;

  11.                 float4 _AO_Target_TexelSize;
  12.                 float2 _AO_Target_Position;

  13.                 v2f_img vert( appdata_img v )
  14.                 {
  15.                         float2 src_scale = _AO_Source_TexelSize.zw / _AO_Target_TexelSize.zw;
  16.                         float2 dst_offset = _AO_Target_Position * ( 1.0 / _AO_Target_TexelSize.zw );

  17.                 #ifdef UNITY_UV_STARTS_AT_TOP
  18.                         src_scale.y *= -1;
  19.                         dst_offset.y = 1 - dst_offset.y;
  20.                 #endif

  21.                         v2f_img OUT;
  22.                         OUT.pos = mul( _AO_CameraProj, float4( v.vertex.xy * src_scale + dst_offset, 0, 1 ) );
  23.                         OUT.uv = v.texcoord.xy;
  24.                 #ifdef UNITY_HALF_TEXEL_OFFSET
  25.                         OUT.pos.xy += ( 1.0 / _AO_Target_TexelSize.zw ) * float2( -1, 1 );
  26.                 #endif
  27.                         return OUT;
  28.                 }
  29.         ENDCG
  30.         SubShader {
  31.                 ZTest Always Cull Off ZWrite Off

  32.                 // 0 => COPY
  33.                 Pass {
  34.                         CGPROGRAM
  35.                                 float4 frag( v2f_img IN ) : SV_Target
  36.                                 {
  37.                                         return tex2Dlod( _AO_Source, float4( IN.uv, 0, 0 ) );
  38.                                 }
  39.                         ENDCG
  40.                 }
  41.         }
  42.         Fallback Off
  43. }
复制代码


回复

使用道具 举报

2254

主题

2764

帖子

9644

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
9644
 楼主| 发表于 2022-7-28 00:37:53 | 显示全部楼层
  1. Shader "Hidden/Amplify Occlusion/Blur"
  2. {
  3.         Properties { }
  4.         CGINCLUDE
  5.                 #pragma vertex vert
  6.                 #pragma fragment frag
  7.                 #pragma target 3.0
  8.                 #include "UnityCG.cginc"

  9.                 float4x4 _AO_CameraProj;

  10.                 sampler2D _AO_Source;
  11.                 float4 _AO_Source_TexelSize;
  12.                 float4 _AO_Target_TexelSize;

  13.                 float _AO_BlurSharpness;
  14.                 float _AO_BlurDepthThreshold;
  15.                 float _AO_BlurFalloff;

  16.                 inline half ComputeSharpness( half linearEyeDepth )
  17.                 {
  18.                         return _AO_BlurSharpness * ( saturate( 1 - linearEyeDepth ) * 100 + 1 );
  19.                 }

  20.                 inline half ComputeFalloff( const int radius )
  21.                 {
  22.                         half sigma = ( ( half ) radius ) * 0.5;
  23.                         return 1.0 / ( 2 * sigma * sigma );
  24.                 }

  25.                 inline half2 CrossBilateralWeight( const half2 r, half2 d, half d0, const half sharpness, const half falloff )
  26.                 {
  27.                         half2 diff = ( d0 - d ) * sharpness;
  28.                         return exp2( -( r * r ) * falloff - diff * diff );
  29.                 }

  30.                 inline half4 CrossBilateralWeight( const half4 r, half4 d, half d0, const half sharpness, const half falloff )
  31.                 {
  32.                         half4 diff = ( d0 - d ) * sharpness;
  33.                         return exp2( -( r * r ) * falloff - diff * diff );
  34.                 }

  35.                 half4 blur1D_1x( v2f_img IN, float2 deltaUV )
  36.                 {
  37.                         half2 center = tex2Dlod( _AO_Source, float4( IN.uv, 0, 0 ) ).xy;

  38.                         const float2 offset1 = 1 * deltaUV;

  39.                         half4 s1;
  40.                         s1.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset1, 0, 0 ) ).xy;
  41.                         s1.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset1, 0, 0 ) ).xy;

  42.                         const half sharpness = ComputeSharpness( center.y );
  43.                         const half falloff = ComputeFalloff( 1 );

  44.                         half2 w1 = CrossBilateralWeight( ( 1 ).xx, s1.yw, center.y, sharpness, falloff );

  45.                         half ao = center.x + dot( s1.xz, w1 );
  46.                         ao /= 1 + dot( ( 1 ).xx, w1 );

  47.                         return half4( ao, center.y, 0, 0 );
  48.                 }

  49.                 half4 blur1D_2x( v2f_img IN, float2 deltaUV )
  50.                 {
  51.                         half2 center = tex2Dlod( _AO_Source, float4( IN.uv, 0, 0 ) ).xy;

  52.                         const float2 offset1 = 1 * deltaUV;
  53.                         const float2 offset2 = 2 * deltaUV;

  54.                         half4 s1, s2;
  55.                         s2.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset2, 0, 0 ) ).xy;
  56.                         s1.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset1, 0, 0 ) ).xy;
  57.                         s1.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset1, 0, 0 ) ).xy;
  58.                         s2.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset2, 0, 0 ) ).xy;

  59.                         const half sharpness = ComputeSharpness( center.y );
  60.                         const half falloff = ComputeFalloff( 2 );

  61.                         half4 w12 = CrossBilateralWeight( half4( 1, 1, 2, 2 ), half4( s1.yw, s2.yw ), center.y, sharpness, falloff );

  62.                         half ao = center.x + dot( half4( s1.xz, s2.xz ), w12 );
  63.                         ao /= 1 + dot( ( 1 ).xxxx, w12 );

  64.                         return half4( ao, center.y, 0, 0 );
  65.                 }

  66.                 half4 blur1D_3x( v2f_img IN, float2 deltaUV )
  67.                 {
  68.                         half2 center = tex2Dlod( _AO_Source, float4( IN.uv, 0, 0 ) ).xy;

  69.                         const float2 offset1 = 1 * deltaUV;
  70.                         const float2 offset2 = 2 * deltaUV;
  71.                         const float2 offset3 = 3 * deltaUV;

  72.                         half4 s1, s2, s3;
  73.                         s3.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset3, 0, 0 ) ).xy;
  74.                         s2.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset2, 0, 0 ) ).xy;
  75.                         s1.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset1, 0, 0 ) ).xy;
  76.                         s1.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset1, 0, 0 ) ).xy;
  77.                         s2.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset2, 0, 0 ) ).xy;
  78.                         s3.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset3, 0, 0 ) ).xy;

  79.                         const half sharpness = ComputeSharpness( center.y );
  80.                         const half falloff = ComputeFalloff( 3 );

  81.                         half4 w12 = CrossBilateralWeight( half4( 1, 1, 2, 2 ), half4( s1.yw, s2.yw ), center.y, sharpness, falloff );
  82.                         half2 w3 = CrossBilateralWeight( ( 3 ).xx, s3.yw, center.y, sharpness, falloff );

  83.                         half ao = center.x + dot( half4( s1.xz, s2.xz ), w12 ) + dot( s3.xz, w3 );
  84.                         ao /= 1 + dot( ( 1 ).xxxx, w12 ) + dot( ( 1 ).xx, w3 );

  85.                         return half4( ao, center.y, 0, 0 );
  86.                 }

  87.                 half4 blur1D_4x( v2f_img IN, float2 deltaUV )
  88.                 {
  89.                         half2 center = tex2Dlod( _AO_Source, float4( IN.uv, 0, 0 ) ).xy;

  90.                         const float2 offset1 = 1 * deltaUV;
  91.                         const float2 offset2 = 2 * deltaUV;
  92.                         const float2 offset3 = 3 * deltaUV;
  93.                         const float2 offset4 = 4 * deltaUV;

  94.                         half4 s1, s2, s3, s4;
  95.                         s4.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset4, 0, 0 ) ).xy;
  96.                         s3.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset3, 0, 0 ) ).xy;
  97.                         s2.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset2, 0, 0 ) ).xy;
  98.                         s1.zw = tex2Dlod( _AO_Source, float4( IN.uv - offset1, 0, 0 ) ).xy;
  99.                         s1.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset1, 0, 0 ) ).xy;
  100.                         s2.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset2, 0, 0 ) ).xy;
  101.                         s3.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset3, 0, 0 ) ).xy;
  102.                         s4.xy = tex2Dlod( _AO_Source, float4( IN.uv + offset4, 0, 0 ) ).xy;

  103.                         const half sharpness = ComputeSharpness( center.y );
  104.                         const half falloff = ComputeFalloff( 4 );

  105.                         half4 w12 = CrossBilateralWeight( half4( 1, 1, 2, 2 ), half4( s1.yw, s2.yw ), center.y, sharpness, falloff );
  106.                         half4 w34 = CrossBilateralWeight( half4( 3, 3, 4, 4 ), half4( s3.yw, s4.yw ), center.y, sharpness, falloff );

  107.                         half ao = center.x + dot( half4( s1.xz, s2.xz ), w12 ) + dot( half4( s3.xz, s4.xz ), w34 );
  108.                         ao /= 1 + dot( ( 1 ).xxxx, w12 ) + dot( ( 1 ).xxxx, w34 );

  109.                         return half4( ao, center.y, 0, 0 );
  110.                 }

  111.                 v2f_img vert( appdata_img v )
  112.                 {
  113.                         v2f_img OUT;
  114.                         OUT.pos = mul( _AO_CameraProj, float4( v.vertex.xy, 0, 1 ) );
  115.                 #ifdef UNITY_HALF_TEXEL_OFFSET
  116.                         OUT.pos.xy += ( 1.0 / _AO_Target_TexelSize.zw ) * float2( -1, 1 );
  117.                 #endif
  118.                         OUT.uv = ComputeScreenPos( OUT.pos ).xy;
  119.                         return OUT;
  120.                 }
  121.         ENDCG
  122.         SubShader {
  123.                 ZTest Always Cull Off ZWrite Off

  124.                 // 0 => BLUR HORIZONTAL R:1
  125.                 Pass {
  126.                         CGPROGRAM
  127.                                 half4 frag( v2f_img IN ) : SV_Target
  128.                                 {
  129.                                         return blur1D_1x( IN, float2( _AO_Source_TexelSize.x, 0 ) );
  130.                                 }
  131.                         ENDCG
  132.                 }

  133.                 // 1 => BLUR VERTICAL R:1
  134.                 Pass {
  135.                         CGPROGRAM
  136.                                 half4 frag( v2f_img IN ) : SV_Target
  137.                                 {
  138.                                         return blur1D_1x( IN, float2( 0, _AO_Source_TexelSize.y ) );
  139.                                 }
  140.                         ENDCG
  141.                 }

  142.                 // 2 => BLUR HORIZONTAL R:2
  143.                 Pass {
  144.                         CGPROGRAM
  145.                                 half4 frag( v2f_img IN ) : SV_Target
  146.                                 {
  147.                                         return blur1D_2x( IN, float2( _AO_Source_TexelSize.x, 0 ) );
  148.                                 }
  149.                         ENDCG
  150.                 }

  151.                 // 3 => BLUR VERTICAL R:2
  152.                 Pass {
  153.                         CGPROGRAM
  154.                                 half4 frag( v2f_img IN ) : SV_Target
  155.                                 {
  156.                                         return blur1D_2x( IN, float2( 0, _AO_Source_TexelSize.y ) );
  157.                                 }
  158.                         ENDCG
  159.                 }

  160.                 // 4 => BLUR HORIZONTAL R:3
  161.                 Pass {
  162.                         CGPROGRAM
  163.                                 half4 frag( v2f_img IN ) : SV_Target
  164.                                 {
  165.                                         return blur1D_3x( IN, float2( _AO_Source_TexelSize.x, 0 ) );
  166.                                 }
  167.                         ENDCG
  168.                 }

  169.                 // 5 => BLUR VERTICAL R:3
  170.                 Pass {
  171.                         CGPROGRAM
  172.                                 half4 frag( v2f_img IN ) : SV_Target
  173.                                 {
  174.                                         return blur1D_3x( IN, float2( 0, _AO_Source_TexelSize.y ) );
  175.                                 }
  176.                         ENDCG
  177.                 }

  178.                 // 6 => BLUR HORIZONTAL R:4
  179.                 Pass {
  180.                         CGPROGRAM
  181.                                 half4 frag( v2f_img IN ) : SV_Target
  182.                                 {
  183.                                         return blur1D_4x( IN, float2( _AO_Source_TexelSize.x, 0 ) );
  184.                                 }
  185.                         ENDCG
  186.                 }

  187.                 // 7 => BLUR VERTICAL R:4
  188.                 Pass {
  189.                         CGPROGRAM
  190.                                 half4 frag( v2f_img IN ) : SV_Target
  191.                                 {
  192.                                         return blur1D_4x( IN, float2( 0, _AO_Source_TexelSize.y ) );
  193.                                 }
  194.                         ENDCG
  195.                 }
  196.         }
  197.         Fallback Off
  198. }
复制代码
回复

使用道具 举报

2254

主题

2764

帖子

9644

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
9644
 楼主| 发表于 2022-7-28 00:38:33 | 显示全部楼层
  1. // Amplify Occlusion - Robust Ambient Occlusion for Unity Pro
  2. // Copyright (c) Amplify Creations, Lda <info@amplify.pt>

  3. Shader "Hidden/Amplify Occlusion/Occlusion" {
  4.         Properties {
  5.                 _AO_RandomTexture( "Random 4x4", 2D ) = "gray" {}
  6.         }
  7.         CGINCLUDE
  8.                 #pragma vertex vert
  9.                 #pragma fragment frag
  10.                 #pragma target 3.0

  11.                 #include "UnityCG.cginc"

  12.                 #define NORMALS_NONE ( 0 )
  13.                 #define NORMALS_CAMERA ( 1 )
  14.                 #define NORMALS_GBUFFER ( 2 )
  15.                 #define NORMALS_GBUFFER_OCTA_ENCODED ( 3 )

  16.                 sampler2D _CameraGBufferTexture2;
  17.                 sampler2D_float _CameraDepthTexture;
  18.                 float4 _CameraDepthTexture_TexelSize;
  19.                 sampler2D _CameraDepthNormalsTexture;

  20.                 float4x4 _AO_CameraProj;
  21.                 float4x4 _AO_CameraView;

  22.                 sampler2D _AO_Source;
  23.                 float4 _AO_Source_TexelSize;
  24.                 float4 _AO_Target_TexelSize;

  25.                 sampler2D _AO_GBufferAlbedo;
  26.                 sampler2D _AO_GBufferEmission;

  27.                 sampler2D _AO_RandomTexture;
  28.                 sampler2D _AO_OcclusionTexture;

  29.                 sampler2D _AO_DepthTexture;
  30.                 sampler2D _AO_NormalTexture;

  31.                 sampler2D _AO_OcclusionAtlas;

  32.                 float2 _AO_LayerOffset;
  33.                 float4 _AO_LayerRandom;

  34.                 float2 _AO_LayerOffset0, _AO_LayerOffset1, _AO_LayerOffset2, _AO_LayerOffset3;
  35.                 float2 _AO_LayerOffset4, _AO_LayerOffset5, _AO_LayerOffset6, _AO_LayerOffset7;

  36.                 float4 _AO_Buffer_PadScale;
  37.                 float4 _AO_Buffer_TexelSize;
  38.                 float4 _AO_QuarterBuffer_TexelSize;
  39.                 float4 _AO_UVToView;

  40.                 half4 _AO_Levels;
  41.                 float _AO_HalfProjScale;
  42.                 float _AO_Radius;
  43.                 float _AO_PowExponent;
  44.                 float _AO_Bias;
  45.                 float _AO_Multiplier;

  46.                 float2 _AO_FadeParams;
  47.                 float3 _AO_FadeValues;

  48.                 struct DepthNormalOutput
  49.                 {
  50.                         float depth : SV_Target0;
  51.                         half4 normal : SV_Target1;
  52.                 };

  53.                 struct DepthOutput4
  54.                 {
  55.                         float4 depth0 : SV_Target0;
  56.                         float4 depth1 : SV_Target1;
  57.                         float4 depth2 : SV_Target2;
  58.                         float4 depth3 : SV_Target3;
  59.                 };

  60.                 struct NormalOutput4
  61.                 {
  62.                         half4 normal0 : SV_Target0;
  63.                         half4 normal1 : SV_Target1;
  64.                         half4 normal2 : SV_Target2;
  65.                         half4 normal3 : SV_Target3;
  66.                 };

  67.                 struct DeferredOutput
  68.                 {
  69.                         half4 albedo : SV_Target0;
  70.                         half4 emission : SV_Target1;
  71.                 };

  72.                 float SampleEyeDepthFromCamera( float4 uv )
  73.                 {
  74.                         // depth
  75.                         return LinearEyeDepth( SAMPLE_DEPTH_TEXTURE_LOD( _CameraDepthTexture, uv ) );

  76.                         // depth+normals
  77.                         //float linear01Depth = DecodeFloatRG( tex2Dlod( _CameraDepthNormalsTexture, uv ).zw );
  78.                         //return linear01Depth * _ProjectionParams.z - ( _ProjectionParams.z / 65535 );
  79.                 }

  80.                 float3 FetchPosition( float2 uv, bool reinterleave )
  81.                 {
  82.                         float viewDepth;
  83.                         if ( reinterleave )
  84.                                 viewDepth = SAMPLE_DEPTH_TEXTURE_LOD( _AO_DepthTexture, float4( uv, 0, 0 ) );
  85.                         else
  86.                                 viewDepth = SampleEyeDepthFromCamera( float4( uv * _AO_Buffer_PadScale.xy, 0, 0 ) );
  87.                         return float3( ( uv * _AO_UVToView.xy + _AO_UVToView.zw ) * viewDepth, viewDepth );
  88.                 }

  89.                 float3 FetchNormal( float2 uv )
  90.                 {
  91.                         return tex2Dlod( _AO_NormalTexture, float4( uv, 0, 0 ) ).rgb * 2 - 1;
  92.                 }

  93.                 half3 ComputeNormal( float2 uv, const int source )
  94.                 {
  95.                         if ( source == NORMALS_CAMERA )
  96.                         {
  97.                                 half3 N = DecodeViewNormalStereo( tex2D( _CameraDepthNormalsTexture, uv * _AO_Buffer_PadScale.xy ) );
  98.                                 return half3( N.x, -N.yz );
  99.                         }
  100.                         else if ( source == NORMALS_GBUFFER || source == NORMALS_GBUFFER_OCTA_ENCODED )
  101.                         {
  102.                                 half4 gbuffer2 = tex2D( _CameraGBufferTexture2, uv * _AO_Buffer_PadScale.xy );
  103.                                 half3 N = gbuffer2.rgb * 2 - 1;
  104.                                 if ( source == NORMALS_GBUFFER_OCTA_ENCODED && gbuffer2.a < 1 )
  105.                                 {
  106.                                         N.z = 1 - abs( N.x ) - abs( N.y );
  107.                                         N.xy = ( N.z >= 0 ) ? N.xy : ( ( 1 - abs( N.yx ) ) * sign( N.xy ) );
  108.                                 }
  109.                                 N = normalize( mul( ( float3x3 ) _AO_CameraView, N ) );
  110.                                 return half3( N.x, -N.yz );
  111.                         }
  112.                         else
  113.                         {
  114.                                 float3 c = FetchPosition( uv, false );
  115.                                 float3 r = FetchPosition( uv + float2( +_AO_Buffer_TexelSize.x, 0 ), false );
  116.                                 float3 l = FetchPosition( uv + float2( -_AO_Buffer_TexelSize.x, 0 ), false );
  117.                                 float3 t = FetchPosition( uv + float2( 0, +_AO_Buffer_TexelSize.y ), false );
  118.                                 float3 b = FetchPosition( uv + float2( 0, -_AO_Buffer_TexelSize.y ), false );
  119.                                 float3 vr = ( r - c ), vl = ( c - l ), vt = ( t - c ), vb = ( c - b );
  120.                                 float3 min_horiz = ( dot( vr, vr ) < dot( vl, vl ) ) ? vr : vl;
  121.                                 float3 min_vert = ( dot( vt, vt ) < dot( vb, vb ) ) ? vt : vb;
  122.                                 return normalize( cross( min_horiz, min_vert ) );
  123.                         }
  124.                 }

  125.                 float4 FullDepth( v2f_img IN )
  126.                 {
  127.                         return SampleEyeDepthFromCamera( float4( IN.uv, 0, 0 ) ).xxxx;
  128.                 }

  129.                 half4 FullNormal( v2f_img IN, const int source )
  130.                 {
  131.                         return half4( ComputeNormal( IN.uv, source ) * 0.5 + 0.5, 0 );
  132.                 }

  133.                 float4 DeinterleaveDepth1( v2f_img IN ) : SV_Target
  134.                 {
  135.                         float2 uv = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset0 ) * _AO_Buffer_TexelSize.xy;
  136.                         return SampleEyeDepthFromCamera( float4( uv * _AO_Buffer_PadScale.xy, 0, 0 ) );
  137.                 }

  138.                 half4 DeinterleaveNormal1( v2f_img IN, const int source ) : SV_Target
  139.                 {
  140.                         float2 uv = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset0 ) * _AO_Buffer_TexelSize.xy;
  141.                         return half4( ComputeNormal( uv, source ) * 0.5 + 0.5, 0 );
  142.                 }

  143.                 DepthOutput4 DeinterleaveDepth4( v2f_img IN )
  144.                 {
  145.                         float2 uv0 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset0 ) * _AO_Buffer_TexelSize.xy * _AO_Buffer_PadScale.xy;
  146.                         float2 uv1 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset1 ) * _AO_Buffer_TexelSize.xy * _AO_Buffer_PadScale.xy;
  147.                         float2 uv2 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset2 ) * _AO_Buffer_TexelSize.xy * _AO_Buffer_PadScale.xy;
  148.                         float2 uv3 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset3 ) * _AO_Buffer_TexelSize.xy * _AO_Buffer_PadScale.xy;

  149.                         DepthOutput4 OUT;
  150.                         OUT.depth1 = SampleEyeDepthFromCamera( float4( uv1, 0, 0 ) ).xxxx;
  151.                         OUT.depth2 = SampleEyeDepthFromCamera( float4( uv2, 0, 0 ) ).xxxx;
  152.                         OUT.depth3 = SampleEyeDepthFromCamera( float4( uv3, 0, 0 ) ).xxxx;
  153.                         OUT.depth0 = SampleEyeDepthFromCamera( float4( uv0, 0, 0 ) ).xxxx;
  154.                         return OUT;
  155.                 }

  156.                 NormalOutput4 DeinterleaveNormal4( v2f_img IN, const int source )
  157.                 {
  158.                         float2 uv0 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset0 ) * _AO_Buffer_TexelSize.xy;
  159.                         float2 uv1 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset1 ) * _AO_Buffer_TexelSize.xy;
  160.                         float2 uv2 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset2 ) * _AO_Buffer_TexelSize.xy;
  161.                         float2 uv3 = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4 + _AO_LayerOffset3 ) * _AO_Buffer_TexelSize.xy;

  162.                         NormalOutput4 OUT;
  163.                         OUT.normal0 = half4( ComputeNormal( uv0, source ) * 0.5 + 0.5, 0 );
  164.                         OUT.normal1 = half4( ComputeNormal( uv1, source ) * 0.5 + 0.5, 0 );
  165.                         OUT.normal2 = half4( ComputeNormal( uv2, source ) * 0.5 + 0.5, 0 );
  166.                         OUT.normal3 = half4( ComputeNormal( uv3, source ) * 0.5 + 0.5, 0 );
  167.                         return OUT;
  168.                 }

  169.                 float ComputeDistanceFade( float distance )
  170.                 {
  171.                         return saturate( max( 0, distance - _AO_FadeParams.x ) * _AO_FadeParams.y );
  172.                 }

  173.                 half2 ComputeOcclusion( v2f_img IN, const int directionCount, const int stepCount, const bool cache, const int source )
  174.                 {
  175.                         float2 uv;
  176.                         float4 rand;
  177.                         if ( cache )
  178.                         {
  179.                                 uv = ( floor( IN.uv * _AO_QuarterBuffer_TexelSize.zw ) * 4.0 + _AO_LayerOffset ) * _AO_Buffer_TexelSize.xy;
  180.                                 rand = _AO_LayerRandom;
  181.                         }
  182.                         else
  183.                         {
  184.                                 uv = IN.uv;
  185.                                 rand = tex2Dlod( _AO_RandomTexture, float4( uv * ( _AO_Buffer_TexelSize.zw / 4 ), 0, 0 ) );
  186.                         }

  187.                         float3 p, n;
  188.                         p = FetchPosition( uv, cache );
  189.                         if ( cache )
  190.                                 n = FetchNormal( uv );
  191.                         else
  192.                                 n = ComputeNormal( uv, source );

  193.                         float2 values = lerp( float2( _AO_Radius, _AO_PowExponent ), _AO_FadeValues.yz, ComputeDistanceFade( p.z ).xx );
  194.                         float radius = values.x;
  195.                         float exponent = values.y;

  196.                         float radiusToScreen = radius * _AO_HalfProjScale;
  197.                         float negRcpR2 = -1.0 / ( radius * radius );

  198.                         float screenRadius;
  199.                         if ( cache )
  200.                                 screenRadius = ( radiusToScreen / p.z ) / 4;
  201.                         else
  202.                                 screenRadius = radiusToScreen / p.z;

  203.                         const float pi = 3.14159265f;
  204.                         const float alpha = 2.0 * pi / directionCount;
  205.                         float stepSize = screenRadius / ( stepCount + 1 );
  206.                         float occlusion = 0;

  207.                         for ( int i = 0; i < directionCount; i++ )
  208.                         {
  209.                                 float angle = alpha * ( ( float ) i );
  210.                                 float2 cos_sin = float2( cos( angle ), sin( angle ) );
  211.                                 float2 dir = float2( cos_sin.x * rand.x - cos_sin.y * rand.y, cos_sin.x * rand.y + cos_sin.y * rand.x );
  212.                                 float ray = rand.z * stepSize + 1.0;

  213.                                 for ( int j = 0; j < stepCount; j++ )
  214.                                 {
  215.                                         float2 snapped_uv;
  216.                                         if ( cache )
  217.                                                 snapped_uv = uv + round( ray * dir ) * _AO_QuarterBuffer_TexelSize.xy;
  218.                                         else
  219.                                                 snapped_uv = uv + round( ray * dir ) * _AO_Buffer_TexelSize.xy;

  220.                                         float3 s = FetchPosition( snapped_uv, cache );
  221.                                         ray += stepSize;

  222.                                         float3 v = s - p;
  223.                                         float vv = dot( v, v );
  224.                                         float nv = dot( n, v ) * rsqrt( vv );

  225.                                         occlusion += saturate( nv - _AO_Bias ) * saturate( vv * negRcpR2 + 1.0 );
  226.                                 }
  227.                         }

  228.                         occlusion *= _AO_Multiplier / ( directionCount * stepCount );
  229.                         occlusion = clamp( 1 - occlusion * 2, 0, 1 );

  230.                         occlusion = saturate( pow( occlusion, exponent ) );

  231.                         return half4( occlusion, p.z, 0, 0 );
  232.                 }

  233.                 half4 CombineDownsampledOcclusionDepth( v2f_img IN )
  234.                 {
  235.                         half occlusion = tex2D( _AO_Source, IN.uv ).r;
  236.                         float depth = SampleEyeDepthFromCamera( float4( IN.uv, 0, 0 ) );
  237.                         return half4( occlusion, depth, 0, 0 );
  238.                 }

  239.                 half4 FetchOcclusion( v2f_img IN )
  240.                 {
  241.                         half2 occlusion_depth = tex2D( _AO_OcclusionTexture, IN.uv * _AO_Buffer_PadScale.zw ).rg;

  242.                         half occlusion = occlusion_depth.x;
  243.                         half depth = occlusion_depth.y;

  244.                         half3 tintedOcclusion = lerp( _AO_Levels.rgb, ( 1 ).xxx, occlusion );

  245.                         float intensity = lerp( _AO_Levels.a, _AO_FadeValues.x, ComputeDistanceFade( depth ) );

  246.                         return lerp( ( 1 ).xxxx, half4( tintedOcclusion.rgb, occlusion ), intensity );
  247.                 }

  248.                 v2f_img vert( appdata_img v )
  249.                 {
  250.                         v2f_img OUT;
  251.                         OUT.pos = mul( _AO_CameraProj, float4( v.vertex.xy, 0, 1 ) );
  252.                 #ifdef UNITY_HALF_TEXEL_OFFSET
  253.                         OUT.pos.xy += ( 1.0 / _AO_Target_TexelSize.zw ) * float2( -1, 1 );
  254.                 #endif
  255.                         OUT.uv = ComputeScreenPos( OUT.pos ).xy;
  256.                         return OUT;
  257.                 }
  258.         ENDCG
  259.         SubShader {
  260.                 ZTest Always Cull Off ZWrite Off

  261.                 // 0-4 => FULL GATHER --------------------------------------------------------------
  262.                 Pass { CGPROGRAM float4 frag( v2f_img IN ) : SV_Target { return FullDepth( IN ); } ENDCG }
  263.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return FullNormal( IN, NORMALS_NONE ); } ENDCG }
  264.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return FullNormal( IN, NORMALS_CAMERA ); } ENDCG }
  265.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return FullNormal( IN, NORMALS_GBUFFER ); } ENDCG }
  266.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return FullNormal( IN, NORMALS_GBUFFER_OCTA_ENCODED ); } ENDCG }

  267.                 // 5-9 => CACHE-AWARE GATHER DEINTERLEAVE 1 --------------------------------------------------------------
  268.                 Pass { CGPROGRAM float4 frag( v2f_img IN ) : SV_Target { return DeinterleaveDepth1( IN ); } ENDCG }
  269.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return DeinterleaveNormal1( IN, NORMALS_NONE ); } ENDCG }
  270.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return DeinterleaveNormal1( IN, NORMALS_CAMERA ); } ENDCG }
  271.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return DeinterleaveNormal1( IN, NORMALS_GBUFFER ); } ENDCG }
  272.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return DeinterleaveNormal1( IN, NORMALS_GBUFFER_OCTA_ENCODED ); } ENDCG }

  273.                 // 10-14 => CACHE-AWARE GATHER DEINTERLEAVE 4 --------------------------------------------------------------
  274.                 Pass { CGPROGRAM DepthOutput4 frag( v2f_img IN ) { return DeinterleaveDepth4( IN ); } ENDCG }
  275.                 Pass { CGPROGRAM NormalOutput4 frag( v2f_img IN ) { return DeinterleaveNormal4( IN, NORMALS_NONE ); } ENDCG }
  276.                 Pass { CGPROGRAM NormalOutput4 frag( v2f_img IN ) { return DeinterleaveNormal4( IN, NORMALS_CAMERA ); } ENDCG }
  277.                 Pass { CGPROGRAM NormalOutput4 frag( v2f_img IN ) { return DeinterleaveNormal4( IN, NORMALS_GBUFFER ); } ENDCG }
  278.                 Pass { CGPROGRAM NormalOutput4 frag( v2f_img IN ) { return DeinterleaveNormal4( IN, NORMALS_GBUFFER_OCTA_ENCODED ); } ENDCG }

  279.                 // 15-18 => CACHE-AWARE OCCLUSION --------------------------------------------------------------
  280.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 4, 4, true, NORMALS_NONE ), 0, 0 ); } ENDCG }
  281.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 6, 4, true, NORMALS_NONE ), 0, 0 ); } ENDCG }
  282.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 8, 4, true, NORMALS_NONE ), 0, 0 ); } ENDCG }
  283.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 10, 6, true, NORMALS_NONE ), 0, 0 ); } ENDCG }

  284.         // -- CACHE-AWARE REINTERLEAVE --------------------------------------------------------------
  285.                 // 19 => REINTERLEAVE
  286.                 Pass {
  287.                         CGPROGRAM
  288.                                 half4 frag( v2f_img IN ) : SV_Target
  289.                                 {
  290.                                         float2 offset = fmod( floor( IN.uv * _AO_Buffer_TexelSize.zw ), 4 );
  291.                                         return tex2Dlod( _AO_OcclusionAtlas, float4( ( IN.uv + offset ) * 0.25, 0, 0 ) );
  292.                                 }
  293.                         ENDCG
  294.                 }

  295.                 // 20-23 => FULL OCCLUSION - LOW QUALITY --------------------------------------------------------------
  296.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 4, 4, false, NORMALS_NONE ), 0, 0 ); } ENDCG }
  297.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 4, 4, false, NORMALS_CAMERA ), 0, 0 ); } ENDCG }
  298.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 4, 4, false, NORMALS_GBUFFER ), 0, 0 ); } ENDCG }
  299.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 4, 4, false, NORMALS_GBUFFER_OCTA_ENCODED ), 0, 0 ); } ENDCG }

  300.         // 24-27 => FULL OCCLUSION / MEDIUM QUALITY --------------------------------------------------------------
  301.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 6, 4, false, NORMALS_NONE ), 0, 0 ); } ENDCG }
  302.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 6, 4, false, NORMALS_CAMERA ), 0, 0 ); } ENDCG }
  303.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 6, 4, false, NORMALS_GBUFFER ), 0, 0 ); } ENDCG }
  304.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 6, 4, false, NORMALS_GBUFFER_OCTA_ENCODED ), 0, 0 ); } ENDCG }

  305.         // 28-31 => FULL OCCLUSION - HIGH QUALITY --------------------------------------------------------------
  306.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 8, 4, false, NORMALS_NONE ), 0, 0 ); } ENDCG }
  307.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 8, 4, false, NORMALS_CAMERA ), 0, 0 ); } ENDCG }
  308.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 8, 4, false, NORMALS_GBUFFER ), 0, 0 ); } ENDCG }
  309.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 8, 4, false, NORMALS_GBUFFER_OCTA_ENCODED ), 0, 0 ); } ENDCG }

  310.         // 32-35 => FULL OCCLUSION / VERYHIGH QUALITY --------------------------------------------------------------
  311.                 Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 10, 6, false, NORMALS_NONE ), 0, 0 ); } ENDCG }
  312.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 10, 6, false, NORMALS_CAMERA ), 0, 0 ); } ENDCG }
  313.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 10, 6, false, NORMALS_GBUFFER ), 0, 0 ); } ENDCG }
  314.         Pass { CGPROGRAM half4 frag( v2f_img IN ) : SV_Target { return half4( ComputeOcclusion( IN, 10, 6, false, NORMALS_GBUFFER_OCTA_ENCODED ), 0, 0 ); } ENDCG }

  315.                 // -- APPLICATION METHODS --------------------------------------------------------------
  316.                 // 36 => APPLY DEBUG
  317.                 Pass {
  318.                         CGPROGRAM
  319.                                 half4 frag( v2f_img IN ) : SV_Target
  320.                                 {
  321.                                         return half4( LinearToGammaSpace( FetchOcclusion( IN ).rgb ), 1 );
  322.                                 }
  323.                         ENDCG
  324.                 }

  325.                 // 37 => APPLY DEFERRED
  326.                 Pass {
  327.                         Blend DstColor Zero, DstAlpha Zero
  328.                         CGPROGRAM
  329.                                 DeferredOutput frag( v2f_img IN )
  330.                                 {
  331.                                         half4 occlusion = FetchOcclusion( IN );

  332.                                         DeferredOutput OUT;
  333.                                         OUT.albedo = half4( 1, 1, 1, occlusion.a );
  334.                                         OUT.emission = half4( occlusion.rgb, 1 );
  335.                                         return OUT;
  336.                                 }
  337.                         ENDCG
  338.                 }

  339.                 // 38 => APPLY DEFERRED (LOG)
  340.                 Pass {
  341.                         CGPROGRAM
  342.                                 DeferredOutput frag( v2f_img IN )
  343.                                 {
  344.                                         half4 occlusion = FetchOcclusion( IN );

  345.                                         half4 albedo = tex2D( _AO_GBufferAlbedo, IN.uv );
  346.                                         half4 emission = tex2D( _AO_GBufferEmission, IN.uv );

  347.                                         albedo.a *= occlusion.a;

  348.                                         emission.rgb = -log2( emission.rgb );
  349.                                         emission.rgb *= occlusion.rgb;
  350.                                         emission.rgb = exp2( -emission.rgb );

  351.                                         DeferredOutput OUT;
  352.                                         OUT.albedo = albedo;
  353.                                         OUT.emission = emission;
  354.                                         return OUT;
  355.                                 }
  356.                         ENDCG
  357.                 }

  358.                 // 39 => APPLY POST-EFFECT
  359.                 Pass {
  360.                         Blend DstColor Zero
  361.                         CGPROGRAM
  362.                                 half4 frag( v2f_img IN ) : SV_Target
  363.                                 {
  364.                                         return half4( FetchOcclusion( IN ).rgb, 1 );
  365.                                 }
  366.                         ENDCG
  367.                 }

  368.                 // 40 => APPLY POST-EFFECT (LOG)
  369.                 Pass {
  370.                         CGPROGRAM
  371.                                 half4 frag( v2f_img IN ) : SV_Target
  372.                                 {
  373.                                         half4 occlusion = FetchOcclusion( IN );

  374.                                         half4 emission = tex2D( _AO_GBufferEmission, IN.uv );

  375.                                         emission.rgb = -log2( emission.rgb );
  376.                                         emission.rgb *= occlusion.rgb;
  377.                                         emission.rgb = exp2( -emission.rgb );

  378.                                         return emission;
  379.                                 }
  380.                         ENDCG
  381.                 }

  382.                 // 41 => COMBINE DOWNSAMPLED OCCLUSION DEPTH
  383.                 Pass {
  384.                         CGPROGRAM
  385.                                 half4 frag( v2f_img IN ) : SV_Target
  386.                                 {
  387.                                         return CombineDownsampledOcclusionDepth( IN );
  388.                                 }
  389.                         ENDCG
  390.                 }
  391.     }
  392.         Fallback Off
  393. }
复制代码
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|starfluidga

GMT+8, 2025-3-9 08:01 , Processed in 0.017349 second(s), 20 queries .

Made by Liga 星鸿阁

Copyright © 2020-2048, LigaStudio.

快速回复 返回顶部 返回列表