PDA

View Full Version : Specify Normal Vectors



L.BB
03-02-2006, 08:20 AM
Hi,

I wanted to ask if it is possible to assign a normal vector to every pixel in a shader, and if yes how to do that. I want to declare a polygon and then assign different colour depending on the normal vector of the pixel (which I got from a normal map), the light direction and the light colour. How would I go about doing that. I so far have this fragment shader that I am tring to change now:

vec3 n,halfV,viewV,ldir;
float NdotL,NdotHV;
vec4 color = ambient;

/* a fragment shader can't write a verying variable, hence we need a new variable to store the normalized interpolated normal */

n = normalize(normal);

/* compute the dot product between normal and ldir */

NdotL = max(dot(n,lightDir),0.0);

if (NdotL > 0.0) {
halfV = normalize(halfVector);
NdotHV = max(dot(n,halfV),0.0);
color += gl_FrontMaterial.specular *
gl_LightSource[0].specular * pow
(NdotHV,gl_FrontMaterial.shininess);
color += diffuse * NdotL;
}
gl_FragColor = color;


But how would I go about specifying a different normal for every pixel?? I would appreciate any tipps or even if I this can be done or not etc. cause am only starting out with GLSL

selwakad
03-02-2006, 09:20 AM
read the normal vector from a texture attached to a sampler ... similar to the way bump mapping is done.

L.BB
03-02-2006, 09:33 AM
Yeah I have looked at the shader but how would I go about reading in the values and then applying them to every pixel? I know how to read in the coordinates of a texel but how would I go about reading in the normal vectors? Oh would I just read in the colour information.....but how would I "attach" it to pixels then? Sorry just a bit confused as it is a completely new thing for me, coming from a "vertex world" so to speak:-)

selwakad
03-02-2006, 09:55 AM
the texture stores the normals as color coded values, so you RGB values would actually represent the X, Y, Z values of each normal vector.
everytime you you get a fragment, read from the normal texture the normal values using the UVs of the color texture.

L.BB
03-02-2006, 10:16 AM
Thank you, I am just worried about actually assigning it to a fragment then but think am getting the hang of it. Would it be something like:

void main()
{
vec4 color = texture2D(tex,gl_TexCoord[0].st);
vec3 nor = (color[0], color[1], color[2]);

intensity = max(dot(lightDir,normalize(nor)),0.0);

...
gl_FragColor = color;
}

L.BB
03-02-2006, 10:18 AM
Thank you, I am just worried about actually assigning it to a fragment then but think am getting the hang of it. Would it be something like:

void main()
{
vec4 color = texture2D(tex,gl_TexCoord[0].st);
vec3 nor = (color[0], color[1], color[2]);

intensity = max(dot(lightDir,normalize(nor)),0.0);
...
gl_FragColor = pixel_color;
}

And then calculate it that way? Oh that would make sense wouldn't it??

Komat
03-02-2006, 11:14 AM
vec4 color = texture2D(tex,gl_TexCoord[0].st);
vec3 nor = (color[0], color[1], color[2]);....
And then calculate it that way?Yes something like that.
You will probably not use float texture to store the normals so you have to encode the normals in colors in such way, that coordinate range <-1,1> maps to colors in <0.0,1.0> range (0-255 in ubyte values). In fragment shader you will covert values back to the original range by calculating ( color * 2.0 - 1.0 )

Additionaly you have to ensure that normal you read from the texture and lighting direction are expressed in the same space or lighting will be incorrect.

L.BB
03-03-2006, 06:06 AM
Thank you so much for all your help! I have finally finished a big part of my project and I understand it and would have never thought of that color value although I had read about it previously! So mch to think about when you are just starting out in a language! THANK YOU!!!