混合是源和目标像素进行的,抖动是在混合后进行的,上面的操作数据都还是放置在临时缓存区中,写入掩码和逻辑操作后才是最终的将结果像素和目标像素进行逻辑写入默认是GL_COPY。深度缓存和模板缓存的写入也受到掩码和操作函数控制,stencil测试公式是:stencil ref &mask op stencil value &mask,sicssor测试更快;alpha测试,深度测试,默认都是禁用的,启用后测试结果受到自己指定的测试比较函数控制。
现代可编程渲染管道中,后期的硬件裁剪测试,alpha测试,模板测试,深度测试(遮挡查询和条件渲染), 混合,抖动,写入掩码和写入逻辑操作,都可以在fragment shader中设置。
透明效果,抗锯齿效果(在多重采样处理边缘 alpha处理也需要),都是要依赖混合的。
累积缓存的这些图像操作(单次或多次绘制物体然后组合结果(时间上的),单次对一副图像多次附近周围采样组合结果(空间上)效果:全景抗锯齿被alpha和多重采样覆盖代替,其它操作被OGL 3.0引入的帧缓冲区对象中的浮点像素格式很容易实现了。
一、帧缓冲区基本概念
帧缓存区包括:
1.颜色缓冲区,有前后台缓存区和辅助缓存区,OGL3.0以上为浮点颜色缓存区,取消了累积缓冲区的支持。
2.模板缓冲区。
3.深度缓冲区。
颜色模板深度缓存区像素位置是一一对应的。
各种缓冲区的成分位数:
GLint rBits, gBits, bBits, aBits;
glGetIntegerv(GL_RED_BITS, &rBits);//8
glGetIntegerv(GL_GREEN_BITS, &gBits);//8
glGetIntegerv(GL_BLUE_BITS, &bBits);//8
glGetIntegerv(GL_ALPHA_BITS, &aBits);//8
GLint iBits, dBits, sBits;
//颜色缓存区中的颜色索引数据, Intel是3.1版本是32; AMD是4.2版本是0,颜色索引数据取消了
glGetIntegerv(GL_INDEX_BITS, &iBits);
glGetIntegerv(GL_DEPTH_BITS, &dBits);//24
glGetIntegerv(GL_STENCIL_BITS, &sBits);//8
// Intel是3.1版本; 0 AMD是4.2版本OGL实现都废弃了ACCUM累积缓存
// 因为OGL 3.0引入了支持本地浮点值的颜色缓存区,ACCUM缓存相关的事情很容易在浮点缓冲区上实现。
GLint acRBits, acGBits, acBBits, acABits;
glGetIntegerv(GL_ACCUM_RED_BITS, &acRBits);//0
glGetIntegerv(GL_ACCUM_GREEN_BITS, &acGBits);//0
glGetIntegerv(GL_ACCUM_BLUE_BITS, &acBBits);//0
glGetIntegerv(GL_ACCUM_ALPHA_BITS, &acABits);//0
颜色缓冲:
// 当前OGL是否立体渲染(3D渲染)屏幕;Intel是3.1版本; 0 AMD是4.2版本都不支持
// 立体渲染, 也就是前-左,前-右,后-左,后-右缓存区; VR中应该就是这样使用。
// 但每个OGL实现都必须支持前-左缓存区。GL_FRONT_LEFT
GLint nStereoSupport;
glGetIntegerv(GL_STEREO, &nStereoSupport); // Win7 OGL 3.1不支持
// 双缓存交换链:前台缓存,后台缓存;还是单缓存只有前台缓存;Intel是3.1版本; 0 AMD是4.2版本启用了都支持
GLint nDoubleFrameBufferSupport;
glGetIntegerv(GL_DOUBLEBUFFER, &nDoubleFrameBufferSupport);// Win7 OGL 3.1支持
// 辅助缓存;Intel是3.1版本不支持; AMD是4.2版本支持4个辅助颜色缓存
// 辅助缓存区,OGL并没有指定这类缓存的特定用途,因此可以用来保存自己需要的帧缓存信息
// 例如从后台缓存区glCopyPixels到这里,下次渲染从这里拿到数据,避免重绘。
GLint nAluColorBuffer;
glGetIntegerv(GL_AUX_BUFFERS, &nAluColorBuffer);// Win7 OGL 3.1不支持,只有0个颜色辅助缓存
深度缓冲:
存储的是NDC坐标规范化后(基于观察坐标系的距离),OGL z值在[-1,1], DX在[0,1]; 然后在视口变换期间,将该z值用默认的glDepthRange函数将z值缩放到[0,1]之间,当然也可以用glDepthRange指定需要缩放到的深度值。
OGL会将变换后的深度值缓存起来,后面光栅化,FragmentShader后,经过了depth Test 可以指定比较函数,那么该位置的深度值就会和当前的深度缓存值比较,通过了则更新该位置的深度值。
模板缓冲:
方便实现规则或不规则形状的遮罩效果。
一般需要二次绘制,设置模板缓存初始值和写入策略,第一次绘制时候将指定形状(一般是图像指定)的数据写入模板缓存对应位置,后面再次渲染场景物体时候根据设置的模板比较函数,确定是否写入到后台缓存中,并确定是否更新模板缓存。
累积缓冲:
累积缓存也用于存储RGBA颜色数据(不能存储颜色索引模式下的索引值),不能直接写入,而是从颜色缓存区拷贝到累积缓存区或者从累积缓存区拷贝到颜色缓存区(以矩形块为单位操作的);通常用于把一系列的图像合成一副图像,经典应用是对图像进行超量采样(多重采样时超量采样的特例,多重多边缘采样,超量是对整副图像采样),然后对样本求平均值,并且将结果写入到颜色缓冲区实现场景抗锯齿效果。也可以实现运动模糊,和模拟照片景深效果。OGL3.0以上为浮点颜色缓存区实现这些效果,取消了累积缓冲区或辅助缓存区的支持。