在OpenGL ES(iPhone)中绘制到屏幕外渲染缓冲区

时间:2009-12-05 21:34:43

标签: iphone opengl-es

我正在尝试在iPhone上的OpenGL ES中创建一个屏幕外渲染缓冲区。我已经创建了这样的缓冲区:

        glGenFramebuffersOES(1, &offscreenFramebuffer);
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, offscreenFramebuffer);

    glGenRenderbuffersOES(1, &offscreenRenderbuffer);
    glBindRenderbufferOES(GL_RENDERBUFFER_OES, offscreenRenderbuffer);
    glFramebufferRenderbufferOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_RENDERBUFFER_OES, offscreenRenderbuffer);

但我对如何渲染存储感到困惑。 Apple的文档说使用EAGLContext renderBufferStorage:fromDrawable:方法,但这似乎只适用于一个渲染缓冲区(显示的主渲染缓冲区)。如果我使用普通的OpenGL函数glRenderBufferStorageOES,那么我似乎无法让它显示出来。这是代码:

        // this is in the initialization section:
    glRenderbufferStorageOES(GL_RENDERBUFFER_OES, GL_RGB8_OES, backingWidth, backingHeight);

    // and this is when I'm trying to draw to it and display it:
    glBindFramebufferOES(GL_FRAMEBUFFER_OES, offscreenFramebuffer);
    GLfloat vc[] = {
        0.0f, 0.0f, 0.0f,
        10.0f, 10.0f, 10.0f,
        0.0f, 0.0f, 0.0f,
        -10.0f, -10.0f, -10.0f,         
    };

    glLoadIdentity();
    glEnableClientState(GL_VERTEX_ARRAY);
    glVertexPointer(3, GL_FLOAT, 0, vc);
    glDrawArrays(GL_LINES, 0, 4);
    glDisableClientState(GL_VERTEX_ARRAY);

    glBindRenderbufferOES(GL_RENDERBUFFER_OES, offscreenRenderbuffer);
    [context presentRenderbuffer:GL_RENDERBUFFER_OES];

这样做,屏幕上不显示任何内容。但是,如果我将对“offscreen ... Buffer”的引用切换到使用renderBufferStorage方法创建的缓冲区,则它可以正常工作。

有什么建议吗?

3 个答案:

答案 0 :(得分:3)

由于您无法将presentRenderbuffer与屏幕外FBO一起使用,因此您应该使用glFramebufferTexture2DOES将其与纹理对象相关联,然后渲染纹理化的全屏四边形。

答案 1 :(得分:2)

@david好主意..你需要做的是@prideout所说的..创建一个纹理并渲染它...并且每次都使用四边形纹理。确保你只绘制一次纹理,就像你的情况一样持久。

- (void)setUpTextureBuffer 
{
 glGenFramebuffersOES(1, &texturebuffer); 
 glBindFramebufferOES(GL_FRAMEBUFFER_OES, texturebuffer);

 // create the texture
 glGenTextures(1, &canvastexture); 
 glBindTexture(GL_TEXTURE_2D, canvastexture); 
 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA,  512, 512, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); 
 glFramebufferTexture2DOES(GL_FRAMEBUFFER_OES, GL_COLOR_ATTACHMENT0_OES, GL_TEXTURE_2D, canvastexture, 0);

 GLenum status = glCheckFramebufferStatusOES(GL_FRAMEBUFFER_OES); 
 if(status != GL_FRAMEBUFFER_COMPLETE_OES) { 
  NSLog(@"failed to make complete framebuffer object %x", status);
 }

 glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
 glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );

 glClearColor(1.0, 1.0, 1.0, 1.0);
 glViewport(0, 0, 512, 512);
 glClear(GL_COLOR_BUFFER_BIT);
}



//setTargetToTexture() function

 glBindFramebufferOES(GL_FRAMEBUFFER_OES, tbuffer);
 glBindTexture(GL_TEXTURE_2D, allbrushes);
 glViewport(0, 0, 512, 512);

//reset pointers after finishing drawing to textures

 glViewport(0, 0, BWIDTH, BHEIGHT);
 glVertexPointer(2, GL_FLOAT, 0, canvas);   //canvas vertices
 glTexCoordPointer(2, GL_FLOAT, 0, texels);
 glBindTexture(GL_TEXTURE_2D, boundtexture);   //bind to the texture which is the special render target 
 glBindFramebufferOES(GL_FRAMEBUFFER_OES, fbuffer); //back to normal framebuffer

答案 2 :(得分:1)

您无法呈现正常的渲染缓冲区(使用glRenderbufferStorage创建),它始终在屏幕外。 presentRenderbuffer:只能用于使用renderbufferStorage:fromDrawable:创建的渲染缓冲区。如果您检查了presentRenderbuffer:的返回值,您应该注意到它失败了。

你想做什么?