Skip to main content
GameDev.net gamedev.net
🔒 Locked

Multitexturing

Started by DuckWizard Jan 23, 2005 at 3:01 AM 2 replies 650+ views
Original Post
DuckWizard
DuckWizard
I've done pretty well at OpenGL so far. But multitexturing kind of has me baffled. Here's my understanding of the underlying idea; please correct me if I'm wrong because when I search for answers I only find code and it doesn't help me. There are a series of sequential texture units. For each one, you tell it where to get its color information, and how to combine it with the other texture units. Then you draw the geometry. Correct? What I am trying to do is put some detail textures on my terrain. Right now I am doing this with multipass rendering. I have the geometry, with a base texture, and several color arrays which correspond to the geometry. These color arrays specify the alpha for each successive texture. I want to speed this up with multitexturing, maybe doing a couple textures in one pass. Is this possible? I don't have alpha blend maps or anything, just the per-vertex alpha. Thanks, -Jeremy
Gorax
Gorax
Multitexturing's annoying to get used to when you start out, but it's not that bad once you grasp what's going on. I assume you already know how to load the functions necessary to use multitexturing...

You need to know exactly how many textures you can apply to any one surface. To do this, you need to call glGetIntegerv with GL_MAX_TEXTURE_UNITS as the param name. Don't exceed this number, or your quads will get messed up, and you'll be left scracthing your head like me. ;)

Then, figure out how many textures you want to put into one surface. Activate the first texture using glActiveTextureARB (the argument should be GL_TEXTURE*_ARB, where * is some number), enable GL_TEXTURE_2D (or 3D), then bind your texture as you normally would. Then do it for the 2nd one, 3rd one, etc.

After that, all you need to do is call glMultiTexCoord2fARB with the first texture as the param (that is GL_TEXTURE*_ARB, not your actual texture), then do the same again, with the 2nd texture, and it's coordinates, and the 3rd, etc. followed by you actually calling glVertex2d (or glVertex3d).

When you're done, reactiveate the texture with glActiveTextureARB, and disable texturing. It's that simple... Kinda confusing, right? ;)

Basically, it's like this:
//replace glBindTexture(GL_TEXTURE_2D,textureID1) with this:glActiveTextureARB(GL_TEXTURE0_ARB);glEnable(GL_TEXTURE_2D);glBindTexture(GL_TEXTURE_2D,textureID1);//followed by the texture you would be using in the 2nd pass:glActiveTextureARB(GL_TEXTURE1_ARB);glEnable(GL_TEXTURE_2D);glBindTexture(GL_TEXTURE_2D,textureID2);/*now to actually draw something...assuming that for the first point, you'd use the texture point 0.5f,0.5f, andfor the 2nd passes texture, you'd use 1.2f,1.2f, you would do this:*/glMultiTexCoord2fARB(GL_TEXTURE0_ARB,0.5f,0.5f);glMultiTexCoord2fARB(GL_TEXTURE1_ARB,1.2f,1.2f);//then draw the pointglVertex3f(0.7f,1.2f,6.4f);//then, once you've finished drawing, release the texturesglActiveTextureARB(GL_TEXTURE0_ARB);glDisable(GL_TEXTURE_2D);glActiveTextureARB(GL_TEXTURE1_ARB);glDisable(GL_TEXTURE_2D);


Another thing to note is that to combine the textures with the appropriate texture env mode, you'll need to use:
glTexEnvf(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE_EXT);
followed by:
glTexEnvf(GL_TEXTURE_ENV,GL_COMBINE_RGB_EXT,mode);
where 'mode' is GL_MODULATE, or GL_REPLACE, etc.

Hopefully this explains it well enough. I know I found the tutorials on this rather confusing, so hopefully relating this back to single-textured surfaces, it makes a little more sense.
DuckWizard
DuckWizard
That did help me understand what's going on, but I can't seem to get the specifics right. To make this simple let's try a simple case:

I have the terrain with the base texture. I have a color array (RGBA) which specifies the alpha for the detail texture at every vertex. Ideally, the terrain should render with the base texture and the detail texture on top of that, with the opacity specified by the color array. Here's the code I have:

	glActiveTextureARB( GL_TEXTURE0_ARB ); //base texture	glEnable(GL_TEXTURE_2D);	tex.SwapTex(0);  //switch to base texture	glEnableClientState(GL_VERTEX_ARRAY);	glEnableClientState(GL_NORMAL_ARRAY);	glEnableClientState(GL_TEXTURE_COORD_ARRAY);	glDisableClientState(GL_COLOR_ARRAY);  //base tex, so disable alpha array	glVertexPointer(3, GL_FLOAT, 0, this->vertices);	glNormalPointer(GL_FLOAT, 0, this->normals);	glTexCoordPointer(2, GL_FLOAT, 0, texcoords);		glActiveTextureARB( GL_TEXTURE1_ARB ); //detail texture	glEnable(GL_TEXTURE_2D);	tex.SwapTex(1); //switch to detail texture	glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);	glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_REPLACE); //not sure what this does		glEnableClientState(GL_VERTEX_ARRAY);	glEnableClientState(GL_NORMAL_ARRAY);	glEnableClientState(GL_TEXTURE_COORD_ARRAY);	glEnableClientState(GL_COLOR_ARRAY);  //enable alpha array	glVertexPointer(3, GL_FLOAT, 0, this->vertices);	glNormalPointer(GL_FLOAT, 0, this->normals);	glTexCoordPointer(2, GL_FLOAT, 0, texcoords);	glColorPointer(4, GL_FLOAT, 0, this->alphas); //specify alpha array	glDrawElements(GL_QUADS, 32*32*4, GL_UNSIGNED_INT, indices); //draw geometry


Clearly it doesn't work or I wouldn't be posting here (c: I just get a weird solid color instead of the desired result. If I comment out either block (either the one for the base or the one for the detail) I get what that block should render. But something goes wrong in combining them. What am I doing wrong?
MARS_999
MARS_999
I am not sure what you are trying to do for sure, but from looking at your code quickly, I am thinking you have your combine function parameters setup wrong...

But here is what I do for detail texturing. Use a RGB image with the image setup as 256 colors or greyscale. Then use the 2nd texture unit as the detail map unit.


this code to setup the texture
glActiveTextureARB(GL_TEXTURE1_ARB);glEnable(GL_TEXTURE_2D);glBindTexture(GL_TEXTURE_2D, texture[GRASS_DETAIL]);glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB);glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_ARB, 2);

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.