Files
dkala-api/src/modules/cart/utils/geographic.utils.ts
T
2026-02-08 08:50:08 +03:30

69 lines
1.8 KiB
TypeScript

/**
* Utility class for geographic calculations
*/
export class GeographicUtils {
/**
* Check if a point is inside a polygon using ray-casting algorithm
* @param point - [longitude, latitude]
* @param polygon - Array of [longitude, latitude] pairs
*/
static isPointInPolygon(point: [number, number], polygon: [number, number][]): boolean {
const x = point[0];
const y = point[1];
let inside = false;
for (let i = 0, j = polygon.length - 1; i < polygon.length; j = i++) {
const xi = polygon[i][0];
const yi = polygon[i][1];
const xj = polygon[j][0];
const yj = polygon[j][1];
const intersect =
yi > y !== yj > y && x < ((xj - xi) * (y - yi)) / (yj - yi + Number.EPSILON) + xi;
if (intersect) inside = !inside;
}
return inside;
}
/**
* Convert degrees to radians
*/
private static toRad(value: number): number {
return (value * Math.PI) / 180;
}
/**
* Calculate distance between two points in kilometers using Haversine formula
*/
static getDistanceKm(lat1: number, lng1: number, lat2: number, lng2: number): number {
const R = 6371; // Earth radius in KM
const dLat = this.toRad(lat2 - lat1);
const dLng = this.toRad(lng2 - lng1);
const a =
Math.sin(dLat / 2) ** 2 +
Math.cos(this.toRad(lat1)) * Math.cos(this.toRad(lat2)) * Math.sin(dLng / 2) ** 2;
const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
return R * c;
}
/**
* Calculate distance between two points in kilometers (rounded)
*/
static getDistanceKmRounded(
lat1: number,
lng1: number,
lat2: number,
lng2: number,
precision = 2,
): number {
const distance = this.getDistanceKm(lat1, lng1, lat2, lng2);
return Number(distance.toFixed(precision));
}
}