OpenGL中的Frame Buffer、Depth Buffer、Color Buffer、Stencil Buffer
Frame Buffer
Frame Buffer: 是一块buffer(即内存),存储了一帧的buffer数据。
从数据结构的角度来看,此处的Frame Buffer并不是一个真正意义上的buffer,其存了一些指针,分别指向Depth Buffer、Color Buffer、Stencil Buffer、Texture、RBO(Render Buffer Object)等。
Wiki中的解释:https://www.khronos.org/opengl/wiki/Framebuffer_Object
Framebuffer objects are a collection of attachments. To help explain lets explicitly define certain terminology.
vulkan中image, surface,framebuffer是什么?它们之间有什么样的联系?
在Vulkan中,image
、surface
和framebuffer
是图形渲染过程中重要的概念,它们各自扮演着不同的角色,并且相互之间存在紧密的联系。
-
Image:
image
是一个二维数组,用于存储图像数据。它可以表示纹理、渲染目标或其他图形资源。在Vulkan中,图像通常用于存储渲染的输出结果,或者在渲染过程中作为纹理或采样器使用。image
具有特定的格式和大小,可以包含颜色、深度或模板等信息。
-
Surface:
surface
是窗口或显示设备的抽象表示。它提供了Vulkan与窗口系统或显示硬件之间的接口,使得Vulkan可以将渲染结果输出到屏幕上。surface
不是直接用于渲染的,但它与窗口系统或显示设备相关联,是创建交换链(swap chain)的基础。交换链是一系列用于双缓冲或多缓冲的图像,用于在渲染过程中存储和展示图像。
-
Framebuffer:
framebuffer
是一个用来表示一组图像的对象,这些图像是图形管线进行渲染的目标。它包含了渲染过程所需的所有附件,如颜色附件、深度附件等。framebuffer
通常与交换链中的图像相关联。在渲染过程中,图形管线会将结果渲染到与当前帧缓冲区关联的图像上。
它们之间的联系:
surface
提供了与窗口系统或显示设备的接口,使得可以创建交换链。交换链中的每个图像都是一个image
。framebuffer
则是对这些image
的封装,用于在图形管线中进行渲染。当进行渲染时,图形管线会将结果输出到与当前帧缓冲区关联的image
上。- 因此,
surface
、image
和framebuffer
共同构成了Vulkan中从窗口系统到图形渲染输出的一整套流程。通过它们之间的协同工作,Vulkan能够高效地将渲染结果输出到屏幕上。
总的来说,image
、surface
和framebuffer
在Vulkan中各自扮演着不同的角色,但它们之间又存在紧密的联系,共同构成了Vulkan图形渲染的核心部分。
- Image
- image指一个像素的2D阵列,这些像素有特殊的格式。
- 注:可以把image简单理解为贴图:VkImage 除了 VkDeviceMemory 还需要 VkImageView 和 VkImageSampler,VkImageView 相当于一个 accessor,具体操作都需要操作这个accessor,所以基本上VkImage和VkImageView就是个强绑定关系。VkImageSampler是采样器,anisotropy、mips等在这里设置,可以多个图共享一个采样器。
- 这在vulkan代码里得到了证实,gfx::image里会有mip_level、if_subsampled这样的设置,vulkan::image里包了gfx::image。
- 注:不理解?同时image也是swapchain里交换的内容????没错,就是这样。
- Layered Image
- layered image指有特殊尺寸和格式的一系列的image。
- Texture
- texture代表了包含若干以上定义的images的对象。
- Renderbuffer
- renderbuffer指代表了包含单个image的对象,其不能被shaders直接访问,唯一能访问renderbuffer的方式除了创建它,就只有把renderbuffer放进FBO(frame buffer object)里。
- Attach
- 用来连接objects,这个概念在OpenGL无处不在,但主要用在FBO中。Attachment和binding是不同的,binding用来描述objects bind在context中,attachment用来描述objects之间互相attach。
Framebuffer Object Structure
作为标准OpenGL对象,FBO具有通常的glGenFramebuffers和glDeleteFramebuffers功能。正如预期的那样,它还具有通常的glBindFramebuffer函数,用于将FBO绑定到上下文。
此对象的目标参数可以采用以下三个值之一:GL_FRAMEBUFFER、GL_READ_FRAMEBUFFER或GL_DRAW_FRAMEBUFFER。最后两个允许您绑定FBO,以便读取命令(glReadPixels等)和写入命令(所有渲染命令)可以发生在两个不同的帧缓冲区上。GL_FRAMEBUFFER绑定目标仅将读取和写入设置为同一FBO。
默认帧缓冲区的缓冲区名称如GL_FRONT、GL_BACK、GL_AUXi、GL_ACCUM等。FBO不使用这些。
相反,FBO有一组不同的image名称。每个FBO image表示一个附着点(attachment),即FBO中可以附着image的位置。FBO具有以下连接点(attachment):
GL_COLOR_ATTACHMENTi:这些是取决于实现的连接点数量。您可以查询GL_MAX_COLOR_ATTACHMENTS以确定实现将允许的颜色附件的数量。此项的最小值为8,因此保证您至少能够拥有0-7个颜色附件。这些附着点只能使用颜色可渲染格式(color-renderable formats)将image绑定到这些附着点。所有压缩图像格式都不可进行颜色渲染,因此无法附加到FBO。
GL_DEPTH_ATTACHMENT:此附着点只能绑定具有深度格式的图像。附着的图像将成为FBO的深度缓冲区。请注意,如果未附加深度图像,则在渲染到此FBO时将禁用“深度测试”。
GL_STENCIL_ATTACHMENT:此附着点只能绑定具有模具格式的图像。附着的图像将成为FBO的模具缓冲区。
GL_DEPTH_STENCIL_ATTACHMENT:这是“深度和模具”的简写。附加的图像同时成为深度缓冲区和模具缓冲区。
注意:如果使用GL_DEPTH_STENCIL_ATTACHMENT,则应为要附加的纹理或渲染缓冲区使用压缩深度模具内部格式。
Depth Buffer
Depth Buffer:深度缓存区。
工作原理如下:
- 在图形渲染过程中,对于每个像素,渲染管线会计算出其在观察空间中的深度值。
- 当一个像素需要进行渲染时,会将其深度值与深度缓冲区中对应像素的深度值进行比较。
- 如果当前像素的深度值小于深度缓冲区中的深度值,说明当前像素位于前面,它将被认为是可见的,并将其深度值写入深度缓冲区。
- 如果当前像素的深度值大于深度缓冲区中的深度值,说明当前像素被前面的物体遮挡,它将被认为是不可见的,深度缓冲区中的深度值不做更新。
深度缓冲区的主要作用是进行深度测试(Depth Test),即通过比较像素的深度值来确定像素的可见性。它可以有效解决遮挡关系,避免对被遮挡像素进行不必要的渲染,从而提高图形渲染的效率。
Color Buffer
Color Buffer:颜色缓存区
OpenGL中的颜色缓冲区(Color Buffer)是一个用于存储渲染结果的内存区域。当我们通过OpenGL渲染场景时,渲染的结果会被存储到颜色缓冲区中。通常情况下,颜色缓冲区是一个二维数组,每个元素代表屏幕上的一个像素点,存储着该像素点的颜色信息。
在OpenGL中,颜色缓冲区可以包括一个或多个颜色缓冲区。例如,我们可以创建一个双缓冲区(Double Buffer),其中包括前缓冲区和后缓冲区,用于实现平滑的动画效果。
当我们完成一次渲染后,OpenGL会将颜色缓冲区中的像素值发送到帧缓冲区(Frame Buffer),并在屏幕上显示出来。我们也可以使用OpenGL的一些API函数对颜色缓冲区进行读写操作,例如修改像素的颜色、清空颜色缓冲区等。
Stencil Buffer
Stencil Buffer:模板缓存区
为屏幕上的每一个像素保存一个8位的无符号整数,跟模板缓冲区进行比较并决定是否保留像素称为模板测试
模板测试发生在透明度测试之后,深度测试之前
模板缓冲区默认值为0(测试得到),并且我推测模板缓冲区每帧执行完会进行一个刷新
要加模板测试,就在Shader的Pass开头写Stencil{ }结构体。如果每个Pass都用,则可以提到外面。
参考连接:
Stencil Buffer:https://www.cnblogs.com/FlyingZiming/p/12937642.html
Stencil Buffer:https://www.jianshu.com/p/f79f0da90103
Depth Buffer:https://zhuanlan.zhihu.com/p/638266570
Color Buffer: https://www.cnblogs.com/errorman/p/17222536.html
Frame Buffer: https://blog.csdn.net/alexhu2010q/article/details/101436270
OpenGL Frame Buffer: https://zhuanlan.zhihu.com/p/631073748
https://blog.csdn.net/alexhu2010q/article/details/101436270(待整理)