天行健 君子当自强而不息

网格模型高级技术(4)

为了使一个.x文件产生动画,必须至少提供一个动画集,每个动画集都应具有一个对某个框架的引用。模板 AnimationSet用来定义动画集:

Contains one or more Animation objects. Each animation within an animation set has the same time at any given point. Increasing the animation set's time increases the time for all the animations it contains.

template AnimationSet
{
< 3D82AB50-62DA-11cf-AB39-0020AF71E433 >
[ Animation < 3D82AB4F-62DA-11cf-AB39-0020AF71E433 > ]
}

Where:

  • [ Animation < 3D82AB4F-62DA-11cf-AB39-0020AF71E433 > ] - Optional animation template.

模板Animation的定义如下:

Contains one or more Animation objects. Each animation within an animation set has the same time at any given point. Increasing the animation set's time increases the time for all the animations it contains.

template AnimationSet
{
< 3D82AB50-62DA-11cf-AB39-0020AF71E433 >
[ Animation < 3D82AB4F-62DA-11cf-AB39-0020AF71E433 > ]
}

Where:

  • [ Animation < 3D82AB4F-62DA-11cf-AB39-0020AF71E433 > ] - Optional animation template.

很显然,Animation是一个完全开放的模板,一般情况下,用模板AnimationKey来填充它,模板AnimationKey的定义如下:

Defines a set of animation keys. A matrix key is useful for sets of animation data that need to be represented as transformation matrices.

template AnimationKey
{
< 10DD46A8-775B-11CF-8F52-0040333594A3 >
DWORD keyType;
DWORD nKeys;
array TimedFloatKeys keys[nKeys];
}

Where:

  • keyType - Specifies whether the keys are rotation, scale, position, or matrix keys (using the integers 0, 1, 2, or 4, respectively).
  • nKeys - Number of keys.
  • keys - An array of keys.

在模板AnimationKey中,keyType可取的值是0、1、2、4。

0表示旋转键,在.x文件中,用一个四元数来实现模型的旋转,旋转值使用4个分量w、x、y、z来存储,也就是说,此时变换数组的大小是4,它依次存储四元数的4个分量。

1表示缩放键,可以使用这种类型的关键帧实现模型的缩放,此时变换数组的大小是3,它们分别对应x、y、z轴的缩放值。

2表示平移键,使用3个分量实现模型的平移,此时变换数组的大小是3,它们分别对应沿x、y、z轴的平移值。

4表示变换矩阵键,此时关键帧的变换数组使用16个浮点数来实现该模型的各种变换。因为矩阵可以实现模型的平移、旋转、缩放以及它们的组合变换。

模板AnimationKey用来定义一组动画关键帧,而模板TimeFloatKeys用来定义每个动画关键帧:

Defines a set of floats and a positive time used in animations.

template TimedFloatKeys 
{
< F406B180-7B3B-11cf-8F52-0040333594A3 >
DWORD time;
FloatKeys tfkeys;
}

Where:

  • tfkeys - See FloatKeys.

Defines an array of floating-point numbers (floats) and the number of floats in that array. This is used for defining sets of animation keys.

template FloatKeys
{
< 10DD46A9-775B-11cf-8F52-0040333594A3 >
DWORD nValues;
array float values[nValues];
}
  • nValues - Number of floats.
  • values[nValues] - Array of float values.

我们在cube_3.x的基础上添加动画部分形成cube_4.x,该动画集定义了立方体绕y轴旋转,增加部分如下:

AnimationSet AnimationSet0 {  //动画集
Animation Animation0 { //动画
{CubeFrame} //引用上面的立方体框架,表示下面的动画是针对立方体框架的
		AnimationKey {                //动画键   沿Y轴旋转网格
0; // Rotation keys
10; // 9 keys
			1000; 4; 0.000000, 0.15643448, 0.000000, 0.98768836;;,
2000; 4; 0.000000, 0.30901700, 0.000000, 0.95105654;;,
3000; 4; 0.000000, 0.45399046, 0.000000, 0.89100653;;,
4000; 4; 0.000000, 0.58778530, 0.000000, 0.80901694;;,
5000; 4; 0.000000, 0.70710671, 0.000000, 0.70710683;;,
6000; 4; 0.000000, 0.80901694, 0.000000, 0.58778530;;,
7000; 4; 0.000000, 0.89100653, 0.000000, 0.45399052;;,
8000; 4; 0.000000, 0.95105654, 0.000000, 0.30901697;;,
9000; 4; 0.000000, 0.98768836, 0.000000, 0.15643449;;,
10000; 4; 0.000000, 1.0000000, 0.000000, 0.00000000;;;
}
}
}

这里一共定义了10个关键帧,在第10个关键帧时回到初始位置开始新一轮的动画。{CubeFrame}表示该动画集是对框架CubeFrame进行的操作。

我们在cube_3.x的基础上添加缩放动画形成cube_5.x:

AnimationSet AnimationSet0 {   //动画集
Animation Animation0 { //动画
{CubeFrame} // Use the frame containing the cube.
		AnimationKey {                 //动画键, 放大和缩小网格
1; // Scaling keys
9; // 9 keys
			1000; 3; 1.000000, 1.000000, 1.000000;;,
2000; 3; 0.800000, 0.800000, 0.800000;;,
3000; 3; 0.600000, 0.600000, 0.600000;;,
4000; 3; 0.400000, 0.400000, 0.400000;;,
5000; 3; 0.200000, 0.200000, 0.200000;;,
6000; 3; 0.400000, 0.400000, 0.400000;;,
7000; 3; 0.600000, 0.600000, 0.600000;;,
8000; 3; 0.800000, 0.800000, 0.800000;;,
9000; 3; 1.000000, 1.000000, 1.000000;;;
}
}
}

效果图:

 

我们也可以在cube_3.x的基础上添加一个沿y轴移动的动画形成cube_6.x:

AnimationSet AnimationSet0 {   //动画集
Animation Animation0 { //动画
{CubeFrame} // Use the frame containing the cube.
		AnimationKey {                 //动画键   沿Y轴方向移动网格
2; // Position keys
19; // 9 keys
1000; 3; 0.000000, -5.000000, 0.000000;;,
2000; 3; 0.000000, -4.000000, 0.000000;;,
3000; 3; 0.000000, -3.000000, 0.000000;;,
4000; 3; 0.000000, -2.000000, 0.000000;;,
5000; 3; 0.000000, -1.000000, 0.000000;;,
6000; 3; 0.000000, 0.000000, 0.000000;;,
7000; 3; 0.000000, 1.000000, 0.000000;;,
8000; 3; 0.000000, 2.000000, 0.000000;;,
9000; 3; 0.000000, 3.000000, 0.000000;;,
10000; 3; 0.000000, 4.000000, 0.000000;;,
11000; 3; 0.000000, 5.000000, 0.000000;;,
12000; 3; 0.000000, 4.000000, 0.000000;;,
12000; 3; 0.000000, 3.000000, 0.000000;;,
13000; 3; 0.000000, 2.000000, 0.000000;;,
14000; 3; 0.000000, 1.000000, 0.000000;;,
15000; 3; 0.000000, 0.000000, 0.000000;;,
16000; 3; 0.000000, -1.000000, 0.000000;;,
17000; 3; 0.000000, -2.000000, 0.000000;;,
18000; 3; 0.000000, -3.000000, 0.000000;;,
19000; 3; 0.000000, -4.000000, 0.000000;;,
}
}
}

效果图:

 

包含在.x文件中的动画通常用来实现模型不同部分之间的相对运动,对于一个模型整体上的运动,应该是在程序中通过其世界变换矩阵来实现。

 

蒙皮信息

一个动画网格模型很多情况下可能涉及到蒙皮信息,模板XSkinMeshHeader仅对于具有蒙皮信息的网格模型有效,它用来记录网格模型的蒙皮信息,该模板的定义如下:

This template is instantiated on a per-mesh basis only in meshes that contain exported skinning information. The purpose of this template is to provide information about the nature of the skinning information that was exported.

template XSkinMeshHeader 
{
< 3CF169CE-FF7C-44ab-93C0-F78F62D172E2 >
WORD nMaxSkinWeightsPerVertex;
WORD nMaxSkinWeightsPerFace;
WORD nBones;
}

Where:

  • nMaxSkinWeightsPerVertex - Maximum number of transforms that affect a vertex in the mesh.
  • nMaxSkinWeightsPerFace - Maximum number of unique transforms that affect the three vertices of any face.
  • nBones - Number of bones that affect vertices in this mesh.

在一个具有蒙皮信息的网格模型中,可能出现模板SkinWeights的n个实例,n等于该网格模型中骨骼的数量。该模板的每个实例都定义了一个具体的骨骼对于相应顶点的影响权重,该模板的具体定义如下:

This template is instantiated on a per-mesh basis. Within a mesh, a sequence of n instances of this template will appear, where n is the number of bones (X file frames) that influence the vertices in the mesh. Each instance of the template basically defines the influence of a particular bone on the mesh. There is a list of vertex indices, and a corresponding list of weights.

template SkinWeights 
{
< 6F0D123B-BAD2-4167-A0D0-80224F25FABB >
STRING transformNodeName;
DWORD nWeights;
array DWORD vertexIndices[nWeights];
array float weights[nWeights];
Matrix4x4 matrixOffset;
}

Where:

  • The name of the bone whose influence is being defined is transformNodeName, and nWeights is the number of vertices affected by this bone.
  • The vertices influenced by this bone are contained in vertexIndices, and the weights for each of the vertices influenced by this bone are contained in weights.
  • The matrix matrixOffset transforms the mesh vertices to the space of the bone. When concatenated to the bone's transform, this provides the world space coordinates of the mesh as affected by the bone.

 

下载cube_1.x ~ cube6.x


posted on 2008-05-27 15:44 lovedday 阅读(2012) 评论(1)  编辑 收藏 引用

评论

# re: 网格模型高级技术(4) 2013-09-06 17:29 abc

讲的太好了  回复  更多评论   


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理


公告

导航

统计

常用链接

随笔分类(178)

3D游戏编程相关链接

搜索

最新评论