Skip to content

Rig: map Kinect trailing-side bone names (ShoulderLeft, SpineBase) #111

Description

@nirholas

What is wrong

three.ws plays one shared library of animation clips on any humanoid avatar a user uploads. That works because every rig is rewritten to one canonical skeleton first, in src/glb-canonicalize.js.

Skeletons coming out of Kinect v2 and Azure Kinect body tracking, and the many mocap and pose-estimation pipelines that copied that naming, put the side word at the end: ShoulderLeft, ElbowLeft, WristLeft, HipLeft, KneeLeft, AnkleLeft, FootLeft, with a spine chain of SpineBase, SpineMid, SpineShoulder.

None of it resolves today. The rig maps zero joints, falls under the retarget coverage floor, and the avatar falls back to a default body.

import { canonicalizeBoneName } from './src/glb-canonicalize.js';
canonicalizeBoneName('ElbowLeft');   // null   <-- the gap
canonicalizeBoneName('elbowL');      // 'LeftForeArm'  (already supported)
canonicalizeBoneName('leftElbow');   // 'LeftForeArm'  (already supported)

Note the shape of the gap: the side-prefix (leftElbow) and the short side-suffix (elbowL) spellings both work. The full trailing side word (ElbowLeft) does not.

What to change

File: src/glb-canonicalize.js, the EXTRA_ALIASES block.

There is already a table for exactly this shape: the Second Life chain (mCollarLeft, mShoulderLeft, mKneeLeft) uses a trailing side word. Read those entries, then decide whether the right fix is more entries or a general trailing-Left/Right rule. Argue for your choice in the code comment the way the neighbouring blocks do.

Two joints need thought, and they are the interesting part of this issue:

  • SpineShoulder is the upper spine near the clavicles, not a shoulder. Map it to the spine chain.
  • ShoulderLeft in Kinect is the upper arm joint, not the clavicle. Compare with how the SMPL collar/shoulder collision is resolved elsewhere in this file, and with the existing test named splits an SMPL collar/shoulder collision.

How to prove it worked

Add cases to tests/glb-canonicalize.test.js beside the other per-convention blocks, then:

npx vitest run tests/glb-canonicalize.test.js   # about 1 second
npm test                                        # before you open the PR

Your test must cover both sides. A mapping that sends a left bone to a right canonical name tears the avatar apart in motion and it is the most common mistake in this file.

Also add a row to the conventions table in docs/rig-doctor.md, and if you want the detector to name the convention on sight, add a fingerprint to CONVENTIONS in src/rig-report.js with a test in tests/rig-report.test.js.

Reference

The MikuMikuDance support added on 2026-08-21 is the same shape of change end to end (alias map, detector fingerprint, tests, doc row). Read that diff, then do this one. The full walkthrough is in Your first contribution.

Comment here to claim it.

Metadata

Metadata

Assignees

No one assigned

    Labels

    area: rigSkeletons, bone mapping, retargetingenhancementNew feature or requestgood first issueGood for newcomers

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions