Time for Action: Using Multi-Texturing

Let's cover an example of multi-texturing in action:

  1. Open the ch07_05_multi-texture.html file with your editor.
  2. At the top of the script block, add another texture variable:
let texture2;
  1. At the bottom of the configure function, add the code to load the second texture. We're using a class to make this process easier, so the new code is as follows:
texture2 = new Texture();
texture2.setImage('/common/images/light.png');
  1. The texture we're using is a white radial gradient that simulates a spot light:

  1. In the render function, directly below the code that binds the first texture, add the following to expose the new texture to the shader:
gl.activeTexture(gl.TEXTURE1);
gl.bindTexture(gl.TEXTURE_2D, texture2.tex);
gl.uniform1i(program.uSampler2, 1);
  1. We need to add the new sampler uniform to the fragment shader:
uniform sampler2D uSampler2;
  1. Don't forget to add the corresponding string to the uniforms list in the configure function.
  2. We add the code to sample the new texture value and blend it with the first texture. Since we want the second texture to simulate a light, we multiply the two values together as we did with the per-vertex lighting in the first texture example:
fragColor = texture(uSampler2, vTextureCoords) * texture(uSampler, vTextureCoords);
  1. Note that we're re-using the same texture coordinate for both textures. This is more convenient but, if needed, a second texture coordinate attribute could be provided or we could calculate a new texture coordinate from the vertex position or some other criteria.
  2. You should see a scene that looks like this when you open the file in your browser:

  1. You can see the completed example in ch07_06_multi-texture-final.html.

What just happened?

We've added a second texture to the render call and blended it with the first to create a new effect, which, in this case, simulates a simple static spotlight.

It's important to realize that the colors sampled from a texture are treated like any other color in the shader—that is, as a generic 4-dimensional vector. As a result, we can combine textures just as we would combine vertex and light colors, or any other color manipulation.