c++ - OpenGL 纹理渲染颠倒且模糊

标签 c++ opengl textures

我之前正在开发一款游戏,遇到了一些问题!我从单张图片开始游戏。每个纹理都有自己的文件。有点深入,我意识到我这样做是多么的白痴,并试图切换到使用一张包含所有纹理的图片(无论如何它们都很小)。现在,问题出现了。当加载比我的原始纹理 ( 10 x 10 ) 更大的图像时,它几乎就像没有使用最近邻大小调整算法显示一样。我得到的是一个模糊的图像。它也翻转了......为什么会发生这些问题?

下面的代码和图片。

这是第一个显示包含文本和符号的 Sprite 表。 (它很小,100 x 100) http://imgur.com/HU5zEAO.jpg

这是我在程序运行时得到的。 http://i.imgur.com/HeVPdPy.jpg

这是main.cpp文件

#include <GL/glew.h>
#include <GL/glut.h>

#include "spritesheet_class.h"
#include "load_img.h"

GLuint TextSheet;
Spritesheet Test;

void LoadFiles()
{

    GLuint TextSheet = LoadTexture( "davetica.png", 100, 100, 0 );

    Test.SetTex( TextSheet, 100, 100, 10, 10 );

}

void Reshape( int width, int height )
{

    glViewport( 0, 0, (GLsizei)width, (GLsizei)height );
    glMatrixMode( GL_PROJECTION );

    glLoadIdentity();
    glOrtho( 0.0f, width, 0.0f, height, 1.0f, 100.0f );

    glMatrixMode( GL_MODELVIEW );

}

void Display()
{

    glClear( GL_COLOR_BUFFER_BIT );
    glLoadIdentity();

    glTranslatef( 0.0f, 0.0f, -1.0f );

    Test.DrawSprite( 1, 0, 0, 400, 400 );

    glutSwapBuffers();

}

int main( int argc, char **argv )
{

    glutInit( &argc, argv );
    glutInitDisplayMode( GLUT_DOUBLE );

    glutInitWindowPosition( 200, 100 );
    glutInitWindowSize( 512, 512 );

    glutCreateWindow( "Sprite Sheets" );

    glutDisplayFunc( Display );
    glutIdleFunc( Display );
    glutReshapeFunc( Reshape );

    LoadFiles();

    glutMainLoop();

}

现在这是我在其中编写 Spritesheet 类的类标题。

#ifndef SPRITESHEET_CLASS_H_INCLUDED
#define SPRITESHEET_CLASS_H_INCLUDED

#include "load_img.h"

class Spritesheet
{

    public:
        void SetTex( GLuint Tex, int ImgW, int ImgH, int HorzAm, int VertAm );

        void DrawSprite( int spriteNum, int xLoc, int yLoc, int width, int height );

    private:
        GLuint Texture;
        int imageWidth, imageHeight, horiAm, vertAm;

};

void Spritesheet::SetTex( GLuint Tex, int ImgW, int ImgH, int HorzAm, int VertAm )
{

    imageWidth = ImgW;
    imageHeight = ImgH;
    horiAm = HorzAm;
    vertAm = VertAm;

    Texture = Tex;

}

void Spritesheet::DrawSprite( int spriteNum, int xLoc, int yLoc, int width, int height )
{

    glEnable( GL_TEXTURE_2D );

    glBindTexture( GL_TEXTURE_2D, Texture );

    glBegin( GL_QUADS );

        glTexCoord2f( 1.0f, 0.0f );
        glVertex2f( xLoc, yLoc );

        glTexCoord2f( 1.0f, 1.0f );
        glVertex2f( xLoc, yLoc+height );

        glTexCoord2f( 0.0f, 1.0f );
        glVertex2f( xLoc+width, yLoc+height );

        glTexCoord2f( 0.0f, 0.0f );
        glVertex2f( xLoc+width, yLoc );

    glEnd();

    glDisable( GL_TEXTURE_2D );

}

#endif // SPRITESHEET_CLASS_H_INCLUDED

最后,如果您需要这个,这里是处理 LoadImage 函数的文件,我在其中加载和格式化纹理。

#ifndef LOAD_IMG_H_INCLUDED
#define LOAD_IMG_H_INCLUDED

#include <iostream>
#include <stbimg.h>
#include <string>

bool loadCorrectly = true;

using namespace std;

GLuint LoadTexture( const char *filename, int w, int h, int n )
{

    unsigned char *data = stbi_load( filename, &w, &h, &n, 4 );
    GLuint texture;

    if( data == NULL )
    {

        cout << "ERROR: '"<< filename << "' HAS BEEN MODIFIED OR IS MISSING." << endl;
        return 0;

    }else
    {

        cout << "Loaded: '" << filename << "' successfully." << endl;

    }

    glGenTextures( 1, &texture );
    glBindTexture( GL_TEXTURE_2D, texture );
    glTexEnvf( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE,GL_MODULATE );

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

    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_MIRRORED_REPEAT );
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_MIRRORED_REPEAT );

    gluBuild2DMipmaps( GL_TEXTURE_2D, 3, w, h,GL_RGBA, GL_UNSIGNED_BYTE, data );

    free( data );

    return texture;
}

编辑:我发现了问题。我的图像不是二的正方形,因此无法正确显示。

最佳答案

  • 您的图像被翻转了,因为您没有翻转它们以正确定向。这听起来像是同义反复,但 OpenGL 的坐标系将纹理向下映射到向上,其中 (0,0) 位于左下角,(1,1) 位于右上角。解决这个问题是教科书式的练习。

  • 您需要调用 glActiveTexture(GL_TEXTURE0) 以使后续的 gl* 调用知道它们正在修改哪个纹理(即使该纹理处于事件状态)。初始值为 GL_TEXTURE0,但我仍将其放入,这样您就不会遇到潜在的问题。

  • 我知道这不是您问题的一部分,但您使用的 OpenGL 代码已被弃用 7 年。作为一般性建议,您应该切换到可编程流水线。 Here's a link to ogldev到现代 OpenGL 的基础知识,或者至少其中一些是 4.0+。有些在 3 级,但着色器比 FFP 更好。 Here's another short few from Swiftless .基本上搜索 OpenGL 4.0 或更高版本,Google 会指导您。这是一个更陡峭的学习曲线,但它是值得的。

关于c++ - OpenGL 纹理渲染颠倒且模糊,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17779467/

相关文章:

c++ - 无法在 Eclipse 中构建项目

c++ - opengl c++ 中的 180 到 -180 运动?

c++ - 应用没有坐标的纹理

android - 位图太大,无法上传到纹理中

c++ - boost spirit语法的不一致行为

c++ - 命令行程序的返回值

opengl - Fedora 19 使用 rpmfussion 的 NVIDIA 驱动 : libGL error: failed to load driver: swrast

c# - 使用新的 Unity 5.1 传输层 API 流式传输 WebCamTexture

c++ - 如何在 linux 上为 c++ 创建动态库?

c++ - 当属性位置 != 0 时,着色器不输出任何内容