Files
healer-man/src/game/inputMath.ts
T
2026-08-14 15:56:39 -04:00

66 lines
2.1 KiB
TypeScript

export type PlanarVector = readonly [x: number, z: number];
export const DEFAULT_CAMERA_PITCH = 0.32;
export function clamp(value: number, minimum: number, maximum: number): number {
return Math.min(maximum, Math.max(minimum, value));
}
export function applyRadialDeadzone(
x: number,
y: number,
deadzone = 0.18,
): PlanarVector {
if (!Number.isFinite(x) || !Number.isFinite(y)) return [0, 0];
const magnitude = Math.hypot(x, y);
if (magnitude <= deadzone || magnitude === 0) return [0, 0];
const remappedMagnitude = clamp((magnitude - deadzone) / (1 - deadzone), 0, 1);
const scale = remappedMagnitude / magnitude;
return [x * scale, y * scale];
}
export function normalizePlanar(x: number, z: number): PlanarVector {
if (!Number.isFinite(x) || !Number.isFinite(z)) return [0, 0];
const magnitude = Math.hypot(x, z);
if (magnitude <= 1) return [x, z];
return [x / magnitude, z / magnitude];
}
/** Converts input into world movement for a Three.js +Z-forward player. */
export function cameraRelativeMovement(
moveX: number,
moveForward: number,
yaw: number,
): PlanarVector {
const [x, forward] = normalizePlanar(moveX, moveForward);
const safeYaw = Number.isFinite(yaw) ? yaw : 0;
const sinYaw = Math.sin(safeYaw);
const cosYaw = Math.cos(safeYaw);
return [
-x * cosYaw + forward * sinYaw,
x * sinYaw + forward * cosYaw,
];
}
/** Applies device-right look using the screen-right basis of the +Z camera rig. */
export function cameraYawAfterHorizontalLook(yaw: number, horizontalLook: number): number {
const safeYaw = Number.isFinite(yaw) ? yaw : 0;
const safeLook = Number.isFinite(horizontalLook) ? horizontalLook : 0;
return wrapAngle(safeYaw - safeLook);
}
export function clampCameraPitch(pitch: number): number {
return Number.isFinite(pitch) ? clamp(pitch, -0.18, 0.88) : DEFAULT_CAMERA_PITCH;
}
export function wrapAngle(angle: number): number {
return Number.isFinite(angle) ? Math.atan2(Math.sin(angle), Math.cos(angle)) : 0;
}
export function planarDistance(
from: readonly [number, number, number],
to: readonly [number, number, number],
): number {
return Math.hypot(to[0] - from[0], to[2] - from[2]);
}