2011-10-27 190 views
2

我想使用FBO渲染紋理,然後顯示紋理,但我得到的只是一個黑色的矩形。我的代碼是:OpenGL渲染紋理(FBO)不起作用

初始化:

#include <GL/glew.h> 
#include <GL/gl.h> 
#include <GL/glext.h> 
#include <assert.h> 

// ... 
GLuint fbo_, rbo_, tex_; 

glGenFramebuffers(1, &fbo_); 
glBindFramebuffer(GL_FRAMEBUFFER, fbo_); 

glGenRenderbuffers(1, &rbo_); 
glBindRenderbuffer(GL_RENDERBUFFER, rbo_); 
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, width_, height_); 
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rbo_); 

glGenTextures(1, &tex_); 
glBindTexture(GL_TEXTURE_2D, tex_); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, width_, height_, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); 
glGenerateMipmap(GL_TEXTURE_2D); 
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex_, 0); 

assert(glCheckFramebufferStatus(GL_FRAMEBUFFER) == GL_FRAMEBUFFER_COMPLETE); 

glBindFramebuffer(GL_FRAMEBUFFER, 0); 

渲染到FBO:

glPushAttrib(GL_VIEWPORT_BIT); 
glViewport(0, 0, width_, height_); 
glBindFramebuffer(GL_FRAMEBUFFER, fbo_); 
//draw stuff 
glPopAttrib(); 
glBindFramebuffer(GL_FRAMEBUFFER, 0); 

使用紋理(這個問題可能是在上面的代碼,因爲如果我只是用一些靜態紋理,下面的代碼工作):

glActiveTexture(GL_TEXTURE0); 
glBindTexture(GL_TEXTURE_2D, tex_); 

glBegin(GL_QUADS); 
glTexCoord2f(0, 0); 
glVertex3f(x_, y_, 0); 
glTexCoord2f(width_, 0); 
glVertex3f(x_ + width_, y_, 0); 
glTexCoord2f(width_, height_); 
glVertex3f(x_ + width_, y_ + height_, 0); 
glTexCoord2f(0, height_); 
glVertex3f(x_, y_ + height_, 0); 
glEnd(); 

你能幫我發現問題嗎?

+0

我想我在我的最後一段代碼(紋理座標相對於x_,y_而不是0,0)中也有一個錯誤。我將更新代碼以反映我的更改。 –

回答

4

如果您要依賴默認紋理環境,請確保您附加的紋理爲complete

+0

感謝您的提示,我添加了mipmap生成代碼。不幸的是,現在不是一個白色的矩形,而是一個黑色的矩形。有任何想法嗎? –

+0

由於您使用了雙線性過濾,因此您不需要mipmap。無論如何,仍然空的(或未定義的)紋理圖像上的'glGenerateMipmap'是垃圾。刪除'glGenerateMipmap'(或者如果你真的需要trialinear過濾,則在渲染到紋理後執行),但保留其他'glTexParameteri'調用。 –

+0

感謝您指出這一點! –

1

我有同樣的問題,並使用genpfault的建議來創建一個完整的紋理。不幸的是,我沒有足夠的聲望來添加評論,所以我只是在這裏添加了這個答案。不過,下面的代碼可以節省您的時間:

// generate full viewport texture 
    glGenTextures(1, &fb_tex); 
    glBindTexture(GL_TEXTURE_2D, fb_tex); 
    // IMPORTANT: texture must be COMPLETE (mipmaps must be specified.. 
    // or the following parameters can be used if there are none) 
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_BASE_LEVEL, 0); 
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0); 

    glTexImage2D(
     GL_TEXTURE_2D, 
     0, 
     GL_RGBA, 
     width, 
     height, 
     0, 
     GL_RGBA, 
     GL_UNSIGNED_BYTE, 
     NULL 
     ); 

我在原來的代碼唯一改變的是兩次與glTexParameteri添加兩行。這些參數可以根據您想要/已經使用的mipmap的數量進行更改。