Search Results

Thursday, February 17, 2011

OpenGL 2D Screen Filters in the BGE - Part 2

Hey. So, today, we'll take a look at another, slightly more complex 2D screen filter - the common Blur filter (yeaah!). A blur filter is a very useful 2D screen filter - some games use them to simulate taking damage, with the screen getting blurrier with time, or apply it in a radial manner (which looks great. This may get covered later on in this series). We'll take a look at the code for a simple blur filter below.

filter.shaderText = """

            uniform sampler2D bgl_RenderedTexture;

            void main(void)
            {
                        float value = 0.0015;      // Here, value = distance away to check for pixel color
                       
                        vec4 color = texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x + value, gl_TexCoord[0].st.y + value)); // Sample area around current pixel
            color += texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x - value, gl_TexCoord[0].st.y - value));
            color += texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x + value, gl_TexCoord[0].st.y - value));
            color += texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x - value, gl_TexCoord[0].st.y + value));
   
            color /= 4.0;         // And average out the final color by number of samples; this could be in a for-loop, but apparently,
            gl_FragColor = color;     // some graphics cards (like mine) won't support them

            }
"""

Since there's not too much of a difference between this source blend file and the previous part's version, I only included the shader code (the text block above that the filter actuator's shaderText property gets assigned). You can easily swap out shader scripts by just copying and pasting different shader scripts to the 2D filter actuator's shaderText property, or even assigning shaders to variables and then applying the actuator with the text you need.

Okay, so as you can see, there's not a lot of new text at the beginning of the script. At the beginning, we set up our rendered screen texture. This is a simple 2D texture that would be normally drawn to the screen, except that we're modifying this texture output. We set up the main function, and inside, we see the meat of this script:

 float value = 0.0015;      // Here, value = distance away to check for pixel color
                       
                        vec4 color = texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x + value, gl_TexCoord[0].st.y + value)); // Sample area around current pixel
            color += texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x - value, gl_TexCoord[0].st.y - value));
            color += texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x + value, gl_TexCoord[0].st.y - value));
            color += texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x - value, gl_TexCoord[0].st.y + value));

In this block above, we create a simple variable that we can easily use to customize how heavy the effect is blurred. In the next line,we create a new variable, color. This is a 4-dimensional vector vualue (Red, green, blue, and alpha), as shown in the previous part in this series. In the next line, we see...

vec4 color = texture2D(bgl_RenderedTexture, vec2(gl_TexCoord[0].st.x + value, gl_TexCoord[0].st.y + value)); // Sample area around current pixel

that the second argument of the texture2D function points to the position to check for color. That argument is the texture coordinate of the pixel we're modifying offset by the distance value we specified before (in percentage, not pixels). 

The difference between blurring and normal.
We do that a few more times for the other directions, and then average them out by dividing the final result by the number of samples we blurred by. Finally, we set the final gl_FragColor variable to the blur average, blurring the pixel by the surrounding pixels. The effect should look a lot like the effect to the left.

Well, that's all there is to a 2D Blur filter for the BGE using GLSL - note that while this is BGE specific, the underlying principle should translate fine to other scripting languages. Click here to download the OpenGL 2D Blur Filter. Have fun!

4 comments:

  1. Wow dude than x a lot.

    keep posting. I have book marked you.

    ReplyDelete
  2. No problem. I'll keep on with the tutorials, and I think I'll put up a 2D Filter library that I've made soon...

    ReplyDelete
  3. One thing I find irritating is that these strips stick out into the actual screen by a little bit - depending on how you place them, up to about 4mm. While they are clear and subsequently see-through, they still represent a bit of an irritation I hope I get used to them.

    ReplyDelete
  4. I found this FX in BlenderArtists and I reply this, there, too:

    "Hey, I was needing just this: very simple blur... but this FX darken the image. Why and how should I avoid that?"

    ReplyDelete