在现代 OpenGL 中,我正在绘制一系列相邻的 Sprite ,为每个 Sprite 使用带纹理的四边形(如笔触)。在不累积 alpha 值的情况下,我可以使用什么技术来绘制 Sprite ?
为了清楚起见,让我举个例子。
其中结果的 alpha 值是源和目标的 alpha 的最大值,就好像它们是同一可视层的一部分。
我想这涉及到我的 blend function . 目前是:
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
我可以使用哪种混合函数或其他技术来获得所需的结果?
最佳答案
(Ab)使用模板缓冲区:
- 清除模板缓冲区为 0xff
- 对于每个圆圈,只写入(和混合)模板缓冲区为 0xff 的颜色和模板缓冲区。如果模板和深度测试成功,则将片段的模板值设置为零。
通过这种方式,您只能一次写入(和混合)一个颜色像素,直到您再次清除模板缓冲区。
示例:
#include <GL/glut.h>
void quad()
{
glBegin( GL_QUADS );
glVertex2i( -1, -1 );
glVertex2i( 1, -1 );
glVertex2i( 1, 1 );
glVertex2i( -1, 1 );
glEnd();
}
void display()
{
glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
glMatrixMode( GL_PROJECTION );
glLoadIdentity();
glOrtho( -2, 2, -2, 2, -1, 1 );
glMatrixMode( GL_MODELVIEW );
glLoadIdentity();
// clear stencil buffer to all 1s
glClearStencil( 0xff );
glClear( GL_STENCIL_BUFFER_BIT );
// turn on stencil testing & make sure we don't mask out any bits
glEnable( GL_STENCIL_TEST );
glStencilMask( 0xff );
// only allow fragments through to the color/depth buffers if
// the stencil buffer at that point is 0xff
glStencilFunc( GL_EQUAL, 0xff, 0xff );
// if the stencil/depth tests succeed for a fragment,
// zero out the stencil buffer at that point;
// that way you can only write to a color buffer pixel once
glStencilOp( GL_KEEP, GL_KEEP, GL_ZERO );
glEnable( GL_BLEND );
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glPushMatrix();
glTranslatef( -0.5, -0.5, 0 );
glColor4ub( 255, 0, 0, 128 );
quad();
glPopMatrix();
glPushMatrix();
glTranslatef( 0.5, 0.5, 0 );
glColor4ub( 255, 0, 0, 128 );
quad();
glPopMatrix();
glutSwapBuffers();
}
int main( int argc, char **argv )
{
glutInit( &argc, argv );
glutInitDisplayMode( GLUT_RGBA | GLUT_DOUBLE | GLUT_STENCIL );
glutInitWindowSize( 600, 600 );
glutCreateWindow( "GLUT" );
glutDisplayFunc( display );
glutMainLoop();
return 0;
}
关于c++ - 为 Sprite 混合设置 alpha 上限,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31613675/