Skip to content

Retarget post-processing controls: Mixamo-style arm-space slider #854

Description

@fernandotonon

Motivation

The bind-referenced retarget (#839, PR #843) generates animations that reference the target rig's bind pose, but retarget quality still varies with body proportions: bulky/cartoon characters (short arms, wide torsos) end up with arms clipping into the body or floating too wide, because the retarget aims bones at the source clip's directions with no awareness of the target's volume.

Mixamo solves this with a "Character Arm-Space" slider — a user-controlled post-process that swings the whole arm chain outward/inward. It is cheap, intuitive, and rescues most intersection cases without touching the retarget math. This issue plans the same idea as a generation post-process.

Design

Core: AnimationMerger::adjustArmSpace(skel, animName, degrees) — a pure post-process on an existing generated animation:

  • For every keyframe of bones mapped to the arm roles (canonical 7/8/9 right, 11/12/13 left; collars 6/10 get a fractional share), pre-multiply a swing rotation about the torso's forward axis (derived from the target bind frame Ct, the same one the retarget uses), sign mirrored per side: +deg swings both arms away from the body, −deg tucks them in.
  • Only the shoulder role needs the full angle — elbows/hands inherit through the hierarchy since keyframes are parent-relative deltas. Distribute across duplicate-role bones like the retarget's canonDup split.
  • Idempotent absolute application: store the applied angle on the animation via UserObjectBindings (qtme.armspace); re-applying with a new slider value first reverts the stored one, so scrubbing the slider never accumulates error.
  • Undoable via a small QUndoCommand (UndoManager pattern).

Surfaces:

  • GUI: a compact "Arm space" slider (−30°…+45°, default 0) in the Animations panel, visible when a generated_* clip is selected; live preview while dragging (apply on release; slider maps to the absolute stored value).
  • CLI: qtmesh anim <file> --generate "<prompt>" --arm-space <deg> and standalone qtmesh anim <file> --arm-space <deg> --animation <name> -o out for post-adjusting existing clips.
  • MCP: arm_space argument on generate_motion + a standalone adjust_arm_space tool.
  • Sentry breadcrumb ai.assist.text_to_motion message arm_space.

Testing: pure-data unit test on a synthetic 22-role skeleton — verify (a) shoulder world direction swings by the requested angle in the torso plane, (b) idempotence (apply 20 then 10 ≡ apply 10), (c) elbows/hands unchanged in parent-relative terms.

Follow-up knobs the same mechanism enables (out of scope here, listed for the design to keep the door open)

Acceptance criteria

  • Slider visibly widens/narrows the arms of a generated clip on the Hip Hop fox without breaking legs/spine.
  • Idempotent (scrubbing the slider back to 0 restores the original clip bit-near-exactly).
  • CLI/MCP parity + unit tests green.

Related: epic #837 (t2m-v2), #839 (canonical clip extraction), PR #843 (bind-referenced retarget).

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions