Files
onboarding-project/docs/worklog/05-camera-facing-lock.md
2026-08-14 15:03:43 +03:00

3.1 KiB
Raw Permalink Blame History

Камера підлаштовується під facing-lock на крейт (2026-08-12)

Користувач: коли персонаж зупиняється біля ящика і "тригер збору" (PlayerC.faceTowards, викликається з updateMovement коли stopped && nearbyObstacle) розвертає його лицем до цілі, камера має підлаштовуватись під новий кут, а не лишатись байдужою. Це саме той кейс, який попередній рух-based lookAhead свідомо ігнорував (розворот на місці = нульовий movement = look-ahead не оновлюється) — правильна поведінка для довільного розвороту, але користувач хотів виключення саме для facing-lock на breakable-ціль.

Рішення без повернення до facing/quaternion-залежності (яка й дала "рух по колу" раніше): PlayerC тепер зберігає, на яку саме ТОЧКУ (не кут!) він зараз locked — facingTarget: Vector3 | null, виставляється в updateMovement() в той самий момент, коли викликається faceTowards() (і скидається в null, коли умова stopped && nearbyObstacle неправдива). Публічний PlayerC.getFacingTarget().

CameraFollowC.setFacingTargetGetter(getter) — injected getter (той самий DI-паттерн, що й ResourceC.setFlyTarget), підключено в TestSceneC.init() відразу після CameraFollowC.init(). В update(): якщо facingTarget не null — desiredLookAhead рахується як напрямок від гравця ДО цієї точки (XZ, нормалізований) × LOOK_AHEAD_DISTANCE, замість напрямку руху; інакше — стара логіка (рух або hold). Ключове: джерело — фіксована ТОЧКА в world-space (nearbyObstacle.center), а не обертовий вектор — поки гравець і ящик обидва стоять на місці, цей напрямок сам по собі константний, тож smoothedLookAhead.lerp(...) дає один плавний лінійний зсув до нової позиції й ЗУПИНЯЄТЬСЯ там, а не описує дугу (на відміну від facing/quaternion-based версії, яка оберталась разом з тілом персонажа).

Перевірено (Playwright, тимчасове логування window.__dbgFacing/ __dbgLookAhead, видалене після): після зупинки біля крейта facingTarget стає non-null, і smoothedLookAhead плавно зсувається від ~(-0.02, 1.46) до нового значення ((-1.03, 1.08) і триває сходитись) — камера реально підлаштовується, а не стоїть на місці.