C++ opengl中的纹理消失

C++ opengl中的纹理消失,c++,opengl,freeimage,C++,Opengl,Freeimage,我看到这个问题,在应用程序使用一两分钟后,纹理消失。为什么纹理会消失?3d立方体始终保持在屏幕上。当纹理消失时,纹理显示为白色框的位置 我的DrawGLScene方法如下所示: glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // Clear Screen And Depth Buffer glLoadIdentity(); // Reset The Current Modelview Matri

我看到这个问题,在应用程序使用一两分钟后,纹理消失。为什么纹理会消失?3d立方体始终保持在屏幕上。当纹理消失时,纹理显示为白色框的位置

我的DrawGLScene方法如下所示:

        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // Clear Screen And Depth Buffer
            glLoadIdentity();   // Reset The Current Modelview Matrix

            glTranslatef(0.0f, 0.0f, -7.0f);    // Translate Into The Screen 7.0 Units

//rotquad is a value that is updated as the user interacts with the ui by +/-9 to rotate the cube
        glRotatef(rotquad, 0.0f, 1.0f, 0.0f);

        //cube code here

            RECT desktop;
            const HWND hDesktop = GetDesktopWindow();
            GetWindowRect(hDesktop, &desktop);
            long horizontal = desktop.right;
            long vertical = desktop.bottom;

            glMatrixMode(GL_PROJECTION);
            glPushMatrix();
            glLoadIdentity();
            glOrtho(-5.0, 3, 3, -5.0, -1.0, 10.0);
            glMatrixMode(GL_MODELVIEW);
            glLoadIdentity();
            glDisable(GL_CULL_FACE);
            glEnable(GL_TEXTURE_2D);

            glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
            glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);

            glClear(GL_DEPTH_BUFFER_BIT);

            glColor4f(255.0f, 255.0f, 255.0f, 0.0f);
            if (hoverRight) {
                imageLoaderOut(outImage);
                imageLoaderIn(inImage);
                imageLoaderUp(upImage);
                imageLoaderLeft(leftHover);
                imageLoaderDown(upImage);
                imageLoaderRight(rightImage);
            }
    // code for hover left, up and down are the same as hover right code above 

        glDisable(GL_TEXTURE_2D);
        return TRUE;    // Keep Going
    }
此方法是imageLoad方法之一(除location/position外,其他被调用的方法几乎相同)

        void imageLoaderOut(const char* value)
        {
            FIBITMAP* bitmap60 = FreeImage_Load(
                FreeImage_GetFileType(value, 0),
                value, PNG_DEFAULT);
            FIBITMAP *pImage60 = FreeImage_ConvertTo32Bits(bitmap60);
            int nWidth60 = FreeImage_GetWidth(pImage60);
            int nHeight60 = FreeImage_GetHeight(pImage60);
            glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, nWidth60, nHeight60, 0, GL_RGBA, GL_UNSIGNED_BYTE, (void*)FreeImage_GetBits(pImage60));
            FreeImage_Unload(pImage60);
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
            glBegin(GL_QUADS);
            glTexCoord2f(0.0f, 0.0f); glVertex2f(2.8f, -1.1f); // moves BOTTOM EDGE UP or DOWN - stretches length of image
            glTexCoord2f(0.0f, 1.0f); glVertex2f(2.8f, -1.9f);
            glTexCoord2f(1.0f, 1.0f); glVertex2f(2.1f, -1.9f);
            glTexCoord2f(1.0f, 0.0f); glVertex2f(2.1f, -1.1f); // moves BOTTOM EDGE UP or DOWN - stretches length of image
            glEnd();
        }

问题似乎出在
glTexImage2D
中。可在此处找到手册:

他们特别说:

glTexImage2D指定当前纹理单元的二维纹理,使用glActiveTexture指定


多次调用
glTexImage2D
后,您似乎正在多次覆盖同一位置。

问题似乎出在
glTexImage2D
中。可在此处找到手册:

他们特别说:

glTexImage2D指定当前纹理单元的二维纹理,使用glActiveTexture指定

一旦您多次调用
glTexImage2D
,似乎您正在多次覆盖同一位置。

这只是一个猜测,但您的代码中存在严重的设计问题,再加上内存泄漏,可能会导致如您所述的未定义结果

首先,在
imageLoaderOut()中
您正在从HDD读取每帧的所有纹理,将其转换为32 bpp并将数据发送到OpenGL。您从
DrawGLScene
调用它,这意味着您在每帧都执行它。这确实是一种无效的操作方式。您不需要加载每帧的资源。如果
Initialize()
功能,只需使用绘图上的GL资源即可

然后,我认为这里有内存泄漏,因为你从来没有卸载
bitmap60
。当你加载每一帧时,可能每秒数千次,这些未释放的内存会累积。因此,一段时间后,事情变得非常糟糕,FreeImage拒绝加载纹理

因此,可能的解决办法是:

  • 将资源加载移动到应用程序的初始化阶段
  • 释放泄漏的资源:
    FreeImage\u在每个加载函数中卸载(bitmap60)
希望有帮助。

这只是一个猜测,但您的代码中存在严重的设计问题,再加上内存泄漏,可能会导致您所描述的未定义的结果

首先,在
imageLoaderOut()中
您正在从HDD读取每帧的所有纹理,将其转换为32 bpp并将数据发送到OpenGL。您从
DrawGLScene
调用它,这意味着您在每帧都执行它。这确实是一种无效的操作方式。您不需要加载每帧的资源。如果
Initialize()
功能,只需使用绘图上的GL资源即可

然后,我认为这里有内存泄漏,因为你从来没有卸载
bitmap60
。当你加载每一帧时,可能每秒数千次,这些未释放的内存会累积。因此,一段时间后,事情变得非常糟糕,FreeImage拒绝加载纹理

因此,可能的解决办法是:

  • 将资源加载移动到应用程序的初始化阶段
  • 释放泄漏的资源:
    FreeImage\u在每个加载函数中卸载(bitmap60)

希望有帮助。

为什么要在绘图代码中加载纹理图像(无条件)?不应该这样做。在一次性初始化函数中只加载一次纹理,或者如果纹理需要更新,请在绘图代码中使用条件。为什么要加载纹理图像(无条件)在绘图代码中?你不应该这样做。在一次初始化函数中只加载一次纹理,或者如果纹理需要更新,在绘图代码中使用一个条件。谢谢…我对opengl第一次使用它不太了解。所以一开始它很混乱。@BlueMonster尝试失败或尝试成功总是可以的。只是好奇,我的猜测是对的吗?你修复了纹理消失吗?是的,你完全正确。我不应该每次都阅读图像。使用胶水将图像存储为资源解决了这个问题。非常感谢!谢谢…我对opengl第一次使用它知之甚少。所以一开始这是一个很大的困惑。@BlueMonster I尝试失败或尝试成功总是可以的。只是好奇,我的猜测是对的吗?你修复了纹理消失了吗?是的,你完全正确。我不应该每次都读取图像。使用胶水将图像存储为资源解决了问题。非常感谢!在API方面,用这种方式更新纹理数据即使在每个帧的相同位置写入相同的数据,也完全有效。当然,以这种方式写入数据是多余的,完全浪费资源,但不太可能导致“应用程序使用一两分钟后纹理消失”/所以我认为这不是问题。@Drop的问题是,他正在将不同的图像更新到相同的上下文中。如果纹理来自不同的大小,则图像的某些部分可能会消失或出错。就API而言,即使您在每个帧的同一位置写入相同的数据,以这种方式更新纹理数据也是完全有效的e、 当然,以这种方式写入数据是多余的,完全浪费资源,但不太可能导致“应用程序使用一两分钟后纹理消失”/所以我认为这不是问题。@Drop问题是他正在将不同的图像更新到相同的上下文中。如果纹理来自不同的大小,则图像的某些部分可能会消失或出错。