Part of the Khronos Group
OpenGL.org

The Industry's Foundation for High Performance Graphics

from games to virtual reality, mobile phones to supercomputers

Results 1 to 5 of 5

Thread: Critique my normal calculations, they're backwards but work!

  1. #1
    Junior Member Newbie
    Join Date
    Feb 2010
    Posts
    16

    Critique my normal calculations, they're backwards but work!

    Hi, I just recently was able to render coherent terrains after quite a long time of trying. I'm not sure why this works but it does, I simply switched the equation around:

    instead of: < what every example i've seen says to do
    normal = (v1 - v2) * (v2 - v3)



    i tried
    normal = (v1 * v2) - (v2 * v3)

    and it looks good

    why is this so? I don't understand this and it baffles me. did the forces of OpenGL come together and i have a working bug, i've been experimenting with light positioning, and it doesn't appear as if the position of my light matches what I feed it. for example. If i set my light position to:
    x = 2571.15
    y = 6000
    z = 3064.18
    ??? = 45

    it appears as if the center of the light source is closer to
    x = z = 60

    at least that is where the center of my spot_light_cutoff point is in relation to the terrain that i am drawing.

    - I am calling glLightfv after a switch to the modelview matrix, and after i translate to my camera position.


    __________________________________________________
    Another question i have is:

    Code cpp:
        GLfloat poslight[4] = {x, y, z, ??? };
        glLightfv(GL_LIGHT0, GL_POSITION, poslight );

    what is the fourth parameter for?
    __________________________________________________




    * Note, this normal list jumps by four because i'm rendering quads

    Code cpp:
    void ModelObject::CalculateNormals()
    {
        for(int i=0;i<normal_count;i+=12) {
            float v1_x = vertexes[i+0];
            float v1_y = vertexes[i+1];
            float v1_z = vertexes[i+2];
     
     
            float v2_x = vertexes[i+3];
            float v2_y = vertexes[i+4];
            float v2_z = vertexes[i+5];
     
     
            float v3_x = vertexes[i+6];
            float v3_y = vertexes[i+7];
            float v3_z = vertexes[i+8];
     
     
     
            normals[i+0] =  (v1_x * v2_x) - (v2_x * v3_x);
            normals[i+1] =  (v1_y * v2_y) - (v2_y * v3_y);
            normals[i+2] =  (v1_z * v2_z) - (v2_z * v3_z);
     
     
            normals[i+3] =  (v1_x * v2_x) - (v2_x * v3_x);
            normals[i+4] =  (v1_y * v2_y) - (v2_y * v3_y);
            normals[i+5] =  (v1_z * v2_z) - (v2_z * v3_z);
     
     
            normals[i+6] =  (v1_x * v2_x) - (v2_x * v3_x);
            normals[i+7] =  (v1_y * v2_y) - (v2_y * v3_y);
            normals[i+8] =  (v1_z * v2_z) - (v2_z * v3_z);
     
     
            normals[i+9] =  (v1_x * v2_x) - (v2_x * v3_x);
            normals[i+10] = (v1_y * v2_y) - (v2_y * v3_y);
            normals[i+11] = (v1_z * v2_z) - (v2_z * v3_z);
     
        }
     
     
    // I believe i should normalize to unit length here
     
        // Smooth the normals (for heightmap only)
        for(int i=0;i<normal_count;i+=12) {
            float n1_x = normals[i+0];
            float n1_y = normals[i+1];
            float n1_z = normals[i+2];
     
     
            float n2_x = normals[i+3];
            float n2_y = normals[i+4];
            float n2_z = normals[i+5];
     
     
            float n3_x = normals[i+6];
            float n3_y = normals[i+7];
            float n3_z = normals[i+8];
     
     
            float n4_x = normals[i+9];
            float n4_y = normals[i+10];
            float n4_z = normals[i+11];
     
            float n1 = n1_x + n2_x + n3_x + n4_x;
            n1 /= 4;
            normals[i+0] = normals[i+3] = normals[i+6] = normals[i+9] = n1;
     
            float n2 = n1_y + n2_y + n3_y + n4_y;
            n2 /= 4;
            normals[i+1] = normals[i+4] = normals[i+7] = normals[i+10] = n2;
     
            float n3 = n1_z + n2_z + n3_z + n4_z;
            n3 /= 4;
            normals[i+2] = normals[i+5] = normals[i+8] = normals[i+11] = n3;
     
     
     
        }
    }

    thank you!
    Last edited by Dark Photon; 11-01-2012 at 05:17 AM.

  2. #2
    Intern Newbie
    Join Date
    Oct 2011
    Posts
    46
    Code cpp:
    //********************************************************************
    bool CVector3f::crossP(CVector3f* v1, CVector3f* v2){
     
        coord[0]= v1->coord[1]*v2->coord[2] - v1->coord[2]*v2->coord[1];
        coord[1]= v1->coord[2]*v2->coord[0] - v1->coord[0]*v2->coord[2];
        coord[2]= v1->coord[0]*v2->coord[1] - v1->coord[1]*v2->coord[0];
     
    if(coord[0] || coord[1] || coord[2]) return true;
    else return false; //if they are paralell.
    }
    //********************************************************************
    ^^^^this is the function Im using

    normal = (v1 - v2) * (v2 - v3) = v2*(v1 - v2) + v3*(v2 - v1) //I never seen this one
    normal = (v1 * v2) - (v2 * v3)

    You need vectors if you want to calculate cross product not vertexes. Except if the "vertex" is a vector that starts from the origo.

    If A,B,C,D are the points of a quad, then you should do:
    AB= B - A
    AC= C - A

    normal = AB x AC

    If you dont need it to be 1.0 long then dont normalize it.

    This seems like some magic

    float n1 = n1_x + n2_x + n3_x + n4_x;
    n1 /= 4;
    normals[i+0] = normals[i+3] = normals[i+6] = normals[i+9] = n1;

    Try this:
    Code cpp:
    //********************************************************************
    float CVector3f::normalize(){
     
     
         float temp;
     
         if( !(temp= sqrt(coord[0]*coord[0] + coord[1]*coord[1] + coord[2]*coord[2])) ) return 0.0;
     
     
         coord[0]/= temp;
         coord[1]/= temp;
         coord[2]/= temp;
     
    return temp;
    }
    //********************************************************************
    Last edited by Dark Photon; 11-01-2012 at 05:18 AM.

  3. #3
    Senior Member OpenGL Guru Dark Photon's Avatar
    Join Date
    Oct 2004
    Location
    Druidia
    Posts
    3,124
    Please use [code]...[/code] tags to mark your source code (or [highlight=cpp]...[/highlight]). Inserted them for you.

  4. #4
    Member Regular Contributor
    Join Date
    Aug 2008
    Posts
    433
    In this equation:
    Quote Originally Posted by dirk103 View Post
    normal = (v1 - v2) * (v2 - v3)
    The "-" is a vector subtraction operation, and the "*" is a cross product, it doesn't mean you multiply each term (x,y,z) in that way.

    Check out this article for more info about vectors.

    If you write a vector class and overload certain operators, eg. "+", "-", "+=", "-=", "*", you could use the original equation directly.

  5. #5
    Junior Member Newbie
    Join Date
    Feb 2010
    Posts
    16
    Ah, very good sir. Thank you!

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •