pbrBlockReflection.fx 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296
  1. #ifdef REFLECTION
  2. struct reflectionOutParams
  3. {
  4. vec4 environmentRadiance;
  5. vec3 environmentIrradiance;
  6. #ifdef REFLECTIONMAP_3D
  7. vec3 reflectionCoords;
  8. #else
  9. vec2 reflectionCoords;
  10. #endif
  11. #ifdef SS_TRANSLUCENCY
  12. #ifdef USESPHERICALFROMREFLECTIONMAP
  13. #if !defined(NORMAL) || !defined(USESPHERICALINVERTEX)
  14. vec3 irradianceVector;
  15. #endif
  16. #endif
  17. #endif
  18. };
  19. #define pbr_inline
  20. void createReflectionCoords(
  21. const in vec3 vPositionW,
  22. const in vec3 normalW,
  23. #ifdef ANISOTROPIC
  24. const in anisotropicOutParams anisotropicOut,
  25. #endif
  26. #ifdef REFLECTIONMAP_3D
  27. out vec3 reflectionCoords
  28. #else
  29. out vec2 reflectionCoords
  30. #endif
  31. )
  32. {
  33. #ifdef ANISOTROPIC
  34. vec3 reflectionVector = computeReflectionCoords(vec4(vPositionW, 1.0), anisotropicOut.anisotropicNormal);
  35. #else
  36. vec3 reflectionVector = computeReflectionCoords(vec4(vPositionW, 1.0), normalW);
  37. #endif
  38. #ifdef REFLECTIONMAP_OPPOSITEZ
  39. reflectionVector.z *= -1.0;
  40. #endif
  41. // _____________________________ 2D vs 3D Maps ________________________________
  42. #ifdef REFLECTIONMAP_3D
  43. reflectionCoords = reflectionVector;
  44. #else
  45. reflectionCoords = reflectionVector.xy;
  46. #ifdef REFLECTIONMAP_PROJECTION
  47. reflectionCoords /= reflectionVector.z;
  48. #endif
  49. reflectionCoords.y = 1.0 - reflectionCoords.y;
  50. #endif
  51. }
  52. #define pbr_inline
  53. #define inline
  54. void sampleReflectionTexture(
  55. const in float alphaG,
  56. const in vec3 vReflectionMicrosurfaceInfos,
  57. const in vec2 vReflectionInfos,
  58. const in vec3 vReflectionColor,
  59. #if defined(LODINREFLECTIONALPHA) && !defined(REFLECTIONMAP_SKYBOX)
  60. const in float NdotVUnclamped,
  61. #endif
  62. #ifdef LINEARSPECULARREFLECTION
  63. const in float roughness,
  64. #endif
  65. #ifdef REFLECTIONMAP_3D
  66. const in samplerCube reflectionSampler,
  67. const vec3 reflectionCoords,
  68. #else
  69. const in sampler2D reflectionSampler,
  70. const vec2 reflectionCoords,
  71. #endif
  72. #ifndef LODBASEDMICROSFURACE
  73. #ifdef REFLECTIONMAP_3D
  74. const in samplerCube reflectionSamplerLow,
  75. const in samplerCube reflectionSamplerHigh,
  76. #else
  77. const in sampler2D reflectionSamplerLow,
  78. const in sampler2D reflectionSamplerHigh,
  79. #endif
  80. #endif
  81. out vec4 environmentRadiance
  82. )
  83. {
  84. // _____________________________ 2D vs 3D Maps ________________________________
  85. #if defined(LODINREFLECTIONALPHA) && !defined(REFLECTIONMAP_SKYBOX)
  86. float reflectionLOD = getLodFromAlphaG(vReflectionMicrosurfaceInfos.x, alphaG, NdotVUnclamped);
  87. #elif defined(LINEARSPECULARREFLECTION)
  88. float reflectionLOD = getLinearLodFromRoughness(vReflectionMicrosurfaceInfos.x, roughness);
  89. #else
  90. float reflectionLOD = getLodFromAlphaG(vReflectionMicrosurfaceInfos.x, alphaG);
  91. #endif
  92. #ifdef LODBASEDMICROSFURACE
  93. // Apply environment convolution scale/offset filter tuning parameters to the mipmap LOD selection
  94. reflectionLOD = reflectionLOD * vReflectionMicrosurfaceInfos.y + vReflectionMicrosurfaceInfos.z;
  95. #ifdef LODINREFLECTIONALPHA
  96. // Automatic LOD adjustment to ensure that the smoothness-based environment LOD selection
  97. // is constrained to appropriate LOD levels in order to prevent aliasing.
  98. // The environment map is first sampled without custom LOD selection to determine
  99. // the hardware-selected LOD, and this is then used to constrain the final LOD selection
  100. // so that excessive surface smoothness does not cause aliasing (e.g. on curved geometry
  101. // where the normal is varying rapidly).
  102. // Note: Shader Model 4.1 or higher can provide this directly via CalculateLevelOfDetail(), and
  103. // manual calculation via derivatives is also possible, but for simplicity we use the
  104. // hardware LOD calculation with the alpha channel containing the LOD for each mipmap.
  105. float automaticReflectionLOD = UNPACK_LOD(sampleReflection(reflectionSampler, reflectionCoords).a);
  106. float requestedReflectionLOD = max(automaticReflectionLOD, reflectionLOD);
  107. #else
  108. float requestedReflectionLOD = reflectionLOD;
  109. #endif
  110. #ifdef REALTIME_FILTERING
  111. environmentRadiance = vec4(radiance(alphaG, reflectionSampler, reflectionCoords, vReflectionFilteringInfo), 1.0);
  112. #else
  113. environmentRadiance = sampleReflectionLod(reflectionSampler, reflectionCoords, reflectionLOD);
  114. #endif
  115. #else
  116. float lodReflectionNormalized = saturate(reflectionLOD / log2(vReflectionMicrosurfaceInfos.x));
  117. float lodReflectionNormalizedDoubled = lodReflectionNormalized * 2.0;
  118. vec4 environmentMid = sampleReflection(reflectionSampler, reflectionCoords);
  119. if (lodReflectionNormalizedDoubled < 1.0){
  120. environmentRadiance = mix(
  121. sampleReflection(reflectionSamplerHigh, reflectionCoords),
  122. environmentMid,
  123. lodReflectionNormalizedDoubled
  124. );
  125. } else {
  126. environmentRadiance = mix(
  127. environmentMid,
  128. sampleReflection(reflectionSamplerLow, reflectionCoords),
  129. lodReflectionNormalizedDoubled - 1.0
  130. );
  131. }
  132. #endif
  133. #ifdef RGBDREFLECTION
  134. environmentRadiance.rgb = fromRGBD(environmentRadiance);
  135. #endif
  136. #ifdef GAMMAREFLECTION
  137. environmentRadiance.rgb = toLinearSpace(environmentRadiance.rgb);
  138. #endif
  139. // _____________________________ Levels _____________________________________
  140. environmentRadiance.rgb *= vReflectionInfos.x;
  141. environmentRadiance.rgb *= vReflectionColor.rgb;
  142. }
  143. #define pbr_inline
  144. #define inline
  145. void reflectionBlock(
  146. const in vec3 vPositionW,
  147. const in vec3 normalW,
  148. const in float alphaG,
  149. const in vec3 vReflectionMicrosurfaceInfos,
  150. const in vec2 vReflectionInfos,
  151. const in vec3 vReflectionColor,
  152. #ifdef ANISOTROPIC
  153. const in anisotropicOutParams anisotropicOut,
  154. #endif
  155. #if defined(LODINREFLECTIONALPHA) && !defined(REFLECTIONMAP_SKYBOX)
  156. const in float NdotVUnclamped,
  157. #endif
  158. #ifdef LINEARSPECULARREFLECTION
  159. const in float roughness,
  160. #endif
  161. #ifdef REFLECTIONMAP_3D
  162. const in samplerCube reflectionSampler,
  163. #else
  164. const in sampler2D reflectionSampler,
  165. #endif
  166. #if defined(NORMAL) && defined(USESPHERICALINVERTEX)
  167. const in vec3 vEnvironmentIrradiance,
  168. #endif
  169. #ifdef USESPHERICALFROMREFLECTIONMAP
  170. #if !defined(NORMAL) || !defined(USESPHERICALINVERTEX)
  171. const in mat4 reflectionMatrix,
  172. #endif
  173. #endif
  174. #ifdef USEIRRADIANCEMAP
  175. #ifdef REFLECTIONMAP_3D
  176. const in samplerCube irradianceSampler,
  177. #else
  178. const in sampler2D irradianceSampler,
  179. #endif
  180. #endif
  181. #ifndef LODBASEDMICROSFURACE
  182. #ifdef REFLECTIONMAP_3D
  183. const in samplerCube reflectionSamplerLow,
  184. const in samplerCube reflectionSamplerHigh,
  185. #else
  186. const in sampler2D reflectionSamplerLow,
  187. const in sampler2D reflectionSamplerHigh,
  188. #endif
  189. #endif
  190. out reflectionOutParams outParams
  191. )
  192. {
  193. // _____________________________ Radiance ________________________________
  194. vec4 environmentRadiance = vec4(0., 0., 0., 0.);
  195. #ifdef REFLECTIONMAP_3D
  196. vec3 reflectionCoords = vec3(0.);
  197. #else
  198. vec2 reflectionCoords = vec2(0.);
  199. #endif
  200. createReflectionCoords(
  201. vPositionW,
  202. normalW,
  203. #ifdef ANISOTROPIC
  204. anisotropicOut,
  205. #endif
  206. reflectionCoords
  207. );
  208. sampleReflectionTexture(
  209. alphaG,
  210. vReflectionMicrosurfaceInfos,
  211. vReflectionInfos,
  212. vReflectionColor,
  213. #if defined(LODINREFLECTIONALPHA) && !defined(REFLECTIONMAP_SKYBOX)
  214. NdotVUnclamped,
  215. #endif
  216. #ifdef LINEARSPECULARREFLECTION
  217. roughness,
  218. #endif
  219. #ifdef REFLECTIONMAP_3D
  220. reflectionSampler,
  221. reflectionCoords,
  222. #else
  223. reflectionSampler,
  224. reflectionCoords,
  225. #endif
  226. #ifndef LODBASEDMICROSFURACE
  227. reflectionSamplerLow,
  228. reflectionSamplerHigh,
  229. #endif
  230. environmentRadiance
  231. );
  232. // _____________________________ Irradiance ________________________________
  233. vec3 environmentIrradiance = vec3(0., 0., 0.);
  234. #ifdef USESPHERICALFROMREFLECTIONMAP
  235. #if defined(NORMAL) && defined(USESPHERICALINVERTEX)
  236. environmentIrradiance = vEnvironmentIrradiance;
  237. #else
  238. #ifdef ANISOTROPIC
  239. vec3 irradianceVector = vec3(reflectionMatrix * vec4(anisotropicOut.anisotropicNormal, 0)).xyz;
  240. #else
  241. vec3 irradianceVector = vec3(reflectionMatrix * vec4(normalW, 0)).xyz;
  242. #endif
  243. #ifdef REFLECTIONMAP_OPPOSITEZ
  244. irradianceVector.z *= -1.0;
  245. #endif
  246. #ifdef INVERTCUBICMAP
  247. irradianceVector.y *= -1.0;
  248. #endif
  249. #if defined(REALTIME_FILTERING)
  250. environmentIrradiance = irradiance(reflectionSampler, irradianceVector, vReflectionFilteringInfo);
  251. #else
  252. environmentIrradiance = computeEnvironmentIrradiance(irradianceVector);
  253. #endif
  254. #ifdef SS_TRANSLUCENCY
  255. outParams.irradianceVector = irradianceVector;
  256. #endif
  257. #endif
  258. #elif defined(USEIRRADIANCEMAP)
  259. vec4 environmentIrradiance4 = sampleReflection(irradianceSampler, reflectionCoords);
  260. environmentIrradiance = environmentIrradiance4.rgb;
  261. #ifdef RGBDREFLECTION
  262. environmentIrradiance.rgb = fromRGBD(environmentIrradiance4);
  263. #endif
  264. #ifdef GAMMAREFLECTION
  265. environmentIrradiance.rgb = toLinearSpace(environmentIrradiance.rgb);
  266. #endif
  267. #endif
  268. environmentIrradiance *= vReflectionColor.rgb;
  269. outParams.environmentRadiance = environmentRadiance;
  270. outParams.environmentIrradiance = environmentIrradiance;
  271. outParams.reflectionCoords = reflectionCoords;
  272. }
  273. #endif