4

我想这是有可能的,因为这样:

glBindFramebuffer(GL_READ_FRAMEBUFFER_APPLE, _multisampleFramebuffer);
glBindFramebuffer(GL_DRAW_FRAMEBUFFER_APPLE, _framebuffer);
glResolveMultisampleFramebufferAPPLE();

正是这样做的,并且最重要的是解决了多重采样。但是,它是一个 Apple 扩展,我想知道是否有类似的东西可以将所有逻辑缓冲区从一个帧缓冲区复制到另一个帧缓冲区,并且在 vanilla 实现中不执行多重采样部分。GL_READ_FRAMEBUFFER似乎不是一个有效的目标,所以我猜没有直接的方法?解决方法如何?

编辑:似乎可以glCopyImageSubData在 OpenGL 4 中使用,不幸的是,我在 iPhone 上使用的是 OpenGL ES 2.0,这似乎缺少该功能。还有什么办法吗?

4

3 回答 3

3

glBlitFramebuffer 完成您正在寻找的内容。此外,您可以在不需要两个帧缓冲区的情况下将一个 TEXTURE 粘贴到另一个上。我不确定 OpenGL ES 2.0 是否可以使用一个 fbo,但可以轻松修改以下代码以使用两个 fbo。您只需要将不同的纹理附加到不同的帧缓冲区附件。glBlitFramebuffer 功能甚至可以管理抗锯齿应用程序的下采样/上采样!这是它的用法示例:

// bind fbo as read / draw fbo
glBindFramebuffer(GL_DRAW_FRAMEBUFFER,m_fbo);
glBindFramebuffer(GL_READ_FRAMEBUFFER, m_fbo);

// bind source texture to color attachment
glBindTexture(GL_TEXTURE_2D,m_textureHandle0);
glFramebufferTexture2D(GL_TEXTURE_2D, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, m_textureHandle0, 0);
glDrawBuffer(GL_COLOR_ATTACHMENT0);

// bind destination texture to another color attachment
glBindTexture(GL_TEXTURE_2D,m_textureHandle1);
glFramebufferTexture2D(GL_TEXTURE_2D, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, m_textureHandle1, 0);
glReadBuffer(GL_COLOR_ATTACHMENT1);


// specify source, destination drawing (sub)rectangles. 
glBlitFramebuffer(from.left(),from.top(), from.width(), from.height(),
                  to.left(),to.top(), to.width(), to.height(), GL_COLOR_BUFFER_BIT, GL_NEAREST);

// release state
glBindTexture(GL_TEXTURE_2D,0);
glBindFramebuffer(GL_READ_FRAMEBUFFER, 0);
glBindFramebuffer(GL_DRAW_FRAMEBUFFER,0);
于 2013-03-09T07:58:19.710 回答
2

在 OpenGL 4 中测试,OpenGL ES 2.0 不支持 glBlitFramebuffer。

我已经修复了上一个答案中的错误,并概括为一个可以支持两个帧缓冲区的函数:

// Assumes the two textures are the same dimensions
void copyFrameBufferTexture(int width, int height, int fboIn, int textureIn, int fboOut, int textureOut)
{
    // Bind input FBO + texture to a color attachment
    glBindFramebuffer(GL_READ_FRAMEBUFFER, fboIn);
    glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, textureIn, 0);
    glReadBuffer(GL_COLOR_ATTACHMENT0);

    // Bind destination FBO + texture to another color attachment
    glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fboOut);
    glFramebufferTexture2D(GL_DRAW_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, textureOut, 0);
    glDrawBuffer(GL_COLOR_ATTACHMENT1);

    // specify source, destination drawing (sub)rectangles.
    glBlitFramebuffer(0, 0, width, height,
                        0, 0, width, height,
                        GL_COLOR_BUFFER_BIT, GL_NEAREST);

    // unbind the color attachments
    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, 0, 0);
    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0);
}
于 2015-07-29T00:54:50.880 回答
0

你可以直接用 OpenGL ES 2.0 来做,而且好像也没有扩展。

我不确定您要实现什么,但总的来说,只需删除您已完成屏幕外渲染的 FBO 的附件。然后绑定默认的 FBO 以便能够在屏幕上绘制,在这里您可以简单地绘制一个四边形,它带有一个填充屏幕的正交相机和一个将屏幕外生成的纹理作为输入的着色器。如果您使用多采样纹理,您也可以进行解析。

glBindFramebuffer(GL_FRAMEBUFFER, off_screenFBO);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0);

glBindFramebuffer(GL_FRAMEBUFFER, 0); // Default FBO, on iOS it is 1 if I am correct

// Set the viewport at the size of screen
// Use your compositing shader (it doesn't have to manage any transform)
// Active and bind your textures
// Sent textures uniforms
// Draw your quad

以下是着色器的示例:

// Vertex
attribute vec2 in_position2D;
attribute vec2 in_texCoord0;
varying lowp vec2 v_texCoord0;
void main()
{
   v_texCoord0 = in_texCoord0;
   gl_Position = vec4(in_position2D, 0.0, 1.0);
}

// Fragment
uniform sampler2D u_texture0;
varying lowp vec2 v_texCoord0;

void main()
{
    gl_FragColor =  texture2D(u_texture0, v_texCoord0);
}
于 2017-12-08T22:30:41.060 回答