2
votes

I'm trying to texturing a quad and to understand how this little sample works. My code is not original, it's mixed from various examples.

Texture: https://jamesmwake.files.wordpress.com/2015/10/uv_texture_map.jpg?w=660

My questions:

  • When I change GL_TEXTURE_MIN_FILTER to GL_TEXTURE_MAG_FILTER in glTexParameteri the texture disappears. Why?
  • When I change GL_LINEAR to GL_NEAREST, nothing happens. The used texture's resolution changed to 300x300px. Why is that?
  • How can I make mipmaps and then using them?
  • The loadImage() function make a texture. How knows PyOpenGL which texture should be used in the makeQuad() function?

Code:

    import pygame
    from pygame.locals import *

    from OpenGL.GL import *
    from OpenGL.GLU import *

    def loadImage():
        img = pygame.image.load("checker_texture_downsized.jpg")
        textureData = pygame.image.tostring(img, "RGB", 1)
        width = img.get_width()
        height = img.get_height()
        bgImgGL = glGenTextures(1)
        glBindTexture(GL_TEXTURE_2D, bgImgGL)
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)
        glTexImage2D(GL_TEXTURE_2D, 0, 3, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, textureData)
        glEnable(GL_TEXTURE_2D)

    def makeQuad():
        glBegin(GL_QUADS)
        glTexCoord2f(0, 0)
        glVertex2f(25, 25)
        glTexCoord2f(0, 1)
        glVertex2f(25, 775)
        glTexCoord2f(1, 1)
        glVertex2f(775, 775)
        glTexCoord2f(1, 0)
        glVertex2f(775, 25)
        glEnd()

    def main():
        pygame.init()
        display = (1280,800)
        pygame.display.set_mode(display, DOUBLEBUF|OPENGL)
        gluOrtho2D(0, 1280, 0, 800)
        loadImage()

        while True:
            for event in pygame.event.get():
                if event.type == pygame.QUIT:
                    pygame.quit()
                    quit()

            glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT)
            makeQuad()
            pygame.display.flip()

    main()
1

1 Answers

3
votes

Note, that drawing by glBegin/glEnd sequences, the fixed function pipeline matrix stack and fixed function pipeline per vertex light model, is deprecated since decades. Read about Fixed Function Pipeline and see Vertex Specification and Shader for a state of the art way of rendering.


When I change GL_TEXTURE_MIN_FILTER to GL_TEXTURE_MAG_FILTER in glTexParameteri the texture disappears. Why?

The initial value of GL_TEXTURE_MIN_FILTER is GL_NEAREST_MIPMAP_LINEAR. If you don't change it and you don't create mipmaps, then the texture is not "complete" and will not be "shown". See glTexParameter.

See OpenGL 4.6 API Compatibility Profile Specification; 8.17 Texture Completeness; page 306

A texture is said to be complete if all the texture images and texture parameters required to utilize the texture for texture application are consistently defined.

... a texture is complete unless any of the following conditions hold true:

  • The minification filter requires a mipmap (is neither NEAREST nor LINEAR), and the texture is not mipmap complete.

When I change GL_LINEAR to GL_NEAREST, nothing happens. The used texture's resolution changed to 300x300px. Why is that?

If the texture is smaller than the region where the texture is wrapped to, the the minification filter has not effect, but the magnification would have an effect. If you set the value GL_NEAREST to the GL_TEXTURE_MAG_FILTER then the texels are not interpolated any more.

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST)

How can I make mipmaps and then using them?

Mipmaps can be generated by glGenerateMipmap:

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_LINEAR)
glTexImage2D(GL_TEXTURE_2D, 0, 3, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, textureData)
glGenerateMipmap(GL_TEXTURE_2D)

The loadImage() function make a texture. How knows PyOpenGL which texture should be used in the makeQuad() function?

OpenGL is a state engine. Each state is kept until you change it again, even beyond frames. Since you have bound the texture in loadImage

glBindTexture(GL_TEXTURE_2D, bgImgGL)

the currently named texture object, which is bound to texture unit 0 is bgImgGL. This texture is used for drawing.