UNPKG

@turf/ellipse

Version:

Takes a Point and calculates the ellipse polygon given two semi-axes expressed in variable units and steps for precision.

92 lines (83 loc) 3.13 kB
"use strict";Object.defineProperty(exports, "__esModule", {value: true});// index.ts var _helpers = require('@turf/helpers'); var _destination = require('@turf/destination'); var _transformrotate = require('@turf/transform-rotate'); var _invariant = require('@turf/invariant'); function ellipse(center, xSemiAxis, ySemiAxis, options) { options = options || {}; let steps = options.steps || 64; const units = options.units || "kilometers"; let angle = options.angle || 0; const pivot = options.pivot || center; const properties = options.properties || {}; if (!center) throw new Error("center is required"); if (!xSemiAxis) throw new Error("xSemiAxis is required"); if (!ySemiAxis) throw new Error("ySemiAxis is required"); if (!_helpers.isObject.call(void 0, options)) throw new Error("options must be an object"); if (!_helpers.isNumber.call(void 0, steps)) throw new Error("steps must be a number"); if (!_helpers.isNumber.call(void 0, angle)) throw new Error("angle must be a number"); const centerCoords = _invariant.getCoord.call(void 0, _transformrotate.transformRotate.call(void 0, _helpers.point.call(void 0, _invariant.getCoord.call(void 0, center)), angle, { pivot }) ); angle = -90 + angle; steps = Math.ceil(steps / 4); let quadrantParameters = []; let parameters = []; const a = xSemiAxis; const b = ySemiAxis; const c = b; const m = (a - b) / (Math.PI / 2); const A = (a + b) * Math.PI / 4; const v = 0.5; const k = steps; let w = 0; let x = 0; for (let i = 0; i < steps; i++) { x += w; if (m === 0) { w = A / k / c; } else { w = (-(m * x + c) + Math.sqrt(Math.pow(m * x + c, 2) - 4 * (v * m) * -(A / k))) / (2 * (v * m)); } if (x != 0) { quadrantParameters.push(x); } } parameters.push(0); for (let i = 0; i < quadrantParameters.length; i++) { parameters.push(quadrantParameters[i]); } parameters.push(Math.PI / 2); for (let i = 0; i < quadrantParameters.length; i++) { parameters.push( Math.PI - quadrantParameters[quadrantParameters.length - i - 1] ); } parameters.push(Math.PI); for (let i = 0; i < quadrantParameters.length; i++) { parameters.push(Math.PI + quadrantParameters[i]); } parameters.push(3 * Math.PI / 2); for (let i = 0; i < quadrantParameters.length; i++) { parameters.push( 2 * Math.PI - quadrantParameters[quadrantParameters.length - i - 1] ); } parameters.push(0); const coords = []; for (const param of parameters) { const theta = Math.atan2(b * Math.sin(param), a * Math.cos(param)); const r = Math.sqrt( Math.pow(a, 2) * Math.pow(b, 2) / (Math.pow(a * Math.sin(theta), 2) + Math.pow(b * Math.cos(theta), 2)) ); coords.push( _destination.destination.call(void 0, centerCoords, r, angle + _helpers.radiansToDegrees.call(void 0, theta), { units }).geometry.coordinates ); } return _helpers.polygon.call(void 0, [coords], properties); } var index_default = ellipse; exports.default = index_default; exports.ellipse = ellipse; //# sourceMappingURL=index.cjs.map