GLES

From Pandora Wiki
Revision as of 19:44, 21 February 2009 by Butterman (talk | contribs)
Jump to: navigation, search

Please don't skim over this tutorial, then just email me because you don't understand something. This tutorial has to be read in its entirety or you wont get it. If you're not up for that, then go find some other code you can copy paste, ya lazy bum. If you do have questions, I hang around on #TINCS in "irc.quakenet.org" or you can email me on "jack@sorok.co.uk"

Introduction

Unfortunately, the OpenGL ES takes away many of the functions that beginner programmers use. They do this, because a lot of those functions are plain rubbish for any high-end application. We're only covering ES 1.1 here, but the Pandora also supports ES 2.0, which, leaves you with a handful of functions, you have to do all of the matrix math on your own. Which can be really hard if you're not good at maths, I'll cover how to do that in a later tutorial. What you're learning here isn't just for the Pandora, you should use these new methods in your Windows/Linux code. These changes are being made to the core OpenGL too, so you're loosing all of this stuff soon enough. Which is silly, OpenGL is good because beginners can pick it up easily. But whatever, I'm not in charge.

The Basics

glBegin() and glEnd()

glBegin(GL_TRIANGLES);

    glVertex3f(1,0,0);
    glVertex3f(0,1,0);
    glVertex3f(-1,0,0);

glEnd();

You know what I just did? Yeah, I drew a triangle! Nope, you can't draw stuff like this in OpenGL ES 1.1, so how would one draw a triangle in ES? Bare with me while you read this if you don't understand it, I'll explain it in depth.

GLfloat vertices[] = {1,0,0, 0,1,0, -1,0,0};

glEnableClientState(GL_VERTEX_ARRAY);

glVertexPointer(3, GL_FLOAT, 0, vertices);

glDrawArrays(GL_TRIANGLES, 0, 3);

glDisableClientState(GL_VERTEX_ARRAY);

This is called drawing with a vertex array. Eww? Yeah, you would never draw like that in a real program, your vertex array would be stored already, you wouldn't have to define it every time you drew somthing. While it's messy for drawing primitives, it's really cool for drawing models, because your models vertices are generally stored in arrays like that already. I'll show you an example from TINCS after I explain this code.

GLfloat vertices[] = {1,0,0, 0,1,0, -1,0,0};

This should be obvious, we're simply creating an array that stores the vertices of our triangle. It can be of any size, you can store as many vertices as you want. Note, how I space out every three numbers, this is because a vertex is made of X,Y,Z components. So we have our X, our Y, our Z then a space for the next three. You don't have to space it like this, it's mainly so you can see what's going on.

glEnableClientState(GL_VERTEX_ARRAY);

We need to do this before we start drawing, this tells OGL that we're going to feed it a vertex array from the client side (rather than the server, which is the graphics card).

glVertexPointer(3, GL_FLOAT, 0, vertices);

Ok, here is where we're telling OGL where to get it's vertices from. The first argument, tells OGL how many components (or floats) there are per vertex. Remember we talked about how we were spacing them out every 3 numbers? Here we're telling OGL that we did that! The next argument tells OpenGL that we're giving it floating point numbers. Now we have a "0". This is called the stride, I could explain it in detail, but you don't need to understand it yet. Just leave it at 0. In the last argument we give OGL our vertex array!

glDrawArrays(GL_TRIANGLES, 0, 3);

Here is where the work is done. The first argument is telling OGL that we're drawing in triangles. (This can be GL_QUADS, GL_LINES, whatever!). The second is specifying where we want to start in the array we passed OGL earier. The last one is telling OpenGL how many vertices we want to draw. In this case, it's just the three.

glDisableClientState(GL_VERTEX_ARRAY);

Finally, we're disabling the vertex array state. We're done!

So this is one of the ways to draw stuff in OpenGL. It's the next step up from glBegin and glEnd and it works fine in ES 1.1, so it works fine on the Pandora!

Drawing Textured Quads

OpenGL can be great for speeding up your 2D application. One of the ways you do this, is by drawing with OpenGL rather than SDL. 2D games are made up of lots of sprites, which are just images that move about in a 2D world. You can use hardware acceleration to speed this up. If you're only planning on using 3D stuff on the Pandora, read this anyway, it introduces you to texturing with texture arrays and you're probably going to need to use sprites somewhere anyway.

So, we can pick apart my method of sprite drawing in TINCS for this tutorial, I mainly use this function to draw text, once it's been rendered by SDL_ttf and converted into a OpenGL texture, but never mind any of that.

static void DrawSprite(GLuint sprite, float X, float Y, float Z, float W, float H)
{
	glLoadIdentity();

	glBindTexture(GL_TEXTURE_2D,sprite);

	GLfloat box[] = {X,Y + H,Z,  X + W,Y + H,Z,     X + W, Y, Z,   X,Y,Z};
	GLfloat tex[] = {0,0, 1,0, 1,1, 0,1};

	glEnableClientState(GL_VERTEX_ARRAY);
	glEnableClientState(GL_TEXTURE_COORD_ARRAY);

	glVertexPointer(3, GL_FLOAT, 0,box);
	glTexCoordPointer(2, GL_FLOAT, 0, tex);

	glDrawArrays(GL_QUADS,0,4);
		
	glDisableClientState(GL_VERTEX_ARRAY);
	glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}

Give it a good read, make sure you understand all of the stuff we've been over before and how it's applied in this example!