Book Image

WebGL HOTSHOT

By : Mitch Williams
Book Image

WebGL HOTSHOT

By: Mitch Williams

Overview of this book

Table of Contents (17 chapters)
WebGL HOTSHOT
Credits
About the Author
About the Reviewers
www.PacktPub.com
Preface
Index

Adding texture maps to 3D meshes


So far, our objects have been pretty basic shapes and in a single color. That's why they are called primitives. But of course, 3D objects are far more complex and require the talent of artists. Texture maps help us to understand how complex 3D objects are assembled based on simple ones. Have a look at the following figure:

Engage thrusters

A solid colored triangle is the simplest object to draw. I often suggest drawing objects on paper and labelling the vertices depending on how they are connected because it can be very tedious to form shapes from memory:

<Shape>
<Appearance>
    <Material diffuseColor="1 1 0"/>
</Appearance>
    <IndexedFaceSet coordIndex="0 1 2 -1">
    <Coordinate point="-2 2 0   -2 -2 0   2 -2 0"/>
    </IndexedFaceSet>
</Shape>

Instead of specifying a box or sphere, the shape in the preceding code consists of IndexedFaceSet with three points or vertices connected in the order listed by coordIndex = "0 1 2 -1". Vertex 0 is connected to vertex 1, vertex 1 is connected to vertex 2, and vertex 2 is connected back to vertex 0. The side that should face us is determined by the right-hand rule. Using your right hand, curve your fingers in the order of the vertices. The direction of your thumb is the direction that the polygon faces. So, as you curve your fingers counter-clockwise, if your thumb is pointing towards you, the polygon will be visible to you. The vertices are connected in a counter-clockwise order.

Let's add a texture map of a wonderful Basset Hound dog with a wet, pink tongue. The camera has been slightly rotated to distinguish this 3D object from a flat image. Have a look at the following screenshot:

Have a look at the following code:

<Shape>
<Appearance>
<ImageTexture url="./textureMaps/bassethound.jpg"/>
</Appearance>
<IndexedFaceSet coordIndex="0 1 2 -1   2 3 0 -1" texCoordIndex="0 1 2 -1   2 3 0 -1">
    <Coordinate point="-2 2 0   -2 -2 0   2 -2 0   2 2 0"/>
    <TextureCoordinate point="0 1   0 0   1 0   1 1"/>
</IndexedFaceSet>
</Shape>

In the preceding code, a fourth coordinate point has been added to form two triangles. The IndexedFaceSet coordIndex node now specifies two triangles. It is preferred to use triangles rather than polygons of four or more vertices for the same reason that a three-legged chair won't wobble, but a four-legged chair may wobble because one leg may be longer than the others and not sit flat on the ground. At least this is a nontechnical and noncomplex answer. Three vertex polygons will always be flat or planer and four vertex polygons can be bent. Additionally, it's often just about selecting a checkbox to export a 3D mesh using only triangles for artists.

The <Appearance> tag now has an <ImageTexture> node tag instead of a <Material> tag and specifies an image similar to how HTML would embed an image into a web page. A texture map on a 3D mesh is like hanging wallpaper on a wall. We paste the wallpaper to the corners. We need to align the corners of the walls with the correct corners of the wallpaper; otherwise, the wallpaper gets hung sideways or upside down. The <TextureCoordinate> point specifies which corner of the texture map is placed at each vertex of the 3D mesh. The lower-left corner of a texture map is (0, 0), and the upper-right corner is (1, 1). The first value is along the x axis, and the second value is along the y axis.

The <TextureCoordinate> point gets aligned to the <Coordinate> point vertices. For example, the first <Coordinate> point is (-2, 2, 0), which is the upper-left vertex, and the first <TextureCoordinate> point is (0, 1), which is the upper-left corner of the texture map.

The final texture map shows the <TextureTransform> tag, which is often used for tiling (such as repeating a brick wall pattern), but it can also be used for shifting and rotating images. For example, texture maps can also be animated to create nice water effects.

The three images in the preceding screenshot show tiling with a texture map of 3 x 2 in the upper-left 3D mesh, rotation of the texture map by 0.2 radians in the image on the right, and translation of the texture map by -0.3 units to the left and 0.6 units upwards in the image in the lower-left-hand side corner. In the following code, within the <Scene> tags, there are three <Transform> tags, one tag for each <Shape> node, and the <TextureTransform> node:

<Scene>
<Transform translation="-3 2 -3">
<Shape>
<Appearance>
<ImageTexture DEF="basset"
url="./textureMaps/bassethound.jpg"/>
<TextureTransform scale="3 2"/>
</Appearance>
    <IndexedFaceSet DEF="bassetIFS"
        coordIndex="0 1 2 -1   2 3 0 -1"
        texCoordIndex="0 1 2 -1   2 3 0 -1">
            <Coordinate point="-2 2 0   -2 -2 0   2 -2 0
            2 2 0"/>
                <TextureCoordinate point="0 1   0 0   1 0
                1 1"/>
    </IndexedFaceSet>
    </Shape>
        </Transform>
        <Transform  translation="2 1 -2">
    <Shape>
        <Appearance>
            <ImageTexture USE="basset"/>
            <TextureTransform rotation=".2"/>
        </Appearance>
        <IndexedFaceSet USE="bassetIFS"/>
    </Shape>
        </Transform>
        <Transform  translation="-3 -3 -4">
    <Shape>
        <Appearance>
            <ImageTexture USE="basset"/>
            <TextureTransform translation=".3 -.6"/>
        </Appearance>
        <IndexedFaceSet USE="bassetIFS"/>
        </Shape>
    </Transform>
</Scene>

Objective complete – mini debriefing

Since each of the 3D meshes shares the same <ImageTexture> and <IndexedFaceSet> nodes, this application is a perfect opportunity to use the DEF and USE properties. Through <DEF> and <USE>, we were able to focus on the capabilities of the <TextureTransform> node.