   Tangent problem
  I am implimenting normal mapping in my program and must calculate the tangent for use in the shader.  So i used terathon.com's method of calculating the tangents, along with code to average the tangents of vertices that are shared among mayn faces (I'm using VA at the moment).  And here is the code:void nrgObject::makeTanArray(){float x1, x2, y1, y2, z1, z2, s1, s2, t1, t2, r, NdotT, BdotT;NORMAL  sdir, tdir, tTan, NcrossT;TANGENT tempTangent;std::vector<TANGENT> allTangents;// for each trianglestd::vector<GEOM_INDEX>::size_type triIndex = std::vector<GEOM_INDEX>::size_type(0);while(triIndex < index.size()){GEOM_INDEX tV2 = index[triIndex];x1 = rVerts[tV2.v2].x - rVerts[tV2.v1].x;x2 = rVerts[tV2.v3].x - rVerts[tV2.v1].x;y1 = rVerts[tV2.v2].y - rVerts[tV2.v1].y;y2 = rVerts[tV2.v3].y - rVerts[tV2.v1].y;z1 = rVerts[tV2.v2].z - rVerts[tV2.v1].z;z2 = rVerts[tV2.v3].z - rVerts[tV2.v1].z;s1 = rVerts[tV2.v2].u - rVerts[tV2.v1].u;s2 = rVerts[tV2.v3].u - rVerts[tV2.v1].u;t1 = rVerts[tV2.v2].v - rVerts[tV2.v1].v;t2 = rVerts[tV2.v3].v - rVerts[tV2.v1].v;r = 1.0f / (s1*t2 - s2*t1);sdir.i = (t2*x1 - t1*x2)*r;sdir.j = (t2*y1 - t1*y2)*r;sdir.k = (t2*z1 - t1*z2)*r;tdir.i = (s1*x2 - s2*x1)*r;tdir.j = (s1*y2 - s2*y1)*r;tdir.k = (s1*z2 - s2*z1)*r;// perform Gram-Schmidt orthogonalize for each vertex of face// sdir - normaltTan.i = sdir.i - rVerts[tV2.v1].i;tTan.j = sdir.j - rVerts[tV2.v1].j;tTan.k = sdir.k - rVerts[tV2.v1].k;// dot(normal, sdir)NdotT = (rVerts[tV2.v1].i * sdir.i) + (rVerts[tV2.v1].j * sdir.j)+ (rVerts[tV2.v1].k * sdir.k);// (sdir - n)*NdotTtTan.i *= NdotT;tTan.j *= NdotT;tTan.k *= NdotT;// normalizetTan.i /= sqrtf((tTan.i * tTan.i) + (tTan.j * tTan.j) + (tTan.k * tTan.k));tTan.j /= sqrtf((tTan.i * tTan.i) + (tTan.j * tTan.j) + (tTan.k * tTan.k));tTan.k /= sqrtf((tTan.i * tTan.i) + (tTan.j * tTan.j) + (tTan.k * tTan.k));// normal X sdir = BitangentNcrossT.i = rVerts[tV2.v1].j*sdir.k - rVerts[tV2.v1].k*sdir.j;NcrossT.j = rVerts[tV2.v1].k*sdir.i - rVerts[tV2.v1].i*sdir.k;NcrossT.k = rVerts[tV2.v1].i*sdir.j - rVerts[tV2.v1].j*sdir.i;// dot(bitangent, tdir)BdotT = (NcrossT.i * tdir.i) + (NcrossT.j * tdir.j)+ (NcrossT.k * tdir.k);tempTangent.s = tTan.i;tempTangent.t = tTan.j;tempTangent.r = tTan.k;tempTangent.h = (BdotT < 0.0f) ? -1.0f : 1.0f; // handednesstempTangent.vert = tV2.v1; // vertex tangetn belongs toallTangents.push_back(tempTangent);  // add it to vector of tangents// which come out to # of faces// times 3 (trianlge)// repeat the code above for the other two verticestriIndex++;}// for each face (each index points to 3 vertices to make on face)triIndex = std::vector<GEOM_INDEX>::size_type(0);while(triIndex < index.size()){GEOM_INDEX tV2 = index[triIndex];int tanCount;std::vector<TANGENT> tempTan;std::vector<TANGENT>::size_type aTans;// rVerts[iterator].h was set to -2.0 since handedness can't equal anything// other then 1.0 or 1.0, so if the vertex's tangent wasn't computed,// compute itif(rVerts[tV2.v1].h == -2.0f){// reset variavlestempTangent.s = 0.0f;tempTangent.t = 0.0f;tempTangent.r = 0.0f;tempTangent.h = -1.0f;//tempTangent.vert = -1.0f;tempTan.clear();aTans = std::vector<TANGENT>::size_type(0);tanCount = 0;// search through vector for all tangents that belong to the current vertexwhile(aTans < allTangents.size()){TANGENT tT = allTangents[aTans];// if the index numbers match, add it to the vector used to average// the tangentsif(tT.vert == tV2.v1)tempTan.push_back(tT);aTans++;}// for all of the tangents of the vertex...aTans = std::vector<TANGENT>::size_type(0);for(aTans = 0; aTans <  tempTan.size(); aTans++){// add them uptempTangent.s += tempTan[aTans].s;tempTangent.t += tempTan[aTans].t;tempTangent.r += tempTan[aTans].r;// um, not sure if this is right :StempTangent.h *= tempTan[aTans].h;tanCount++; // keep count of the number of tangents}// average the componentstempTangent.s /= float(tanCount);tempTangent.t /= float(tanCount);tempTangent.r /= float(tanCount);// set the current vertex's tangent inforVerts[tV2.v1].s = tempTangent.s;rVerts[tV2.v1].t = tempTangent.t;rVerts[tV2.v1].r = tempTangent.r;rVerts[tV2.v1].h = tempTangent.h;}// same as above for the other 2 vertices would go heretriIndex++;}}Sorry for the lack of vector classes.  I then pass those tangents in the vertex array via GL_TEXTURE_COORD_ARRAY.  Then, in the vertex shader, I calculate the bitangent, multipling it by the handedness.  In the fragment shader, I use the normal map as the normal of the fragment.  My shader code (note: code taken from an online tutorial and modified):Vert shader:varying vec4 lightDir;varying vec3 normal, halfVector, spotDir;void main(){vec3 tempLight;// computing TBN matrix for tangent space ****************************************************vec3 v_Normal = normalize(gl_NormalMatrix*gl_Normal); // normal to eye spacevec3 v_Tangent = normalize(gl_NormalMatrix*gl_MultiTexCoord7.xyz); // tangent to eye spacevec3 v_Binormal = cross(v_Normal, v_Tangent) * gl_MultiTexCoord7.w; // binormal to eye spacemat3 tangentBasis = mat3( // in column major orderv_Tangent.x, v_Binormal.x, v_Normal.x,v_Tangent.y, v_Binormal.y, v_Normal.y,v_Tangent.z, v_Binormal.z, v_Normal.z);// compute light vector ***********************************************************************vec4 ecPos, bb;vec3 aux;ecPos = gl_ModelViewMatrix * gl_Vertex;aux = vec3(gl_LightSource[1].position-ecPos);tempLight = aux;// compute normal and half vector **************************************************************normal = normalize(gl_NormalMatrix * gl_Normal);// vertex to eye coordinateshalfVector = normalize(gl_LightSource[1].halfVector.xyz);// convert coordinates to tangent space ********************************************************tempLight = tangentBasis * tempLight;halfVector = tangentBasis * halfVector;spotDir = tangentBasis * gl_LightSource[1].spotDirection;// pass texture coords to fragment shader ******************************************************gl_TexCoord[0] = gl_MultiTexCoord0;gl_TexCoord[1] = gl_MultiTexCoord1;// putting distance in w component of light ****************************************************lightDir = vec4(tempLight, 0.0);lightDir.w = length(aux);// convert vertex position *********************************************************************gl_Position = ftransform();}Frag shadervarying vec4 lightDir;varying vec3 normal, halfVector, spotDir;uniform sampler2D tex;uniform sampler2D norm;void main(){vec3 n,l,halfV;vec4 texel;float NdotL,NdotHV;float att;float spotEffect;float dist;// retrieve material parameters ***************************************************************vec4 color = gl_FrontLightModelProduct.sceneColor;vec4 ambient = gl_FrontLightProduct[1].ambient;vec4 diffuse = gl_FrontLightProduct[1].diffuse;vec4 specular = gl_FrontLightProduct[1].specular;// compute normals from normal map ************************************************************vec2 tuv = vec2(gl_TexCoord[1].s, gl_TexCoord[1].t);n = 2.0 * (texture2D(norm, tuv).rgb - 0.5);n = normalize(n);//n = normalize(normal);// compute light ******************************************************************************l = normalize(lightDir.xyz);dist = lightDir.w;NdotL = max(dot(n,l),0.0);if (NdotL > 0.0){spotEffect = dot(normalize(spotDir), normalize(-l));if (spotEffect > gl_LightSource[1].spotCosCutoff){spotEffect = pow(spotEffect, gl_LightSource[1].spotExponent);att = spotEffect / (gl_LightSource[1].constantAttenuation +gl_LightSource[1].linearAttenuation * dist +gl_LightSource[1].quadraticAttenuation * dist * dist);color += att * (diffuse * NdotL + ambient);halfV = normalize(halfVector);NdotHV = max(dot(n,halfV),0.0);color += att * specular * pow(NdotHV, gl_FrontMaterial.shininess);}}// apply texture ******************************************************************************texel = texture2D(tex,gl_TexCoord[0].st);color *= texel;// set fragment color *************************************************************************gl_FragColor = color;}The result is that the entire object is tinted blue; there is no bump; on a cube object, only 2 faces of the six light up, and before those two faces light up, there is a flicker or black snow when it gets to a certain angle.  Other objects also light wierdly.  Here are some examples:note: the light stays in the same postion of (-3.0, 4.0, -5.0)http://img.photobucket.com/albums/v296/dante4016/cube1.jpghttp://img.photobucket.com/albums/v296/dante4016/cube2.jpghttp://img.photobucket.com/albums/v296/dante4016/octo.jpghttp://img.photobucket.com/albums/v296/dante4016/sphere.jpgThe yellow and magenta bars you see are just from photoshop; don't know why it does that sometimes.  One more thing is that when I don't multiple the bitangent by the handedness, the same thing happens except I don't get the black snow flicker, it just lights up the entire face in one frame or so.  Being that the shader is from a tutorial, I think the problem lies in the tangent code (very sorry that it's a bit messy), but I'm not sure where.  Any ideas what the problem could be?   