使用GL_NEAREST处的GL_TEXTURE_MIN_FILTER打开GL纹理闪烁

时间:2014-03-29 22:33:01

标签: opengl textures flicker

我有一个简单的OpenGL程序,用GLUT绘制,绘制了一些建筑物,有一个键盘控制的移动摄像头,我正在尝试纹理地面。动画很流畅。

我遇到的问题是纹理映射地面。两个单独的问题有两个不同的方法

1)如果我使用glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR_MIPMAP_NEAREST);然后我没有 当我缩小到很远的地方时闪烁。但问题是,当我从远处缩小时,它显示为单一的纯色。

远方:

GL_LINEAREST_MIPMAP from far

从关闭:

GL_LINEAREST_MIPMAP from close

2)如果我使用,glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST);然后我有很多闪烁 当我移动时缩小到远处,当你失调时,几乎看起来像电视噪音 但是静止不动,看起来更自然。

远方:

GL_NEAREST from far

从关闭:

GL_NEAREST from close

问题:从现有代码中获取两全其美的简单方法是什么?从远处看起来自然,并且当我移动时没有纹理的闪烁。谢谢。

以下是相关代码:

GLuint  grassTextureId;
GLfloat GROUND_PLANE_WIDTH = 1000.0f;

void Display()
{   
    glLoadIdentity();
    camera.Update();
    ...
    FlatGroundPlane_Draw(void);
    ...

    glutSwapBuffers();
}

void FlatGroundPlane_Draw(void) 
{   

    glEnable(GL_TEXTURE_2D);            
    glBindTexture( GL_TEXTURE_2D, grassTextureId); // call glBindTexture before glBegin     
    glBegin(GL_QUADS);  

    glNormal3f(0, 1, 0);
    glTexCoord2d(0, 0); 

    GLdouble textCoord = GROUND_PLANE_WIDTH;

    glVertex3f( -GROUND_PLANE_WIDTH, 0, -GROUND_PLANE_WIDTH);

    // go beyond 1 for texture coordinate so it repeats and tiles
    glTexCoord2d(0, textCoord); 
    glVertex3f( -GROUND_PLANE_WIDTH, 0, GROUND_PLANE_WIDTH);

    glTexCoord2d(textCoord, textCoord); 
    glVertex3f( GROUND_PLANE_WIDTH, 0, GROUND_PLANE_WIDTH);

    glTexCoord2d(textCoord, 0); 
    glVertex3f( GROUND_PLANE_WIDTH, 0, -GROUND_PLANE_WIDTH);        

    glEnd();

    glDisable(GL_TEXTURE_2D);

}

void Initialise()
{

    glEnable(GL_DEPTH_TEST);    
    glClearDepth(1.0f);    
    glDepthFunc(GL_LEQUAL); 
    glHint(GL_PERSPECTIVE_CORRECTION_HINT,GL_NICEST);   

    modelParser = new ModelParser();
    // grass texture is 1024x1024
    // from http://seamless-pixels.blogspot.ca/2012_10_01_archive.html
    grassTextureId = modelParser->LoadTiledTextureFromFile("./Grass/Grass_1024.ppm");

}

void ModelParser::UploadTiledTexture(unsigned int &iTexture, const RGBImage &img)
{
    glGenTextures(1, &iTexture); // create the texture
    glBindTexture(GL_TEXTURE_2D, iTexture);

    // Issue 1: no flickering, but appear solid color from far away 
    //glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST);
    //glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);


    // Issue 2: flickering noise during movement but appear realistic from far away
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);


    // the texture would wrap over at the edges (repeat)
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT );
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );

    gluBuild2DMipmaps(GL_TEXTURE_2D, 3, img.Width(), img.Height(), GL_RGB, GL_UNSIGNED_BYTE, img.Data());
}

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

    ...
    glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGBA | GLUT_DEPTH);
    ...
    glutDisplayFunc(&GLUT::Display);
    ...
    glutMainLoop();
}

0 个答案:

没有答案