应用程序使用单缓冲绘图时可能会存在图像闪烁的问题。 这是因为生成的图像不是一下子被绘制出来的,而是按照从左到右,由上而下逐像素地绘制而成的。最终图像不是在瞬间显示给用户,而是通过一步一步生成的,这会导致渲染的结果很不真实。为了规避这些问题,我们应用双缓冲渲染窗口应用程序。前缓冲保存着最终输出的图像,它会在屏幕上显示;而所有的的渲染指令都会在后缓冲上绘制。当所有的渲染指令执行完毕后,我们交换(Swap)前缓冲和后缓冲,这样图像就立即呈显出来,之前提到的不真实感就消除了。
所以就有了双缓存区,形如下图
我们之前说的深度测试、模板测试、混合,最后通过的结果都写入到后帧缓冲,然后通过函数glfwSwapBuffers(window);
,立马从后缓冲交换到前缓存,然后显示到屏幕上。
但是有时候只有前、后2个缓存区是不能达到我们的效果的,比如下面的场景
只要一个后缓冲区(一般前缓冲区就是直接存放后缓冲区的内容)就不够用了,因为他们都有一个共同的特点,他们最终的颜色都是通过周边的像素的颜色计算出来的,这样的话就会对存放在后缓冲区的数据造成污染,怎么理解呢,举个例子:
只要一个后缓冲区的情况:
1
1
1
1
,你的算法是后面的数是左右2个数的和,那么期望的结果是 1
2
2
1
(忽略左右缺失的元素),然而遗憾的是最后的结果却是1
2
3
1
你当然会问这是为什么,那是因为:
- 在算序号为
1
(下标从0开始)的时候,0
号元素是1
,2
号元素也是1
,所以结果是2
, - 但是在算序号为
2
的元素的时候,1
号元素已经变成了2
了,所以2
号元素 =2
+1
=3
,最后给到前缓冲区的就是1
2
3
1
,这就是数据被污染了。
新加一个帧缓冲:
上面说到造成数据不对的原因是被污染了,如果我们新加一个帧缓冲就可以解决这个问题了,把数据1
1
1
1
写到新加的缓冲中,当在后缓冲区计算的时候,此时要从新加的缓冲区
去取值,把计算后的是写入到后缓冲区
,最后把后缓冲区写入的值1
2
2
1
送到前缓冲区
完成渲染。
相信到这里你应该知道为什么要引入一个新的缓冲区了。