关于c ++:使用ASSIMP进行骨骼动画

Skeletal animation with ASSIMP

我一直在尝试使用ASSIMP导入模型在自己的3D openGL / c ++游戏引擎中实现骨骼动画。

我认为问题是由在着色器中作为统一变量加载的骨骼矩阵的计算引起的,因为如果将它们分配给身份,网格将以其绑定姿势加载。

这些是我用来初始化和计算就绪骨骼矩阵的函数:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
    void Joint::AddToSceneGraph(GameObject* root)
    {
        GameObject* parent = root->FindChild(m_name);
        //m_globalInverseMatrix = inverse(root->GetTransform().GetMatrix());
        parent->AddComponent(this);
        while (parent->GetParent() != root)
            parent = parent->GetParent();

        parent->GetTransform().SetParent(NULL); (1)
    }

    mat4 Joint::GetMatrix()
    {
        mat4 ans = /*m_globalInverseMatrix*/GetTransform().GetMatrix()*m_offsetMatrix;
        return ans;
    }

由于我试图以绑定姿势渲染模型,因此我不会向您提供计算动画矩阵的代码。

一些澄清-我有一个Transform类,该类具有Transform *父对象,并且其GetMatrix()方法根据父对象的矩阵计算矩阵,缩放和平移vec3和旋转四元数,因此考虑了父子对象之间的关系。我假设根关节的父代变换必须为NULL,因此其矩阵-身份,这是(1)的目的。尽管我不确定这个假设,但是我确信带有骨架根的节点和包含网格的节点都是同级的。

另外,我不确定我是否应该使用m_globalInverseMatrix以及它的确切用途。

总的来说,我认为我的主要问题是对ASSIMP如何计算offset matrix或所谓的inverse bind pose matrix以及如何反转其效果的误解。此问题导致模型本身看起来"打包":

this is maybe the most famous md5 model


根据Assimp中的文档,骨骼的偏移矩阵从网格空间转换为骨骼空间。

我设法用类似于您的层次结构来呈现bind pos(如果我没有误解,您有一个带有两个子节点的根节点,一个生成骨架层次结构,另一个生成网格物体)。 您要做的是将m_globalInverseMatrix设置为包含网格的节点的逆变换。 然后,每个骨骼的变换为:

boneTransform = m_globalInverseMatrix * boneHierarchyTransforms * boneOffsetMatrix

boneHierarchyTransform来自遍历树到每个骨骼节点,而boneOffsetMatrix是您提到的,我在第一段中提到过。