54 lines
1.4 KiB
TypeScript
54 lines
1.4 KiB
TypeScript
import type {
|
|
CircularZone,
|
|
CustomZone,
|
|
InterestZone,
|
|
RectangularZone,
|
|
Vector3,
|
|
} from "./interest-manager.types.js";
|
|
|
|
export function vectorDistance(a: Vector3, b: Vector3): number {
|
|
const dx = a.x - b.x;
|
|
const dy = a.y - b.y;
|
|
const dz = (a.z ?? 0) - (b.z ?? 0);
|
|
return Math.sqrt(dx * dx + dy * dy + dz * dz);
|
|
}
|
|
|
|
export function zoneContains(zone: InterestZone, point: Vector3): boolean {
|
|
if (zone.shape === "circular") {
|
|
return (
|
|
vectorDistance(zone.center, point) <= (zone as CircularZone).radius
|
|
);
|
|
}
|
|
if (zone.shape === "rectangular") {
|
|
const r = zone as RectangularZone;
|
|
const hw = r.width / 2;
|
|
const hh = r.height / 2;
|
|
const inX = Math.abs(point.x - r.center.x) <= hw;
|
|
const inY = Math.abs(point.y - r.center.y) <= hh;
|
|
if (r.depth !== undefined && point.z !== undefined) {
|
|
return (
|
|
inX &&
|
|
inY &&
|
|
Math.abs(point.z - (r.center.z ?? 0)) <= r.depth / 2
|
|
);
|
|
}
|
|
return inX && inY;
|
|
}
|
|
return (zone as CustomZone).containsPoint(point);
|
|
}
|
|
|
|
export function calcPriority(
|
|
distance: number,
|
|
sharedZoneCount: number,
|
|
maxPriority: number,
|
|
decayRate: number
|
|
): number {
|
|
return Math.max(
|
|
0,
|
|
Math.min(
|
|
maxPriority,
|
|
maxPriority - distance * decayRate + sharedZoneCount * 0.5
|
|
)
|
|
);
|
|
}
|