ShadowmapsResolve.ankiprog 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240
  1. // Copyright (C) 2009-present, Panagiotis Christopoulos Charitos and contributors.
  2. // All rights reserved.
  3. // Code licensed under the BSD License.
  4. // http://www.anki3d.org/LICENSE
  5. #pragma anki mutator QUALITY 0 1 2 // No filtering, PCF, PCSS
  6. #pragma anki mutator DIRECTIONAL_LIGHT_SHADOW_RESOLVED 0 1
  7. #pragma anki technique vert pixel comp
  8. #include <AnKi/Shaders/QuadVert.hlsl>
  9. #if ANKI_COMPUTE_SHADER || ANKI_PIXEL_SHADER
  10. # include <AnKi/Shaders/ClusteredShadingFunctions.hlsl>
  11. # include <AnKi/Shaders/ImportanceSampling.hlsl>
  12. # define DEBUG_CASCADES 0
  13. ConstantBuffer<GlobalRendererConstants> g_globalConstants : register(b0);
  14. StructuredBuffer<PointLight> g_pointLights : register(t0);
  15. StructuredBuffer<SpotLight> g_spotLights : register(t1);
  16. Texture2D<Vec4> g_shadowAtlasTex : register(t2);
  17. StructuredBuffer<Cluster> g_clusters : register(t3);
  18. SamplerState g_linearAnyClampSampler : register(s0);
  19. SamplerComparisonState g_linearAnyClampShadowSampler : register(s1);
  20. SamplerState g_trilinearRepeatSampler : register(s2);
  21. Texture2D<Vec4> g_depthRt : register(t4);
  22. Texture2D<Vec4> g_noiseTex : register(t5);
  23. # if DIRECTIONAL_LIGHT_SHADOW_RESOLVED
  24. Texture2D<Vec4> g_dirLightResolvedShadowsTex : register(t6);
  25. # endif
  26. # if ANKI_COMPUTE_SHADER
  27. RWTexture2D<Vec4> g_storageTex : register(u0);
  28. # endif
  29. struct Constants
  30. {
  31. Vec2 m_framebufferSize;
  32. F32 m_padding0;
  33. F32 m_padding1;
  34. };
  35. ANKI_FAST_CONSTANTS(Constants, g_consts)
  36. Vec3 computeDebugShadowCascadeColor(U32 cascade)
  37. {
  38. if(cascade == 0u)
  39. {
  40. return Vec3(0.0f, 1.0f, 0.0f);
  41. }
  42. else if(cascade == 1u)
  43. {
  44. return Vec3(0.0f, 0.0f, 1.0f);
  45. }
  46. else if(cascade == 2u)
  47. {
  48. return Vec3(0.0f, 1.0f, 1.0f);
  49. }
  50. else
  51. {
  52. return Vec3(1.0f, 0.0f, 0.0f);
  53. }
  54. }
  55. # if ANKI_COMPUTE_SHADER
  56. [numthreads(8, 8, 1)] void main(UVec2 svDispatchThreadId : SV_DISPATCHTHREADID)
  57. # else
  58. Vec4 main(VertOut input) : SV_TARGET0
  59. # endif
  60. {
  61. # if ANKI_COMPUTE_SHADER
  62. svDispatchThreadId = min(svDispatchThreadId, UVec2(g_consts.m_framebufferSize - 1.0f)); // Just to be sure
  63. const Vec2 uv = (Vec2(svDispatchThreadId) + 0.5) / g_consts.m_framebufferSize;
  64. # else
  65. const Vec2 uv = input.m_uv;
  66. const UVec2 svDispatchThreadId = input.m_svPosition;
  67. ANKI_MAYBE_UNUSED(svDispatchThreadId);
  68. # endif
  69. # if QUALITY > 0
  70. # if 1
  71. // Noise
  72. Vec2 noiseTexSize;
  73. g_noiseTex.GetDimensions(noiseTexSize.x, noiseTexSize.y);
  74. const Vec2 noiseUv = g_consts.m_framebufferSize / noiseTexSize * uv;
  75. Vec3 noise = g_noiseTex.SampleLevel(g_trilinearRepeatSampler, noiseUv, 0.0).rgb;
  76. noise = animateBlueNoise(noise, g_globalConstants.m_frame % 16u);
  77. const F32 randFactor = noise.x;
  78. # else
  79. const Vec2 noise2 = spatioTemporalNoise(svDispatchThreadId, g_globalConstants.m_frame);
  80. const F32 randFactor = noise2.x;
  81. # endif
  82. # endif
  83. // World position
  84. const Vec2 ndc = uvToNdc(uv);
  85. const F32 depth = g_depthRt.SampleLevel(g_linearAnyClampSampler, uv, 0.0).r;
  86. const Vec4 worldPos4 = mul(g_globalConstants.m_matrices.m_invertedViewProjectionJitter, Vec4(ndc, depth, 1.0));
  87. const Vec3 worldPos = worldPos4.xyz / worldPos4.w;
  88. // Cluster
  89. const Vec2 fragCoord = uv * g_globalConstants.m_renderingSize;
  90. Cluster cluster = getClusterFragCoord(g_clusters, g_globalConstants, Vec3(fragCoord, depth));
  91. // Layers
  92. U32 shadowCasterCountPerFragment = 0u;
  93. const U32 kMaxShadowCastersPerFragment = 4u;
  94. Vec4 shadowFactors = 0.0f;
  95. // Dir light
  96. # if DIRECTIONAL_LIGHT_SHADOW_RESOLVED
  97. shadowFactors[0] = g_dirLightResolvedShadowsTex.SampleLevel(g_linearAnyClampSampler, uv, 0.0f).x;
  98. ++shadowCasterCountPerFragment;
  99. # else
  100. const DirectionalLight dirLight = g_globalConstants.m_directionalLight;
  101. if(dirLight.m_active && dirLight.m_shadowCascadeCount)
  102. {
  103. const U32 shadowCascadeCount = dirLight.m_shadowCascadeCount;
  104. const F32 positiveZViewSpace = testPlanePoint(g_globalConstants.m_nearPlaneWSpace.xyz, g_globalConstants.m_nearPlaneWSpace.w, worldPos)
  105. + g_globalConstants.m_matrices.m_near;
  106. const F32 lastCascadeDistance = dirLight.m_shadowCascadeDistances[shadowCascadeCount - 1u];
  107. F32 shadowFactor;
  108. if(positiveZViewSpace < lastCascadeDistance)
  109. {
  110. F32 cascadeBlendFactor;
  111. const UVec2 cascadeIndices =
  112. computeShadowCascadeIndex2(positiveZViewSpace, dirLight.m_shadowCascadeDistances, shadowCascadeCount, cascadeBlendFactor);
  113. # if DEBUG_CASCADES
  114. const Vec3 debugColorA = computeDebugShadowCascadeColor(cascadeIndices[0]);
  115. const Vec3 debugColorB = computeDebugShadowCascadeColor(cascadeIndices[1]);
  116. const Vec3 debugColor = lerp(debugColorA, debugColorB, cascadeBlendFactor);
  117. # if ANKI_COMPUTE_SHADER
  118. g_storageTex[svDispatchThreadId.xy] = shadowFactors;
  119. return;
  120. # else
  121. return shadowFactors;
  122. # endif
  123. # endif
  124. # if QUALITY == 2
  125. const F32 shadowFactorCascadeA = computeShadowFactorDirLightPcss<F32>(dirLight, cascadeIndices.x, worldPos, g_shadowAtlasTex,
  126. g_linearAnyClampShadowSampler, randFactor, g_linearAnyClampSampler);
  127. # elif QUALITY == 1
  128. const F32 shadowFactorCascadeA = computeShadowFactorDirLightPcf<F32>(dirLight, cascadeIndices.x, worldPos, g_shadowAtlasTex,
  129. g_linearAnyClampShadowSampler, randFactor);
  130. # else
  131. const F32 shadowFactorCascadeA =
  132. computeShadowFactorDirLight<F32>(dirLight, cascadeIndices.x, worldPos, g_shadowAtlasTex, g_linearAnyClampShadowSampler);
  133. # endif
  134. if(cascadeBlendFactor < 0.01 || cascadeIndices.x == cascadeIndices.y)
  135. {
  136. // Don't blend cascades
  137. shadowFactor = shadowFactorCascadeA;
  138. }
  139. else
  140. {
  141. # if QUALITY == 2
  142. // Blend cascades
  143. const F32 shadowFactorCascadeB = computeShadowFactorDirLightPcss<F32>(
  144. dirLight, cascadeIndices.y, worldPos, g_shadowAtlasTex, g_linearAnyClampShadowSampler, randFactor, g_linearAnyClampSampler);
  145. # elif QUALITY == 1
  146. // Blend cascades
  147. const F32 shadowFactorCascadeB = computeShadowFactorDirLightPcf<F32>(dirLight, cascadeIndices.y, worldPos, g_shadowAtlasTex,
  148. g_linearAnyClampShadowSampler, randFactor);
  149. # else
  150. // Blend cascades
  151. const F32 shadowFactorCascadeB =
  152. computeShadowFactorDirLight<F32>(dirLight, cascadeIndices.y, worldPos, g_shadowAtlasTex, g_linearAnyClampShadowSampler);
  153. # endif
  154. shadowFactor = lerp(shadowFactorCascadeA, shadowFactorCascadeB, cascadeBlendFactor);
  155. }
  156. F32 distanceFadeFactor = saturate(positiveZViewSpace / lastCascadeDistance);
  157. distanceFadeFactor = pow(distanceFadeFactor, 8.0);
  158. shadowFactor += distanceFadeFactor;
  159. }
  160. else
  161. {
  162. shadowFactor = 1.0;
  163. }
  164. shadowFactors[0] = shadowFactor;
  165. ++shadowCasterCountPerFragment;
  166. }
  167. # endif // DIRECTIONAL_LIGHT_SHADOW_RESOLVED
  168. // Point lights
  169. U32 idx = 0;
  170. [loop] while((idx = iteratePointLights(cluster)) != kMaxU32)
  171. {
  172. const PointLight light = g_pointLights[idx];
  173. [branch] if(light.m_shadow)
  174. {
  175. const Vec3 frag2Light = light.m_position - worldPos;
  176. # if QUALITY > 0
  177. const F32 shadowFactor = computeShadowFactorPointLightPcf(light, frag2Light, g_shadowAtlasTex, g_linearAnyClampShadowSampler, randFactor);
  178. # else
  179. const F32 shadowFactor = computeShadowFactorPointLight<F32>(light, frag2Light, g_shadowAtlasTex, g_linearAnyClampShadowSampler);
  180. # endif
  181. shadowFactors[min(kMaxShadowCastersPerFragment - 1u, shadowCasterCountPerFragment++)] = shadowFactor;
  182. }
  183. }
  184. // Spot lights
  185. [loop] while((idx = iterateSpotLights(cluster)) != kMaxU32)
  186. {
  187. const SpotLight light = g_spotLights[idx];
  188. [branch] if(light.m_shadow)
  189. {
  190. # if QUALITY == 2
  191. const F32 shadowFactor = computeShadowFactorSpotLightPcss<F32>(light, worldPos, g_shadowAtlasTex, g_linearAnyClampShadowSampler,
  192. randFactor, g_linearAnyClampSampler);
  193. # elif QUALITY == 1
  194. const F32 shadowFactor =
  195. computeShadowFactorSpotLightPcf<F32>(light, worldPos, g_shadowAtlasTex, g_linearAnyClampShadowSampler, randFactor);
  196. # else
  197. const F32 shadowFactor = computeShadowFactorSpotLight<F32>(light, worldPos, g_shadowAtlasTex, g_linearAnyClampShadowSampler);
  198. # endif
  199. shadowFactors[min(kMaxShadowCastersPerFragment - 1u, shadowCasterCountPerFragment++)] = shadowFactor;
  200. }
  201. }
  202. // Store
  203. # if ANKI_COMPUTE_SHADER
  204. g_storageTex[svDispatchThreadId] = shadowFactors;
  205. # else
  206. return shadowFactors;
  207. # endif
  208. }
  209. #endif // ANKI_COMPUTE_SHADER || ANKI_PIXEL_SHADER