View Full Version : Writing a texture to a stencil buffer

Ross Oliver
03-03-2010, 12:09 PM

I have a black and white texture and want to set the value in the stencil buffer corresponding to the white pixels. So far I have tried using blending to make the black portion of a textured quad face transparent before rendering, but this appears to set all the stencil values to 1, not just the non-transparent white ones. I thought I could use glColorMask to only render white pixels, but this function doesn't work as I expected - is there a function that would cull the black pixels upon rendering?

The code I have is as follows:

glBindTexture( GL_TEXTURE_2D, stencil_tex );
glBlendFunc( GL_ONE, GL_ONE );
glStencilFunc( GL_ALWAYS, 1, 1 );

glBegin( GL_QUADS );
glTexCoord2f( 0.0f, 0.0f ); glVertex3f( -1.7f, -1.7f, 1.7f );
glTexCoord2f( 1.0f, 0.0f ); glVertex3f( 1.7, -1.7f, 1.7f );
glTexCoord2f( 1.0f, 1.0f ); glVertex3f( 1.7f, 1.7f, 1.7f );
glTexCoord2f( 0.0f, 1.0f ); glVertex3f( -1.7f, 1.7f, 1.7f );

The effect I am trying to achieve is rendering a black and white texture onto the face of a quad, then for everything else that is rendered on top of the textured quad I want only the bits directly over the non-white part of the texture to render. My thinking is if I can put the white portion of the texture into the stencil buffer then use that to cull pixels over the white values of the texture.

Thanks for your time,


03-03-2010, 12:39 PM
If instead of black and white you have alpha values, alpha test would do exactly what you want.
A fragment program in GLSL can discard based on whatever formula you come up with, but of course that would be like killing a bee with megatons of TNT.

An what about simply drawing the textured pattern last ? With additive blending (as you have currently) white will stay white, black will not change whatever what already written. If you can disable depth test, it is a sure win.

Ross Oliver
03-03-2010, 12:50 PM
I've managed to get it working with your alpha test suggestion:

glAlphaFunc( GL_NOTEQUAL, 0.0 );

Thanks for the help!