threepipe
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

SSAOPlugin.pass.glsl 5.1KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. #include <randomHelpers>
  2. #include <common>
  3. #include <packing>
  4. #define THREE_PACKING_INCLUDED
  5. #include <cameraHelpers>
  6. varying vec2 vUv;
  7. uniform sampler2D tLastThis;
  8. uniform float frameCount;
  9. uniform vec4 saoData;
  10. uniform vec3 saoBiasEpsilon;
  11. uniform vec2 screenSize;
  12. const float INV_NUM_SAMPLES = 1.0 / float(NUM_SAMPLES);
  13. //int getSelectionBit(in int number) {
  14. // #ifdef WebGL2Context
  15. // return (number/4) % 2;
  16. // #else
  17. // return int(mod(floor(float(number)/4.), 2.));
  18. // #endif
  19. //}
  20. vec3 packFloatToRGB(const in float x) {
  21. const vec3 code = vec3(1.0, 255.0, 65025.0);
  22. vec3 pack = vec3(code * x);
  23. pack.gb = fract(pack.gb);
  24. pack.rg -= pack.gb * (1.0 / 256.0);
  25. return pack;
  26. }
  27. vec3 getPositionFromOffset(const in vec2 uv,
  28. const in vec2 offset,
  29. const in float screenSpaceRadius) {
  30. vec2 uvOffset = uv + floor(screenSpaceRadius * offset) / screenSize;
  31. #if defined(HAS_DEPTH_BUFFER) || defined(HAS_NORMAL_DEPTH_BUFFER)
  32. float d = getDepth(uvOffset);
  33. #else
  34. float d = 0.5;
  35. #endif
  36. #if LINEAR_DEPTH == 0
  37. float centerViewZ = viewZFromNDCZ(d);
  38. return screenToView(uvOffset, centerViewZ);
  39. #else
  40. d = mix(-cameraNearFar.x, -cameraNearFar.y, d);
  41. return screenToView(uvOffset, d);
  42. #endif
  43. }
  44. float getOcclusion(const in vec2 uv,
  45. const in int id,
  46. const in float randomAngle,
  47. const in float occlusionSphereRadius,
  48. const in vec3 centerPosition,
  49. const in vec3 centerNormal) {
  50. float screenSpaceRadius = (float(id) + mod(randomAngle, 1.) + 0.5) * INV_NUM_SAMPLES;
  51. float angle = screenSpaceRadius * (float(NUM_SPIRAL_TURNS) * 6.28) + randomAngle;
  52. screenSpaceRadius = (screenSpaceRadius * occlusionSphereRadius);
  53. vec2 offset = vec2(cos(angle), sin(angle));
  54. vec3 samplePosition = getPositionFromOffset(uv, offset, screenSpaceRadius);
  55. vec3 direction = samplePosition - centerPosition;
  56. float d2 = dot(direction, direction);
  57. float ao = max((dot(centerNormal, direction) + centerPosition.z * saoBiasEpsilon.x) / (saoBiasEpsilon.z * d2 + saoBiasEpsilon.y), 0.0);
  58. return ao;
  59. }
  60. void main() {
  61. // initial values
  62. float centerDepth = 0.5;
  63. vec3 centerNormal = vec3(0, 1, 0);
  64. #ifdef HAS_NORMAL_DEPTH_BUFFER
  65. getDepthNormal(vUv, centerDepth, centerNormal);
  66. #else
  67. #ifdef HAS_DEPTH_BUFFER
  68. centerDepth = getDepth(vUv);
  69. #endif
  70. // todo - add support for NormalBufferPlugin
  71. // #ifdef HAS_NORMAL_BUFFER
  72. // centerDepth = getDepth(vUv);
  73. // #endif
  74. #endif
  75. // if (centerDepth >= (1.0 - EPSILON)) {
  76. // discard;
  77. // }
  78. #if LINEAR_DEPTH == 0
  79. float centerViewZ = viewZFromNDCZ(centerDepth);
  80. #else
  81. float centerViewZ = mix(-cameraNearFar.x, -cameraNearFar.y, centerDepth);
  82. #endif
  83. vec3 centerPosition = screenToView(vUv, centerViewZ);
  84. float occlusionSphereScreenRadius = 200. * saoData.z / (-centerPosition.z);
  85. // if (occlusionSphereScreenRadius < 1.) {
  86. // discard;
  87. // }
  88. float randomAngle = 6.2 * random3(vec3(vUv, frameCount * 0.1));
  89. float sum = 0.0;
  90. sum += getOcclusion(vUv, 0, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  91. #if NUM_SAMPLES > 1
  92. sum += getOcclusion(vUv, 1, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  93. #endif
  94. #if NUM_SAMPLES > 2
  95. sum += getOcclusion(vUv, 2, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  96. #endif
  97. #if NUM_SAMPLES > 3
  98. sum += getOcclusion(vUv, 3, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  99. #endif
  100. #if NUM_SAMPLES > 4
  101. sum += getOcclusion(vUv, 4, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  102. #endif
  103. #if NUM_SAMPLES > 5
  104. sum += getOcclusion(vUv, 5, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  105. #endif
  106. #if NUM_SAMPLES > 6
  107. sum += getOcclusion(vUv, 6, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  108. #endif
  109. #if NUM_SAMPLES > 7
  110. sum += getOcclusion(vUv, 7, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  111. #endif
  112. #if NUM_SAMPLES > 8
  113. sum += getOcclusion(vUv, 8, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  114. #endif
  115. #if NUM_SAMPLES > 9
  116. sum += getOcclusion(vUv, 9, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  117. #endif
  118. #if NUM_SAMPLES > 10
  119. sum += getOcclusion(vUv, 10, randomAngle, occlusionSphereScreenRadius, centerPosition, centerNormal);
  120. #endif
  121. float aoValue = sum * saoData.y * INV_NUM_SAMPLES;
  122. // bool disableAO = getSelectionBit(getGBufferFlags(vUv).a) > 0 ? true : false;
  123. aoValue = 1. - clamp(aoValue, 0., 1.);
  124. // so that depth can also be sampled with ssao if required?
  125. gl_FragColor.gba = packFloatToRGB(centerDepth);
  126. // vec4 lastAO = texture2D( tLastThis, vUv );
  127. // gl_FragColor.r = (vec4(aoValue)).r;// + (lastAO.r) * frameCount)/(frameCount+1.);
  128. gl_FragColor.r = aoValue;// + (lastAO.r) * frameCount)/(frameCount+1.);
  129. // gl_FragColor.r = aoValue;
  130. // gl_FragColor = vec4(centerDepth);
  131. }