RtShadowsRayGen.ankiprog 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215
  1. // Copyright (C) 2009-2022, 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 RAYS_PER_PIXEL 1 2 4 8
  6. #pragma anki library RtShadows
  7. #pragma anki ray_type 0
  8. #pragma anki start rgen
  9. #include <AnKi/Shaders/ImportanceSampling.glsl>
  10. #include <AnKi/Shaders/PackFunctions.glsl>
  11. #include <AnKi/Shaders/RtShadows.glsl>
  12. #define CLUSTERED_SHADING_SET 0u
  13. #define CLUSTERED_SHADING_UNIFORMS_BINDING 0u
  14. #define CLUSTERED_SHADING_LIGHTS_BINDING 1u
  15. #define CLUSTERED_SHADING_CLUSTERS_BINDING 4u
  16. #include <AnKi/Shaders/ClusteredShadingCommon.glsl>
  17. // Used by the hit shaders. When changing the binding you need to update other shaders
  18. layout(set = 0, binding = 5) uniform sampler u_trilinearRepeatSampler;
  19. layout(set = 0, binding = 6) uniform uimage2D u_shadowsImage;
  20. layout(set = 0, binding = 7) uniform utexture2D u_historyShadowsTex;
  21. layout(set = 0, binding = 8) uniform sampler u_linearAnyClampSampler;
  22. layout(set = 0, binding = 9) uniform sampler u_nearestAnyClampSampler;
  23. layout(set = 0, binding = 10) uniform texture2D u_depthRt;
  24. layout(set = 0, binding = 11) uniform texture2D u_motionVectorsRt;
  25. layout(set = 0, binding = 12) uniform texture2D u_historyLengthTex;
  26. layout(set = 0, binding = 13) uniform texture2D u_normalRt;
  27. layout(set = 0, binding = 14) uniform accelerationStructureEXT u_tlas;
  28. layout(set = 0, binding = 15) uniform texture2D u_prevMomentsTex;
  29. layout(set = 0, binding = 16) uniform image2D u_momentsImage;
  30. layout(set = 0, binding = 17) uniform texture2D u_blueNoiseTex;
  31. ANKI_BINDLESS_SET(1); // Used by the hit shaders
  32. layout(push_constant, std430) uniform b_pc
  33. {
  34. RtShadowsUniforms u_unis;
  35. };
  36. layout(location = 0) rayPayloadEXT F32 g_payload;
  37. F32 trace(const Vec3 rayOrigin, const Vec3 rayDir, F32 tMax)
  38. {
  39. const U32 flags = gl_RayFlagsOpaqueEXT | gl_RayFlagsTerminateOnFirstHitEXT | gl_RayFlagsSkipClosestHitShaderEXT;
  40. const U32 cullMask = 0xFFu;
  41. const U32 sbtRecordOffset = 0u;
  42. const U32 sbtRecordStride = 0u;
  43. const U32 missIndex = 0u;
  44. const F32 tMin = 0.1;
  45. const I32 payloadLocation = 0;
  46. g_payload = 0.0;
  47. traceRayEXT(u_tlas, flags, cullMask, sbtRecordOffset, sbtRecordStride, missIndex, rayOrigin, tMin, rayDir, tMax,
  48. payloadLocation);
  49. return g_payload;
  50. }
  51. void main()
  52. {
  53. // World position
  54. const Vec2 uv = (Vec2(gl_LaunchIDEXT.xy) + 0.5) / Vec2(gl_LaunchSizeEXT.xy);
  55. const Vec2 ndc = UV_TO_NDC(uv);
  56. const F32 depth = textureLod(u_depthRt, u_linearAnyClampSampler, uv, 0.0).r;
  57. const Vec4 worldPos4 = u_clusteredShading.m_matrices.m_invertedViewProjectionJitter * Vec4(ndc, depth, 1.0);
  58. const Vec3 worldPos = worldPos4.xyz / worldPos4.w;
  59. if(depth == 1.0)
  60. {
  61. imageStore(u_shadowsImage, IVec2(gl_LaunchIDEXT.xy), UVec4(0));
  62. imageStore(u_momentsImage, IVec2(gl_LaunchIDEXT.xy), Vec4(0.0));
  63. return;
  64. }
  65. // World normal
  66. const Vec3 normal = unpackNormalFromGBuffer(textureLod(u_normalRt, u_linearAnyClampSampler, uv, 0.0));
  67. // Cluster
  68. Cluster cluster = getClusterFragCoord(Vec3(uv * u_clusteredShading.m_renderingSize, depth));
  69. F32 shadowFactors[MAX_RT_SHADOW_LAYERS];
  70. zeroRtShadowLayers(shadowFactors);
  71. // Get a random factor
  72. Vec3 random[RAYS_PER_PIXEL];
  73. for(I32 i = 0; i < RAYS_PER_PIXEL; ++i)
  74. {
  75. const U32 frameIdx = u_clusteredShading.m_frame * U32(RAYS_PER_PIXEL + i);
  76. #if 0
  77. const UVec3 irandom = rand3DPCG16(UVec3(gl_LaunchIDEXT.xy, frameIdx));
  78. random[i] = Vec3(irandom) / F32(0xFFFF) * 2.0 - 1.0; // In [-1.0, 1.0]
  79. #else
  80. random[i] =
  81. textureLod(u_blueNoiseTex, u_trilinearRepeatSampler, Vec2(gl_LaunchSizeEXT.xy) / Vec2(64.0) * uv, 0.0).rgb;
  82. random[i] = animateBlueNoise(random[i], frameIdx);
  83. random[i] = random[i] * 2.0 - 1.0; // In [-1.0, 1.0]
  84. #endif
  85. }
  86. // Dir light
  87. const DirectionalLight dirLight = u_clusteredShading.m_directionalLight;
  88. ANKI_BRANCH if(dirLight.m_active != 0u && dirLight.m_cascadeCount > 0u)
  89. {
  90. for(I32 i = 0; i < RAYS_PER_PIXEL; ++i)
  91. {
  92. const Vec3 dirLightPos = worldPos + -dirLight.m_direction * 10.0 + random[i];
  93. const Vec3 rayDir = normalize(dirLightPos - worldPos);
  94. const F32 lambertTerm = dot(rayDir, normal);
  95. ANKI_BRANCH if(lambertTerm > 0.0)
  96. {
  97. shadowFactors[dirLight.m_shadowLayer] += trace(worldPos, rayDir, 10000.0) / F32(RAYS_PER_PIXEL);
  98. }
  99. }
  100. }
  101. // Point lights
  102. ANKI_LOOP while(cluster.m_pointLightsMask != ExtendedClusterObjectMask(0))
  103. {
  104. const I32 idx = findLSB2(cluster.m_pointLightsMask);
  105. cluster.m_pointLightsMask &= ~(ExtendedClusterObjectMask(1) << ExtendedClusterObjectMask(idx));
  106. const PointLight light = u_pointLights2[idx];
  107. ANKI_BRANCH if(light.m_shadowAtlasTileScale >= 0.0)
  108. {
  109. for(I32 i = 0; i < RAYS_PER_PIXEL; ++i)
  110. {
  111. const Vec3 lightPos = light.m_position + 0.05 * light.m_radius * random[i];
  112. const Vec3 toLight = lightPos - worldPos;
  113. const F32 distanceToLight = length(toLight);
  114. const Vec3 rayDir = toLight / distanceToLight; // normalize
  115. const Bool inside = distanceToLight < light.m_radius;
  116. const F32 lambertTerm = dot(rayDir, normal);
  117. ANKI_BRANCH if(inside && lambertTerm > 0.0)
  118. {
  119. shadowFactors[light.m_shadowLayer] +=
  120. trace(worldPos, rayDir, distanceToLight) / F32(RAYS_PER_PIXEL);
  121. }
  122. }
  123. }
  124. }
  125. // Spot lights
  126. ANKI_LOOP while(cluster.m_spotLightsMask != ExtendedClusterObjectMask(0))
  127. {
  128. const I32 idx = findLSB2(cluster.m_spotLightsMask);
  129. cluster.m_spotLightsMask &= ~(ExtendedClusterObjectMask(1) << ExtendedClusterObjectMask(idx));
  130. const SpotLight light = u_spotLights[idx];
  131. ANKI_BRANCH if(light.m_shadowLayer != MAX_U32)
  132. {
  133. for(I32 i = 0; i < RAYS_PER_PIXEL; ++i)
  134. {
  135. const Vec3 lightPos = light.m_position + 0.05 * light.m_radius * random[i];
  136. const Vec3 toLight = lightPos - worldPos;
  137. const F32 distanceToLight = length(toLight);
  138. const Vec3 rayDir = toLight / distanceToLight; // normalize
  139. const F32 lambertTerm = dot(rayDir, normal);
  140. ANKI_BRANCH if(lambertTerm > 0.0)
  141. {
  142. shadowFactors[light.m_shadowLayer] +=
  143. trace(worldPos, rayDir, distanceToLight) / F32(RAYS_PER_PIXEL);
  144. }
  145. }
  146. }
  147. }
  148. // Get history length
  149. const Vec2 historyUv = uv + textureLod(u_motionVectorsRt, u_linearAnyClampSampler, uv, 0.0).xy;
  150. const F32 historyLength = textureLod(u_historyLengthTex, u_linearAnyClampSampler, uv, 0.0).x;
  151. // Compute blend fractor. Use nearest sampler because it's an integer texture
  152. const F32 lowestBlendFactor = 0.1;
  153. const F32 stableFrames = 4.0;
  154. const F32 lerp = min(1.0, (historyLength * RT_SHADOWS_MAX_HISTORY_LENGTH - 1.0) / stableFrames);
  155. const F32 blendFactor = mix(1.0, lowestBlendFactor, lerp);
  156. // Blend with history
  157. const UVec4 packedhistory = textureLod(u_historyShadowsTex, u_nearestAnyClampSampler, historyUv, 0.0);
  158. F32 history[MAX_RT_SHADOW_LAYERS];
  159. unpackRtShadows(packedhistory, history);
  160. for(U32 i = 0u; i < MAX_RT_SHADOW_LAYERS; ++i)
  161. {
  162. const F32 lerp = min(1.0, u_unis.historyRejectFactor[i] + blendFactor);
  163. shadowFactors[i] = mix(history[i], shadowFactors[i], lerp);
  164. }
  165. // Store the shadows image
  166. const UVec4 packed = packRtShadows(shadowFactors);
  167. imageStore(u_shadowsImage, IVec2(gl_LaunchIDEXT.xy), packed);
  168. // Compute the moments that will give temporal variance
  169. Vec2 moments = Vec2(0.0);
  170. ANKI_UNROLL for(U32 i = 0u; i < MAX_RT_SHADOW_LAYERS; ++i)
  171. {
  172. moments.x += shadowFactors[i];
  173. }
  174. moments.y = moments.x * moments.x;
  175. // Blend the moments
  176. const Vec2 prevMoments = textureLod(u_prevMomentsTex, u_linearAnyClampSampler, historyUv, 0.0).xy;
  177. const F32 lowestMomentsBlendFactor = 0.2;
  178. const F32 momentsBlendFactor = mix(1.0, lowestMomentsBlendFactor, lerp);
  179. moments = mix(prevMoments, moments, momentsBlendFactor);
  180. // Store the moments
  181. imageStore(u_momentsImage, IVec2(gl_LaunchIDEXT.xy), Vec4(moments, 0.0, 0.0));
  182. }
  183. #pragma anki end