【问题标题】:Texture is not loading through glGenerateMipmap()纹理未通过 glGenerateMipmap() 加载
【发布时间】:2013-09-10 07:15:39
【问题描述】:

我无法通过我的立方体上的glGenerateMipmap 加载纹理。

我从resource.h 文件加载 BMP 纹理。

我的加载函数在 WM_CREATE 上调用,如下所示:

void LoadTEX()
{
 GLuint texture;  
 HBITMAP GLtex;
 BITMAP tex;
 byte Texture=TEX;
 GLtex= (HBITMAP)LoadImage(GetModuleHandle(NULL),MAKEINTRESOURCE(Texture), IMAGE_BITMAP, 0, 0, LR_CREATEDIBSECTION);

  GetObject(GLtex,sizeof(tex), &tex);
  glPixelStorei(GL_UNPACK_ALIGNMENT,sizeof(Texture));
  glEnable(GL_TEXTURE_2D);
  glGenTextures(sizeof(Texture), &texture);
  glBindTexture( GL_TEXTURE_2D, texture );
  glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
  glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,GL_LINEAR_MIPMAP_NEAREST );
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );  
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
  glTexImage2D( GL_TEXTURE_2D,
            0,
            GL_RGB,
            tex.bmWidth,
            tex.bmHeight,
            0,
            GL_RGB,GL_UNSIGNED_BYTE,
            tex.bmBits);

 glDeleteTextures(sizeof(Texture), &texture);
}

开启WM_PAINT

 glColor3f(1.0f,1.0f,1.0f);
 glEnable(GL_TEXTURE_2D);
 glBindTexture( GL_TEXTURE_2D, texture );
 // glActiveTexture(GL_TEXTURE0);
 // glGenerateMipmap(GL_TEXTURE_2D);
 gluBuild2DMipmaps(GL_TEXTURE_2D, 3, tex.bmWidth, tex.bmHeight, GL_RGB, GL_UNSIGNED_BYTE, tex.bmBits);

上面的代码工作正常(纹理到位),但问题是它给了我 40 FPS,这是非常糟糕的结果(没有绑定纹理我得到大约 300 FPS)。

第二个是我不想用gluBuild2DMipmaps,因为它有点老了,我想用glGenerateMipmap。问题是如果我注释掉gluBuild2DMipmaps 并取消注释glActiveTexture(GL_TEXTURE0);glGenerateMipmap(GL_TEXTURE_2D) 什么都不会显示。

我的PIXELFORMATDESCRIPTOR 看起来像:

PIXELFORMATDESCRIPTOR pfd;
int format;

// get the device context (DC)
*hdc = GetDC( hwnd );

// set the pixel format for the DC
ZeroMemory( &pfd, sizeof( pfd ) );
pfd.nSize = sizeof( pfd );
pfd.nVersion = 1;
pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
pfd.iPixelType = PFD_TYPE_RGBA;
pfd.cColorBits = 32;
pfd.cDepthBits = 32;
pfd.iLayerType = PFD_MAIN_PLANE;
format = ChoosePixelFormat( *hdc, &pfd );
SetPixelFormat( *hdc, format, &pfd );

所有这些都在 ATI 和 OPENGL 3.1 支持下运行。我打电话给glEnable(GL_TEXTURE_2D);,所以这应该适用于 ati 卡,所以问题出在其他地方。

【问题讨论】:

    标签: c++ winapi opengl textures


    【解决方案1】:

    在 LoadTEX 中,不要在加载后立即删除纹理。 (也应该是 glGenTextures(1, &texture) 和 glDeleteTextures(1, &texture) 来生成和删除一个纹理句柄)

    然后在用 glTexImage2D 加载之后调用 glGenerateMipmap。除非纹理发生变化,并且您需要在每一帧重新生成 mipmap,在这种情况下,将调用留在原处。

    glActiveTexture(GL_TEXTURE0) 无论如何都是默认值。如果您同时绑定其他纹理,您将使用 glActiveTexture(GL_TEXTURE1) 或 glActiveTexture(GL_TEXTURE0 + textureIndex) 等。

    我不确定 Windows 位图加载的细节,但请仔细检查 glPixelStorei 行,考虑到其他 sizeof(Texture) 用途,我不得不假设这也可能不正确。为了安全起见,只需将其设置为 1 个字节即可。

    【讨论】:

    • 我在我的绘图函数上的“glGenerateMipmap”之前粘贴了glTexImage2D。结果是抛出异常,MS Visual Studio 将tex.bmBits: 0x005f0000 的值涂成红色。我使用 24 像素位的 512x512 BMP 文件。这对于 glTexImage2D 来说是不是太小/太大了?
    • glTexImage2D 上的崩溃表明 OpenGL 正在尝试读取一些无效数据。这意味着它期望某些东西在那里,但事实并非如此。要么 1. tex.bmBits 无效/未初始化/null,2. 宽度/高度太大(导致过度读取),3. GL_UNPACK_ALIGNMENT 太大,导致读取的数据多于存在,4. 少于3 个通道和 GL_RGBA 预计 3 个。还要仔细检查,GL_UNSIGNED_BYTE 应该在你的例子中使用。
    • @NightKn8 这个答案的第一行是最重要的。为什么在地球上创建一个纹理,然后立即删除它。之后每次使用纹理 ID 都必然会导致错误或奇怪的行为。所以简单的答案是放弃glDeleteTextures 呼叫。当然,答案也是正确的,因为您应该认真考虑是否有必要重新构建每一帧的 mipmap。但最好的答案可能是更深入地了解纹理和 OpenGL 对象的实际工作方式。
    【解决方案2】:

    我在加载纹理时使用以下顺序:

    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR_MIPMAP_LINEAR);
    
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, n2width, n2height, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixmap);
    
    glHint(GL_GENERATE_MIPMAP_HINT, GL_FASTEST);//GL_FASTEST);
    glGenerateMipmap(GL_TEXTURE_2D); // Generate mip mapping
    

    并且不要在每一帧上重建 mipmap。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-03-10
      • 1970-01-01
      • 1970-01-01
      • 2013-11-27
      • 2021-08-31
      • 2015-05-30
      • 2012-09-15
      • 1970-01-01
      相关资源
      最近更新 更多