网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!
接着,将当前骨骼变换矩阵乘以其父骨骼的变换矩阵( mxGlobalTransformation = mxNodeTransformation * mxParentTransform),就得到了当前骨骼相对于整个模型空间的变换矩阵。然后根据骨骼名称,找到之前所述的骨骼数组中当前骨骼对应的元素索引,先将数组中的“逆位姿绑定矩阵”乘以一个当前骨骼变换矩阵再乘以整个模型的变换矩阵:
stMeshData.m_arBoneDatas[nBoneIndex].m_mxFinalTransformation
= stMeshData.m_arBoneDatas[nBoneIndex].m_mxBoneOffset
\* mxGlobalTransformation
\* stMeshData.m_mxModel;
就得到了最终的骨骼相对于世界空间中的变换矩阵。
void ReadNodeHeirarchy(ST_GRS_MESH_DATA& stMeshData
, const aiAnimation\* pAnimation
, FLOAT AnimationTime
, const aiNode\* pNode
, const XMMATRIX& mxParentTransform)
{
XMMATRIX mxNodeTransformation = XMMatrixIdentity();
MXEqual(mxNodeTransformation, pNode->mTransformation);
mxNodeTransformation = XMMatrixTranspose(mxNodeTransformation);
CStringA strNodeName(pNode->mName.data);
const aiNodeAnim\* pNodeAnim = FindNodeAnim(pAnimation, strNodeName);
if ( pNodeAnim )
{
// 缩放
XMVECTOR vScaling = {};
CalcInterpolatedScaling(vScaling, AnimationTime, pNodeAnim);
XMMATRIX mxScaling = XMMatrixScalingFromVector(vScaling);
// 四元数旋转
XMVECTOR vRotationQ = {};
CalcInterpolatedRotation(vRotationQ, AnimationTime, pNodeAnim);
XMMATRIX mxRotationM = XMMatrixRotationQuaternion(vRotationQ);
// 位移
XMVECTOR vTranslation = {};
CalcInterpolatedPosition(vTranslation, AnimationTime, pNodeAnim);
XMMATRIX mxTranslationM = XMMatrixTranslationFromVector(vTranslation);
// 骨骼动画中 最经典的 SQT 组合变换
mxNodeTransformation = mxScaling \* mxRotationM \* mxTranslationM;
}
XMMATRIX mxGlobalTransformation = mxNodeTransformation \* mx