Pack.glsl 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188
  1. // Copyright (C) 2009-2018, Panagiotis Christopoulos Charitos and contributors.
  2. // All rights reserved.
  3. // Code licensed under the BSD License.
  4. // http://www.anki3d.org/LICENSE
  5. #ifndef ANKI_SHADERS_PACK_GLSL
  6. #define ANKI_SHADERS_PACK_GLSL
  7. #include "shaders/Common.glsl"
  8. /// Pack 3D normal to 2D vector
  9. /// See the clean code in comments in revision < r467
  10. vec2 packNormal(in vec3 normal)
  11. {
  12. const float SCALE = 1.7777;
  13. float scalar1 = (normal.z + 1.0) * (SCALE * 2.0);
  14. return normal.xy / scalar1 + 0.5;
  15. }
  16. /// Reverse the packNormal
  17. vec3 unpackNormal(in vec2 enc)
  18. {
  19. const float SCALE = 1.7777;
  20. vec2 nn = enc * (2.0 * SCALE) - SCALE;
  21. float g = 2.0 / (dot(nn.xy, nn.xy) + 1.0);
  22. vec3 normal;
  23. normal.xy = g * nn.xy;
  24. normal.z = g - 1.0;
  25. return normalize(normal);
  26. }
  27. // See http://johnwhite3d.blogspot.no/2017/10/signed-octahedron-normal-encoding.html
  28. // Result in [0.0, 1.0]
  29. vec3 signedOctEncode(vec3 n)
  30. {
  31. vec3 outn;
  32. vec3 nabs = abs(n);
  33. n /= nabs.x + nabs.y + nabs.z;
  34. outn.y = n.y * 0.5 + 0.5;
  35. outn.x = n.x * 0.5 + outn.y;
  36. outn.y = n.x * -0.5 + outn.y;
  37. outn.z = saturate(n.z * FLT_MAX);
  38. return outn;
  39. }
  40. // See http://johnwhite3d.blogspot.no/2017/10/signed-octahedron-normal-encoding.html
  41. vec3 signedOctDecode(vec3 n)
  42. {
  43. vec3 outn;
  44. outn.x = n.x - n.y;
  45. outn.y = n.x + n.y - 1.0;
  46. outn.z = n.z * 2.0 - 1.0;
  47. outn.z = outn.z * (1.0 - abs(outn.x) - abs(outn.y));
  48. outn = normalize(outn);
  49. return outn;
  50. }
  51. #if GL_ES || __VERSION__ < 400
  52. // Vectorized version. See clean one at <= r1048
  53. uint packUnorm4x8(in vec4 v)
  54. {
  55. vec4 a = clamp(v, 0.0, 1.0) * 255.0;
  56. uvec4 b = uvec4(a) << uvec4(0U, 8U, 16U, 24U);
  57. uvec2 c = b.xy | b.zw;
  58. return c.x | c.y;
  59. }
  60. // Vectorized version. See clean one at <= r1048
  61. vec4 unpackUnorm4x8(in highp uint u)
  62. {
  63. uvec4 a = uvec4(u) >> uvec4(0U, 8U, 16U, 24U);
  64. uvec4 b = a & uvec4(0xFFU);
  65. vec4 c = vec4(b);
  66. return c * (1.0 / 255.0);
  67. }
  68. #endif
  69. // Convert from RGB to YCbCr.
  70. // The RGB should be in [0, 1] and the output YCbCr will be in [0, 1] as well.
  71. vec3 rgbToYCbCr(in vec3 rgb)
  72. {
  73. float y = dot(rgb, vec3(0.299, 0.587, 0.114));
  74. float cb = 0.5 + dot(rgb, vec3(-0.168736, -0.331264, 0.5));
  75. float cr = 0.5 + dot(rgb, vec3(0.5, -0.418688, -0.081312));
  76. return vec3(y, cb, cr);
  77. }
  78. // Convert the output of rgbToYCbCr back to RGB.
  79. vec3 yCbCrToRgb(in vec3 ycbcr)
  80. {
  81. float cb = ycbcr.y - 0.5;
  82. float cr = ycbcr.z - 0.5;
  83. float y = ycbcr.x;
  84. float r = 1.402 * cr;
  85. float g = -0.344 * cb - 0.714 * cr;
  86. float b = 1.772 * cb;
  87. return vec3(r, g, b) + y;
  88. }
  89. // Pack a vec2 to a single float.
  90. // comp should be in [0, 1] and the output will be in [0, 1].
  91. float packUnorm2ToUnorm1(in vec2 comp)
  92. {
  93. return dot(round(comp * 15.0), vec2(1.0 / (255.0 / 16.0), 1.0 / 255.0));
  94. }
  95. // Unpack a single float to vec2. Does the oposite of packUnorm2ToUnorm1.
  96. vec2 unpackUnorm1ToUnorm2(in float c)
  97. {
  98. #if 1
  99. float temp = c * (255.0 / 16.0);
  100. float a = floor(temp);
  101. float b = temp - a; // b = fract(temp)
  102. return vec2(a, b) * vec2(1.0 / 15.0, 16.0 / 15.0);
  103. #else
  104. uint temp = uint(c * 255.0);
  105. uint a = temp >> 4;
  106. uint b = temp & 0xF;
  107. return vec2(a, b) / 15.0;
  108. #endif
  109. }
  110. // Max emission. Keep as low as possible
  111. const float MAX_EMISSION = 20.0;
  112. // G-Buffer structure
  113. struct GbufferInfo
  114. {
  115. vec3 diffuse;
  116. vec3 specular;
  117. vec3 normal;
  118. float roughness;
  119. float metallic;
  120. float subsurface;
  121. float emission;
  122. };
  123. // Populate the G buffer
  124. void writeGBuffer(in GbufferInfo g, out vec4 rt0, out vec4 rt1, out vec4 rt2)
  125. {
  126. rt0 = vec4(g.diffuse, g.subsurface);
  127. rt1 = vec4(g.roughness, g.metallic, g.specular.x, 0.0);
  128. vec3 encNorm = signedOctEncode(g.normal);
  129. rt2 = vec4(encNorm.xy, g.emission / MAX_EMISSION, encNorm.z);
  130. }
  131. // Read from G-buffer
  132. void readNormalFromGBuffer(in sampler2D rt2, in vec2 uv, out vec3 normal)
  133. {
  134. normal = signedOctDecode(texture(rt2, uv).rga);
  135. }
  136. // Read from the G buffer
  137. void readGBuffer(in sampler2D rt0, in sampler2D rt1, in sampler2D rt2, in vec2 uv, in float lod, out GbufferInfo g)
  138. {
  139. vec4 comp = textureLod(rt0, uv, 0.0);
  140. g.diffuse = comp.xyz;
  141. g.subsurface = comp.w;
  142. comp = textureLod(rt1, uv, 0.0);
  143. g.roughness = comp.x;
  144. g.metallic = comp.y;
  145. g.specular = vec3(comp.z);
  146. comp = textureLod(rt2, uv, 0.0);
  147. g.normal = signedOctDecode(comp.xyw);
  148. g.emission = comp.z * MAX_EMISSION;
  149. // Fix roughness
  150. const float MIN_ROUGHNESS = 0.05;
  151. g.roughness = g.roughness * (1.0 - MIN_ROUGHNESS) + MIN_ROUGHNESS;
  152. // Compute reflectance
  153. g.specular = mix(g.specular, g.diffuse, g.metallic);
  154. // Compute diffuse
  155. g.diffuse = g.diffuse - g.diffuse * g.metallic;
  156. }
  157. #endif