Upcoming Events
Virtual Worlds Forum Europe 2008
10/6 - 10/8 @ London, United Kingdom

Tokyo Game Show
10/9 - 10/12 @ Tokyo, Japan

IndieCade
10/10 - 10/17 @ Bellevue, WA

Blizzcon
10/10 - 10/11 @ Anaheim, CA

More events...


Quick Stats
5369 people currently visiting GDNet.
2220 articles in the reference section.

Help us fight cancer!
Join SETI Team GDNet!



Link to us

  search:   

Excerpt from OpenGLŪ SuperBible: Comprehensive Tutorial and Reference, 4th Edition.
Chapter 9: Texture Mapping: Beyond the Basics



Contents
  Secondary Color & Anisotropic Filtering
  Texture Compression
  Texture Coordinate Generation
  Multitexture
  Texture Combiners
  Point Sprites

  Printable version
  Discuss this article

What you'll learn in this chapter:

How To

Functions You'll Use

Add specular highlights to textured objects

glLightModel/glSecondaryColor

Use anisotropic texture filtering

glTexParameterf

Load and use compressed textures

glCompressedTexImage/glCompressedTexSubImage

Use points as textured quads

glPointParameter

Texture mapping is perhaps one of the most exciting features of OpenGL (well, close behind shaders anyway!) and is heavily relied on in the games and simulation industry. In Chapter 8, "Texture Mapping: The Basics," you learned the basics of loading and applying texture maps to geometry. In this chapter, we'll expand on this knowledge and cover some of the finer points of texture mapping in OpenGL.

Secondary Color

Applying texture to geometry, in regard to how lighting works, causes a hidden and often undesirable side effect. In general, you set the texture environment to GL_MODULATE, causing lit geometry to be combined with the texture map in such a way that the textured geometry also appears lit. Normally, OpenGL performs lighting calculations and calculates the color of individual fragments according to the standard light model. These fragment colors are then multiplied by the filtered texel colors being applied to the geometry. However, this process has the side effect of suppressing the visibility of specular highlights on the geometry. Basically, any texture color multiplied by ones (the white spot) is the same texture color. You cannot, by multiplication of any number less than or equal to one, make a color brighter than it already is!

For example, Figure 9.1 shows the original lit SPHEREWORLD sample from Chapter 5, "Color, Materials, and Lighting: The Basics." In this figure, you can see clearly the specular highlights reflecting off the surface of the torus. In contrast, Figure 9.2 shows the SPHEREWORLD sample from Chapter 8. In this figure, you can see the effects of having the texture applied after the lighting has been added.

Figure 9.1
The original SPHEREWORLD torus with specular highlights.

Figure 9.2
The textured torus with muted highlights.

The solution to this problem is to apply (by adding instead of multiplication) the specular highlights after texturing. This technique, called the secondary specular color, can be manually applied or automatically calculated by the lighting model. Usually, you do this using the normal OpenGL lighting model and simply turn it on using glLightModeli, as shown here:

glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL, GL_SEPARATE_SPECULAR_COLOR);

You can switch back to the normal lighting model by specifying GL_SINGLE_COLOR for the light model parameter:

glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL, GL_COLOR_SINGLE);

Figure 9.3 shows the output from this chapter's version of SPHEREWORLD with the restored specular highlights on the torus. We do not provide a listing for this sample because it simply contains the addition of the preceding single line of code.

Figure 9.3
Highlights restored to the textured torus.

You can also directly specify a secondary color after texturing when you are not using lighting (lighting is disabled) using the glSecondaryColor function. This function comes in many variations just as glColor does and is fully documented in the reference section. You should also note that if you specify a secondary color, you must also explicitly enable the use of the secondary color by enabling the GL_COLOR_SUM flag:

glEnable(GL_COLOR_SUM);

Manually setting the secondary color only works when lighting is disabled.

Anisotropic Filtering

Anisotropic texture filtering is not a part of the core OpenGL specification, but it is a widely supported extension that can dramatically improve the quality of texture filtering operations. Texture filtering is covered in the preceding chapter, where you learned about the two basic texture filters: nearest neighbor (GL_NEAREST) and linear (GL_LINEAR). When a texture map is filtered, OpenGL uses the texture coordinates to figure out where in the texture map a particular fragment of geometry falls. The texels immediately around that position are then sampled using either the GL_NEAREST or the GL_LINEAR filtering operations.

This process works perfectly when the geometry being textured is viewed directly perpendicular to the viewpoint, as shown on the left in Figure 9.4. However, when the geometry is viewed from an angle more oblique to the point of view, a regular sampling of the surrounding texels results in the loss of some information in the texture (it looks blurry!). A more realistic and accurate sample would be elongated along the direction of the plane containing the texture. This result is shown on the right in Figure 9.4. Taking this viewing angle into account for texture filtering is called anisotropic filtering.

Figure 9.4
Normal texture sampling versus anisotropic sampling.

You can apply anisotropic filtering to any of the basic or mipmapped texture filtering modes; applying it requires three steps. First, you must determine whether the extension is supported. You can do this by querying for the extension string GL_EXT_texture_filter_anisotropic. You can use the glTools function named gltIsExtSupported for this task:

if(gltIsExtSupported("GL_EXT_texture_filter_anisotropic"))
  // Set Flag that extension is supported

After you determine that this extension is supported, you can find the maximum amount of anisotropy supported. You can query for it using glGetFloatv and the parameter GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT:

GLfloat fLargest;
. . .
. . .
glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &fLargest);

The larger the amount of anisotropy applied, the more texels are sampled along the direction of greatest change (along the strongest point of view). A value of 1.0 represents normal texture filtering (called isotropic filtering). Bear in mind that anisotropic filtering is not free. The extra amount of work, including other texels, can sometimes result in substantial performance penalties. On modern hardware, this feature is getting quite fast and is becoming a standard feature of popular games, animation, and simulation programs.

Finally, you set the amount of anisotropy you want applied using glTexParameter and the constant GL_TEXTURE_MAX_ANISOTROPY_EXT. For example, using the preceding code, if you want the maximum amount of anisotropy applied, you would call glTexParameterf as shown here:

glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, fLargest);

This modifier is applied per texture object just like the standard filtering parameters.

The sample program ANISOTROPIC provides a striking example of anisotropic texture filtering in action. This program displays a tunnel with walls, a floor, and ceiling geometry. The arrow keys move your point of view (or the tunnel) back and forth along the tunnel interior. A right mouse click brings up a menu that allows you to select from the various texture filters, and turn on and off anisotropic filtering. Figure 9.5 shows the tunnel using trilinear filtered mipmapping. Notice how blurred the patterns become in the distance, particularly with the bricks.

Figure 9.5
ANISOTROPIC tunnel sample with trilinear filtering.

Now compare Figure 9.5 with Figure 9.6, in which anisotropic filtering has been enabled. The mortar between the bricks is now clearly visible all the way to the end of the tunnel. In fact, anisotropic filtering can also greatly reduce the visible mipmap transition patterns for the GL_LINEAR_MIPMAP_NEAREST and GL_NEAREST_MIPMAP_NEAREST mipmapped filters.

Figure 9.6
ANISOTROPIC tunnel sample with anisotropic filtering.





Texture Compression