73 lines
2.8 KiB
JavaScript
Executable File
73 lines
2.8 KiB
JavaScript
Executable File
import { coordEach } from '@turf/meta';
|
|
import { isObject } from '@turf/helpers';
|
|
import { getCoords } from '@turf/invariant';
|
|
import clone from '@turf/clone';
|
|
import rhumbDestination from '@turf/rhumb-destination';
|
|
|
|
/**
|
|
* Moves any geojson Feature or Geometry of a specified distance along a Rhumb Line
|
|
* on the provided direction angle.
|
|
*
|
|
* @name transformTranslate
|
|
* @param {GeoJSON} geojson object to be translated
|
|
* @param {number} distance length of the motion; negative values determine motion in opposite direction
|
|
* @param {number} direction of the motion; angle from North in decimal degrees, positive clockwise
|
|
* @param {Object} [options={}] Optional parameters
|
|
* @param {string} [options.units='kilometers'] in which `distance` will be express; miles, kilometers, degrees, or radians
|
|
* @param {number} [options.zTranslation=0] length of the vertical motion, same unit of distance
|
|
* @param {boolean} [options.mutate=false] allows GeoJSON input to be mutated (significant performance increase if true)
|
|
* @returns {GeoJSON} the translated GeoJSON object
|
|
* @example
|
|
* var poly = turf.polygon([[[0,29],[3.5,29],[2.5,32],[0,29]]]);
|
|
* var translatedPoly = turf.transformTranslate(poly, 100, 35);
|
|
*
|
|
* //addToMap
|
|
* var addToMap = [poly, translatedPoly];
|
|
* translatedPoly.properties = {stroke: '#F00', 'stroke-width': 4};
|
|
*/
|
|
function transformTranslate(geojson, distance, direction, options) {
|
|
// Optional parameters
|
|
options = options || {};
|
|
if (!isObject(options)) throw new Error("options is invalid");
|
|
var units = options.units;
|
|
var zTranslation = options.zTranslation;
|
|
var mutate = options.mutate;
|
|
|
|
// Input validation
|
|
if (!geojson) throw new Error("geojson is required");
|
|
if (distance === undefined || distance === null || isNaN(distance))
|
|
throw new Error("distance is required");
|
|
if (zTranslation && typeof zTranslation !== "number" && isNaN(zTranslation))
|
|
throw new Error("zTranslation is not a number");
|
|
|
|
// Shortcut no-motion
|
|
zTranslation = zTranslation !== undefined ? zTranslation : 0;
|
|
if (distance === 0 && zTranslation === 0) return geojson;
|
|
|
|
if (direction === undefined || direction === null || isNaN(direction))
|
|
throw new Error("direction is required");
|
|
|
|
// Invert with negative distances
|
|
if (distance < 0) {
|
|
distance = -distance;
|
|
direction = direction + 180;
|
|
}
|
|
|
|
// Clone geojson to avoid side effects
|
|
if (mutate === false || mutate === undefined) geojson = clone(geojson);
|
|
|
|
// Translate each coordinate
|
|
coordEach(geojson, function (pointCoords) {
|
|
var newCoords = getCoords(
|
|
rhumbDestination(pointCoords, distance, direction, { units: units })
|
|
);
|
|
pointCoords[0] = newCoords[0];
|
|
pointCoords[1] = newCoords[1];
|
|
if (zTranslation && pointCoords.length === 3)
|
|
pointCoords[2] += zTranslation;
|
|
});
|
|
return geojson;
|
|
}
|
|
|
|
export default transformTranslate;
|