Docs/Tutorials/Keyframe Animation

Animation Concepts

MeshCraft animations are organised into three levels:

All 23 animatable properties are scalars — you need three separate channels to animate full 3D position (one each for position.x, position.y, position.z).

Step 1 — Prepare a Scene

Start with a simple scene containing at least one named object. We will animate a sphere bouncing up and down.

Create bounce.mc3.xml:

<?xml version="1.0" encoding="UTF-8"?>
<mc3 version="0.3" model="BounceDemo">
  <lights>
    <ambient     color="0.3 0.3 0.4" brightness="0.5"/>
    <directional name="Sun" direction="-0.5 -1 -0.3" brightness="2.0"/>
  </lights>
  <materials>
    <material id="red"><base_color>0.9 0.2 0.2 1.0</base_color></material>
    <material id="grey"><base_color>0.5 0.5 0.5 1.0</base_color></material>
  </materials>
  <objects>
    <plane  name="Ground" size="10 10" axis="y" material="grey"/>
    <sphere name="Ball"   radius="0.5"  position="0 0.5 0" material="red"/>
  </objects>
</mc3>

Step 2 — Add an Action

Add the <actions> block after </objects> and before </mc3>:

  <actions>
    <action name="Bounce" duration="1.0" loop="true">

      <channel target="Ball" property="position.y">
        <keyframe time="0.0" value="0.5"  interp="cubic">
          <handle_left  dt="-0.1" dv="0.0"/>
          <handle_right dt=" 0.1" dv="3.0"/>
        </keyframe>
        <keyframe time="0.5" value="3.5"  interp="cubic">
          <handle_left  dt="-0.1" dv="3.0"/>
          <handle_right dt=" 0.1" dv="-3.0"/>
        </keyframe>
        <keyframe time="1.0" value="0.5"  interp="linear"/>
      </channel>

    </action>
  </actions>

This animates the Ball sphere's Y position from 0.5 → 3.5 → 0.5 over one second, looping indefinitely. The cubic interpolation with tangent handles gives a smooth ease-in/ease-out arc.

Step 3 — Open and Play

./cmake-build-debug/MeshCraft bounce.mc3.xml
  1. The scene opens. You should see the red sphere and grey ground plane.
  2. In the editor, find the Timeline panel (bottom area).
  3. Select the Bounce action from the drop-down.
  4. Press the Play button — the sphere animates up and down in the viewport.
  5. Drag the scrubber to a specific time to preview that pose.
ℹ️

Animation playback applies AnimOverride transforms to each object. This means keyframe transforms are independent of the static transform stored in the scene — the static transform is the base pose when no animation is playing. When a channel covers only one axis, the other two axes are read from the object's static transform.

Step 4 — Adding a Rotation Channel

Extend the same action with a spin channel. Add another <channel> inside the same <action>:

      <channel target="Ball" property="rotation.y">
        <keyframe time="0.0"  value="0.0"   interp="linear"/>
        <keyframe time="1.0"  value="360.0" interp="linear"/>
      </channel>

Now the sphere bounces and spins simultaneously within the same clip.

Step 5 — Visibility Flash

The visible property (0.0 = hidden, ≥0.5 = visible) combined with step interpolation creates a strobe effect:

    <action name="Flash" duration="0.4" loop="true">
      <channel target="Ball" property="visible">
        <keyframe time="0.0" value="1.0" interp="step"/>
        <keyframe time="0.2" value="0.0" interp="step"/>
      </channel>
    </action>

Interpolation Modes Summary

ModeAttributeBehaviourBest for
Stepinterp="step"Value holds until next keyframe then jumpsVisibility, discrete states
Linearinterp="linear"Straight-line lerp between keyframesConstant-velocity motion, rotation
Cubic Bézierinterp="cubic"Smooth curve using handle_left/handle_right tangentsOrganic motion, bouncing, easing

Exporting the Animation

Position, rotation (XYZ Euler → glTF quaternion), and scale channels are exported to glTF. See Export to glTF/GLB for the full pipeline.

./cmake-build-debug/mc3togltf/mc3togltf bounce.mc3.xml bounce.glb

Open bounce.glb in Blender or Godot — the "Bounce" animation clip will be importable directly.

⚠️

Cubic Bézier channels are sampled at 30 fps and stored as LINEAR in the glTF output. The smooth curve is preserved visually, but the file size is larger than a pure 2-keyframe linear clip.

Animatable Properties Reference

See the complete list in the Animation Format Reference. All 23 properties are scalars — vector properties require one channel per component.