PDA

View Full Version : simple blending question



kazmalak
04-12-2005, 04:09 AM
Hello
In my project, I have drawn two objects. They are moving on the screen with mouse inputs and in some situations they have to share the same location but with different depth values. In that case, the one at the back have to be seen, that means the one on the front should be translucent.
Therefore to make it translucent, I am using blending functions. However, since the order of object creation is important, it works if the second created object is front of the other, but it doesnt work if the first created object comes in front of the second one.

Is there a way to make those functions work independent of the creation order? I mean do I always have to create the behind object first ?

Aeluned
04-12-2005, 04:44 AM
Unfortunately, this is a common problem in
graphics programming.

One way to rectify the situation is to render the
scene in 2 passes.

the first pass should be set up like this:
glEnable(GL_ALPHA_TEST);
if(pass == 1)
glAlphaFunc(GL_EQUAL,1.0);
glDepthMask(GL_TRUE);
else
glAlphaFunc(GL_NOTEQUAL,1.0);
glDepthMask(GL_FALSE);

this will first render all opaque fragments and
then all translucent ones.

of course you run into the same problem if you
have overlapping translucent objects, in which
case you need to sort your objects manually.

The problem is due to the fact that your first
object (translucent one) is blending with an
empty color buffer and also writing to the depth
buffer. Then, when the second object goes to draw
itself, (the opaque one behind the translucent
one) it ends up failing the depth test and no
fragments are generated.

kazmalak
04-13-2005, 01:19 AM
Thanks aeluned,
You said I have to render the scene in 2 passes and give some sample codes. I read the related topic in Red Book and begin to understand what you have described. The way you described can help me a lot. However,I dont know how can I apply it to my program (Where to use those sample codes.)

Aeluned
04-13-2005, 09:16 AM
Let's say you had a function that is the entry
point for all of your rendering; something like:

void Render();

inside Render() you would have something like:

Render()
{
for(int pass=0; pass < 2; pass++)
{
if(pass == 0)
Set the alpha func stuff i showed before
if(pass == 1)
Set the alpha func the other way

//Now render all objects
}
}Basically, you need to enable the alpha test and
set the func prior to any rendering.

kazmalak
04-13-2005, 10:23 PM
Thanks again aeluned
I have done what you have described and program works quite well, but with one exception.You gave me the sample code


glEnable(GL_ALPHA_TEST);
if(pass == 1)
glAlphaFunc(GL_EQUAL,1.0);
glDepthMask(GL_TRUE);
else
glAlphaFunc(GL_NOTEQUAL,1.0);
glDepthMask(GL_FALSE);
If I make glDepthMask false for the second pass, the opaque object begins to disappear from the screen. If I dont make it false (if it always stay true) then no problem occurs. What is the reason for that?

kazmalak
04-14-2005, 03:12 AM
Sorry, I have made a mistake and now solve it. Thanks again.