当前位置:文档之家› 骨骼蒙皮动画(Skinned Mesh)的原理解析(一)

骨骼蒙皮动画(Skinned Mesh)的原理解析(一)

骨骼蒙皮动画(Skinned Mesh)的原理解析(一)
骨骼蒙皮动画(Skinned Mesh)的原理解析(一)

骨骼蒙皮动画(Skinned Mesh)的原理解析(一)

一)3D模型动画基本原理和分类

3D模型动画的基本原理是让模型中各顶点的位置随时间变化。主要种类有Morph动画,关节动画和骨骼蒙皮动画(Skinned Mesh)。从动画数据的角度来说,三者一般都采用关键帧技术,即只给出关键帧的数据,其他帧的数据使用插值得到。但由于这三种技术的不同,关键帧的数据是不一样的。

Morph(渐变,变形)动画是直接指定动画每一帧的顶点位置,其动画关键中存储的是Mesh 所有顶点在关键帧对应时刻的位置。

关节动画的模型不是一个整体的Mesh,而是分成很多部分(Mesh),通过一个父子层次结构将这些分散的Mesh组织在一起,父Mesh带动其下子Mesh的运动,各Mesh中的顶点坐标定义在自己的坐标系中,这样各个Mesh是作为一个整体参与运动的。动画帧中设置各子Mesh相对于其父Mesh的变换(主要是旋转,当然也可包括移动和缩放),通过子到父,一级级的变换累加(当然从技术上,如果是矩阵操作是累乘)得到该Mesh在整个动画模型所在的坐标空间中的变换(从本文的视角来说就是世界坐标系了,下同),从而确定每个Mesh在世界坐标系中的位置和方向,然后以Mesh为单位渲染即可。关节动画的问题是,各部分Mesh中的顶点是固定在其Mesh坐标系中的,这样在两个Mesh结合处就可能产生裂缝。

第三类就是骨骼蒙皮动画即Skinned Mesh了,骨骼蒙皮动画的出现解决了关节动画的裂缝问题,而且效果非常酷,发明这个算法的人一定是个天才,因为Skinned Mesh的原理简单的难以置信,而效果却那么好。骨骼动画的基本原理可概括为:在骨骼控制下,通过顶点混合动态计算蒙皮网格的顶点,而骨骼的运动相对于其父骨骼,并由动画关键帧数据驱动。一个骨骼动画通常包括骨骼层次结构数据,网格(Mesh)数据,网格蒙皮数据(skin info)和骨骼的动画(关键帧)数据。下面将具体分析。

二)Skinned Mesh原理和结构分析

Skinned Mesh中文一般称作骨骼蒙皮动画,正如其名,这种动画中包含骨骼(Bone)和蒙皮(Skinned Mesh)两个部分,Bone的层次结构和关节动画类似,Mesh则和关节动画不同:关节动画中是使用多个分散的Mesh,而Skinned Mesh中Mesh是一个整体,也就是说只有一个Mesh,实际上如果没有骨骼让Mesh运动变形,Mesh就和静态模型一样了。Skinned

Mesh技术的精华在于蒙皮,所谓的皮并不是模型的贴图(也许会有人这么想过吧),而是Mesh本身,蒙皮是指将Mesh中的顶点附着(绑定)在骨骼之上,而且每个顶点可以被多个骨骼所控制,这样在关节处的顶点由于同时受到父子骨骼的拉扯而改变位置就消除了裂缝。Skinned Mesh这个词从字面上理解似乎是有皮的模型,哦,如果贴图是皮,那么普通静态模型不也都有吗?所以我觉得应该理解为具有蒙皮信息的Mesh或可当做皮肤用的Mesh,这个皮肤就是Mesh。而为了有皮肤功能,Mesh还需要蒙皮信息,即Skin数据,没有Skin数据就是一个普通的静态Mesh了。Skin数据决定顶点如何绑定到骨骼上。顶点的Skin数据包括顶点受哪些骨骼影响以及这些骨骼影响该顶点时的权重(weight),另外对于每块骨骼还需要骨骼偏移矩阵(BoneOffsetMatrix)用来将顶点从Mesh空间变换到骨骼空间。在本文中,提到骨骼动画中的Mesh特指这个皮肤Mesh,提到模型是指骨骼动画模型整体。骨骼控制蒙皮运动,而骨骼本身的运动呢?当然是动画数据了。每个关键帧中包含时间和骨骼运动信息,运动信息可以用一个矩阵直接表示骨骼新的变换,也可用四元数表示骨骼的旋转,也可以随便自己定义什么只要能让骨骼动就行。除了使用编辑设定好的动画帧数据,也可以使用物理计算对骨骼进行实时控制。

下面分别具体分析骨骼蒙皮动画中的结构部件。

1)理解骨骼和骨骼层次结构(Bone Hierarchy)

首先要明确一个观念:骨骼决定了模型整体在世界坐标系中的位置和朝向。

先看看静态模型吧,静态模型没有骨骼,我们在世界坐标系中放置静态模型时,只要指定模型自身坐标系在世界坐标系中的位置和朝向。在骨骼动画中,不是把Mesh直接放到世界坐标系中,Mesh只是作为Skin使用的,是依附于骨骼的,真正决定模型在世界坐标系中的位置和朝向的是骨骼。在渲染静态模型时,由于模型的顶点都是定义在模型坐标系中的,所以各顶点只要经过模型坐标系到世界坐标系的变换后就可进行渲染。而对于骨骼动画,我们设置模型的位置和朝向,实际是在设置根骨骼的位置和朝向,然后根据骨骼层次结构中父子骨骼之间的变换关系计算出各个骨骼的位置和朝向,然后根据骨骼对Mesh中顶点的绑定计算出顶点在世界坐标系中的坐标,从而对顶点进行渲染。要记住,在骨骼动画中,骨骼才是模型主体,Mesh不过是一层皮,一件衣服。

如何理解骨骼?请看第二个观念:骨骼可理解为一个坐标空间。

在一些文章中往往会提到关节和骨骼,那么关节是什么?骨骼又是什么?下图是一个手臂的骨骼层次的示例。

骨骼只是一个形象的说法,实际上骨骼可理解为一个坐标空间,关节可理解为骨骼坐标空间

的原点。关节的位置由它在父骨骼坐标空间中的位置描述。上图中有三块骨骼,分别是上臂,前臂和两个手指。Clavicle(锁骨)是一个关节,它是上臂的原点,同样肘关节(elbow joint)是前臂的原点,腕关节(wrist)是手指骨骼的原点。关节既决定了骨骼空间的位置,又是骨骼空间的旋转和缩放中心。为什么用一个4X4矩阵就可以表达一个骨骼,因为4X4矩阵中含有的平移分量决定了关节的位置,旋转和缩放分量决定了骨骼空间的旋转和缩放。我们来看前臂这个骨骼,其原点位置是位于上臂上某处的,对于上臂来说,它知道自己的坐标空间某处(即肘关节所在的位置)有一个子空间,那就是前臂,至于前臂里面是啥就不考虑了。当前臂绕肘关节旋转时,实际是前臂坐标空间在旋转,从而其中包含的子空间也在绕肘关节旋转,在这个例子中是finger骨骼。和实际生物骨骼不同的是,我们这里的骨骼并没有实质的骨头,所以前臂旋转时,他自己没啥可转的,改变的只是坐标空间的朝向。你可以说上图的蓝线在转,但实际蓝线并不存在,蓝线只是画上去表示骨骼之间关系的,真正转的是骨骼空间,我们能看到在转的是wrist joint,也就是两个finger骨骼的坐标空间,因为他们是子空间,会跟随父空间运动,就好比人跟着地球转一样。

骨骼就是坐标空间,骨骼层次就是嵌套的坐标空间。关节只是描述骨骼的位置即骨骼自己的坐标空间原点在其父空间中的位置,绕关节旋转是指骨骼坐标空间(包括所有子空间)自身的旋转,如此理解足矣。但还有两个可能的疑问,一是骨骼的长度问题,由于骨骼是坐标空间,没有所谓的长度和宽度的限制,我们看到的长度一方面是蒙皮后的结果,另一方面子骨骼的原点(也就是关节)的位置往往决定了视觉上父骨骼的长度,比如这里upper arm线段的长度实际是由elbow joint的位置决定的。第二个问题,手指的那个端点是啥啊?实际上在我们的例子中手指没有子骨骼,所以那个端点并不存在:)那是为了方便演示画上去的。实际问题中总有最下层的骨骼,他们不能决定其他骨骼了,他们的作用只剩下控制Mesh顶点。对了,那么手指的长度如何确定?我们看到的长度应该是由蒙皮决定的,也就是由Mesh 中属于手指的那些点离腕关节的距离决定。

经过一段长篇大论,我们终于清楚骨骼和骨骼层次是啥了,但是为什么要将骨骼组织成层次结构呢?答案是为了做动画方便,设想如果只有一块骨骼,那么让他动起来就太简单了,动画每一帧直接指定他的位置即可。如果是n块呢?通过组成一个层次结构,就可以通过父骨骼控制子骨骼的运动,牵一发而动全身,改变某骨骼时并不需要设置其下子骨骼的位置,子骨骼的位置会通过计算自动得到。上文已经说过,父子骨骼之间的关系可以理解为,子骨骼位于父骨骼的坐标系中。我们知道物体在坐标系中可以做平移变换,以及自身的旋转和缩放变换。子骨骼在父骨骼的坐标系中也可以做这些变换来改变自己在其父骨骼坐标系中的位置和朝向等。那么如何表示呢?由于4X4矩阵可以同时表示上述三种变换,所以一般描述骨骼在其父骨骼坐标系中的变换时使用一个矩阵,也就是DirectX SkinnedMesh中的FrameTransformMatrix。实际上这不是唯一的方法,但应该是公认的方法,因为矩阵不光可以同时表示多种变换还可以方便的通过连乘进行变换的组合,这在层次结构中非常方便。

在本文的例子-最简单的skinned mesh实例中,我只演示了平移变换,所以只用一个3d坐标就可以表示子骨骼在父骨骼中的位置。下面是Bone Class最初的定义:

class Bone

{

public:

float m_x, m_y, m_z;//这个坐标是定义在父骨骼坐标系中的

};

OK,除了使用矩阵,坐标或某东西描述子骨骼的位置,我们的Bone Class定义中还需要一些指针来建立层次结构,也就是说我们要能通过父骨骼找到子骨骼或反之。问题是我们需要什么指针呢?从父指向子还是反之?结论是看你需要怎么用了。如果使用矩阵,需要将父子骨骼矩阵级联相乘,无论你的矩阵是左乘列向量还是右乘行向量,从哪边开始乘不重要,只要乘法中父子矩阵的左右位置正确,所以可以在骨骼中只存放指向父的指针,从子到父每次得到父矩阵循环相乘。也可以像DX中那样从根开始相乘并递归。在文本的DEMO中由于没用矩阵,直接使用坐标相加计算坐标,所以要指定父的位置,然后计算出子的位置,那么需要在Bone Class中加入子骨骼的指针,因为子骨骼有n个,所以需要n个指针吗?不一定,看看DirectX的做法,只需要两个就搞定了,指向第一子的和指向兄弟骨骼的。这样事先就不需要知道有多少子了。下面是修改后的Bone Class:

class Bone

{

Bone* m_pSibling;

Bone* m_pFirstChild;

float m_x, m_y, m_z;//pos in its parent's space

float m_wx, m_wy, m_wz; //pos in world space

};

同时增加了一组坐标,存放计算好的世界坐标系坐标。

将各个骨骼相对于其父骨骼摆放好,就行成了一个骨骼层次结构的初始位置,所谓初始是指定义骨骼层次时,那后来呢?后来动画改变了骨骼的相对位置,准确的说一般是改变了骨骼自身的旋转而位置保持不变(特殊情况总是存在,比如雷曼,可以把拳头扔出去的那个家伙),总之骨骼动了,位置变化了。初始位置很重要,因为通过初始位置骨骼层次间的变换,我们确定了骨骼之间的关系,然后在动画中你可以只用旋转。

假设我们通过某种方法建立了骨骼层次结构,那么每一块骨骼的位置都依赖于其父骨骼的位置,而根骨骼没有父,他的位置就是整个骨骼体系在世界坐标系中的位置。可以认为root 的父就是世界坐标系。但是初始位置时,根骨骼一般不是在世界原点的,比如使用3d max character studio创建的biped骨架时,一般两脚之间是世界原点,而根骨骼-骨盆位于原点上方(+z轴上)。这有什么关系呢?其实也没什么大不了的,只是我们在指定骨骼动画模型整体坐标时,比如设定坐标为(0,0,0),则根骨骼-骨盆被置于世界原点,假如xy平面是地面,那么人下半个身子到地面下了。我们想让两脚之间算作人的原点,这样设定(0,0,0)的坐标时人就站在地面上了,所以可以在两脚之间设定一个额外的根骨骼放在世界原点上,或者这个骨骼并不需要真实存在,只是在你的骨骼模型结构中保存骨盆骨骼到世界原点的变换矩阵。在微软X文件中,一般有一个Scene_Root节点,这算一个额外的骨骼吧,他的变换矩阵为单位阵,表示他初始位于世界原点,而真正骨骼的根Bip01,作为Scene_root 的子骨骼,其变换矩阵表示相对于root的位置。说这么多其实我只是想解释下,为什么要存在Scene_Root这种额外的骨骼,以及加深理解骨骼定位骨骼动画模型整体的世界坐标的作用。

有了骨骼类,现在让我们看一下建立骨骼层次的代码,在bone class中增加一个构造函数和两个成员函数:

class Bone

{

public:

Bone(float x, float y, float z)

:m_pSibling(NULL),m_pFirstChild(NULL),m_pFather(NULL),

m_x(x),m_y(y),m_z(z){}

void SetFirstChild(Bone* pChild)

{

m_pFirstChild = pChild; m_pFirstChild->m_pFather = this;

}

void SetSibling(Bone* pSibling)

{

m_pSibling = pSibling; m_pSibling->m_pFather = m_pFather;

}

};

注意我增加了一个成员变量,Bone* m_pFather,这是指向父骨骼的指针,在这个例子中计算骨骼动画时本不需要这个指针,但我为了画一条从父骨骼关节到子骨骼关节的连线,增加了它,因为每个骨骼只有第一子骨骼的指针,绘制父骨骼时从父到子画线就只能画一条,所以记录每个骨骼的父,在绘制子骨骼时画这根线。

有了这个函数,就可以创建骨骼层次了,例如:

Bone* g_boneRoot;

Bone* g_bone1, *g_bone21, *g_bone22;

void buildBones()

{

g_boneRoot = new Bone(0, 0, 0);

g_bone1 = new Bone(0.1, 0, 0);

g_bone21 = new Bone(0.0, 0.1, 0);

g_bone22 = new Bone(0.1, 0.0, 0);

g_boneRoot->SetFirstChild(g_bone1);

g_bone1->SetFirstChild(g_bone21);

g_bone21->SetSibling(g_bone22);

}

接下来是骨骼层次中最核心的部分,更新骨骼!由于动画的作用,某个骨骼的变换(TransformMatrix)变了,这时就要根据新的变换来计算,所以这个过程一般称作UpdateBoneMatrix。因为骨骼的变换都是相对父的,要变换顶点必须使用世界变换矩阵,所以这个过程是根据更新了的某些骨骼的骨骼变换矩阵(TransformMatrix)计算出所有骨骼的世界变换矩阵(也即CombinedMatrix)。在本文的例子中,骨骼只能平移,甚至我们没有用矩阵,所以当有骨骼变动时要做的只是直接计算骨骼的世界坐标,因此函数命名为ComputeWorldPos,相当于UpdateBoneMatrix后再用顶点乘以CombinedMatrix。

class Bone

{

//give father's world pos, compute the bone's world pos

void ComputeWorldPos(float fatherWX, float fatherWY, float fatherWZ)

m_wx = fatherWX+m_x;

m_wy = fatherWY+m_y;

m_wz = fatherWZ+m_z;

if(m_pSibling!=NULL)

m_pSibling->ComputeWorldPos(fatherWX, fatherWY, fatherWZ);

if(m_pFirstChild!=NULL)

m_pFirstChild->ComputeWorldPos(m_wx, m_wy, m_wz);

}

};

其中的递归调用使用了微软例子的思想。

有了上述函数,当某骨骼运动时就可以让其子骨骼跟随运动了,但是怎么让骨骼运动呢?这就是动画问题了。我不打算在这个简单的例子中使用关键帧动画,而只是通过程序每帧改变某些骨骼的位置,DEMO中animateBones就是做这个的,你可以在里面改变不同的骨骼看看效果。在本文下面会对骨骼的关键帧动画做简单的讨论。

至此,我们定义了骨骼类的结构,手工创建了骨骼层次(实际引擎应该从文件读入),并且可以根据新位置更新骨骼了(实际引擎应该从动画数据读入新的变换或使用物理计算),这样假如我们用连线将骨骼画出来,并且让某个骨骼动起来,我们就会看见他下面的子骨骼跟着动了。当然只有骨骼是不够的,我们要让Mesh跟随骨骼运动,下面就是蒙皮了。

骨骼蒙皮动画(Skinned Mesh)的原理解析(二)

2)蒙皮信息和蒙皮过程

2-1)Skin info的定义

上文曾讨论过,Skinned Mesh中Mesh是作为皮肤使用,蒙在骨骼之上的。为了让普通的Mesh具有蒙皮的功能,必须添加蒙皮信息,即Skin info。我们知道Mesh是由顶点构成的,建模时顶点是定义在模型自身坐标系的,即相对于Mesh原点的,而骨骼动画中决定模型顶点最终世界坐标的是骨骼,所以要让骨骼决定顶点的世界坐标,这就要将顶点和骨骼联系起来,Skin info正是起了这个作用。下面是DEMO中顶点类的定义的代码片段:

#define MAX_BONE_PER_VERTEX 4

{

float m_x, m_y, m_z; //local pos in mesh space

float m_wX, m_wY, m_wZ;//blended vertex pos, in world space

//skin info

int m_boneNum;

Bone* m_bones[MAX_BONE_PER_VERTEX];

float m_boneWeights[MAX_BONE_PER_VERTEX];

};

顶点的Skin info包含影响该顶点的骨骼数目,指向这些骨骼的指针,这些骨骼作用于该顶点的权重(Skin weight)。由于只是一个简单的例子,这儿没有考虑优化,所以用静态数组存放骨骼指针和权重,且实际引擎中Skin info的定义方式不一定是这样的,但基本原理一致。MAX_BONE_PER_VERTEX在这儿用来设置可同时影响顶点的最大骨骼数,实际上由于这个DEMO是手工进行Vertex Blending并且也没用硬件加速,可影响顶点的骨骼数量并没有限制,只是恰好需要一个常量来定义数组,所以定义了一下。在实际引擎中由于要使用硬件加速,以及为了确保速度,一般会定义最大骨骼数。另外在本DEMO中,Skin info是手工设定的,而在实际项目中,一般是在建模软件中生成这些信息并导出。

Skin info的作用是使用各个骨骼的变换矩阵对顶点进行变换并乘以权重,这样某块骨骼只能对该顶点产生部分影响。各骨骼权重之和应该为1。

Skin info是针对顶点的,然而在使用Skin info前我们必须要使用Bone Offset Matrix对顶点进行变换,下面具体讨论Bone offset Matrix。(写下这句话的时候我感觉有些不妥,因为实际是先将所有的矩阵相乘最后再作用于顶点,这儿是按照理论上的顺序进行讲述吧,请不要与实际情况混淆,其实他们也并不矛盾。而且在我们的DEMO中由于没有使用矩阵,所以变换的顺序和理论顺序是一致的)

2-2)Bone Offset Matrix的含义和计算方法

上文已经说过:“骨骼动画中决定模型顶点最终世界坐标的是骨骼,所以要让骨骼决定顶点的世界坐标”,现在让我们看下顶点受一块骨骼的作用时的坐标变换过程:

mesh vertex (defined in mesh space)------>Bone space

------>World

从这个过程中可看出,需要首先将模型顶点从模型空间变换到某块骨骼自身的骨骼空间,然

后才能利用骨骼的世界变换计算顶点的世界坐标。Bone Offset Matrix的作用正是将模型从顶点空间变换到骨骼空间。那么Bone Offset Matrix如何得到呢?下面具体分析:

Mesh space是建模时使用的空间,mesh中顶点的位置相对于这个空间的原点定义。比如在3d max中建模时(视xy平面为地面,+z朝上),可将模型两脚之间的中点作为Mesh空间的原点,并将其放置在世界原点,这样左脚上某一顶点坐标是(10,10,2),右脚上对称的一点坐标是(-10,10,2),头顶上某一顶点的坐标是(0,0,170)。由于此时Mesh 空间和世界空间重合,上述坐标既在Mesh空间也在世界空间,换句话说,此时实际是以世界空间作为Mesh空间了。在骨骼动画中,在世界中放置的是骨骼而不是Mesh,所以这个区别并不重要。在3d max中添加骨骼的时候,也是将骨骼放入世界空间中,并调整骨骼的相对位置使得和mesh相吻合(即设置骨骼的TransformMatrix),得到骨架的初始姿势以及相应的Transform Matrix(按惯例模型做成两臂侧平举直立,骨骼也要适合这个姿态)。由于骨骼的Transform Matrix(作用是将顶点从骨骼空间变换到上层空间)是基于其父骨骼空间的,只有根骨骼的Transform是基于世界空间的,所以要通过自下而上一层层Transform变换(如果使用行向量右乘矩阵,这个Transform的累积过程就是

C=Mbone*Mfather*Mgrandpar*...*Mroot),得到该骨骼在世界空间上的变换矩阵- Combined Transform Matrix,即通过这个矩阵可将顶点从骨骼空间变换到世界空间。那么这个矩阵的逆矩阵就可以将世界空间中的顶点变换到某块骨骼的骨骼空间。由于Mesh实际上就是定义在世界空间了,所以这个逆矩阵就是Offset Matrix。即OffsetMatrix就是骨骼在初始位置(没有经过任何动画改变)时将bone变换到世界空间的矩阵(CombinedTransformMatrix)的逆矩阵,有一些资料称之为InverseMatrix。在几何流水线中,是通过变换矩阵将顶点变换到上层空间,最终得到世界坐标,逆矩阵则做相反的事,所以Inverse这种提法也符合惯例。那么Offset这种提法从字面上怎么理解呢?Offset即骨骼相对于世界原点的偏移,世界原点加上这个偏移就变成骨骼空间的原点,同样定义在世界空间中的点经过这个偏移矩阵的作用也被变换到骨骼空间了。从另一角度理解,在动画中模型中顶点的位置是根据骨骼位置动态计算的,也就是说顶点跟着骨骼动,但首先必须确定顶点和骨骼之间的相对位置(即顶点在该骨骼坐标系中的位置),一个骨骼可能对应很多顶点,如果要保存这个相对位置每个顶点对于每块受控制的骨骼都要保存,这样就要保存太多的矩阵了。。。所以只保存mesh空间到骨骼空间的变换(即OffsetMatrix),然后通过这个变换计算每个顶点在该骨骼空间中的坐标,所以OffsetMatrix也反应了mesh和每块骨骼的相对位置,只是这个位置是间接的通过和世界坐标空间的关系表达的,在初始位置将骨骼按照模型的形状摆好是关键之处。

以上的分析是通过将mesh space和world space重合得到Offset Matrix的计算方法。那么如果他们不重合呢?那就要先计算顶点从mesh space变换到world space的变换矩阵,并乘上(还是右乘为例)Combined Matrix的Inverse Matrix从而得到Offset Matrix。但是这

不是找麻烦吗?因为Mesh的原点在哪儿并不重要,为啥不让他们重合呢?

还有一个问题是,既然Offset Matrix可以计算出来,为啥还要在骨骼动画文件中同时提供TransformMatrix和OffsetMatrix呢?实际上文件中确实可以不提供OffsetMatrix,而只在载入时计算。但TransformMatrix不可缺少,动画关键帧数据一般只存储骨骼的旋转和根骨骼的位置,骨骼间的相对位置还是要靠TransformMatrix提供。在微软的X文件结构中提供了OffsetMatrix,原因是什么呢?我不知道。我猜想一个可能的原因是为了兼容性和灵活性,比如mesh并没有定义在世界坐标系,而是作为一个object放置在3d max中,在导出骨骼动画时不能简单的认为mesh的顶点坐标是相对于世界原点的,还要把这个object的位置考虑进去,于是导出插件要计算出OffsetMatrix并保存在x文件中以避免兼容性问题。

关于OffsetMatrix和TransformMatrix含有平移,旋转和缩放的讨论:

首先,OffsetMatrix取决于骨骼的初始位置(即TransformMatrix),由于骨骼动画中我们使用的是动画中的位置,初始位置是什么样并不重要,所以可以在初始位置中只包含平移,而旋转和缩放在动画中设置(一般也仅仅使用旋转,这也是为啥动画通常中可以用一个四元数表示骨骼的关键帧)。在这种情况下,OffsetMatrix只包含平移即可。因此一些引擎的Bone

中不存放Transform矩阵,而只存放骨骼在父骨骼空间中的坐标,然后旋转只在动画帧中设置,最基本的骨骼动画即可实现。但也可在Transform和Offset Matrix中包括旋转和缩放,这样可以提高创建动画时的容错性。

在本文DEMO中,我们也没有使用矩阵保存Bone Offset,而只用了一个坐标保存偏移位置。class BoneOffset

{

public:

float m_offx, m_offy, m_offz;

};

在Bone class中,有一个方法用来计算Bone Offset

class Bone

{

public:

BoneOffset m_boneOffset;

//called after ComputeWorldPos() when bone loaded but not animated

void ComputeBoneOffset()

{

m_boneOffset.m_offx = -m_wx;

m_boneOffset.m_offy = -m_wy;

m_boneOffset.m_offz = -m_wz;

if(m_pSibling!=NULL)

m_pSibling->ComputeBoneOffset();

if(m_pFirstChild!=NULL)

m_pFirstChild->ComputeBoneOffset();

}

};

在ComputeBoneOffset()中,使用计算好的骨骼的世界坐标来计算bone offset,这儿的计算只是取一个负数,在实际引擎中,如果bone offset是一个矩阵,这儿就应该是求逆矩阵,本文不做讨论了。注意由于我们计算Bone offset时是使用计算好的世界坐标,所以在这之前必须在初始位置时对根骨骼调用ComputeWorldPos()以计算出各个骨骼在初始位置时的世界坐标。

2-3)最终:顶点混合(vertex blending)

现在我们有了Skin info,有了Bone offset,可谓万事具备,只欠东风了。现在就可以做顶点混合了,这是骨骼动画的精髓所在,正是这个技术消除了关节处的裂缝。顶点混合后得到了顶点新的世界坐标,对所有的顶点执行vertex blending后,从Mesh的角度看,Mesh deform(变形)了,变成动画需要的形状了。

首先,让我们看看使用单块骨骼对顶点进行作用的过程,以下是DEMO中的相关代码:class Vertex

{

public:

void ComputeWorldPosByBone(Bone* pBone, float& outX, float& outY, float& outZ) {

//step1: transform vertex from mesh space to bone space

outX = m_x+pBone->m_boneOffset.m_offx;

outY = m_y+pBone->m_boneOffset.m_offy;

outZ = m_z+pBone->m_boneOffset.m_offz;

//step2: transform vertex from bone space to world sapce

outX += pBone->m_wx;

outY += pBone->m_wy;

outZ += pBone->m_wz;

}

};

这个函数使用一块骨骼对顶点进行变换,将顶点从Mesh坐标系变换到世界坐标系,这儿使用了骨骼的Bone Offset Matrix和Combined Transform Matrix (嗯,我知道这儿没用矩阵,但意思是一样的对吗)

对于多块骨骼,对每块骨骼执行这个过程并将结果根据权重混合(即vertex blending)就得到顶点最终的世界坐标。进行vertex blending的代码如下:

class Vertex

{

void BlendVertex()

{//do the vertex blending,get the vertex's pos in world space

m_wX = 0;

m_wY = 0;

m_wZ = 0;

for(int i=0; i

{

float tx, ty, tz;

ComputeWorldPosByBone(m_bones[i], tx, ty, tz);

tx*= m_boneWeights[i];

ty*= m_boneWeights[i];

tz*= m_boneWeights[i];

m_wX += tx;

m_wY += ty;

m_wZ += tz;

}

}

};

这些函数我都放在Vertex类中了,因为只是一个简单DEMO所以没有特别考虑引擎结构问题,在BlendVertex()中,遍历影响该顶点的所有骨骼,用每块骨骼计算出顶点的世界坐标,然后使用Skin Weight对这些坐标进行加权平均。tx,ty,tz是某块骨骼作用后顶点的世界坐标乘以权重后的值,这些值相加后就是最终的世界坐标了。

现在让我们用一个公式回顾一下Vertex blending的整个过程(使用矩阵变换)

Vworld = Vmesh * BoneOffsetMatrix1 * CombindMatrix1 * Weight1

+ Vmesh* BoneOffsetMatrix2 * CombinedMatrix2 * Weight2

+ …

+ Vmesh * BoneOffsetMatrixN * CombindMatrixN * WeightN

(这个公式使用的是行向量左乘矩阵)

由于BoneOffsetMatrix和Combined Matrix都是矩阵,可以先相乘这样就减少很多计算了,在实际PC游戏中可以使用VS进行硬件加速计算。

3)动画数据和播放动画

正如前面所说,本例子中并没有使用动画数据,但动画数据在骨骼动画中确实最重要的,因为我们的最终目的就是播放动画。所以作为DEMO的补充,这儿简要讨论一下动画数据相关问题。其实我觉得动画的处理在骨骼动画中是很灵活的,需要专门的一篇文章讨论。

本文的最开始说,3D模型动画的基本原理是让模型中各顶点的位置随时间变化。骨骼动画的情况是,骨骼的位置随时间变化,顶点位置随骨骼变化。所以动画数据中必然包含的是骨骼的运动信息。可以在动画帧中包含某时刻骨骼的Transform Matrix,但骨骼一般只是做旋转,所以也可以用一个四元数表示。但有时候骨骼层次整体会在动画中进行平移,所以可能需要在动画帧中包含根骨骼的位置信息。播放动画时,给出当前播放的时间值,对于每块需要动画的骨骼,根据这个值找出该骨骼前后两个关键帧,根据时间差进行插值,对于四元数要使用四元数球面插值。然后将插值得到的四元数转换成Transform Matrix,再调用UpdateBoneMatrix(其含义上文已介绍)更新计算整个骨骼层次的CombinedMatrix。

4)总结

从结构上看,SkinnedMesh包括:动画数据,骨骼数据,包含Skin info的Mesh

数据,以及Bone Offset Matrix。

从过程上看,载入阶段:载入并建立骨骼层次结构,计算或载入Bone Offset Matrix,

载入Mesh数据和Skin info(如果是DX的Skinned Mesh这个过程更复杂,因为还涉及到Matrix Palette等)。运行阶段:根据时间从动画数据中获取骨骼当前时刻的Transform Matrix,调用UpdateBoneMatrix计算出各骨骼的CombinedMatrix,对于每个顶点根据Skin info进行Vertex Blending计算出顶点的世界坐标,最终进行模型的渲染。

骨骼动画及示例Skinned

骨骼动画及示例Skinned Mesh的解析 来源:ChinaItLab作者:佚名时间:2007-7-12 这是我自个写的,第一次发。没想到这个贴子编辑器极差。原文是有字体字色的。现在只能清一色了。 版主,发贴的编辑器太难用!你有必要向上反映一下。下面的字体是我敲html标记加上的,大家凑和看。 关于骨骼动画及微软示例Skinned Mesh的解析骨骼动画是D3D的一个重要应用。尽管微软DXSDK提供了示例Skinned Mesh,但由于涉及众多概念和技术细节,示例相对于初学者非常复杂,难以看懂。在此,提供一些重要问题评论,以使初学者走出迷局,顺利上手。文中所述都是参照各种资料加上自己的理解,也有可能出些偏差,有则回贴拍砖,无则权当一笑。 一骨骼动画原理原理方面在网上资料比较多,大家都基本明白。在此说一下重点:总体上,绝大部分动画实现原理一致,就是“提供一种机制,描述各顶点位置随时间的变化”。有三种方法:1.1 关节动画:由于大部分运动,都是皮肤随骨骼在动,皮肤相对于它的骨骼本身并没有发生运动,所以只要描述清楚骨骼的运动就行了。用矩阵描述各个骨骼的相对于父骨骼运动。(大多运动都是旋转型)易知,从子骨骼用矩阵乘法累积到最顶层根骨骼,就可以得到每个子骨骼相对于世界坐标系的转换矩阵。 这种动画,只须用普通Mesh保存最初始的各顶点坐标,以及一系列后续时刻所对应的各骨骼的运动矩阵。不用保存每时刻的顶点数据,节省了大量存储空间。而且比较灵活,可以利用关键帧插值运算,便于通过运算调节动作。缺点是在两段骨骼交接处,容易产生裂缝,影响效果。 1.2 渐变动画:通过保存一系列时刻的顶点坐标来完成动画。虽然比较逼真,但占用大量空间,灵活性也不高。 1.3 骨骼蒙皮动画(skinned Mesh) 相当于上面两方法的折中。现在比较流行。 在关节动画的基础上,利用顶点混合(Vertex Blend)技术,对于关节附近的顶点,由影响这些顶点的两段(或多段)骨骼运动,分别赋以权值,共同决定顶点位置。相当于在骨骼关节上动态蒙皮,有效解决了裂缝问题。 这里,引入一个D3D技术概念:“Vertex Blending”——顶点混合技术。比如说,你肯定用过SetTransform(D3DTS_WORLD,……),但SetTransform (D3DTS_WORLDMATRIX(i),……)是不是很奇怪?这个问题后文会讲到。你也可以在微软的DXSDK的帮助文件中搜索“Geometry Blending”主题,有裂缝及其解决办法

魔兽模型制作教学教程第二讲骨骼

第二讲骨骼、皮肤和动画 教程附带模型源文件下载地址:猛击此处 第一节骨骼 演示环境:3dsmax 5.0做人物动画当然少不了骨骼啦。用骨骼带动皮肤运动可以达到关节的平滑过渡,也可以比直接操纵皮肤减少许多工作量。总之是好处多多啦。 Art tool支持max骨骼、几何体和帮助物体(helpers)作为动画的骨骼。做魔兽模型时一般用几何体来充当骨骼,因为用它比较随意操作起来也方便一点。当然,习惯用其他骨骼的高手也不必刻意更换,其实3种骨骼的用法都是一样的。 首先,打开上次做好的箱子模型。 创建骨骼的第一步是想好人物的动作、有几块骨骼、各骨骼的位置。仔细观察箱子的模型。我们希望箱子能走动,所以应该有2条腿;有腿就应该有连接腿的骨骼(chest);其次,我们希望箱盖可以一张一合,所以应该有一个类似嘴的骨骼(jaw)。 下面我们用基本形体box来构造骨骼。创建6个骨骼物体(英文为物体名字)如下图所示。(大小位置差不多就可以了)

呵呵,就像上面这个样子。(有点像变形金刚?……) 创建好骨骼以后一件非常重要的事就是确定骨骼的父子关系(也就是层级关系啦!)。 你问我什么是父子关系?……简单的讲就是儿子要跟着父亲运动。比如,把作为嘴的骨骼定义为作为身子的骨骼的儿子。这样,当身子骨骼运动时“嘴”是时时跟随的,而嘴也可以有自己的动画(一张一合之类)。也就是说“父亲”的动作可以影响“儿子”,而“儿子”的动作不影响“父亲”。 3dsmax提供了一个工具进行这种链接,如下图示: 使用方法如下: 1.打开链接工具(就是刚才的按钮)。 2.左键点击你想让其作为“儿子”的几何体,并按住左键不放。 3.拖动鼠标到“父亲”上(这时可以看到一条虚线),同时释放鼠标左键。 4.你可以看到“父亲”物体闪动一下(变白),表明链接成功。 为了使我们的链接工作不受影响。我们要先将箱子隐藏,只留下骨骼。

骨骼动画及微软示例:Skinned Mesh的解析

骨骼动画及微软示例: Skinned Mesh的解析 骨骼动画是D3D的一个重要应用。尽管微软DXSDK提供了示例Skinned Mesh,但由于涉及众多概念和技术局,顺利上手。文中所述都是参照各种资料加上自己的理解,也有可能出些偏差,有则回贴拍砖,无则权当一笑一骨骼动画原理 原理方面在网上资料比较多,大家都基本明白。在此说一下重点: ! |' s9 _9 L; M! x" _总体上,绝大部分动画实现原理一致,就是“提供一种机制,描述各顶点位置随时间的变化”。有三种方法: 1.1关节动画: 由于大部分运动,都是皮肤随骨骼在动,皮肤相对于它的骨骼本身并没有发生运动,所以只要知,从子骨骼用矩阵乘法累积到最顶层根骨骼,就可以得到每个子骨骼相对于世界坐标系的转换矩阵。 这种动画,只须用普通Mesh保存最初始的各顶点坐标,以及一系列后续时刻所对应的各骨骼的运动矩阵。不通过运算调节动作。缺点是在两段骨骼交接处,容易产生裂缝,影响效果。 1.3骨骼蒙皮动画(skinned Mesh) / A' R4 r5L; R4 C 1.2渐变动画: 通过保存一系列时刻的顶点坐标来完成动画。虽然比较逼真,但占用大量空间,灵活性也不高 $ T3 P# J, y4 F9 Q& r" C- R6 U 相当于上面两方法的折中。现在比较流行。

在关节动画的基础上,利用顶点混合(Vertex Blend)技术,对于关节附近的顶点,由影响这些顶点的两段(或裂缝问题。 + r2 E/ c+ O+ R: o 这里,引入一个D3D技术概念: “Vertex Blending”---顶点混合技术。比如说,你肯定用过SetTransform个问题后文会讲到。你也可以在微软的DXSDK的帮助文件中搜索“GeometryBlending”主题,有裂缝及其二X文件如何保存骨骼动画 理解X文件格式,对用好相关的DX函数是非常重要的。 不含动画的普通X文件,有一个Mesh单元,保存了各顶点信息、各三角面的索引信息、材质种类及定义等。 动画X文件,则在这个单元中增加了“各骨骼蒙皮信息”、“骨骼层次及结构信息”、“各时刻骨骼矩阵信息”等。 ( ? 2.1网格蒙皮信息: 首先,在Mesh{}单元中,在原有的普通网格顶点数据基础上,新增了XSkinMeshHead其中,XSkinMeshHeader是总括,举一实例,如下: XSkinMeshHeader{& a2 `8 J- o( l- p% m R$ p8 RK- t. ?" ?9 J3 r9 G0 b2G8 D. | x7 `& l! A0 d) b#O9 {5@7 G2,//一个顶点可以受到骨骼影响的最大骨骼数,可用于计算共同作用时减少遍历次数35 //当前Mesh的骨骼总数。 }4,//一个三角面可以受到骨骼影响的最大骨骼数。这个数字对硬件顶点混合计算提出了基本要求。

飞机蒙皮结构

飞机结构详细讲解 2006年12月18日星期一上午 02:25 机翼 机翼是飞机的重要部件之一,安装在机身 上。其最主要作用是产生升力,同时也可以 在机翼内布置弹药仓和油箱,在飞行中可以 收藏起落架。另外,在机翼上还安装有改善 起飞和着陆性能的襟翼和用于飞机横向操 纵的副翼,有的还在机翼前缘装有缝翼等增 加升力的装置。 由于飞机是在空中飞行的,因此和一般的运输工具和机械相比,就有很大的不同。飞机的各个组成部分要求在能够满足结构强度和刚度的情况下尽可能轻,机翼自然也不例外,加之机翼是产生升力的主要部件,而且许多飞机的发动机也安装在机翼上或机翼下,因此所承受的载荷就更大,这就需要机翼有很好的结构强度以承受这巨大的载荷,同时也要有很大的刚度保证机翼在巨大载荷的作用下不会过分变形。 机翼的基本受力构件包括纵向骨架、横向骨架、蒙皮和接头。其中接头的作用是将机翼上的载荷传递到机身上,而有些飞机整个就是一个大的飞翼,如B2隐形轰炸机则根本就没有接头。以下是典型的梁式机翼的结构。 一、纵向骨架机翼的纵向骨架由翼梁、纵 樯和桁条等组成,所谓纵向是指沿翼展方 向,它们都是沿翼展方向布置的。 * 翼梁是最主要的纵向构件,它 承受全部或大部分弯矩和剪力。翼梁一般由 凸缘、腹板和支柱构成(如图所示)。凸缘 通常由锻造铝合金或高强度合金钢制成,腹 板用硬铝合金板材制成,与上下凸缘用螺钉 或铆钉相连接。凸缘和腹板组成工字型梁, 承受由外载荷转化而成的弯矩和剪力。 * 纵樯与翼梁十分相像,二者的区别在于纵 樯的凸缘很弱并且不与机身相连,其长度有 时仅为翼展的一部分。纵樯通常布置在机翼 的前后缘部分,与上下蒙皮相连,形成封闭 盒段,承受扭矩。靠后缘的纵樯还可以悬挂 襟翼和副翼。 * 桁条是用铝合金挤压或板材弯制而成,铆接在蒙皮内表面,支持蒙皮以提高其承载能

maya教程:骨骼绑定+蒙皮+动画

maya教程:骨骼绑定+蒙皮+动画 日期 2011年11月19日星期六发布人豆豆来源朱峰社区 我通常会确保我的模型是我喜欢的方式开始。虽然这是不是你没有做才能使一个非法的字符,这些都是我觉得帮助的步骤。你可以看到我在这种情况下,模型是对称的。向下中线边缘了,我已经沿z轴为中心的模式。我也把双脚y轴的原点。我缩放模型的大小,我想它以及。这几个步骤可以从长远来看更容易的事情。 我会开始前从臀部开始了模型中心6关节。我将作为一个规则的网格单元,当我把我从来不到位,旋转或缩放的关节在x。我只把它们翻译成地方。这确保我有一个干净的旋转和尺度,当我开始剥皮,可以很容易地重新定位,一切回0到原来的绑定构成。如果你有旋转的钻机上,当你开始剥皮,如果您需要取回绑定构成某种原因作出调整,你会知道什么样的地位这些关节原来当你第一次skinned.n。

现在不认为我只是随机决定6关节的关节。这些关节的选择,并专门放置。在中心的臀部开始,我一个联合的重心(cog)的,然后扭动的臀部之一以上,权利。下一个是躯干的扭动。上面的脖子和肩膀的基础之一。颈联,然后头部的基地,然后,我们结束在头顶。

如果这是一个更复杂的钻机,具有更为现实的脊椎和ik,我会把它scurve像一个真正的脊柱会。但由于它的fk我要保持挺直脊椎从侧面。这将使得更容易扭动身体,而动画。如果我们有一个scurve 脊柱x中,如果我们扭曲的躯干,它会扭动身体的角度,倾斜的同时回。

如果你现在看看这个关节链在前面视图,你可以看到,其跌幅为中心。现在的位置

注意保持腿直。如果腿不是腿在一条直线太多可能无法弯曲你太期望他们的方式。 下一步,而仍然在前面视图中,我们将手臂关节。锁骨,肩,肘,前臂手腕之一。

1改进的骨骼蒙皮算法模拟皮肤变形

第26卷第12期 计算机应用与软件 Vo l 26No .12 2009年12月 Co m puter Applicati o ns and Soft w are Dec .2009 改进的骨骼蒙皮算法模拟皮肤变形 夏开建 王士同 (江南大学信息工程学院 江苏无锡214122) 收稿日期:2008-06-20。夏开建,硕士生,主研领域:计算机动画和仿真技术。 摘 要 骨骼蒙皮算法以其速度快等优点在角色人物变形动画中始终是使用最为广泛的皮肤变形算法。针对骨骼蒙皮算法所产 生的 塌陷 、 裹糖纸 等问题,在基于拉伸蒙皮算法的基础上,提出了一种向皮肤可变区域中增加辅助节点的改进的蒙皮变形技术。实验结果显示,该方法能够有效地消除骨骼蒙皮技术中存在的 裹糖纸效应 缺陷,真实感效果明显增加。关键词 骨骼动画 蒙皮算法 拉伸 辅助节点 S K IN DEFOR MATION SIMULATED W I TH IMPROVED S MOOTH S K INNING ALGORIT HM X i a K aijian W ang Shitong (S c h ool of Infor ma tion Technol ogy,Ji angnan University ,W uxi 214122,Ji ang su,Ch i na ) Abstrac t S m ooth skinn i ng is al w ays a mo st w ide l y usedm e t hod of sk i n defor m a ti on w ith the advantag e o f a f aster algor it h m f o r t he an i m a ti on of defor m able hu m an and creature characters .H ow ever i t suffers fro m a nu m be r of proble m s ,such as the co llapsi ng elbow and candy w rappe r effec t .The paper proposes a ne w skinn i ng de f o r m ati on techno l ogy that it i ncreases the aux ili ary nodes i n t he ski n variab l e reg i ons based on the stretch s m ooth sk i nn i ng algor i th m.The exper i m ent show s t hat the m e t hod can ban i sh candy w rappe r eff ec t defec ts ,and the rea li sti c e ffect is si gnificantly i ncreased . K eywords Ske leta l an i m ati on Smoo t h sk i nn i ng Stretch A ux iliary node 0 引 言 皮肤变形技术在角色动画 [1] 中是一个非常重要的研究课 题,近20年来已经得到了很多研究者的关注,但是由于人物动画和一些角色特征都非常复杂,这块研究领域仍然面临很大的困难和挑战。目前主要有两个常见的方法,一个是基于解剖学变形技术,另一个是基于特征皮肤的直接变形。 本文主要应用第二种方法,通常叫作骨骼蒙皮法。皮肤的外形主要是通过骨架上的连接点的转变来控制的,该算法比较简单,而且给动画师留出了足够的创造空间来得到自己想要的结果,但是,蒙皮算法也会出现很多缺陷,最常见的就是 塌陷 问题和 裹糖纸 效应,之后众多学者也作了一些改进,文献[2]讨论了蒙皮算法的严重缺陷,也就是蒙皮算法对大角度旋转的失真,并提出了基于顶点混合技术加以改进,之后文献[3]提出了基于骨骼混合算法,这种方法需要较多的手工调整参数,同时也只能用于有两个关节控制的顶点。文献[4]提出了一种几何方法,虽然该方法能够模拟出比较真实的结果,但是却大大地加大了计算量,同时也增加了计算机硬件的需求。之后文献[5]又在其基础上提出了一种基于皮肤拉伸的蒙皮算法,该算法比较简单,但是该方法加大了蒙皮算法的自由度,真实感问题上仍然存在一定的缺陷。 本文在上述文献的基础上,分析了骨骼蒙皮算法的基本原理和一些缺陷,在基于文献[5]的基于皮肤拉伸的蒙皮算法基础上,提出了一种向皮肤可变区域中增加辅助节点的改进的蒙皮变形技术。实验结果显示,该方法能够有效地改善骨骼蒙皮 技术的 裹糖纸效应 缺陷,真实感效果明显增加。 1 基本蒙皮算法原理 蒙皮是一种基于局部操作的表面变形算法,该方法可以通过图形化界面为每个皮肤顶点指定对应的骨骼以及对应的权 重。 蒙皮 算法速度较快,但是在指定权重时需要动画师具有一定的经验。 蒙皮 方法本质上是一种插值算法,其基本原理可以用下式表示: v != ?n i =1 i M i D i -1v ?n i=1 i =1(1) 其中,v 是变形前的皮肤顶点坐标,M i 表示在初始参考姿态下与皮肤顶点相关的第i 段骨骼的由局部坐标到全局坐标的转换矩阵,D i -1v 表示在第i 段骨骼局部坐标系中皮肤顶点的坐标值, i 表示第i 段骨骼对于当前顶点的权值,v !表示变形后的皮肤顶点坐标。 蒙皮 算法的基本思想是使关节附近的皮肤顶点同时受到与关节相邻的两段骨骼的影响,影响的大小由权值 i 确定。 2 存在的主要缺陷 骨骼蒙皮算法最容易出现的两个问题就是 塌陷 、 裹糖纸 问题。其中, 塌陷 指的是关节弯曲时,皮肤产生的压扁、

3DMAX蒙皮教程

1.Character Studio骨骼蒙皮基础教程Copy to clipboard Posted by: 雪姬儿 Posted on: 2007-12-25 13:47 Character Studio骨骼蒙皮基础教程作者:飞菲 001 骨骼蒙皮是为模型加入一个Physique(体格)修改命令后,在结合到骨骼物体上,这样模型就会遵循骨骼物体的运动,达到蒙皮的效果。蒙皮可以针对各种类型的模型,如Polygon多边型网格物体,Patch面片模型,我们使用的是多边型模型。 002 在蒙皮之前我们首先要设置这个两足步迹骨骼的结构。现在我要做的工作是对齐骨骼,就是在形体模式下进行骨骼的调节包括位置,角度和比例,让他们正好放置在对应的模型部位的中心。

003 现在调入我们要蒙皮的角色模型,这是个已经完成的男角色模型。注意现在的手脚都是分开的姿势,这是个比较好的预备姿势,利于以后的骨骼蒙皮。

004 选择男角色模型,我们准备冻结这个模型。在冻结模型之前我们要把它的冻结属性改成不是灰色的,这样有利于我们调整骨骼。如图选择这个模型,鼠标反键选择Properties(属性)把Show frozen in Gray(以灰色显示冻结对象)的勾去掉。

.Re:Character Studio骨骼蒙皮基础教程 [Re: 雪姬儿] Copy to clipboard Posted by: 雪姬儿 Posted on: 2007-12-25 13:57 006 选择Systeme(系统)>Biped(二足骨骼)按钮 8.Re:Character Studio骨骼蒙皮基础教程[Re: 雪姬儿] Copy to clipboard Posted by: 雪姬儿 Posted on: 2007-12-25 13:58 007 在Front(前)视图中在模型的两脚之间向上移动鼠标,拖动出骨骼。直到高度比例都差不多。

骨骼蒙皮动画(SkinnedMesh)的原理解析(一)

骨骼蒙皮动画(SkinnedMesh)的原理解析(一) 一)3D模型动画基本原理和分类 3D模型动画的基本原理是让模型中各顶点的位置随时间变化。主要种类有Morph(变形)动画,关节动画和骨骼蒙皮动画(SkinnedMesh)。从动画数据的角度来说,三者一般都采用关键帧技术,即只给出关键帧的数据,其他帧的数据使用插值得到。但由于这三种技术的不同,关键帧的数据是不一样的。 Morph(渐变,变形)动画是直接指定动画每一帧的顶点位置,其动画关键中存储的是Mesh 所有顶点在关键帧对应时刻的位置。 关节动画的模型不是一个整体的Mesh,而是分成很多部分(Mesh),通过一个父子层次结构将这些分散的Mesh组织在一起,父Mesh带动其下子Mesh的运动,各Mesh中的顶点坐标定义在自己的坐标系中,这样各个Mesh是作为一个整体参与运动的。动画帧中设置各子Mesh相对于其父Mesh的变换(主要是旋转,当然也可包括移动和缩放),通过子到父,一级级的变换累加(当然从技术上,如果是矩阵操作是累乘)得到该Mesh在整个动画模型所在的坐标空间中的变换(从本文的视角来说就是世界坐标系了,下同),从而确定每个Mesh在世界坐标系中的位置和方向,然后以Mesh为单位渲染即可。关节动画的问题是,各部分Mesh中的顶点是固定在其Mesh坐标系中的,这样在两个Mesh结合处就可能产生裂缝。 第三类就是骨骼蒙皮动画即SkinnedMesh了,骨骼蒙皮动画的出现解决了关节动画的裂缝问题,而且效果非常酷,发明这个算法的人一定是个天才,因为SkinnedMesh的原理简单的难以置信,而效果却那么好。骨骼动画的基本原理可概括为:在骨骼控制下,通过顶点混合动态计算蒙皮网格的顶点,而骨骼的运动相对于其父骨骼,并由动画关键帧数据驱动。一个骨骼动画通常包括骨骼层次结构数据,网格(Mesh)数据,网格蒙皮数据(skin info)和骨骼的动画(关键帧)数据。下面将具体分析。 二)SkinnedMesh原理和结构分析 SkinnedMesh中文一般称作骨骼蒙皮动画,正如其名,这种动画中包含骨骼(Bone)和蒙皮(Skinned Mesh)两个部分,Bone的层次结构和关节动画类似,Mesh则和关节动画不同:关节动画中是使用多个分散的Mesh,而Skinned Mesh中Mesh是一个整体,也就是说只有一个Mesh,实际上如果没有骨骼让Mesh运动变形,Mesh就和静态模型一样了。Skinned Mesh技术的精华在于蒙皮,所谓的皮并不是模型的贴图(也许会有人这么想过吧),而是Mesh本身,蒙皮是指将Mesh中的顶点附着(绑定)在骨骼之上,而且每个顶点可以被多个骨骼所控制,这样在关节处的顶点由于同时受到父子骨骼的拉扯而改变位置就消除了裂缝。Skinned Mesh这个词从字面上理解似乎是有皮的模型,哦,如果贴图是皮,那么普通静态模型不也都有吗?所以我觉得应该理解为具有蒙皮信息的Mesh或可当做皮肤用的Mesh,这个皮肤就是Mesh。而为了有皮肤功能,Mesh还需要蒙皮信息,即Skin数据,没有Skin数据就是一个普通的静态Mesh了。Skin数据决定顶点如何绑定到骨骼上。顶点

游戏动画—CAT骨骼系统讲解

游戏动画—CAT骨骼系统讲解 第1节 CAT动画系统介绍 【录播】CAT动画系统介绍(9分钟) 第2节 街霸骨骼骨骼架设 【录播】街霸骨骼骨骼架设1(17分钟) 【录播】街霸骨骼骨骼架设2(9分钟) 【录播】街霸骨骼骨骼架设3(10分钟) 第3节 绿巨人骨骼架设 【录播】绿巨人骨骼架设(23分钟) 第4节 绿巨人骨骼颜色变化

【录播】绿巨人骨骼颜色变化(5分钟) 第5节 绿巨人骨骼形状变化 【录播】绿巨人骨骼形状变化(上)(5分钟) 【录播】绿巨人骨骼形状变化(中)(13分钟) 【录播】绿巨人骨骼形状变化(下)(8分钟) 第6节 绿巨人蒙皮封套的调节 【录播】绿巨人蒙皮封套的调节(15分钟) 第7节 绿巨人蒙皮笔刷调节 【录播】绿巨人蒙皮笔刷调节(17分钟) 第8节 肌肉股的应用

【录播】肌肉股的应用(上)(12分钟) 【录播】肌肉股的应用(下)(18分钟) 第9节 CAT片肌肉系统介绍 【录播】CAT片肌肉系统介绍(11分钟) 第10节 CAT片肌肉系统实例讲解 【录播】CAT片肌肉系统实例讲解(27分钟) 第11节 CAT控制器的添加与操作 【录播】CAT控制器的添加与操作(11分钟) 第12节 CAT绝对层的讲解 【录播】CAT绝对层的讲解01(11分钟)

【录播】CAT绝对层的讲解02(11分钟) 第13节 CAT运动层讲解默认面板讲解 【录播】CAT运动层讲解1 默认面板讲解(8分钟) 【录播】CAT运动层讲解2 默认面板讲解1(14分钟) 【录播】CAT运动层讲解1 默认面板讲解2(13分钟) 第14节 CAT在上下起伏的地面上进行运动 【录播】CAT在上下起伏的地面上进行运动(10分钟) 第15节 CAT盆骨控制器 【录播】CAT盆骨控制器(11分钟) 第16节 CAT胳膊和腿部控制器

浅谈Maya骨骼邦定及蒙皮

毕业设计论文 浅谈Maya人物骨骼邦定及蒙皮 ——短片《纸想对你说》创作 教学单位:广播电影电视管理干部学院 专业名称:动画系 班级名称:09数字动画 学号:2009052121 学生姓名: 指导教师:

摘要: 三维动画在国内的迅速发展开来,三维动画越来越成为大家所喜爱的动画片。具有独特的视觉效果和换面的冲击力和真实自然的动作,而要做到运动自然,就必须充分研究人体、动物等的运动规律,以及支配他们运动的骨骼系统。所以在以完美和真实为最终追求的三维动画中,一套好的骨骼装配有着其不可替代的作用。 关键词:maya动画;骨骼;蒙皮 一部好的三维动画片需要流畅的动画,良好的骨骼建立邦定有着决定性的作用,建立一整套的骨骼需要了解人体的结构和运动规律.大家所看到动画片里面的人物或者物体的变形是隐藏背后的绑带起着重要的作用。邦定的时候根据动作需要的表现来用需要的邦定解决问题.从而创建精确灵活的人物动画。 通过毕业设计《纸想对你说》的创作,进一步的了解与掌握三维动画的骨骼装配及动作调试各个技术要点,骨骼装配及动作调试在三维动画创作过程中所占的重要地位,以及短片《纸想对你说》中的骨骼装配技巧与运用。 《纸想对你说》骨骼邦定和蒙皮 检查模型 在《纸想对你说》创作过程中,人物的模型,需要对关节运动的地方布线合理匀称.当人物需要做动作的时候有的时候不好的布线会产生错误的变形和穿插.所以邦定前一定能够要仔细观察关节运动的地方的布线是否合理,是否有破面和穿插面的困扰.一旦邦定后就无法调节面和线的穿插问题.良好的模型需要有匀称的布线,合理的布线,以及精确的定位.尤其注意肩部和腿部的布线是否合理,他们的动作幅度较大.布线要密集一些。这些需要配合好建模人员,组员之间的配合相当重要,经常在一起讨论动画片中遇到的问题并解决。

Maya的FBIK角色骨骼创建及皮肤绑定(基础篇)

Maya】手把手教学:Maya的FBIK角色骨骼创建及皮肤绑定(基础篇) 一.理论介绍 Maya蒙皮Bind Skin(也叫皮肤绑定)分光滑蒙皮和刚直蒙皮,前者适用于肌肉皮肤等会挤压伸缩的物体,后者适用机器人及骨架的刚硬物体。骨骼与模型进行刚直蒙皮,模型点对应的骨骼关节权重为1,即一个点只能被一个关节所影响(光滑蒙皮则可由多个关节控制1个点);但这并不是说刚直蒙皮不能进行生物体的绑定,因为其特有的屈肌控制器,在某些情况下会比光滑蒙皮的影响物体更有效率。 蒙皮也仅仅是对物体上点进行簇权重的赋值,因此,其与变形器的作用是一样的,即不能删除历史,否则 权重效果消失。 *执行蒙皮操作前,模型必须要进行历史清空操作,如果因为蒙皮前遗留过多的操作历史,在蒙皮后,可执行Edit->Delete by Type->Non-DeformerHistory,即删除非变形器的历史;但这也不是万能的,有时仍会 出现些难以挽回的异常。 Maya对点的控制通常有4种方式:Weighted Deformer(变形权重),Rigid Skins(刚直蒙皮),BlendShapeDeformers(融合变形),SmoothSkins(光滑蒙皮)。因此,对物体进行蒙皮后,仍可加入 变形器进行特殊控制,包括表情制作。 BindSkin(绑定皮肤):将模型与骨骼进行绑定 现在我们就先来了解下Skin(皮肤)菜单的功能。进入Animation模块的Skin->BindSkin,在BindSkin(绑定皮肤)菜单下,有SmoothBind(光滑绑定)和RigidBind(刚直绑定)两种。展开各自的设置选项: 光滑蒙皮(Smooth Bind Skin):默认设置以Joint hierarchy(关节层级)进行蒙皮,也就是物体组或整个物体以所有关节为基本进行权重赋值;Selected joints(选择关节)仅对选择的关节部分进行权重赋值; Object hierarchy(物体层级):当选择多个物体进行蒙皮,使用该项才能赋值 刚直蒙皮(Rigid Bind Skin):默认的Complete skeletion为对选择的物体进行整个骨骼的绑定;Selected joints为将当前物体进行对应骨骼的蒙皮。 Coloring:勾选Color joints的话会自动给骨骼进行上色。

3dmax骨骼之SKIN蒙皮教程

1 ?在视图中创建一个跟模型差不多高的 CS 骨骼。 Φ ∣π ∕?∣vM1 fX ∣ Jlii ?i?odr?l ∣ Fh W UY 氏 1 WlTl - I i rr a d 1 --- S3. :L l 丫 ; a iflκ?1 二 IWr ?,ι H* **回? Q 国辽L Eki Sd ? 34 ? -1?- r ■ ^??w ?n? X W I ?f! F “ P r 'i ?'l $” 或"帝 Hb ELt TJLL Se OMW *?∣∣* 3j?ιsΛ? FyLLK J S IIIjtLiI G-a ∣∕fcI≠JU i > E,7∣

2 ?根据列图在运动面版中修改参数,主要是调整颈部,胸部,手指,腿部和脚趾的关节数量,使骨骼关节数与模型适当。 ?∣-j÷iα 1-^J-哄H - * I 1' -T ^ [ X -P-"iT : I - - II Irrl 八g T 厂 ” ? 二 」 £ ? C τ - e V

3 ?当骨骼数量设置好以后,使用移动和旋转工具调整骨骼的位置,并缩放骨骼大小,使骨骼的一边与模型相匹配,另一边我们可以复制后粘贴。 4 ?对骨骼的另一边进行复制后粘贴,检查骨骼是否与模型完全匹配。

*srzπ∣7TPE∏d?- '?,d?∣' Xi sz* ι*rιKJr i ■ ≡≠ ! ?-B>Lj, j≡! Lf*l-?rf ∣l C 、 3M 住n? 甦>fi?? ??LTg Si'?f^ 5 .选择模型,在修改器中选择Skin修改器。 ?r S? ?1 ■> L r ?>Y-i? !l I ■ '≡1'∣4* ?F?.r r∣≠t-?* l r5t-≡- ∣*f ∕WT*!T Γ?!??? Γ ∣jb'Arik ■ 「商??c? Γ LlFkta -j Λ-? t∣>π?^^ I 沽?≠uηβ∣H 3 W M-t> I l,η-' M S R ■件h U - V,M A?,!∣ jt÷e Ii i LW -F ?7i?r . *X = ∣Γ ?L P JL ^ l?卜IeX^ JLJ-J l*< 1? ? ?i" ? i HtM ftt∣∣* TtMcOjG1AVri J !≡*J ?∏p3? ,-yτ ,√r∣ S i--',≡≠ ■ ? I m Ξ榔3 : ”I E&n f∣z?cte 1:C4-JUEL O5k ??:?!**?∣ *?也肝??τ:■?£ j!' τ?≡ [ej

第6章 骨骼与蒙皮动画

第 6 章 骨骼与蒙皮动画 6.1 骨骼动画 6.1.1【相关知识】Biped 骨骼系统 1.Biped 骨骼系统简介 (1)Biped 骨骼系统 在 3ds max 9 中,集成了为两足动物设计动作的的角色动画编辑插件 Character Studio。它提供了全套 3D 角色模 型的动画编辑解决方案,包括 Biped(两足动物)骨骼系统、Physique 修改器和群组系统三个部分的内容。 通过内部的 Biped(两足动物)骨骼系统来设计各种不同运动方式,3ds max 系统就会将 Biped 骨骼系统的运动编 辑过程记录下来,并通过绑定功能来完成角色模型的运动赋予,最终实现角色的动画效果。 3ds Max 9 中的 Biped 骨骼系统,不但可以同以前的版本一样直观地模拟两足动物骨骼系统,还新增了男性骨骼 和女性骨骼,以及 Character Studio 中的默认骨骼系统等多种基本骨骼类型。图 6-1-1 所示。 character studio 的 Biped 骨骼系统是针对两足动物的基本骨骼的共性来建立的,可以进行增减操作的特殊骨骼 系统。它的基础形态非常接近于人类的骨骼结构,为编辑人物角色动画提供了方便条件,为更好地区别角色中的性别差 异,男性骨骼和女性骨骼两个骨骼系统,有别于基础骨骼形态,男性的头骨上眉弓较宽,下颌骨方正,而女性下颌内收, 呈尖形。男性的锁骨和肱二头肌都比女性大,显得发达。二者的上臂和前臂也有所差异,最突出的变化是胸部和盆骨的 形态,在女性骨骼系统中,胸部明显突起,盆骨宽大,在大腿根部的骨骼也随之变粗,为女性角色提供了更加合理的骨 骼形态。 小腿与脚掌骨骼部分没有明显变化, 这两种骨骼在与网格模型的合理匹配上提供了比之前版本更加吻合的形态, 节省了调整时间,提高了骨骼与角色模型对位的效率。

骨骼蒙皮动画(Skinned Mesh)的原理解析(二)

骨骼蒙皮动画(Skinned Mesh)的原理解析(二) 2)蒙皮信息和蒙皮过程 2-1)Skin info的定义 上文曾讨论过,SkinnedMesh中Mesh是作为皮肤使用,蒙在骨骼之上的。为了让普通的Mesh具有蒙皮的功能,必须添加蒙皮信息,即Skininfo。我们知道Mesh是由顶点构成的,建模时顶点是定义在模型自身坐标系的,即相对于Mesh原点的,而骨骼动画中决定模型顶点最终世界坐标的是骨骼,所以要让骨骼决定顶点的世界坐标,这就要将顶点和骨骼联系起来,Skininfo正是起了这个作用。下面是DEMO中顶点类的定义的代码片段: #defineMAX_BONE_PER_VERTEX 4 //用来设置可同时影响该顶点的最大骨骼数classVertex { floatm_x, m_y, m_z; //local pos in mesh space floatm_wX, m_wY, m_wZ;//blended vertex pos, in world space //skininfo intm_boneNum; //影响该顶点的骨骼数目 Bone*m_bones[MAX_BONE_PER_VERTEX]; //指向这些骨骼的指针 floatm_boneWeights[MAX_BONE_PER_VERTEX]; //这些骨骼作用于该点的权重 }; 顶点的Skininfo包含影响该顶点的骨骼数目,指向这些骨骼的指针,这些骨骼作用于该顶点的权重(Skinweight)。由于只是一个简单的例子,这儿没有考虑优化,所以用静态数组存放骨骼指针和权重,且实际引擎中Skin info的定义方式不一定是这样的,但基本原理一致。MAX_BONE_PER_VERTEX在这儿用来设置可同时影响顶点的最大骨骼数,实际上由于这个DEMO是手工进行VertexBlending并且也没用硬件加速,可影响顶点的骨骼数量并没有限制,只是恰好需要一个常量来定义数组,所以定义了一下。在实际引擎中由于要使用硬件加速,以及为了确保速度,一般会定义最大骨骼数。另外在本DEMO中,Skin info是手工设定的,而在实际项目中,一般是在建模软件中生成这些信息并导出。 Skin info的作用是使用各个骨骼的变换矩阵对顶点进行变换并乘以权重,这样某块骨骼只能对该顶点产生部分影响。各骨骼权重之和应该为1。 Skin info是针对顶点的,然而在使用Skininfo前我们必须要使用Bone OffsetMatrix对顶点进行变换,下面具体讨论Bone offset Matrix。(写下这句话的时候我感觉有些不妥,因为实际是先将所有的矩阵相乘最后再作用于顶点,这儿是按照理论上的顺序进行讲述吧,请不要与实际情况混淆,其实他们也并不矛盾。而且在我们的DEMO中由于没有使用矩阵,所以变换的顺序和理论顺序是一致的) 2-2)BoneOffset Matrix的含义和计算方法

硬件支持下骨骼蒙皮动画的实现

硬件支持下骨骼蒙皮动画的实现 作者:Octane3d MSN:Octane3d@https://www.doczj.com/doc/015109507.html, 电邮:Octane3d@https://www.doczj.com/doc/015109507.html, 一引言 角色动画是计算机动画技术的一个重要组成部分,在计算机辅助动画电影制作和各类广告制作中一直扮演着重要的角色。动画制作种所使用的角色动画技术的一个重要特点是动画渲染需要耗费大量时间,因此动画作品必须预先制作,渲染,然后作为视频文件播放,也就是说,是非实时。但是,虚拟现实,电子游戏,甚至是传统的动画制作软件对实时角色动画同样有很大的需求。现在,随着计算机硬件技术的发展,特别是消费级别的带有硬件加速功能的显卡技术的发展,实时角色动画逐渐获得了越来越广泛的应用。本文将在简单回顾实时角色动画发展的基础上,结合SkeAni 演示程序,介绍在现有硬件基础上骨骼蒙皮动画的基本原理和实现方法。 实时角色动画技术主要有三种类型。 第一类是关节动画。关节动画中的角色由若干独立的部分组成。每一个部分对应着一个独立的网格模型,不同的部分按照角色的特点组织成一个层次结构。比如说,一个人体模型可以由头,上身,左上臂,左前臂,左手,右上臂,右前臂,右手,左大腿,左小腿,左脚,右大腿,右小腿,右脚等各部分组成。而某个部分,可能是另一个部分的子节点,同时又是另一个部分的父节点。比如上面的人体模型中,右前臂就是右上臂的子节点,同时也是右手的父节点。而右上臂是上身的子节点,后者则是躯体的子节点。通过改变不同部分之间的相对位置,比如夹角,位移等等,就可以实现所需要的各种动画效果。这类动画的优点很多。首先,在动画序列关键帧中只需要存储节点间的相对变化,因此动画文件占用的空间很小。其次,可以实现很多复杂的动画效果,如果应用程序支持反向动力学还可以动态实现预先存储的动画序列之外的新的动画效果。当然这类动画也有不少缺点。其中之一是由于角色模型是一个层次模型,要获得某一个部分相对于世界坐标的位置,必须从根结点开始遍历该节点所有的祖先节点累计计算模型--- 世界变换。但最关键的问题是在不同部分的结合处往往会有很明显的接缝,这会严重的影响模型的真实感。 第二类是单一网格模型动画。这种动画中的角色由一个完整的网格模型构成。在动画序列的关键帧中记录着组成网格的各个顶点的新位置或者是相对于原位置的改变量。通过在相邻关键帧之间插值来直接改变该网格模型中各个顶点的位置就可以实现动画效果。相对于关节动画,单一网格模型动画的角色看上去更真实,也不会有关节动画所面临的接缝问题。由于没有使用层次模型,获得模型网格顶点在世界坐标中位置的计算量也很小。但是,这类动画的适应性很弱,角色很难通过实时计算来与环境进行良好的互动,以获得预先存储的动画序列之外的动画效果。另一方面,由于关键帧要存储网格模型所有的顶点信息,动画文件占用的空间特别大。 第三类是骨骼蒙皮动画,本文的第二部分将重点讨论这类动画。 二骨骼蒙皮动画 骨骼蒙皮动画可以看作是关节动画和单一网格模型动画的结合。在骨骼蒙皮动画中,一个角色由作为皮肤的单一网格模型和按照一定层次组织起来的骨骼组成。骨骼层次描述了角色的结构,就像关节动画中的不同部分一样,骨骼蒙皮动画中的骨骼按照角色的特点组成

Bones pro 3 骨骼蒙皮插件教程

首先我们在模型上应用Bones pro3 。 在Bones pro3的操作面板中,分为bone(骨骼编辑),verter(点编辑)两种编辑模式 我们先从Bone 这个编辑模式讲起。 Edit(编辑) 进入Bone的编辑模式: Assign(指定分配):我们可以通过点击这个按钮在对话框里精确的查找自己想要添加控制 的骨骼。 Copy(复制):将已经指定的骨骼复制给其他模型 Refresh(刷新):刷新当前指定信息 Show/Hide:显示以及隐藏骨骼

**use stack(叠加操作):这个是必须要勾选的一个命令~当我们针对一个模型进行多个修改 器操作的时候,如不勾选修改器将会失效! **Visualize:(显示骨骼当前全重值):这个命令很常用也很直观,在我们工作的时候通过这个命令可以很清楚的看到当前骨骼的状态。

Jigglig(摇动) Inertia(惯性)/Oscillation(震动) 可以设置骨骼的惯性和震动 MetuBones:控制Bones pro 的两种骨骼的选项。勾选后开启

Bones Visualize Viewer(当前查看视图):可以通过视图左上角的几个选项进行骨骼影响的查看。

Falloff%:衰减值 Strength:(强度)当前骨骼的应用强度 Apply:(生成应用)调节当前骨骼的衰减和强度后点击Apply才可以生效否则之前调节的参 数将不能被采用 Read-time(实时显示当前全重衰减范围):这个命令在操作的过程中非常有效,全重可以通过颜色的形式实时的在视图中显示出来,很直观的观察到当前测试骨骼对于蒙皮的影响情 况。 注意Read-time必须在Visualize选中时才可看到实时效果 Cync:配合copy一同使用可以实时的看到复制后无敌的影响值 Set as defanlt(设置为默认):可以将当前选择的骨骼参数设置为默认

骨骼动画的原理与实现

骨骼动画的原理与实现 3D 2008-05-28 14:04:10 阅读176 评论0 字号:大中小订阅 这里的骨骼蒙皮动画特指skinnd mesh,也叫骨骼动画。无论是合金装备,波斯王子,还是魔兽世界,到处都是骨骼动画技术的运用。用它塑造了各种各样,栩栩如生的生物。其中,人类体格的骨骼动画运用最为广泛。现在让我们一步一步揭开它神秘的面纱。 从本质上来讲,所有的3D角色动画系统都是基于一种逻辑,就是用一定的方法去改变Mesh顶点的位置,只是具体改变的方法不同而已。骨骼动画也是一样的。 骨骼动画的基本原理就是首先控制各个骨骼和关节,再使符在上面的skinned mesh与其匹配。在骨骼蒙皮动画中,一个角色由作为皮肤的单一网格模型和按照一定层次组织起来的骨骼组成。骨骼层次描述了角色的结构,就像关节动画中的不同部分一样,骨骼蒙皮动画中的骨骼按照角色的特点组成一个层次结构。相邻的骨骼通过关节相连,并且可以作相对的运动。通过改变相邻骨骼间的夹角,位移,组成角色的骨骼就可以做出不同的动作,实现不同的动画效果。皮肤则作为一个网格蒙在骨骼之上,规定角色的外观。这里的皮肤不是固定不变的刚性网格,而是可以在骨骼影响下变化的一个可变形网格。组成皮肤的每一个顶点都会受到一个或者多个骨骼的影响。在顶点受到多个骨骼影响的情况下,不同的骨骼按照与顶点的几何,物理关系确定对该顶点的影响权重,这一权重可以通过建模软件计算,也可以手工设置。通过计算影响该顶点的不同骨骼对它影响的加权和就可以得到该顶点在世界坐标系中的正确位置。动画文件中的关键帧一般保存着骨骼的位置,朝向等信息。通过在动画序列中相邻的两个关键帧间插值可以确定某一时刻各个骨骼的新位置和新朝向。然后按照皮肤网格各个顶点中保存的影响它的骨骼索引和相应的权重信息可以计算出该顶点的新位置。这样就实现了在骨骼驱动下的单一皮肤网格变形动画。或者简单地说骨骼蒙皮动画。骨骼蒙皮动画的效果比关节动画和单一网格动画更逼真,更生动。而且,随着3D硬件性能的提高,越来越多的相关计算可以通过硬件来完成,骨骼蒙皮动画已经成为各类实时动画应用中使用最广泛的动画技术。 下面讨论骨骼蒙皮动画实现的技术细节。在一个典型的骨骼蒙皮动画模型文件中,会保存如下信息:网格信息,骨骼信息和动画信息。网格信息是角色的多边形模型。该多边形模型一般由三角形面片组成,每一三角形面片有三个指向模型的顶点表的索引。通过该索引,可以确定该三角形的三个顶点。顶点表中的每一顶点除了带有位置,法向量,材质,纹理等基本信息外,还会指出有哪些骨骼影响了该顶点,影响权重又是多少。影响一个顶点的最大骨骼数一般取决于模型的设计和目标硬件平台的限制。比如,对于一个典型的人体骨架,一般只有在关节附近的顶点才会受到相邻几块骨骼的影响,而同时影响某一顶点的骨骼数,也不会超过四块。骨骼信息包括全部骨骼的数量和每一骨骼的具体信息。所有的骨骼按照父子关系组织成一棵树。树根代表整个骨架,其余每一节点包括叶子节点代表一根骨骼。每一根骨骼包括该骨骼在父骨骼坐标系中的变换矩阵,通过该变化矩阵确定了该骨骼在父骨骼坐标系中的位置。在动画信息中则保存了若干关键帧。每一关键帧指出了每一骨骼在该时刻相对于父骨骼坐标系的变换矩阵,当然也可以是该骨骼相对于父骨骼的位置,朝向等变动。在播放动画序列中的任一时刻:

相关主题
文本预览
相关文档 最新文档