【发布时间】:2016-01-31 22:48:05
【问题描述】:
尝试在 OpenGL 上使用定向阴影映射。需要生成一个深度纹理,不是一个渲染缓冲区(需要能够从中读取)它未来通过。在 Android 上运行时不断获取 GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT(作为 glCheckFramebufferStatus 的结果)(在 OSX 上运行时不会出错)。
这是我的代码:
//Shadow
//gen tex
gl_shadow_bogus_texture_active_n = 7;
glActiveTexture(GL_TEXTURE0+gl_shadow_bogus_texture_active_n);
glGenTextures(1, &gl_shadow_bogus_texture_buff_id);
glBindTexture(GL_TEXTURE_2D, gl_shadow_bogus_texture_buff_id);
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_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexImage2D(GL_TEXTURE_2D,0,GL_RGB,tex_dim.x,tex_dim.y,0,GL_RGB,GL_UNSIGNED_BYTE,0);
//gen depth
gl_shadow_texture_active_n = 4;
glActiveTexture(GL_TEXTURE0+gl_shadow_texture_active_n);
glGenTextures(1, &gl_shadow_texture_buff_id);
glBindTexture(GL_TEXTURE_2D, gl_shadow_texture_buff_id);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexImage2D(GL_TEXTURE_2D,0,GL_DEPTH_COMPONENT16,1024,1024,0,GL_DEPTH_COMPONENT,GL_FLOAT,0);
glGenFramebuffers(1, &gl_shadow_framebuffer_id); //gen fb
glBindFramebuffer(GL_FRAMEBUFFER, gl_shadow_framebuffer_id); //bind fb
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gl_shadow_bogus_texture_buff_id, 0); //attach tex
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, gl_shadow_texture_buff_id, 0); //attach depth
请注意,整个gl_shadow_bogus_texture_buff_id 事情(颜色纹理的生成和绑定)只是尝试填充帧缓冲区,从而消除错误。我实际上并不关心颜色数据。
另外需要注意的是,“color tex gen/bind”在 mac 上不是必需的,可以用glDrawBuffer(GL_NONE) 和glReadBuffer(GL_NONE) 替换。但是我不能用那些在 for android 编译...
【问题讨论】:
-
gl_shadow_texture_active_n是干什么用的?另外,您是否正在检查其他 OpenGL 错误? -
@NicolBolas -
gl_blah_texture_active_n是我跟踪纹理绑定到哪个 glActiveTexture 的一种方式。我的纹理很少,我目前正在使用一对一的 texture_id-to-active_texture_n 架构。大大简化了事情(尽管它使间接的“ActiveTexture”层变得多余......)。是的 - 我正在检查其他 OpenGL 错误。它们都通过了,所以为了便于阅读,我将它们排除在示例代码之外。 -
"在我目前使用一对一的 texture_id-to-active_texture_n 架构的情况下,我的纹理很少。" 这完全没有意义。如果您正在创建纹理,它应该只用于该目的;创建后,您取消绑定它。
-
也许我使用了关于“绑定”的错误术语。归根结底,我需要将
uniform sampler2D blah_tex;传递给我的着色器。我这样做的方法是将ActiveTexture(GLuint)传递给glUniform1i。因此,我使用的任何纹理都必须与 ActiveTexture 相关联。在某些情况下,可能会在使用它们的绘制调用之前设置“活动纹理”,然后将它们切换到需要差异纹理的下一个绘制调用,我只是将每个纹理设置为一个 activeTexture 一次,并且从不打乱它们.这种思路有问题吗? -
"在某些情况下,可能会在使用它们的绘图调用之前设置“活动纹理”," 不,这不是“在某些情况下”;这是大多数 OpenGL 应用程序的标准行为。原因是您的方式(保持所有纹理边界并让您更改制服)将您可以拥有的纹理数量限制为可用纹理图像单元的数量。纹理绑定点应该是短暂的;您可以根据需要设置它们,并在不再需要它们时取消设置它们。也许这适用于小例子,但不适用于任何重要的程序。
标签: android c++ opengl-es shadow-mapping