-
Notifications
You must be signed in to change notification settings - Fork 9
Expand file tree
/
Copy pathposes.ts
More file actions
107 lines (96 loc) · 3.66 KB
/
Copy pathposes.ts
File metadata and controls
107 lines (96 loc) · 3.66 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
/**
* A small registry of named base poses referenced by `pose start = <name>`.
*
* A base pose sets the figure's root transform and a starting set of joint
* angles. Phase targets from the `.posecode` document are layered on top of it.
* Angles are in DEGREES, in the same local convention as posecode-parser.
*/
export interface PoseSpec {
root?: {
position?: [number, number, number];
rotationDeg?: [number, number, number];
};
joints?: Record<string, [number, number, number]>;
}
const NEUTRAL: PoseSpec = {
root: { position: [0, 0, 0], rotationDeg: [0, 0, 0] },
joints: {},
};
/** Half-pronated forearms: palms face the thighs instead of away from them. */
const RELAXED_FOREARMS: NonNullable<PoseSpec["joints"]> = {
elbow_left: [0, -80, 0],
elbow_right: [0, 80, 0],
};
// Face-down support position: torso horizontal, arms reaching to the floor.
// Ground-lock IK plants hands and feet; this just gets the gross posture right.
const PLANK: PoseSpec = {
// Face-down diagonal: rotating the standing figure by +72° about X (the same
// direction as prone's +90°) tips it chest-toward-the-floor with the
// head/shoulders HIGH and the feet trailing low behind (a value past 90
// would kick the feet up instead). Arms drop straight down toward the floor
// (shoulder flex 90 = local -X); toes curl under (ankle dorsiflex = local
// -X). groundFigure() then drops the body so the lowest contact rests on
// the floor.
root: { position: [0, 0.6, 0], rotationDeg: [72, 0, 0] },
joints: {
shoulder_left: [-90, 0, 0],
shoulder_right: [-90, 0, 0],
ankle_left: [-25, 0, 0],
ankle_right: [-25, 0, 0],
},
};
// Relaxed standing: forearms are half-pronated so each palm faces the thigh
// instead of the anatomical-model default (palms facing straight forward).
// Left/right Y signs mirror in the rig, matching `elbows: pronate 80`.
const STANDING: PoseSpec = {
root: { position: [0, 0, 0], rotationDeg: [0, 0, 0] },
joints: { ...RELAXED_FOREARMS },
};
// Ballet first position: legs externally rotated from the hips while the
// straight-leg chain stays vertical. Seeding turnout in the base pose means a
// demi-plié can keep it constant instead of visibly twisting planted feet on
// every descent and rise.
const FIRST_POSITION: PoseSpec = {
root: { position: [0, 0, 0], rotationDeg: [0, 0, 0] },
joints: {
...RELAXED_FOREARMS,
hip_left: [0, 30, 0],
hip_right: [0, -30, 0],
},
};
// Lying face-up. Rotating the standing figure -90° about X lays it on its back:
// the original front (+Z) ends up facing the ceiling (+Y) and the head points
// toward -Z. groundFigure() (bounding-box drop) then rests the back on the floor.
const SUPINE: PoseSpec = {
root: { position: [0, 0.5, 0], rotationDeg: [-90, 0, 0] },
joints: {},
};
// Lying face-down (+90° about X): the front faces the floor, head toward +Z.
const PRONE: PoseSpec = {
root: { position: [0, 0.5, 0], rotationDeg: [90, 0, 0] },
joints: {},
};
// Long-sit on the floor: torso upright, hips flexed 90° so the legs extend
// forward, knees straight. (Hip flexion resolves to -X in the rig, matching the
// parser's flexion sign.) groundFigure() drops the glutes/legs to the floor.
const SEATED: PoseSpec = {
root: { position: [0, 0.5, 0], rotationDeg: [0, 0, 0] },
joints: {
...RELAXED_FOREARMS,
hip_left: [-90, 0, 0],
hip_right: [-90, 0, 0],
},
};
const POSES: Record<string, PoseSpec> = {
neutral: NEUTRAL,
standing: STANDING,
"first-position": FIRST_POSITION,
plank: PLANK,
supine: SUPINE,
prone: PRONE,
seated: SEATED,
};
export function poseFor(name: string | undefined): PoseSpec {
if (!name) return NEUTRAL;
return POSES[name] ?? NEUTRAL;
}