Friday, September 21, 2007

GPU Water

My second attempt at water rendering uses a vertex/pixel shader along with normal and dudv map's. Using the normal and dudv map's along with the reflection texture, which is dynamically generated each frame, the final effect is achieved.

The image above is the normal map. Instead of using each pixel for a color, the nomal map stores a normal (between -1 and 1). The normals naturally give the image a purple, pink and blue color. What we do with this image is basically use it to bump map our water to give it the appearance of being highly tessellated and realistic. This realism comes when we use per-pixel lighting on the water. If we didn't have a normal map we would just depend on the normal of the water surface, which is pointing straight up, the water would look like a flat mirror.

The image above is the dudv map. It is called that because it's actually the derivative of a normal map. In mathematics the notation for a derivative is du/dv. What this texture does is give us a way to calculate refraction and how the light will react and bend on the water. Notice how the dudv map looks like waves of water.

The image above is the reflection texture. This is caculated each frame by inverting the scene, setting up a clipping plane and rendering the reflective data. Projective texture mapping is then used to apply this texture to the water.

Although I am happy with this implementation there are a few changes that need to be made. Memories of my first implementation of CPU water are coming back. My lake again looks like a mirror. It is too bright and too reflective. It should be possible to see some way under the surface of the water. I have tried to implement the simple changes which were required by CPU water, after I changed to using a reflection texture rather than drawing the inverted scene to the screen, however there is no differnce. Adding Alpha Blending with a fixed function does not seem to make any difference when the pixel shader is used. If I remove the shader from the rendering, a correct flat blue alpha blended quad is rendered. Since the GPU water is effected by per pixel lighting prehaps I need to modify the pixel shader in some way. I have read a few tutorials on OpenGL shaders, however I feel that I need to complete a few more before I have the confidence to say for sure.

1 comment:

  1. Can I use the UV texture in one of my projects I will publish?