When done right, terrain provides a smooth-surface model of mountains, rivers, cliffs, hills, and other geographic phenomena. The point of terrain is that it gives users the impression they are traversing the real world. From a more abstract perspective, however, terrain really only involves variations in height. For instance, a grassy plain is a terrain with constant height (except for maybe some bumps and hills). On the other hand, a mountain region is a terrain that has significant height variations, creating large glyphs between areas that lend the illusion of mountains. Rivers are plains combined with curves that contain lower heights than the surrounding plain. For example, the terrain in Figure 1 is described by three areas of greater heightthe three green hillsand the rest is a deep gorge filled with water.
Heightmaps let you create natural terrain by providing an elegant solution to storing variations in height and smoothing surfaces. To illustrate, Figure 2 is a grayscale image that looks like a donut with a white speck in the middle. A grayscale image is a collection of pixels where each pixel goes from 0 to 255, where 0 is black and 255 white. What if you could use each pixel to determine height? If a black pixel (value 0) could be the lowest height and a white pixel (value 255) the highest, you'd have a map that depicts heighta heightmap. Another great thing about this is that since pixels go from 0 to 255, you get automatic interpolation of the terrain (thus creating smooth terrain) if you just blur images.
In this article, I examine how to use heightmaps for creating realistic 3D graphics. For purposes of illustration, the platform I use is the Java ME JSR 184 specification (www.jcp.org/en/jsr/detail?id=184), the Mobile 3D Graphics (M3G) API that provides a scalable, small-footprint, interactive 3D API for mobile devices such as cell phones from Sony Ericsson. The complete source code accompanying this article is available at http://www.ddj.com/code/.