Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMitchell Stokes <mogurijin@gmail.com>2012-07-30 03:49:17 +0400
committerMitchell Stokes <mogurijin@gmail.com>2012-07-30 03:49:17 +0400
commit0690f6287cce55bd3dc094c7b9723c8ace4e4128 (patch)
tree04762c52c25fb072a92b3f4dc4d20c88321af29e /source/gameengine/Converter
parent3151a9f145ea5f2920426f28dada76a9e537719e (diff)
BGE: Fix for [#31993] "BGE Vertex deformer optimized method does not work properly" reported by Mario Mey plus some other cleanup. The bug was caused by not taking the object matrix into account when doing the transforms (when I developed the deformer, my test file had the object at the origin...).
Diffstat (limited to 'source/gameengine/Converter')
-rw-r--r--source/gameengine/Converter/BL_SkinDeformer.cpp32
1 files changed, 17 insertions, 15 deletions
diff --git a/source/gameengine/Converter/BL_SkinDeformer.cpp b/source/gameengine/Converter/BL_SkinDeformer.cpp
index 9bbf07a3ed2..47cba81798d 100644
--- a/source/gameengine/Converter/BL_SkinDeformer.cpp
+++ b/source/gameengine/Converter/BL_SkinDeformer.cpp
@@ -238,6 +238,7 @@ void BL_SkinDeformer::BGEDeformVerts()
MDeformVert *dverts = m_bmesh->dvert;
bDeformGroup *dg;
int defbase_tot = BLI_countlist(&m_objMesh->defbase);
+ Eigen::Matrix4f pre_mat, post_mat, chan_mat, norm_chan_mat;
if (!dverts)
return;
@@ -257,15 +258,18 @@ void BL_SkinDeformer::BGEDeformVerts()
}
}
+ post_mat = Eigen::Matrix4f::Map((float*)m_obmat).inverse() * Eigen::Matrix4f::Map((float*)m_armobj->GetArmatureObject()->obmat);
+ pre_mat = post_mat.inverse();
+
MDeformVert *dv= dverts;
+ MDeformWeight *dw;
for (int i=0; i<m_bmesh->totvert; ++i, dv++)
{
- float contrib = 0.f, weight, max_weight=0.f;
+ float contrib = 0.f, weight, max_weight=-1.f;
bPoseChannel *pchan=NULL;
- Eigen::Map<Eigen::Vector3f> norm(m_transnors[i]);
+ Eigen::Map<Eigen::Vector3f> norm = Eigen::Vector3f::Map(m_transnors[i]);
Eigen::Vector4f vec(0, 0, 0, 1);
- Eigen::Matrix4f norm_chan_mat;
Eigen::Vector4f co(m_transverts[i][0],
m_transverts[i][1],
m_transverts[i][2],
@@ -274,7 +278,9 @@ void BL_SkinDeformer::BGEDeformVerts()
if (!dv->totweight)
continue;
- MDeformWeight *dw= dv->dw;
+ co = pre_mat * co;
+
+ dw= dv->dw;
for (unsigned int j= dv->totweight; j != 0; j--, dw++)
{
@@ -286,12 +292,10 @@ void BL_SkinDeformer::BGEDeformVerts()
if (weight)
{
- Eigen::Vector4f cop(co);
- Eigen::Matrix4f chan_mat = Eigen::Matrix4f::Map((float*)pchan->chan_mat);
+ chan_mat = Eigen::Matrix4f::Map((float*)pchan->chan_mat);
// Update Vertex Position
- cop = chan_mat*cop;
- vec += (cop - co)*weight;
+ vec.noalias() += (chan_mat*co - co)*weight;
// Save the most influential channel so we can use it to update the vertex normal
if (weight > max_weight)
@@ -304,16 +308,14 @@ void BL_SkinDeformer::BGEDeformVerts()
}
}
}
-
// Update Vertex Normal
norm = norm_chan_mat.topLeftCorner<3, 3>()*norm;
-
- if (contrib > 0.0001f)
- {
- vec *= 1.f/contrib;
- co += vec;
- }
+
+ co.noalias() += vec/contrib;
+ co[3] = 1.f; // Make sure we have a 1 for the w component!
+
+ co = post_mat * co;
m_transverts[i][0] = co[0];
m_transverts[i][1] = co[1];