9

我有一个带有颜色和深度附件的 FBO 对象,我渲染到它然后从使用中读取glReadPixels(),我正在尝试向它添加多重采样支持。
而不是glRenderbufferStorage()我要求glRenderbufferStorageMultisampleEXT()颜色附件和深度附件。帧缓冲区对象似乎已成功创建并报告为完整。
渲染后,我尝试使用glReadPixels(). 当样本数为 0 时,即多重采样禁用它可以完美地工作,我得到了我想要的图像。当我将样本数设置为其他值(例如 4)时,帧缓冲区仍然可以正常构建,但glReadPixels()失败并出现INVALID_OPERATION

有人知道这里可能出了什么问题吗?

编辑: glReadPixels 的代码:

glReadPixels(0, 0, width, height, GL_RGBA, GL_UNSIGNED_BYTE, ptr);

其中 ptr 指向宽度*高度单位的数组。

4

2 回答 2

29

我认为您无法使用 glReadPixels() 从多采样 FBO 中读取数据。您需要从多重采样 FBO 到普通 FBO,绑定普通 FBO,然后从普通 FBO 读取像素。

像这样的东西:

// Bind the multisampled FBO for reading
glBindFramebufferEXT(GL_READ_FRAMEBUFFER_EXT, my_multisample_fbo);
// Bind the normal FBO for drawing
glBindFramebufferEXT(GL_DRAW_FRAMEBUFFER_EXT, my_fbo);
// Blit the multisampled FBO to the normal FBO
glBlitFramebufferEXT(0, 0, width, height, 0, 0, width, height, GL_COLOR_BUFFER_BIT, GL_NEAREST);
//Bind the normal FBO for reading
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, my_fbo);
// Read the pixels!
glReadPixels(0, 0, width, height, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
于 2009-04-29T18:03:51.663 回答
1

您不能直接使用 glReadPixels 读取多重采样缓冲区,因为它会引发 GL_INVALID_OPERATION 错误。您需要 blit 到另一个表面,以便 GPU 可以进行下采样。您可以对后台缓冲区进行 blit,但存在“像素所有者船舶测试”的问题。最好再做一个FBO。假设您制作了另一个 FBO,现在您想要 blit。这需要 GL_EXT_framebuffer_blit。通常,当您的驱动程序支持 GL_EXT_framebuffer_multisample 时,它​​也支持 GL_EXT_framebuffer_blit,例如 nVidia Geforce 8 系列。

 //Bind the MS FBO
 glBindFramebufferEXT(GL_READ_FRAMEBUFFER_EXT, multisample_fboID);
 //Bind the standard FBO
 glBindFramebufferEXT(GL_DRAW_FRAMEBUFFER_EXT, fboID);
 //Let's say I want to copy the entire surface
 //Let's say I only want to copy the color buffer only
 //Let's say I don't need the GPU to do filtering since both surfaces have the same dimension
 glBlitFramebufferEXT(0, 0, width, height, 0, 0, width, height, GL_COLOR_BUFFER_BIT, GL_NEAREST);
 //--------------------
 //Bind the standard FBO for reading
 glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fboID);
 glReadPixels(0, 0, width, height, GL_BGRA, GL_UNSIGNED_BYTE, pixels);

来源:GL EXT 帧缓冲多样本

于 2009-05-04T11:53:17.097 回答