OpenGL Bloom Shader
Habe gestern für Galaxy War Commander einen bloom shader geschrieben und wollte den hier nochmal explizit vorstellen. Zu beachten ist das der Shader auf eine Framebuffer-Textur angewendet wird.
Vertexshader Source:
varying vec2 texcoord; void main(void) { gl_Position = ftransform(); texcoord = vec2(ftransform() * 0.5 + 0.5); }
Der Vertexshader transformiert die position und gibt diese zur weiteren Verarbeitung an den Fragmentshader weiter.
Fragmentshader Source:
uniform sampler2D rscene; varying vec2 texcoord; void main() { vec4 pxl = texture2D(rscene, texcoord); float avg = ((pxl.r + pxl.g + pxl.b) / 3.0); // bloom { vec4 sum = vec4(0.0); for (int i = -5; i <= 5; i++) { for (int j = -5; j <= 5; j++) { sum += texture2D(rscene, (texcoord + vec2(i, j) * 0.0018)) * 0.015; } } if (avg < 0.025) { gl_FragColor = pxl + sum * 0.335; } else if (avg < 0.10) { gl_FragColor = pxl + (sum * sum) * 0.5; } else if (avg < 0.88) { gl_FragColor = pxl + ((sum * sum) * 0.333); } else if (avg >= 0.88) { gl_FragColor = pxl + sum; } else { gl_FragColor = pxl; } } }
Hier wird das gerenderte Bild zunächst weichgezeichnet und dann je nach Intensität des darunterliegenden Pixels über den Render gelegt. Die Werte (Weichzeichengröße- und Auflösung, Intensität) können je nach Geschmack angepasst werden.
Viel Spaß!

2 Kommentare zu “OpenGL Bloom Shader”
[...] http://doenemeier.de/2011/03-opengl-bloom-shader.html [...]
Habe den Shader als ersten Anhaltspunkt für ein Projekt verwendet, dann aber doch von Grund auf neu geschrieben. Unterschiede:
Gauss Blur anstatt Averaging. Die etwas komplizierteren Berechnungen machen den Braten auch nicht fett. Dafür gibt es keine Kantenfehler im Bild (kann bei rechteckigen Strukturen negativ auffallen).
Zwei Durchgänge für die Glättung. Ich glätte das Bild erst mit einem Shader auf der X-Achse, dann mit einem zweiten auf der Y-Achse (der zweite Shader nutzt dazu die Ausgabe des ersten). Dadurch erhält man eine nur lineare Anzahl von Texture Lookups, anstatt einer quadratischen, wie bei dir (SEHR viele redundante Berechnungen). Da diese Lookups bei größeren Radien und bei genauerem Sampling einen Flaschenhals darstellen, lohnt sich der Aufwand zweier Renderdurchgänge schnell.
Wünsche noch viel Spaß bei eurem Projekt!