present_gaussian.frag 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869
  1. // SPDX-FileCopyrightText: Copyright 2021 yuzu Emulator Project
  2. // SPDX-License-Identifier: GPL-2.0-or-later
  3. // Code adapted from the following sources:
  4. // - https://learnopengl.com/Advanced-Lighting/Bloom
  5. // - https://www.rastergrid.com/blog/2010/09/efficient-gaussian-blur-with-linear-sampling/
  6. #version 460 core
  7. #ifdef VULKAN
  8. #define BINDING_COLOR_TEXTURE 1
  9. #else // ^^^ Vulkan ^^^ // vvv OpenGL vvv
  10. #define BINDING_COLOR_TEXTURE 0
  11. #endif
  12. layout(location = 0) in vec2 frag_tex_coord;
  13. layout(location = 0) out vec4 color;
  14. layout(binding = BINDING_COLOR_TEXTURE) uniform sampler2D color_texture;
  15. const float offset[3] = float[](0.0, 1.3846153846, 3.2307692308);
  16. const float weight[3] = float[](0.2270270270, 0.3162162162, 0.0702702703);
  17. vec4 blurVertical(sampler2D textureSampler, vec2 coord, vec2 norm) {
  18. vec4 result = vec4(0.0f);
  19. for (int i = 1; i < 3; i++) {
  20. result += texture(textureSampler, vec2(coord) + (vec2(0.0, offset[i]) * norm)) * weight[i];
  21. result += texture(textureSampler, vec2(coord) - (vec2(0.0, offset[i]) * norm)) * weight[i];
  22. }
  23. return result;
  24. }
  25. vec4 blurHorizontal(sampler2D textureSampler, vec2 coord, vec2 norm) {
  26. vec4 result = vec4(0.0f);
  27. for (int i = 1; i < 3; i++) {
  28. result += texture(textureSampler, vec2(coord) + (vec2(offset[i], 0.0) * norm)) * weight[i];
  29. result += texture(textureSampler, vec2(coord) - (vec2(offset[i], 0.0) * norm)) * weight[i];
  30. }
  31. return result;
  32. }
  33. vec4 blurDiagonal(sampler2D textureSampler, vec2 coord, vec2 norm) {
  34. vec4 result = vec4(0.0f);
  35. for (int i = 1; i < 3; i++) {
  36. result +=
  37. texture(textureSampler, vec2(coord) + (vec2(offset[i], offset[i]) * norm)) * weight[i];
  38. result +=
  39. texture(textureSampler, vec2(coord) - (vec2(offset[i], offset[i]) * norm)) * weight[i];
  40. }
  41. return result;
  42. }
  43. void main() {
  44. vec3 base = texture(color_texture, vec2(frag_tex_coord)).rgb * weight[0];
  45. vec2 tex_offset = 1.0f / textureSize(color_texture, 0);
  46. // TODO(Blinkhawk): This code can be optimized through shader group instructions.
  47. vec3 horizontal = blurHorizontal(color_texture, frag_tex_coord, tex_offset).rgb;
  48. vec3 vertical = blurVertical(color_texture, frag_tex_coord, tex_offset).rgb;
  49. vec3 diagonalA = blurDiagonal(color_texture, frag_tex_coord, tex_offset).rgb;
  50. vec3 diagonalB = blurDiagonal(color_texture, frag_tex_coord, tex_offset * vec2(1.0, -1.0)).rgb;
  51. vec3 combination = mix(mix(horizontal, vertical, 0.5f), mix(diagonalA, diagonalB, 0.5f), 0.5f);
  52. color = vec4(combination + base, 1.0f);
  53. }