2013-12-03 72 views
4

我包我的头左右的飞行产生的贴图,并读取该位,此代码:http://www.g-truc.net/post-0256.html的OpenGL glGeneratemipmap和帧缓存

//Create the mipmapped texture 
glGenTextures(1, &ColorbufferName); 
glBindTexture(ColorbufferName); 
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 512, 512, 0, GL_UNSIGNED_BYTE, NULL); 
glGenerateMipmap(GL_TEXTURE_2D); // /!\ Allocate the mipmaps /!\ 
... 
//Create the framebuffer object and attach the mipmapped texture 
glBindFramebuffer(GL_FRAMEBUFFER, FramebufferName); 
glFramebufferTexture2D(
GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, ColorbufferName, 0); 
... 
//Commands to actually draw something 
render(); 
... 
//Generate the mipmaps of ColorbufferName 
glActiveTexture(GL_TEXTURE0); 
glBindTexture(GL_TEXTURE_2D, ColorbufferName); 
glGenerateMipmap(GL_TEXTURE_2D); 

我的问题:

  1. 为什么glGenerateMipmap需求在渲染为纹理的情况下被调用两次?
  2. 这是否必须像这样每帧调用?

如果我例如导入漫2D纹理我只需要调用一次后,我将其加载到OpenGL的是这样的:

GLCALL(glGenTextures(1, &mTexture)); 
    GLCALL(glBindTexture(GL_TEXTURE_2D, mTexture)); 

    GLint format = (colorFormat == ColorFormat::COLOR_FORMAT_RGB ? GL_RGB : colorFormat == ColorFormat::COLOR_FORMAT_RGBA ? GL_RGBA : GL_RED); 
    GLCALL(glTexImage2D(GL_TEXTURE_2D, 0, format, textureWidth, textureHeight, 0, format, GL_UNSIGNED_BYTE, &textureData[0])); 

    GLCALL(glGenerateMipmap(GL_TEXTURE_2D)); 
    GLCALL(glBindTexture(GL_TEXTURE_2D, 0)); 

我怀疑这是因为纹理被重绘每帧mipmap生成过程在过程中使用它的内容,但我希望对此进行确认。

3 - 此外,如果我呈现给我的gbuffer,然后立即glBlitFramebuffer它到默认的FBO,我需要绑定和glGenerateMipmap这样?

GLCALL(glBindTexture(GL_TEXTURE_2D, mGBufferTextures[GBuffer::GBUFFER_TEXTURE_DIFFUSE])); 
GLCALL(glGenerateMipmap(GL_TEXTURE_2D)); 
GLCALL(glReadBuffer(GL_COLOR_ATTACHMENT0 + GBuffer::GBUFFER_TEXTURE_DIFFUSE)); 
GLCALL(glBlitFramebuffer(0, 0, mWindowWidth, mWindowHeight, 0, 0, mWindowWidth, mWindowHeight, GL_COLOR_BUFFER_BIT, GL_LINEAR)); 

回答

7
  1. 如您链接到后解释说:“[glGenerateMipmap]实际上做了两件事情是可能与它的唯一问题:它分配的贴图内存和生成的贴图”

    请注意,第一个glGenerateMipmap调用之前的内容是带有NULL数据指针的glTexImage2D调用。这两个调用组合将简单地为所有纹理的级别分配内存。他们在这里包含的数据是垃圾。

    将图像加载到纹理的第一级之后,您必须再次调用glGenerateMipmap才能使用降采样图像实际填充较小的级别。

  2. 你的猜测是正确的,glGenerateMipmap被称为每帧,因为渲染到纹理的第一级别的图像会改变每一帧(因为它被渲染到)。如果您不调用该函数,那么较小的mipmap将永远不会被修改(如果您要映射这样的纹理,则在距离足够远时会看到未初始化的较小mipmap级别)。

  3. 不可以。只有在您打算将纹理映射到使用mipmap的纹理过滤模式的三角形时才需要使用Mipmap。如果您只处理纹理的第一级,则不需要生成mipmap。事实上,如果你从不映射纹理,你可以在你的帧缓冲区中使用渲染缓冲而不是纹理。