[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

Re: [pygame] OpenGL textures flipped



OpenGL doesn't actually have a set coordinate system like you describe - you can always use the coordinate system however you want in OpenGL. For the geometry coordinate system (or more specifically the mapping of coordinates to your screen), the openGL user can set that themself, so you can make OpenGL operate in pretty much whatever way you like. For texture coordinate systems, "top" and "bottom" have no meaning in terms of the coordinate system - top and bottom are simply a function of the content placed in the textures. You can load your graphics in any way you like, you can even change it up from one texture to the other, the only thing that matters is that the texture coordinates in the vertices are correct for the content in the texture. In the end, the whole system really functions on conventions, and anything that is self-consistent is, in fact, correct. This is very different from pygame and SDL, where those coordinate systems are hardcoded. OpenGL is flexible, but there are common conventions.

...So what are the conventions for openGL then? It's pretty well understood that +y is up (increase y, you go higher), for both geometry and textures. Note that this convention is exactly opposite of the fixed coordinate systems of pygame, SDL and many others, where +y is down (increase y, go down). And openGL uses this convention for a very good reason - mathematics uses that same convention, so you'll have an easier time working with math funcs and stuff if you get into rotations and such.

... So what coordinate mappings is that code you referenced using?

It appears that it is using textures in a way that +y is up (like the openGL convention). I can tell that because of the line that gets the pygame surface as a string:
  textureData = pygame.image.tostring(textureSurface, "RGBA", 1)
The "1" argument, is the "flip" argument. It's telling pygame to use the opposite y direction of normal pygame use. Since +y is down in surfaces, flipping means +y becomes up, so hence that's the meaning of the data that is then loaded into a texture.

It also appears that it is using geometry in a way that +y is down (so like pygame usage, opposite the openGL convention, and opposite the way the code is using textures). I can tell this because of the call that's being used to create the perspective:
    gluOrtho2D(0, w, h, 0)
The arguments to gluOrtho2D are "left, right, bottom, top", since it passed 0 as top and h as bottom, and h is positive, it means increasing y goes down.

So that code is explictly making the texture stuff different than the geometry stuff, which doesn't match pygame or conventional openGL use. If you wanted to modify that code to use PyOpenGL conventions, you'd change the gluOrtho2D call. If you want it to be like pygame, you'd change the flip argument to image.tostring to "False"



... and as an aside, one way in which texture and geometry coordinate systems are different in conventional openGL use, is NOT the direction +y is (both are normally up), but in where the origin is - textures don't have negative coordinates, so (0,0) is the bottom left. However in geometry, negative coordinates are common, so (0,0) is actually the center of the screen by default. There are some very good reasons to use that openGL convention of the origin being the center (camera zoom and rotation foremost among them), but with 2D usage, people often just make (0,0) the bottom left instead, probably because it's what they are used to.


On Sat, Jan 23, 2010 at 3:11 PM, B W <stabbingfinger@xxxxxxxxx> wrote:
Hey, all.

An OpenGL noob problem. Loading a texture from an image, let's say some.png, is oriented upside-down and backwards when displayed. I've noticed this in two cases, I'll present the simplest.

I was looking at this nice module http://www.pygame.org/wiki/SimpleOpenGL2dClasses?parent=CookBook. I made a 32x32 image in GIMP according to the module's instructions and put an alphabetic character (L in the upper left corner) on it so I could see the orientation. When I run the module's __main__ demo the image is displayed upside-down and backwards. The image is attached to this post for those who care to try this.

I experimentally modified the code in function createTexDL based on a recollection of something I read once: the coordinate system for geometric objects (lines, triangels, etc.) is not the same as that for textures. Geometry has origin 0,0 at the bottom left corner, whereas textures have origin 0,0 at the upper left corner.

So the original code which displays upside-down/backwards...

    # Bottom Left Of The Texture and Quad
    glTexCoord2f(0, 0); glVertex2f(0, 0)
    # Top Left Of The Texture and Quad
    glTexCoord2f(0, 1); glVertex2f(0, height)
    # Top Right Of The Texture and Quad
    glTexCoord2f(1, 1); glVertex2f( width,  height)
    # Bottom Right Of The Texture and Quad
    glTexCoord2f(1, 0); glVertex2f(width, 0)

Became this, the "right" orientation facing forward and upright...

    # Bottom Left Of The Texture and Quad
    glTexCoord2f(0, 0); glVertex2f(0, height)
    # Bottom Right Of The Texture and Quad
    glTexCoord2f(1, 0); glVertex2f( width,  height)
    # Top Right Of The Texture and Quad
    glTexCoord2f(1, 1); glVertex2f(width, 0)
    # Top Left Of The Texture and Quad
    glTexCoord2f(0, 1); glVertex2f(0, 0)

I'm posing this puzzle because I can't find where I think I may have read about the coordinate systems (I *will*, but in the meantime this is eating at me). I don't know enough yet to tell if this flip-behavior is due to an anomaly in my OpenGL environment or if the way I've mapped the texture is correct. And I'm sure the module's author saw that his/her images displayed correctly, which kinda makes me unsure of anything.

You OpenGL experts, could you please properly align my thinking on this topic?

Thanks. :)

Gumm