Skip to main content
GameDev.net gamedev.net
🔒 Locked

How to: Glow effects using Framebuffer Objects

Started by MrDoomMaster Apr 27, 2006 at 4:43 PM 8 replies 4.5k views
Original Post
MrDoomMaster
MrDoomMaster
Hi, I'm trying to create a flow effect via using Frame Buffer Objects, but I can't seem to get any worthy results. Here is the process I am following: 1) Create the FBO Object 2) Create 2 blank textures 3) Use glFramebufferTexture2DEXT() to set Texture 1 as the FBO render target 4) Draw glowing object to texture 1 using FBO 5) Convert projection into orthographic projection 6) Use glFramebufferTexture2DEXT() to set Texture 2 as the FBO render target 7) Use glBindTexture() to set Texture 1 as the current texture 8) Draw a screen-sized quad across the screen horizontally several times (shifting each time). The quad will be drawn with the image in Texture 1 (which should be an image of the glowing object drawn previously) 9) Disable FBO rendering so that I can now render to the default render target 10) Use glBindTexture() to set Texture 2 as the current texture 11) Draw a screen-sized quad across the screen vertically several times (shifting each time). The quad will be drawn with the image in Texture 2 (which should now be a horizontal blur of the single glowing object in Texture 1). As this final step is performed, it is blended with the scene which was originally drawn in the default backbuffer, NOT the FBO. The FBO is only used for the blur calculation. There are a few things about the above method: 1) The blur sucks. Even just examining a horizontal blur, it totally sucks. As you zoom further away from the object the blur looks more and more like a long strip of object copies. The blur also does not become smaller as you move further away 2) If I include steps 6 through 9, I get absolutely no output. For some reason, using setting texture 2 doesn't work because nothing is being drawn. Note that if steps 6 through 9 are skipped, then in step 10 we will glBindTexture() on Texture 1, and not texture 2. I have a few questions: 1) When you change your render target in the FBO, do you have to re-do your projection and/or viewport, even if the viewport dimensions have not changed? (aka, the screen size is the same as the FBO texture size) 2) What reasons would the FBO have for not working when you actually process steps 6 through 9? In conclusion I would just like to mention that there is NOT much documentation on FBO's and I am very frustrated with that. I can't really figure out how the hell to use FBO's. I'm sure if I knew 100% how they worked I wouldn't be having stupid problems like this. Not to mention that I can't find any samples where a program uses 1 FBO to render to XX many textures. Any guidance would be greatly appreciated. Thanks!
OrangyTang
OrangyTang
I was messing with glow effects a little while ago, you might want to read the entries in my journal on it. Although I wasn't using FBOs (the main reason being the distinct lack of documentation on them) I find the key thing to getting good glow is carefully chosen weights and offsets. If you're getting something which looks very obviously like a set of horizontal copies then your weights are probably not setup right - exponential falloff seems to work best IMHO.

Also you might want to consider using GLSL and multitexturing, as you can drastically reduce the number of passes you need to perform.
MrDoomMaster
MrDoomMaster
Quote:
Original post by OrangyTang
I was messing with glow effects a little while ago, you might want to read the entries in my journal on it. Although I wasn't using FBOs (the main reason being the distinct lack of documentation on them) I find the key thing to getting good glow is carefully chosen weights and offsets. If you're getting something which looks very obviously like a set of horizontal copies then your weights are probably not setup right - exponential falloff seems to work best IMHO.

Also you might want to consider using GLSL and multitexturing, as you can drastically reduce the number of passes you need to perform.


The target hardware does not support shaders, unfortunately, so I have to rely on either the shifting (as explained above) or texture downsampling (which I am now trying, but the stupid FBO's still won't render!!)
cwhite
cwhite
How are you switching between textures? The standard acceptable way is to set one texture to GL_COLOR_ATTACHMENT0_EXT and the other texture to GL_COLOR_ATTACHMENT1_EXT and then do a call to glWriteBuffer(GL_COLOR_ATTACHMENTn_EXT) to switch between textures. Is this how you are doing it?

Second, you should be doing error checking to see if your fbo is actually valid. If you set it up improperly (ie, wrong texture format) then it won't render.
MrDoomMaster
MrDoomMaster
Quote:
Original post by cwhite
How are you switching between textures? The standard acceptable way is to set one texture to GL_COLOR_ATTACHMENT0_EXT and the other texture to GL_COLOR_ATTACHMENT1_EXT and then do a call to glWriteBuffer(GL_COLOR_ATTACHMENTn_EXT) to switch between textures. Is this how you are doing it?

Second, you should be doing error checking to see if your fbo is actually valid. If you set it up improperly (ie, wrong texture format) then it won't render.


Currently I do the following:

1) Create FBO *WITH* error checking (no errors occur)
2) Use glFramebufferTexture2D() to attach Texture 1 to slot 0
3) Draw to the FBO (should draw to texture 1)
4) Now use glFramebufferTexture2D() again and this time attach Texture 2 to slot 0 again. This will now change the render target to Texture 2.
5) Draw to the FBO (should now draw to texture 2)
MrDoomMaster
MrDoomMaster
Okay so I FINALLY figured out what was going on, it's completely stupid. I didn't update my viewport in the appropriate places. I don't want to get into the details because it's a lot of code, but just remember this small bit of advice which took me countless hours to learn:

When using multiple FBO's, each containing different resolutions of render targets, always update your viewport. Since each FBO shares the same render context (unlike PBuffers), this means they all share the same transformation matrices. This means that you don't need to really change your modelview or projection matricies when you switch or update the viewport. This little bit of information helped me the most in my quest to learn about FBO's.


Now, moving right along. I have successfully blurred my object, except now I need some advice on how to make the bluring look better.

Currently this is how I apply my bluring:

1) Draw the object by itself
2) Down-sample this object several times. For example, I would draw this same image to a 128x128, then to a 64x64, 32x32, 16x16. You get the pattern, right?
3) Draw each downsampled copy over the original-sized glowing object to form the blur effect.

The technique is handsome, but the results are not. My problem is not knowing any neat techniques to modify the downsampled versions even more so that I can generate a more realistic blur effect. There are many artifacts in the final blur result which basically results in blur only appearing when you move the camera to a certain position (thus the flaws of the filtering in the downsampling process begins to reveal itself).

If anyone could provide some nice bluring techniques, it would be extremely helpful. Thanks!
mandrav
mandrav
This article might help you since it presents the glow effect without using shaders.
It's not using FBOs (rather glCopySubTexImage2D()) but it wouldn't matter: you 're only interested in the technique, right?

Yiannis.
Boruki
Boruki
Quote:
Original post by mandrav
This article might help you since it presents the glow effect without using shaders.
It's not using FBOs (rather glCopySubTexImage2D()) but it wouldn't matter: you 're only interested in the technique, right?

Yiannis.


I tried using that.. and it gave me a quarter screen problems (due to all the viewport changing). I never managed to get my head around which viewport calls and such to change in order to make it work. I ended up using a texture the same size as the screen.. which lags the crap out of even a 6600 :).
MrDoomMaster
MrDoomMaster
Quote:
Original post by mandrav
This article might help you since it presents the glow effect without using shaders.
It's not using FBOs (rather glCopySubTexImage2D()) but it wouldn't matter: you 're only interested in the technique, right?

Yiannis.


I have read this article numerous times before even posting here. The code is very unclear. It wasn't helpful at all.

It discusses techniques but doesn't really clearly represent how they're done, at least from what I can tell.

Thank you for the reference, but unfortunately I still remain in a helpless state.
deavik
deavik
It sounds like this is already what you have, but still, have you seen Nutty's glare demo?

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.