# Weird vertex-normal calculation bug.

This topic is 5139 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

Sorry if this has been posted here alot before, I can't seem to find the problem in my code. Anyways.. on to the problem.. As you can see above the smooth lighting gets calculated incorrectly. The lines in the image point to the direction of the vertex-normals, face normals are calculated correctly. To explain how I calculate the vertex-normal based on which face-normals, I made this map that goes with the sourcecode: Here's the code with documentation:

// Here's the struct I use for storing every "quad" (actually 2
// triangles,.. 4 vertixes, sinc two are always obsolete this way).
struct POLYGON{
GLfloat Pos[4][3];	// Vertex position
CVector3 Light[4];	// smooth Normal for each vertex
CVector3 nLight[2];	// face Normal for each triangle
GLfloat Text[4][2];	// Texture coordinats for each vertex
};

POLYGON NewMap[1024][1024];

void RAWTERRAIN::CalculateSmoothLighting()
{
int Xrender, Zrender;

// Calculate Smooth Lighting
// X side
Xrender = 0;
while (Xrender < LvlMem.MapSize)
{

// Z side
Zrender = 0;
while (Zrender < LvlMem.MapSize)
{
int setPos[18];

// Set Array positions, left setPos = x, right setPos = z.
setPos[0] = Xrender - 1; setPos[9]  = Zrender - 1;	// A - Left   Top
setPos[1] = Xrender    ; setPos[10] = Zrender - 1;	// B - Center Top
setPos[2] = Xrender + 1; setPos[11] = Zrender - 1;	// C - Right  Top
setPos[3] = Xrender - 1; setPos[12] = Zrender;		// D - Left   Middle
setPos[4] = Xrender    ; setPos[13] = Zrender;		// E - Center Middle
setPos[5] = Xrender + 1; setPos[14] = Zrender;		// F - Right  Middle
setPos[6] = Xrender - 1; setPos[15] = Zrender + 1;	// G - Left   Bottom
setPos[7] = Xrender    ; setPos[16] = Zrender + 1;	// H - Center Bottom
setPos[ 8]= Xrender + 1; setPos[17] = Zrender + 1;	// I - Right  Bottom

// Check to see if we go out of our array.
for (int counter = 0; counter < 16; counter++)
{
// Smaller than zero, go to the end of the array.
if (setPos[counter] < 0) setPos[counter] += LvlMem.MapSize;
// Bigger than the array, go to the start of it.
else if (setPos[counter] >= LvlMem.MapSize) setPos[counter] -= LvlMem.MapSize;
}

// Corner 1
NewMap[Xrender][Zrender].Light[0] = (
NewMap[ setPos[0] ][ setPos[9] ].nLight[1] +	// A o
NewMap[ setPos[1] ][ setPos[10]].nLight[0] +	// B
NewMap[ setPos[1] ][ setPos[10]].nLight[1] +	// B o
NewMap[ setPos[3] ][ setPos[12]].nLight[0] +	// D
NewMap[ setPos[3] ][ setPos[12]].nLight[1] +	// D o
NewMap[ setPos[4] ][ setPos[13]].nLight[0])/6;	// E
// Corner 2
NewMap[Xrender][Zrender].Light[1] = (
NewMap[ setPos[1] ][ setPos[10]].nLight[1] +	// B o
NewMap[ setPos[2] ][ setPos[11]].nLight[0] +	// C
NewMap[ setPos[2] ][ setPos[11]].nLight[1] +	// C o
NewMap[ setPos[4] ][ setPos[13]].nLight[1] +	// E o
NewMap[ setPos[4] ][ setPos[13]].nLight[0] +	// E
NewMap[ setPos[5] ][ setPos[14]].nLight[0])/6;	// F
// Corner 3
NewMap[Xrender][Zrender].Light[2] = (
NewMap[ setPos[3] ][ setPos[12]].nLight[1] +	// D o
NewMap[ setPos[4] ][ setPos[13]].nLight[1] +	// E o
NewMap[ setPos[4] ][ setPos[13]].nLight[0] +	// E
NewMap[ setPos[6] ][ setPos[15]].nLight[0] +	// G
NewMap[ setPos[6] ][ setPos[15]].nLight[1] +	// G o
NewMap[ setPos[7] ][ setPos[16]].nLight[0])/6;	// H

// Corner 4
NewMap[Xrender][Zrender].Light[3] = (
NewMap[ setPos[4] ][ setPos[13]].nLight[1] +	// E o
NewMap[ setPos[5] ][ setPos[14]].nLight[0] +	// F
NewMap[ setPos[5] ][ setPos[14]].nLight[1] +	// F o
NewMap[ setPos[7] ][ setPos[16]].nLight[0] +	// H
NewMap[ setPos[7] ][ setPos[16]].nLight[1] +	// H o
NewMap[ setPos[ 8]][ setPos[17]].nLight[0])/6;	// I

// All corners calculated
Zrender++;
}
Xrender++;
}
// Done
dbg.report(' ' , 0 , 0 , "RawTerrain: Smooth lighting calculated.");
}


I have no idea whats wrong with it, for each vertex I calculate 6 face-normal's ( there are only 6 connecting faces per vertex ). I would really appreciate it if someone finds the mistake I made, thanks in advance for your time!!

##### Share on other sites
I sugest you read this thread as it show another much better (faster and more corect) way of calculation normals for terrains.

##### Share on other sites
Here's a tip.

Don't divide the normals with 6 after adding them together, instead normalise them, it will yeald a better result.
You could allso share the normal with the vertics that share the same coords to insure that you get the same normal.

and then theres allways the option of using a normal map.

1. 1
Rutin
40
2. 2
3. 3
4. 4
5. 5

• 18
• 20
• 13
• 14
• 9
• ### Forum Statistics

• Total Topics
633365
• Total Posts
3011520
• ### Who's Online (See full list)

There are no registered users currently online

×