【发布时间】:2014-05-26 12:10:46
【问题描述】:
带有两个立方体的图像是使用 BLIT 调用 - 测试代码
带有一个 Cube 的图像在不使用 BLIT CALL - 测试代码时显示
各位, 请按照所附图片和代码如下..
从过去 2 天开始一直在为此苦苦挣扎..
在下面的代码中使用 FBO 时遇到问题,我能够成功地附加和渲染到 FBo,但是在同一程序中无法将其用作纹理(颜色和深度缓冲区),我的 glReadpixel 调用之后渲染到 FBO 向我展示 Zero 的所有数据...
当在 GLSL-shader 代码中使用生成的 FBO(color,depth) 时,从 Draw2() 函数调用的代码显示一个没有纹理的混合白色立方体..
请建议...,下面是完整的代码...,我正在创建一个 FBO 并使用 2 个着色器,一个用于正常渲染,另一个使用之前处理的 FBO 的颜色和深度..
这是我的着色器代码
init_gl()
{
此片段着色器代码用于在draw()下的程序中使用的正常渲染
static const char *fragment_shader_source =
"precision mediump float; \n"
" \n"
"varying vec4 vVaryingColor; \n"
" \n"
"void main() \n"
"{ \n"
" gl_FragColor = vVaryingColor; \n"
"} \n";
这个 Fragment Shader Code 用在 Program2 下 draw2()
static const char *fragment_shader_source2 =
"precision mediump float; \n"
" \n"
"varying vec4 vVaryingColor; \n"
"uniform sampler2D color; \n"
"uniform sampler2D depth; \n"
" \n"
"void main() \n"
"{ \n"
"float r = pow(texture2D(color, gl_FragCoord.xy / vec2(256, 256)).a, 128.0); \n"
"float g = texture2D(depth, gl_FragCoord.xy / vec2(256, 256)).a;\n"
"float b = pow(texture2D(depth, gl_FragCoord.xy / vec2(256, 256)).a, 128.0); \n"
"gl_FragColor = vec4(r, g, b, 1.); \n"
"} \n";
我在 FBO 上的第一幅画
static void draw(uint32_t i)
{
EGL_CHECK(glEnable(GL_DEPTH_TEST));
glEnable(GL_TEXTURE_2D);
EGL_CHECK(glDepthFunc(GL_ALWAYS));
EGL_CHECK(glBindFramebuffer(GL_FRAMEBUFFER, fboInfo.id));
EGL_CHECK(glUseProgram(program));
//CUBE DRAWING
在这里读取像素,返回全零
GLubyte *pixels = malloc(4 * 256 * 256);
EGL_CHECK(glReadBuffer(GL_COLOR_ATTACHMENT0));
EGL_CHECK(glReadPixels(0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, pixels));
//**TO TEST my FBO , IF ITS HAVING SOME RENDER DATA**
EGL_CHECK(glBindFramebuffer(GL_FRAMEBUFFER, 0));
glBindFramebuffer(GL_READ_FRAMEBUFFER, fboInfo.id);
glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0);
glBlitFramebuffer(0, 0, 256, 256, 0, 0, 256, 256, GL_COLOR_BUFFER_BIT, GL_NEAREST);
glBindFramebuffer(GL_READ_FRAMEBUFFER, 0);
//TEST CODE ONLY
glBindTexture(GL_TEXTURE_2D, fboInfo.id);
glGenerateMipmap(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, 0);
draw2(i);
}
没有 FBO 的第二张图(但这使用了可以访问 FBO 数据颜色、深度的 FRAG 着色器)
static void draw2(uint32_t i)
{
glUseProgram(program2);
//Draw Same Kind of Cube , Which we draw in draw() function
}
这些是创建 FBO(颜色、深度)的函数
GLuint createTexture2D(const int w, const int h, GLint internalFormat, GLenum format, GLenum type)
{
GLuint textureIdX;
EGL_CHECK(glGenTextures(1, &textureIdX));
EGL_CHECK(glBindTexture(GL_TEXTURE_2D, textureIdX));
EGL_CHECK(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST));
EGL_CHECK(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST));
EGL_CHECK(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE));
EGL_CHECK(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE));
if (GL_DEPTH_COMPONENT == format) {
EGL_CHECK(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE, GL_NONE));
EGL_CHECK(glTexParameteri(GL_TEXTURE_2D, GL_DEPTH_TEXTURE_MODE, GL_INTENSITY));
}
EGL_CHECK(glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, w, h, 0, format, type, 0));
EGL_CHECK(glBindTexture(GL_TEXTURE_2D, 0));
return textureIdX;
}
int createFBO(void)
{
int result = 0;
unsigned int fb = 0;
fboInfo.color = createTexture2D(WINDOW_WIDTH, WINDOW_HEIGHT, GL_RGBA, GL_RGBA, GL_UNSIGNED_BYTE);
fboInfo.depth = createTexture2D(WINDOW_WIDTH, WINDOW_HEIGHT, GL_DEPTH_COMPONENT16, GL_DEPTH_COMPONENT, GL_FLOAT);
EGL_CHECK(glGenFramebuffers(1, &fboInfo.id));
EGL_CHECK(glBindFramebuffer(GL_FRAMEBUFFER, fboInfo.id));
EGL_CHECK(glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, fboInfo.color, 0));
EGL_CHECK(glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, fboInfo.depth, 0));
int data = EGL_CHECK(glCheckFramebufferStatus(GL_FRAMEBUFFER));
if (GL_FRAMEBUFFER_COMPLETE == glCheckFramebufferStatus(GL_FRAMEBUFFER)) {
printf("FBO %d set up successfully\n", fboInfo.id);
result = 1;
}
else {
printf("FBO %d NOT set up properly!\n", fboInfo.id);
}
EGL_CHECK(glBindFramebuffer(GL_FRAMEBUFFER, 0));
return result;
}
这就是我的 FBO 结构的样子
typedef struct {
GLuint id;
GLuint color;
GLuint depth;
}FBOInfo;
我的 MAIN 函数如下所示,我在其中创建 FBO,然后调用我的绘图函数并交换缓冲区..
unsigned long i = 0;
int ret = init_gl();
ret = createFBO();
draw(i);
EGL_CHECK(eglSwapBuffers(eglDisplay, eglSurface));
【问题讨论】:
标签: opengl graphics opengl-es opengl-es-2.0 fbo