Parent epic: #517
Goal
Animate any scene node's transform over time — position, rotation, scale — independent of any skeleton. Useful for props, doors, simple machinery, animated lights (#482), animated cameras, and basically anything that doesn't need bones.
Scope
NodeAnimationManager singleton wraps Ogre::NodeAnimationTrack. Per-scene timeline since multiple nodes can animate simultaneously.
- Inspector "Node Animation" section under Animation Mode for the selected scene node:
- Add clip (named, with duration).
- Set keyframe (
Auto-key toggle reuses the existing keyframe pattern from Phase 5).
- List of TRS tracks; toggle per-channel (e.g. only animate position).
- Dope sheet: node-transform tracks appear as TRS rows alongside bone rows.
- Curve editor: identical to bone TRS curves — same editing model.
- Playback: integrates with
AnimationControlController and the global timeline.
- Multiple clips per node: switchable like skeleton clips; named.
- Round-trip: glTF (via existing scene exporter) supports node animation natively — extend the exporter to write it. FBX likewise.
- CLI:
qtmesh nodeanim scene.gltf --list [--json], qtmesh nodeanim scene.gltf --add <node>:position --keyframes "0:0,0,0;1:5,0,0" -o out.gltf.
- MCP:
add_node_animation_clip, set_node_keyframe, list_node_animations.
Acceptance Criteria
Effort
~8 days.
Parent epic: #517
Goal
Animate any scene node's transform over time — position, rotation, scale — independent of any skeleton. Useful for props, doors, simple machinery, animated lights (#482), animated cameras, and basically anything that doesn't need bones.
Scope
NodeAnimationManagersingleton wrapsOgre::NodeAnimationTrack. Per-scene timeline since multiple nodes can animate simultaneously.Auto-keytoggle reuses the existing keyframe pattern from Phase 5).AnimationControlControllerand the global timeline.qtmesh nodeanim scene.gltf --list [--json],qtmesh nodeanim scene.gltf --add <node>:position --keyframes "0:0,0,0;1:5,0,0" -o out.gltf.add_node_animation_clip,set_node_keyframe,list_node_animations.Acceptance Criteria
t=0andt=1, plays it back smoothly.scene.anim.node.*recorded.Effort
~8 days.