Here's what it looks like with a color and normal map:
Here's what the tangents look like when drawn to the color channel:
And here's what my tangent generation code looks like:
//do the bitangent and tangent crap
VectorType sdir, tdir;
TempVertexType vertex1, vertex2, vertex3;
int counter = 0;
unsigned long i1 = 0, i2 = 0, i3 = 0;
//this is all for the tangents
VectorType* tan1 = new VectorType[m_vertexCount * 2];
VectorType* tan2 = tan1 + m_vertexCount;
ZeroMemory(tan1, m_vertexCount * sizeof(VectorType) * 2);
for(unsigned int i = 0; i < m_indexCount; i++)
{
// get vertex1, vertex2 & vertex3
// Get the three vertices for this face from the model.
i1 = indices;
i++;
i2 = indices;
i++;
i3 = indices;
vertex1.x = m_model[i1].x;
vertex1.y = m_model[i1].y;
vertex1.z = m_model[i1].z;
vertex1.tu = m_model[i1].tu;
vertex1.tv = m_model[i1].tv;
vertex1.nx = m_model[i1].nx;
vertex1.ny = m_model[i1].ny;
vertex1.nz = m_model[i1].nz;
vertex2.x = m_model[i2].x;
vertex2.y = m_model[i2].y;
vertex2.z = m_model[i2].z;
vertex2.tu = m_model[i2].tu;
vertex2.tv = m_model[i2].tv;
vertex2.nx = m_model[i2].nx;
vertex2.ny = m_model[i2].ny;
vertex2.nz = m_model[i2].nz;
vertex3.x = m_model[i3].x;
vertex3.y = m_model[i3].y;
vertex3.z = m_model[i3].z;
vertex3.tu = m_model[i3].tu;
vertex3.tv = m_model[i3].tv;
vertex3.nx = m_model[i3].nx;
vertex3.ny = m_model[i3].ny;
vertex3.nz = m_model[i3].nz;
sdir.x = 0;
sdir.y = 0;
sdir.z = 0;
tdir.x = 0;
tdir.y = 0;
tdir.z = 0;
// Calculate the tangent and bitangent of that face.
CalculateTangentBitangent(vertex1, vertex2, vertex3, sdir, tdir);
tan1[i1].x += sdir.x; tan1[i1].y += sdir.y; tan1[i1].z += sdir.z;
tan1[i2].x += sdir.x; tan1[i2].y += sdir.y; tan1[i2].z += sdir.z;
tan1[i3].x += sdir.x; tan1[i3].y += sdir.y; tan1[i3].z += sdir.z;
tan2[i1].x += tdir.x; tan2[i1].y += tdir.y; tan2[i1].z += tdir.z;
tan2[i2].x += tdir.x; tan2[i2].y += tdir.y; tan2[i2].z += tdir.z;
tan2[i3].x += tdir.x; tan2[i3].y += tdir.y; tan2[i3].z += tdir.z;
}
vector<int> handedness;
for (unsigned long a = 0; a < m_vertexCount; a++)
{
VectorType n;
n.x = vertexList[a].nx; n.y = vertexList[a].ny; n.z = vertexList[a].nz;
const VectorType& t = tan1[a];
// Gram-Schmidt orthogonalize
tempTangents.push_back(normalize((t - n * dot(n, t))));
// Calculate handedness
handedness.push_back( (dot(cross(n, t), tan2[a]) < 0.0F) ? -1.0F : 1.0F );
}
//calculate bitangents
for (unsigned long a = 0; a < m_vertexCount; a++)
{
//B' = m(N × T')
VectorType tempN;
tempN.x = vertexList[a].nx; tempN.y = vertexList[a].ny; tempN.z = vertexList[a].nz;
tempBitangent.push_back(cross(tempN,tempTangents[a]) * handedness[a]);
}
Here's the CalculateTangentBitangent function:
void ModelClass::CalculateTangentBitangent(TempVertexType vertex1, TempVertexType vertex2, TempVertexType vertex3,
VectorType& sdir, VectorType& tdir)
{
float x1 = vertex2.x - vertex1.x;
float y1 = vertex2.y - vertex1.y;
float z1 = vertex2.z - vertex1.z;
float x2 = vertex3.x - vertex1.x;
float y2 = vertex3.y - vertex1.y;
float z2 = vertex3.z - vertex1.z;
float s1 = vertex2.tu - vertex1.tu;
float t1 = vertex2.tv - vertex1.tv;
float s2 = vertex3.tu - vertex1.tu;
float t2 = vertex3.tv - vertex1.tv;
float r = 1.0f / (s1 * t2 - s2 * t1);
sdir.x = (t2 * x1 - t1 * x2) * r;
sdir.y = (t2 * y1 - t1 * y2) * r;
sdir.z = (t2 * z1 - t1 * z2) * r;
tdir.x = (s1 * x2 - s2 * x1) * r;
tdir.y = (s1 * y2 - s2 * y1) * r;
tdir.z = (s1 * z2 - s2 * z1) * r;
}
Any ideas on how I can fix this?
Edit: The tangents looked a lot worse before, but I deleted some internal geometry in the model that didn't need to be there and for some reason this fixed a lot of the problems with the tangents. They still aren't that smooth though, and there are some artifacts I'd like to get rid of if possible.