DX Animation

From ActiveWiki
Jump to: navigation, search

Overview

DX Animation, also known as X or .x files, is a character animation format following Microsoft DirectX specifications. The file format is ASCII text, readable and editable.
BlenderAnimExporter002.jpg
The reason to use this format is compatibility to 3D modeller software, including Blender, 3ds Max, Maya, to name a few of the most common 3D tools today (the listed names are protected by copyright, and/or registered and/or trademarked by their owner(s)/author(s)).
A dedicated exporter for Blender exists, without having to post-process the resulting DX animation file. The standard extension .seq is used, but the extension .x is also accepted for use with animation sequences in Activeworlds.
Activeworlds 5.1 build 1172 or later is required in order to get advantage of this file format.


File Format

The file format follows the guidelines for Microsoft's text encoded DirectX 3D format.

The file format uses brackets { and } to open and close a section, comma and semicolon are used as separators and delimiters. Sections are hierarchical organized.

The number of character per line is limited for use in Activeworlds by 250. Proper line breaks, <CR><NL> Windows style line breaks, are necessary in order to process the file with Activeworlds software.

File Header

An DX animation file must contain the file magic in the very first line of the file:

    xof 0303txt 0032

xof is the magic number for DX files. 0303 is the minimum version of the file format specification used. txt says this is a text encoded, readable file. 0032 is a suggestion for the bit length for real numbers.

AnimationSet

An DX animation file could contain more than one animation. Activeworlds currently does not support more than one AnimationSet with a single file, but the the file format requests this section. An application specific name can be given next to the keyword AnimationSet, specifying the name of the animation. The Blender exporter will generate an AnimationSet with default name BlenderAnim.

    AnimationSet BlenderAnim {
     ...
    }

AnimTicksPerSecond

This section defines the tick per seconds used with the animation and takes one number, used by the application to set or adjust the animation playback speed. The default value for AnimTicksPerSecond is 30. The application will play 30 frames per second of the frames defined in the AnimationKey section later. The valid range for animation ticks per second is a value from 2 to 200 (Activeworlds specific limitation). This value can be set by the Blender exporter.

    AnimTicksPerSecond {
     30;
    }

Animation

This section defines a limb or tag the animation will be applied to. The application must know this name in order to associate it with a limb or tag. Activeworlds currently supports 84 different limbs or tags, where a single animated model, e.g. an avatar, must not use more than 64 different tags in total.

    Animation {
     { pelvis }
     ...
    }

AnimationKey

This section takes the keyframes of an animation for the specified limb or tag. Note, that the application assumes, that the first keyframe for each limb is the standard pose of the avatar / object without local transformation applied. This section also defines, the used type how the keyframes are represented and the count of keyframes following.

    AnimationKey {
     <keyType>;
     <nKeys>;
     <keyFrame>;<cntFloats>;<float1>,...<float16>;;,
     ...
     <keyFrame>;<cntFloats>;<float1>,...<float16>;;;
    }

<keyType> takes an integer value in the range from 0 to 3

    0 = rotation, 4 floats, quaternion result: angle, x-axis, y-axis, z-axis in object space
    1 = scale, 3 floats, not supported
    2 = positions/translation, 3 floats, 3d vector: x, y z in world space
    3 = matrix, 16 floats, transform matrix

<nKeys> specifying the count of keyframes following.

<keyFrame> specifies the tick of this keyframe. The actual time when the keyframe is played is determined by the application applying the value given earlier by AnimTicksPerSecond to all keyframes. Blender uses 25 tick/second as default, Activeworlds uses 30 ticks/second. AnimTicksPerSecond will tell Activeworlds client software how many frames between the keyFrames it has to interpolate.

<cntFloats> the number of floating point numbers specifying the transformation. See above at keyType.

<float1> to <float16> take the floating point numbers representing the selected keyType, between 3 and 16 values.


Example

xof 0303txt 0032
#  Exported from Blender using AWDXAnimExporter.py version 0.91 (C) 2010 Chris Muerwald.
#  Options  Right-Handed coordinate system Y axis up
#  Comments I made this animation in the hope it will be usesful. ~The3DDesigner
#  Filename ani_crouch_f.seq
#  Date     2010-30-10 09:46:13 

AnimationSet BlenderAnim_Armature0 {
  AnimTicksPerSecond {
    30;
  }
  Animation {
    {aw_pelvis}
    AnimationKey {
      2; //Position
      5;
      0;3;    0.000000,-0.033048,0.054183;;
      14;3;   0.000000,0.013172,0.072930;;
      74;3;   0.000000,0.013172,0.072930;;
      84;3;   -0.000000,-0.033048,0.054183;;
      99;3;   0.000000,-0.033048,0.054183;;
    }
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,0.000000,-0.000000,-0.000000;;
      14;4;   1.000000,0.000000,-0.000000,-0.000000;;
      74;4;   1.000000,0.000000,-0.000000,-0.000000;;
      84;4;   1.000000,0.000000,-0.000000,-0.000000;;
      99;4;   1.000000,0.000000,-0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_hip_l}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,-0.000000,0.000000,-0.000000;;
      14;4;   0.999780,0.010006,-0.001562,-0.018373;;
      74;4;   0.999780,0.010006,-0.001562,-0.018373;;
      83;4;   1.000000,0.000222,-0.000035,-0.000407;;
      99;4;   1.000000,-0.000000,0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_knee_l}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,0.000000,0.000000,-0.000000;;
      13;4;   0.998100,-0.061619,-0.000153,-0.000140;;
      74;4;   0.998073,-0.062051,-0.000154,-0.000141;;
      84;4;   1.000000,0.000000,0.000000,-0.000000;;
      99;4;   1.000000,0.000000,0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_ankle_l}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,-0.000000,0.000000,-0.000000;;
      13;4;   0.876362,0.475199,0.074648,0.024572;;
      74;4;   0.874727,0.478121,0.075107,0.024723;;
      84;4;   1.000000,-0.000000,-0.000000,-0.000000;;
      99;4;   1.000000,-0.000000,0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_toes_l}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,0.000000,-0.000000,-0.000000;;
      14;4;   0.887377,-0.456894,-0.022768,-0.057370;;
      74;4;   0.887266,-0.457105,-0.022779,-0.057397;;
      84;4;   0.998681,-0.016797,-0.001289,-0.048492;;
      99;4;   1.000000,0.000000,-0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_hip_r}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,0.000000,0.000000,-0.000000;;
      14;4;   0.999401,0.015899,0.002521,0.030642;;
      74;4;   0.999401,0.015899,0.002521,0.030642;;
      84;4;   1.000000,0.000000,0.000000,0.000000;;
      99;4;   1.000000,0.000000,0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_knee_r}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,-0.000000,-0.000000,-0.000000;;
      14;4;   0.999522,0.030897,-0.001233,-0.000004;;
      74;4;   0.999522,0.030897,-0.001233,-0.000004;;
      84;4;   1.000000,-0.000000,-0.000000,-0.000000;;
      99;4;   1.000000,-0.000000,-0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_ankle_r}
    AnimationKey {
      0; //Rotation
      5;
      0;4;    1.000000,0.000000,-0.000000,-0.000000;;
      14;4;   0.921273,0.387627,-0.031131,-0.005684;;
      74;4;   0.875409,0.476901,-0.074954,-0.024607;;
      84;4;   1.000000,0.000000,-0.000000,-0.000000;;
      99;4;   1.000000,0.000000,-0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_toes_r}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,-0.000000,0.000000,0.000000;;
      14;4;   0.894812,-0.442983,0.020976,0.051354;;
      74;4;   0.841271,-0.536782,0.029553,0.057056;;
      84;4;   0.998723,-0.006405,0.002590,0.050055;;
      99;4;   1.000000,-0.000000,0.000000,0.000000;;
      99;4;   1.000000,-0.000000,0.000000,0.000000;;
    }
  }
  Animation {
    {aw_sternum_l}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,0.000000,-0.000000,-0.000000;;
      8;4;    0.998586,0.012193,-0.003943,0.051601;;
      8;4;    0.998586,0.012193,-0.003943,0.051601;;
      38;4;   0.925035,0.090757,-0.040073,0.366698;;
      59;4;   0.924758,0.090919,-0.040148,0.367348;;
      99;4;   1.000000,0.000000,-0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_shoulder_l}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,-0.000000,0.000000,0.000000;;
      14;4;   0.665743,-0.520343,-0.351425,0.403150;;
      39;4;   0.504892,-0.074261,-0.154747,0.845945;;
      59;4;   0.504892,-0.074261,-0.154746,0.845945;;
      89;4;   0.720049,-0.060072,-0.101350,0.683848;;
      99;4;   1.000000,-0.000000,0.000000,0.000000;;
    }
  }
  Animation {
    {aw_elbow_l}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,-0.000000,0.000000,-0.000000;;
      14;4;   0.767226,-0.479415,0.184782,0.383901;;
      39;4;   0.788001,0.508467,-0.198311,0.284936;;
      59;4;   0.788001,0.508467,-0.198311,0.284936;;
      89;4;   0.887890,0.399120,-0.151052,0.171866;;
      99;4;   1.000000,-0.000000,0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_wrist_l}
    AnimationKey {
      0; //Rotation
      3;
      39;4;   0.988418,0.082479,-0.041047,-0.120595;;
      59;4;   0.988418,0.082479,-0.041047,-0.120595;;
      89;4;   0.988418,0.082479,-0.041047,-0.120595;;
    }
  }
  Animation {
    {aw_sternum_r}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,0.000000,0.000000,0.000000;;
      8;4;    0.999413,0.007855,0.002540,-0.033245;;
      8;4;    0.999413,0.007855,0.002540,-0.033245;;
      39;4;   0.924758,0.090919,0.040148,-0.367348;;
      59;4;   0.924758,0.090919,0.040148,-0.367348;;
      99;4;   1.000000,0.000000,0.000000,0.000000;;
    }
  }
  Animation {
    {aw_shoulder_r}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,0.000000,-0.000000,-0.000000;;
      14;4;   0.607488,-0.551865,0.432973,-0.372743;;
      39;4;   0.509627,-0.046007,0.073553,-0.856010;;
      59;4;   0.509627,-0.046007,0.073553,-0.856011;;
      89;4;   0.730866,-0.041310,0.055956,-0.678968;;
      99;4;   1.000000,0.000000,-0.000000,-0.000000;;
    }
  }
  Animation {
    {aw_elbow_r}
    AnimationKey {
      0; //Rotation
      6;
      0;4;    1.000000,-0.000000,0.000000,0.000000;;
      14;4;   0.851470,-0.419150,-0.199190,-0.244205;;
      39;4;   0.856734,0.247125,-0.202236,-0.405014;;
      59;4;   0.856734,0.247125,-0.202236,-0.405014;;
      89;4;   0.926655,0.196148,-0.159370,-0.278278;;
      99;4;   1.000000,-0.000000,0.000000,0.000000;;
    }
  }
  Animation {
    {aw_wrist_r}
    AnimationKey {
      0; //Rotation
      3;
      39;4;   0.993816,0.035423,-0.003002,0.105194;;
      59;4;   0.993816,0.035423,-0.003002,0.105194;;
      89;4;   0.993816,0.035423,-0.003002,0.105194;;
    }
  }
  Animation {
    {aw_head}
    AnimationKey {
      0; //Rotation
      3;
      0;4;    1.000000,0.000000,0.000000,0.000000;;
      39;4;   0.999015,-0.038375,-0.013628,-0.017639;;
      99;4;   1.000000,0.000000,0.000000,0.000000;;
    }
  }
} //End of AnimationSet BlenderAnim_Armature0

Blender Exporter

Blender version 2.49, showing a skeleton with an animation attached and the Activeworlds Animation export dialog opened.

The exporter is easy to use. Just move the mouse over the buttons to display help context. Only the Preset AW / OGL will work for Activeworlds. It sets the coordinate system to Right-Handed with Y axis up. This is the default. The exporter is written for Blender version 2.49, their current stable version, and will be updated to 2.5x as soon the current Blender beta version becomes stable and Blender has finished the python script API.

Copyright, usage and disclamer for the Blender 2.49 exporter script version 0.91 and later:

#
# AWDXAnimExporter.py version 0.92
# Copyright (C) 2010  Chris Muerwald -- chris@activeworlds.com  
#
# This program is free software; you can redistribute it and/or modify
# considering all other copyright notices that came with your installation
# of Blender whatsoever.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
#

Tips for Artists

There are a few things you should consider when creating an animation for Activeworlds.

  • The pelvis should be the root bone of the skeleton always.
  • Avoid having more than one root bone.
  • Start the animation at a neutral pose.
  • Start the animation at the keyframe #1.
  • When moving the whole skeleton in world space, move the pelvis only, not any other limb.
  • Position translations of any other limb than pelvis is supported with build 1176 and later of the browser, and v0.92 of the exporter.
  • Include the pelvis into the animation always, even it has no rotation and no position translation applied.
  • Avoid rotating a bone over 180 degrees.
  • Activeworlds can only apply linear interpolations between keyframes currently.
  • Try to minimize the total count of keyframes used. This will help to reduce loading time of the animation sequence, will help to reduce memory used and will improve the performance.

Also look at Skinned Avatars.