94 lines
2.7 KiB
TypeScript
94 lines
2.7 KiB
TypeScript
import { describe, expect, it } from 'vitest';
|
|
|
|
import {
|
|
applyChildMotionWarmupCompletion,
|
|
CHILD_MOTION_CENTER_X,
|
|
CHILD_MOTION_WARMUP_STEPS,
|
|
createEmptyChildMotionCalibration,
|
|
getChildMotionWarmupStep,
|
|
isAvatarOnWarmupTarget,
|
|
resolveNextChildMotionWarmupStep,
|
|
} from './childMotionWarmupModel';
|
|
|
|
describe('childMotionWarmupModel', () => {
|
|
it('keeps the confirmed warmup order as a strict state chain', () => {
|
|
expect(CHILD_MOTION_WARMUP_STEPS.map((step) => step.id)).toEqual([
|
|
'center_arrive',
|
|
'wave_greeting',
|
|
'warmup_intro',
|
|
'move_left',
|
|
'return_center_1',
|
|
'move_right',
|
|
'return_center_2',
|
|
'wave_left_hand',
|
|
'wave_right_hand',
|
|
'warmup_finish',
|
|
'level_select',
|
|
]);
|
|
expect(resolveNextChildMotionWarmupStep('center_arrive')).toBe(
|
|
'wave_greeting',
|
|
);
|
|
expect(resolveNextChildMotionWarmupStep('level_select')).toBe('level_select');
|
|
});
|
|
|
|
it('checks position completion against the active green ring target', () => {
|
|
expect(
|
|
isAvatarOnWarmupTarget(
|
|
getChildMotionWarmupStep('center_arrive'),
|
|
CHILD_MOTION_CENTER_X,
|
|
),
|
|
).toBe(true);
|
|
expect(
|
|
isAvatarOnWarmupTarget(getChildMotionWarmupStep('move_left'), 0.66),
|
|
).toBe(false);
|
|
});
|
|
|
|
it('records session-only calibration values from completed steps', () => {
|
|
const empty = createEmptyChildMotionCalibration();
|
|
const withLeft = applyChildMotionWarmupCompletion('move_left', empty, {
|
|
type: 'position',
|
|
avatarX: 0.34,
|
|
});
|
|
const withRight = applyChildMotionWarmupCompletion('move_right', withLeft, {
|
|
type: 'position',
|
|
avatarX: 0.66,
|
|
});
|
|
const withLeftHand = applyChildMotionWarmupCompletion(
|
|
'wave_left_hand',
|
|
withRight,
|
|
{
|
|
type: 'left-hand',
|
|
path: [
|
|
{ x: 0.3, y: 0.4, armAngleDeg: 12, armReach: 0.2 },
|
|
{ x: 0.34, y: 0.32, armAngleDeg: 44, armReach: 0.28 },
|
|
],
|
|
},
|
|
);
|
|
const withRightHand = applyChildMotionWarmupCompletion(
|
|
'wave_right_hand',
|
|
withLeftHand,
|
|
{
|
|
type: 'right-hand',
|
|
path: [
|
|
{ x: 0.7, y: 0.42, armAngleDeg: 10, armReach: 0.22 },
|
|
{ x: 0.82, y: 0.3, armAngleDeg: 46, armReach: 0.31 },
|
|
],
|
|
},
|
|
);
|
|
|
|
expect(withRightHand.leftBoundary).toBeCloseTo(0.16);
|
|
expect(withRightHand.rightBoundary).toBeCloseTo(0.16);
|
|
expect(withRightHand.leftHandPath).toHaveLength(2);
|
|
expect(withRightHand.leftHandSpace).toEqual({
|
|
minX: 0.3,
|
|
maxX: 0.34,
|
|
minY: 0.32,
|
|
maxY: 0.4,
|
|
minAngleDeg: 12,
|
|
maxAngleDeg: 44,
|
|
maxReach: 0.28,
|
|
});
|
|
expect(withRightHand.rightHandSpace?.maxReach).toBe(0.31);
|
|
});
|
|
});
|