import { STATE, CONFIG } from '../core/State.js'; // Integrates a single frame of free-fly "ship" navigation: turns the WASDQE/Shift // move state into camera displacement through the pointer-lock controls, applying // damping and the dynamic turbo (Shift) multiplier. // // Kept as a standalone, frame-stepped function (rather than inline in the rAF // loop) so it can be driven deterministically with a fixed `delta` from tests — // headless browsers throttle requestAnimationFrame, which otherwise makes the // navigation path impossible to assert on. Operates on the shared STATE plus the // passed `camera`/`controls`. export function updateNavigation(camera, controls, delta) { // Exponential damping toward rest. STATE.velocity.x -= STATE.velocity.x * CONFIG.damping * delta; STATE.velocity.y -= STATE.velocity.y * CONFIG.damping * delta; STATE.velocity.z -= STATE.velocity.z * CONFIG.damping * delta; STATE.direction.z = Number(STATE.moveState.forward) - Number(STATE.moveState.backward); STATE.direction.x = Number(STATE.moveState.right) - Number(STATE.moveState.left); STATE.direction.y = Number(STATE.moveState.up) - Number(STATE.moveState.down); STATE.direction.normalize(); // Dynamic turbo: Shift ramps the multiplier up to a cap while held. if (STATE.moveState.shift) { if (STATE.currentRunMultiplier < CONFIG.runBaseMultiplier) { STATE.currentRunMultiplier = CONFIG.runBaseMultiplier; } STATE.currentRunMultiplier += CONFIG.runAcceleration * delta; STATE.currentRunMultiplier = Math.min(STATE.currentRunMultiplier, CONFIG.runMaxMultiplier); } else { STATE.currentRunMultiplier = 1.0; } const effectiveAcceleration = CONFIG.acceleration * STATE.currentRunMultiplier; if (STATE.moveState.forward || STATE.moveState.backward) STATE.velocity.z -= STATE.direction.z * effectiveAcceleration * delta; if (STATE.moveState.left || STATE.moveState.right) STATE.velocity.x -= STATE.direction.x * effectiveAcceleration * delta; if (STATE.moveState.up || STATE.moveState.down) STATE.velocity.y += STATE.direction.y * effectiveAcceleration * delta; controls.moveRight(-STATE.velocity.x * delta); controls.moveForward(-STATE.velocity.z * delta); camera.position.y += STATE.velocity.y * delta; }