Microsoft DirectX 8.1 (C++) |
Applications often need to apply textures to geometry in a scene so that texels map directly to on-screen pixels. For example, take an application that needs to display text within a texture on an object within a scene. In order to clearly display textual information in a texture, the application needs some way to ensure that the textured geometry receives texels undisrupted by texture filtering. Failing this, the resulting image is often blurred, or in the case of point-sampled texture filtering, can cause rough edges.
Because the Microsoft® Direct3D® pixel and texture sampling rules are carefully defined to unify pixel and texture sampling while supporting image and texture filtering, getting the texels in a texture to map directly to on-screen pixels can be a significant and often frustrating challenge. Overcoming this challenge requires a clear understanding of how Direct3D maps the floating-point texture coordinates for a vertex to the integer pixel coordinates used by the rasterizer.
Direct3D performs the following computations to map floating point texture coordinates to texel addresses.
In these formulas, Tx and Ty are the horizontal and vertical output texel coordinates, and u and v are the horizontal and vertical texture coordinates supplied for the vertex. The Mx and My elements represent the number of horizontal or vertical texels at the current mipmap level. The remainder of this discussion targets horizontal mapping of texels to pixels; keep in mind that mapping in the vertical is identical to the horizontal case.
Placing the texture coordinate limits 0.0 and 1.0 into these formulas maps a texture coordinate of 0.0 halfway between the first and last texels of a repeated texture map. The coordinate 1.0 is mapped halfway between the last texel of the current iteration of the texture map and the next iteration. For a repeated texture that's four texels wide, at mipmap level 0, the following illustration shows where the system maps the coordinates 0.0 and 1.0.
Given an understanding of this mapping, you can apply a simple bias to your screen-space geometry coordinates to force the system to map each texel to a corresponding pixel. For example, to draw a four-sided polygon that maps each texel from the preceding texture to one, and only one, pixel on the screen, you must force geometry coordinates to overlap the pixels, effectively placing the center of each texel at the center of each pixel. The result is the 1-to-1 mapping often sought-after by applications.
To map the texture with a 4-texel width to the pixel coordinates 0 through 3, draw a four-sided polygon, from two triangles, that has screen-space coordinates of –0.5 to 3.5 and texture coordinates of 0.0 to 1.0. For example, take the pixel at screen coordinate 0.0. Because 0.0 is one-half pixel away from the first vertex, at -0.5, and the total width is 4.0, the iterated texture coordinate is 0.125. Scaling this by the texture size, which is 4, results in the coordinate 0.5. Subtracting this 0.5 bias produces a texture address of 0.0, which fully maps to the first texel in the map.
To summarize, texture coordinates overlap the texture map evenly on both sides. The following illustration shows the mapping of a texture that is four texels wide.
The system normalizes pixel coordinates in the same way it normalizes texel coordinates. Therefore, if the vertices overlap the pixels into which to render, and if the vertices use texture coordinates of 0.0 and 1.0, the pixels and texels line up. If both are of similar size and properly aligned, they match exactly, texel to pixel, as shown in the following figure.