2012-09-30 57 views
9

那麼,FBO的用法很廣泛,它有助於使複雜的效果更容易。我設置了FBO並對其進行繪製,然後渲染FBO紋理四元組,即使測試了簡單的屏幕處理顏色着色器也沒有任何問題。但是由於某種原因,我爲FBO呈現的所有內容都變得顛倒了。如果我渲染到股票屏幕FBO,一切都是正常的,我甚至不會對精靈進行任何旋轉。繪製到FBO - 精靈上下顛倒問題

FBO建立

typedef struct tex 
{ 
dim2i size; // int width, int height 
GLuint id; 
} tex; 

typedef struct fbo 
{ 
GLuint frame_buffer; 
tex buffer_tex; 
}fbo; 

void set_fbo(fbo* res, int width, int height) 
{ 
GLint tex_size; 
glGetIntegerv(GL_MAX_TEXTURE_SIZE, &tex_size); 
GLint render_buffer_size; 
glGetIntegerv(GL_MAX_RENDERBUFFER_SIZE, &render_buffer_size); 
LOGI("Max render buffer size: %d, max texture size: %d", render_buffer_size, tex_size); //max render buffer size: 3838, max texture size: 2048 
glGenFramebuffers(1, &res->frame_buffer); 
GLuint depth_buffer; 
glGenRenderbuffers(1, &depth_buffer); 
glGenTextures(1, &res->buffer_tex.id); 
res->buffer_tex.size.w = width; 
res->buffer_tex.size.h = height; 
glBindTexture(GL_TEXTURE_2D, res->buffer_tex.id); 
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, res->buffer_tex.size.w, res->buffer_tex.size.h, 0, GL_RGB, GL_UNSIGNED_BYTE, NULL); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 
glBindRenderbuffer(GL_RENDERBUFFER, depth_buffer); 
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, res->buffer_tex.size.w, res->buffer_tex.size.h); 
glBindFramebuffer(GL_FRAMEBUFFER, res->frame_buffer); 
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, res->buffer_tex.id, 0); 
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depth_buffer); 
if(glCheckFramebufferStatus(GL_FRAMEBUFFER) == GL_FRAMEBUFFER_COMPLETE) 
    LOGE("BUFFER OK"); 
else 
    LOGE("BUFFER NOT OK"); 
//BUFFER OK 
glBindFramebuffer(GL_FRAMEBUFFER, 0); 
glBindTexture(GL_TEXTURE_2D, 0); 
} 

FBO使用

static fbo FBO; 
static decor DECOR; //shield quad 
static decor SCREEN_DECOR;// FBO textured quad 

void on_surface_changed(int width, int height) 
{ 
set_fbo(&FBO, width, height); 
... 
} 

void on_draw() 
{ 
glBindFramebuffer(GL_FRAMEBUFFER, FBO.frame_buffer); 
set_render_color(YELLOW); //glClearColor(...) 
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 
draw_decor(&DECOR, get_shader(SPRITE_SIMPLE_SHADER), *get_proj(ORTHO_PROJ)); 
glBindFramebuffer(GL_FRAMEBUFFER, 0); 
set_render_color(BLACK); 
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 
draw_decor(&SCREEN_DECOR, get_shader(SPRITE_SIMPLE_SHADER), *get_proj(ORTHO_PROJ)); 
} 

結果: with FBO 結果與灰度渲染: with grayscale shader

渲染無FBO:

void on_draw_simple() 
{ 
set_render_color(YELLOW); //glClearColor(...) 
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 
draw_decor(&DECOR, get_shader(SPRITE_SIMPLE_SHADER), *get_proj(ORTHO_PROJ)); 
} 

without FBO

+8

看到這個:http://www.java-gaming.org/index.php?topic=24126.0 尤其是這個部分:'紋理起源和窗口起源是OpenGL中的左下角。「可能是這個問題? :) – Jite

+0

我的不好)。那麼簡單的方法就是將精靈旋轉到z軸上的180.0f? – Aristarhys

+2

不行,你必須在繪製fbo時翻轉y座標。不要旋轉180°,因爲這也會反映您的圖像。 – kritzikratzi

回答

4

從意見彙總:

這是因爲OpenGL的在左下角的起源,與大多數視窗系統使用,原點位於左上角。

只需確保紋理座標從左上角的0.1到右下角的1,0上正確繪製FBO,或繪製垂直翻轉紋理的四邊形。