Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Waterwave normals calculation slightly off

Tags:

math

opengl

glsl

I implemented "The Sum of Sines Approximation" in this article: https://developer.nvidia.com/gpugems/gpugems/part-i-natural-effects/chapter-1-effective-water-simulation-physical-models

My geometry is working fine, but the normals are somewhat wrong. They x- and z-values are flipped, and I wonder what i did wrong in the implementation.

The following equations are used: enter image description here

The generation of the normals looks like this in the shader:

vec3 generateWaveSineSumNormal(sineParams _params[sineCount])
{
        vec2 pos = vec2(aPos.x, aPos.z);
        vec3 normal = vec3(0.0f, 1.0f, 0.0f);

        for(int i=0; i<sineCount; i++)
        {
            sinParams curParams = _params[i];
            normal.x += sineExponent * curParams.direction.x * curParams.frequency * curParams.amplitude * 
                        pow((sin(dot(curParams.direction, pos) * curParams.frequency + curTime * curParams.speed)+1)/2, sineExponent-1)
                        * cos(dot(curParams.direction, pos) * curParams.frequency + curTime * curParams.speed);

            normal.z += sineExponent * curParams.direction.y * curParams.frequency * curParams.amplitude * 
                        pow((sin(dot(curParams.direction, pos) * curParams.frequency + curTime * curParams.speed)+1)/2, sineExponent-1)
                        * cos(dot(curParams.direction, pos) * curParams.frequency + curTime * curParams.speed);
        }

        return vec3(-normal.x, normal.y, -normal.z);

}

When the x- and z-values are flipped like this, the normals are fine. I'm just wondering what I did wrong implementing it, since I just can't find it.


1 Answers

Your normal.xz calculates the gradient of the heightmap correctly. The gradient points uphill, i.e. where the height values increase. The normal, when projected on the horizontal plane, would point backwards.

This can be derived mathematically through the use of cross-product of two tangents, which is what that article does in the "Normals and Tangents" section. In particular the relevant result is the formula for the normal in "Equation 6b", which includes the negative signs:

Equation 6b

like image 50
Yakov Galka Avatar answered Oct 19 '25 00:10

Yakov Galka



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!