OpenGL 模板测试 glStencilOp, glStencilFunc

下面来设置蒙板缓存和蒙板测试。
首先我们启用蒙板测试,这样就可以修改蒙板缓存中的值。

下面我们来解释蒙板测试函数的含义:
当你使用 glEnable (GL_STENCIL_TEST) 启用蒙板测试之后,蒙板函数用于确定一个颜色片段是应该丢弃还是保留(被绘制)。蒙板缓存区 中的值与参考值 ref 进行比较,比较标准是 func 所指定的比较函数。参考值和蒙板缓存区的值都可以与掩码进行为 AND 操作。蒙板测试的结果还导致蒙板缓 存区根据 glStencilOp 函数所指定的行为进行修改。

func 的参数值如下:

常量含义
GL_NEVER从不通过蒙板测试
GL_ALWAYS总是通过蒙板测试
GL_LESS只有参考值 <(蒙板缓存区的值 & mask) 时才通过
GL_LEQUAL只有参考值 <=(蒙板缓存区的值 & mask) 时才通过
GL_EQUAL只有参考值 =(蒙板缓存区的值 & mask) 时才通过
GL_GEQUAL只有参考值 >=(蒙板缓存区的值 & mask) 时才通过
GL_GREATER只有参考值 >(蒙板缓存区的值 & mask) 时才通过
GL_NOTEQUAL只有参考值!=(蒙板缓存区的值 & mask) 时才通过

接下来我们解释 glStencilOp 函数,它用来根据比较结果修改蒙板缓存区中的值,它的函数原形为:
void glStencilOp (GLenum sfail, GLenum zfail, GLenum zpass),各个参数的含义如下:

sfail
当蒙板测试失败时所执行的操作

zfail
当蒙板测试通过,深度测试失败时所执行的操作

zpass
当蒙板测试通过,深度测试通过时所执行的操作

具体的操作包括以下几种

常量描述
GL_KEEP保持当前的蒙板缓存区值
GL_ZERO把当前的蒙板缓存区值设为 0
GL_REPLACE用 glStencilFunc 函数所指定的参考值替换蒙板参数值
GL_INCR增加当前的蒙板缓存区值,但限制在允许的范围内
GL_DECR减少当前的蒙板缓存区值,但限制在允许的范围内
GL_INVERT将当前的蒙板缓存区值进行逐位的翻转

当完成了以上操作后我们绘制一个地面,当然现在你什么也看不到,它只是把覆盖地面的蒙板缓存区中的相应位置设为 1。

glEnable(GL_STENCIL_TEST);			// 启用蒙板缓存
glStencilFunc(GL_ALWAYS, 1, 1);			// 设置蒙板测试总是通过,参考值设为1,掩码值也设为1
glStencilOp(GL_KEEP, GL_KEEP, GL_REPLACE);	// 设置当深度测试不通过时,保留蒙板中的值不变。如果通过则使用参考值替换蒙板值
glDisable(GL_DEPTH_TEST);			// 禁用深度测试
DrawFloor();					// 绘制地面