PDA

View Full Version : Depth Texture -> MipMap -> GLSL Shader?



PickleWorld
06-17-2005, 05:11 AM
I have a OpenGLSL shader which access a depth texture and then performs some calculations. However, additionally I would like to have a mipmapped version of the depth texture and this is where things go wrong.

What works..
1) I can set up a depth texture
2) I can access the depth texture in my shader (with mipmapping turned off).
3) I can mipmap my depth texture (I know it works because I can use glGetTexImage() and pull the mipmapped versions off the card to main memory).

What doesn't
1) Once I turn on mipmapping I can no longer access it correctly in my shader.

Code snippets...

To set up the depth texture:

glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE);
glTexParameteri(GL_TEXTURE_2D, GL_DEPTH_TEXTURE_MODE_ARB, GL_LUMINANCE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE_ARB, GL_NONE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP );
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
glCopyTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT32_ARB , x, y, width, height, 0);To mipmap the depth texture:

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 2);
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE);
glCopyTexImage2D(GL_TEXTURE_2D, 1, GL_DEPTH_COMPONENT32_ARB , x, y, (int)baseWidth/2, (int)baseHeight/2, 0);
glCopyTexImage2D(GL_TEXTURE_2D, 2, GL_DEPTH_COMPONENT32_ARB , x, y, (int)baseWidth/4, (int)baseHeight/4, 0);
glCopyTexImage2D(GL_TEXTURE_2D, 3, GL_DEPTH_COMPONENT32_ARB , x, y, (int)baseWidth/8, (int)baseHeight/8, 0);each pass (the mipmaps are generated automatically after this call):

glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, x,y, width, height);quick and easy GLSL shader to test it out:

uniform sampler2D DepthImage;
vec4 fragDepth = texture2D(DepthImage, gl_TexCoord[0].st, 0.00);
if (fragDepth.r == 1.0)
gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);
else
gl_FragColor = vec4(0.0, 1.0, 0.0, 1.0);When I have mipmapping turned off I get green where objects are located and red everywhere else (as I should). However, once I turn on mipmapping all I get back is red everywhere (in every channel).

Anyone have any ideas?

P.S. I know I know, mipmapping a depth texture will not give me correct depth information. I don't need the "correct" values.

dorbie
06-17-2005, 08:17 AM
I think your fragment code has a typo.

PickleWorld
06-17-2005, 08:45 AM
Yep it did, I have fixed it now. However that is not the problem (the typo occurred moving the code to these boards)

The code works fine up until the point I mipmap the depth texture.

PickleWorld
06-20-2005, 06:52 AM
Update:

When mipmapping is turned on and I move the camera very close to the object I do get green. Which would seem to indicate that it works at least on some level and that access to the base lvl texture may still be correct.

However, even when I use a large negative bias during the shader texture lookup I still see the same behaviour.

Overmind
06-20-2005, 09:18 AM
Are you sure the mipmaps are generated correctly? Try manually putting some known values into the mipmaps so you can see if it's really the lookup that's not working...

I know, there is not really much that you can do wrong with automatic mipmap generation, but you never know, and it might help narrow down the bug ;)

zeckensack
06-20-2005, 10:33 AM
It's very bad practice to check equality of floating point data.

Try this instead:
if (fragDepth.r >= 0.5)

PickleWorld
06-21-2005, 05:07 AM
Overmind: That is a good idea and if I get time it is something I will test out.

Zeckensack: You are normally correct. However, with the non-linear nature of the depth buffer in mind, anything further that a few untis from the near clipping plane will have a depth value of around 0.95-0.99. Thus checking for > 0.5 will not be affective at all. I use the equality check because 1.0 is the clear value and *should* have been set exactly.. if it has been modified in any fashion then I want the check to fail.

YengaMatic
06-22-2005, 02:04 AM
Have you tried to autogenerate mipmaps? look for sgis_generate_mipmap extension. It generates mipmap levels automatically when you render to texture.
You could then access each mipmap in GLSL with an overloaded version of texture sample function.

PickleWorld
06-22-2005, 04:58 AM
Thanks YengaMatic but that is what I am doing with the call...

glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE);I assume the SGI extension was promoted to core functionality and is now just GL_GENERATE_MIPMAP.