index.cjs 9.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273
  1. "use strict";Object.defineProperty(exports, "__esModule", {value: true});// index.js
  2. var _helpers = require('@turf/helpers');
  3. var _invariant = require('@turf/invariant');
  4. // lib/arc.js
  5. var D2R = Math.PI / 180;
  6. var R2D = 180 / Math.PI;
  7. var Coord = function(lon, lat) {
  8. this.lon = lon;
  9. this.lat = lat;
  10. this.x = D2R * lon;
  11. this.y = D2R * lat;
  12. };
  13. Coord.prototype.view = function() {
  14. return String(this.lon).slice(0, 4) + "," + String(this.lat).slice(0, 4);
  15. };
  16. Coord.prototype.antipode = function() {
  17. var anti_lat = -1 * this.lat;
  18. var anti_lon = this.lon < 0 ? 180 + this.lon : (180 - this.lon) * -1;
  19. return new Coord(anti_lon, anti_lat);
  20. };
  21. var LineString = function() {
  22. this.coords = [];
  23. this.length = 0;
  24. };
  25. LineString.prototype.move_to = function(coord) {
  26. this.length++;
  27. this.coords.push(coord);
  28. };
  29. var Arc = function(properties) {
  30. this.properties = properties || {};
  31. this.geometries = [];
  32. };
  33. Arc.prototype.json = function() {
  34. if (this.geometries.length <= 0) {
  35. return {
  36. geometry: { type: "LineString", coordinates: null },
  37. type: "Feature",
  38. properties: this.properties
  39. };
  40. } else if (this.geometries.length === 1) {
  41. return {
  42. geometry: { type: "LineString", coordinates: this.geometries[0].coords },
  43. type: "Feature",
  44. properties: this.properties
  45. };
  46. } else {
  47. var multiline = [];
  48. for (var i = 0; i < this.geometries.length; i++) {
  49. multiline.push(this.geometries[i].coords);
  50. }
  51. return {
  52. geometry: { type: "MultiLineString", coordinates: multiline },
  53. type: "Feature",
  54. properties: this.properties
  55. };
  56. }
  57. };
  58. Arc.prototype.wkt = function() {
  59. var wkt_string = "";
  60. var wkt = "LINESTRING(";
  61. var collect = function(c) {
  62. wkt += c[0] + " " + c[1] + ",";
  63. };
  64. for (var i = 0; i < this.geometries.length; i++) {
  65. if (this.geometries[i].coords.length === 0) {
  66. return "LINESTRING(empty)";
  67. } else {
  68. var coords = this.geometries[i].coords;
  69. coords.forEach(collect);
  70. wkt_string += wkt.substring(0, wkt.length - 1) + ")";
  71. }
  72. }
  73. return wkt_string;
  74. };
  75. var GreatCircle = function(start, end, properties) {
  76. if (!start || start.x === void 0 || start.y === void 0) {
  77. throw new Error(
  78. "GreatCircle constructor expects two args: start and end objects with x and y properties"
  79. );
  80. }
  81. if (!end || end.x === void 0 || end.y === void 0) {
  82. throw new Error(
  83. "GreatCircle constructor expects two args: start and end objects with x and y properties"
  84. );
  85. }
  86. this.start = new Coord(start.x, start.y);
  87. this.end = new Coord(end.x, end.y);
  88. this.properties = properties || {};
  89. var w = this.start.x - this.end.x;
  90. var h = this.start.y - this.end.y;
  91. var z = Math.pow(Math.sin(h / 2), 2) + Math.cos(this.start.y) * Math.cos(this.end.y) * Math.pow(Math.sin(w / 2), 2);
  92. this.g = 2 * Math.asin(Math.sqrt(z));
  93. if (this.g === Math.PI) {
  94. throw new Error(
  95. "it appears " + start.view() + " and " + end.view() + " are 'antipodal', e.g diametrically opposite, thus there is no single route but rather infinite"
  96. );
  97. } else if (isNaN(this.g)) {
  98. throw new Error(
  99. "could not calculate great circle between " + start + " and " + end
  100. );
  101. }
  102. };
  103. GreatCircle.prototype.interpolate = function(f) {
  104. var A = Math.sin((1 - f) * this.g) / Math.sin(this.g);
  105. var B = Math.sin(f * this.g) / Math.sin(this.g);
  106. var x = A * Math.cos(this.start.y) * Math.cos(this.start.x) + B * Math.cos(this.end.y) * Math.cos(this.end.x);
  107. var y = A * Math.cos(this.start.y) * Math.sin(this.start.x) + B * Math.cos(this.end.y) * Math.sin(this.end.x);
  108. var z = A * Math.sin(this.start.y) + B * Math.sin(this.end.y);
  109. var lat = R2D * Math.atan2(z, Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2)));
  110. var lon = R2D * Math.atan2(y, x);
  111. return [lon, lat];
  112. };
  113. GreatCircle.prototype.Arc = function(npoints, options) {
  114. var first_pass = [];
  115. if (!npoints || npoints <= 2) {
  116. first_pass.push([this.start.lon, this.start.lat]);
  117. first_pass.push([this.end.lon, this.end.lat]);
  118. } else {
  119. var delta = 1 / (npoints - 1);
  120. for (var i = 0; i < npoints; ++i) {
  121. var step = delta * i;
  122. var pair = this.interpolate(step);
  123. first_pass.push(pair);
  124. }
  125. }
  126. var bHasBigDiff = false;
  127. var dfMaxSmallDiffLong = 0;
  128. var dfDateLineOffset = options && options.offset ? options.offset : 10;
  129. var dfLeftBorderX = 180 - dfDateLineOffset;
  130. var dfRightBorderX = -180 + dfDateLineOffset;
  131. var dfDiffSpace = 360 - dfDateLineOffset;
  132. for (var j = 1; j < first_pass.length; ++j) {
  133. var dfPrevX = first_pass[j - 1][0];
  134. var dfX = first_pass[j][0];
  135. var dfDiffLong = Math.abs(dfX - dfPrevX);
  136. if (dfDiffLong > dfDiffSpace && (dfX > dfLeftBorderX && dfPrevX < dfRightBorderX || dfPrevX > dfLeftBorderX && dfX < dfRightBorderX)) {
  137. bHasBigDiff = true;
  138. } else if (dfDiffLong > dfMaxSmallDiffLong) {
  139. dfMaxSmallDiffLong = dfDiffLong;
  140. }
  141. }
  142. var poMulti = [];
  143. if (bHasBigDiff && dfMaxSmallDiffLong < dfDateLineOffset) {
  144. var poNewLS = [];
  145. poMulti.push(poNewLS);
  146. for (var k = 0; k < first_pass.length; ++k) {
  147. var dfX0 = parseFloat(first_pass[k][0]);
  148. if (k > 0 && Math.abs(dfX0 - first_pass[k - 1][0]) > dfDiffSpace) {
  149. var dfX1 = parseFloat(first_pass[k - 1][0]);
  150. var dfY1 = parseFloat(first_pass[k - 1][1]);
  151. var dfX2 = parseFloat(first_pass[k][0]);
  152. var dfY2 = parseFloat(first_pass[k][1]);
  153. if (dfX1 > -180 && dfX1 < dfRightBorderX && dfX2 === 180 && k + 1 < first_pass.length && first_pass[k - 1][0] > -180 && first_pass[k - 1][0] < dfRightBorderX) {
  154. poNewLS.push([-180, first_pass[k][1]]);
  155. k++;
  156. poNewLS.push([first_pass[k][0], first_pass[k][1]]);
  157. continue;
  158. } else if (dfX1 > dfLeftBorderX && dfX1 < 180 && dfX2 === -180 && k + 1 < first_pass.length && first_pass[k - 1][0] > dfLeftBorderX && first_pass[k - 1][0] < 180) {
  159. poNewLS.push([180, first_pass[k][1]]);
  160. k++;
  161. poNewLS.push([first_pass[k][0], first_pass[k][1]]);
  162. continue;
  163. }
  164. if (dfX1 < dfRightBorderX && dfX2 > dfLeftBorderX) {
  165. var tmpX = dfX1;
  166. dfX1 = dfX2;
  167. dfX2 = tmpX;
  168. var tmpY = dfY1;
  169. dfY1 = dfY2;
  170. dfY2 = tmpY;
  171. }
  172. if (dfX1 > dfLeftBorderX && dfX2 < dfRightBorderX) {
  173. dfX2 += 360;
  174. }
  175. if (dfX1 <= 180 && dfX2 >= 180 && dfX1 < dfX2) {
  176. var dfRatio = (180 - dfX1) / (dfX2 - dfX1);
  177. var dfY = dfRatio * dfY2 + (1 - dfRatio) * dfY1;
  178. poNewLS.push([
  179. first_pass[k - 1][0] > dfLeftBorderX ? 180 : -180,
  180. dfY
  181. ]);
  182. poNewLS = [];
  183. poNewLS.push([
  184. first_pass[k - 1][0] > dfLeftBorderX ? -180 : 180,
  185. dfY
  186. ]);
  187. poMulti.push(poNewLS);
  188. } else {
  189. poNewLS = [];
  190. poMulti.push(poNewLS);
  191. }
  192. poNewLS.push([dfX0, first_pass[k][1]]);
  193. } else {
  194. poNewLS.push([first_pass[k][0], first_pass[k][1]]);
  195. }
  196. }
  197. } else {
  198. var poNewLS0 = [];
  199. poMulti.push(poNewLS0);
  200. for (var l = 0; l < first_pass.length; ++l) {
  201. poNewLS0.push([first_pass[l][0], first_pass[l][1]]);
  202. }
  203. }
  204. var arc = new Arc(this.properties);
  205. for (var m = 0; m < poMulti.length; ++m) {
  206. var line = new LineString();
  207. arc.geometries.push(line);
  208. var points = poMulti[m];
  209. for (var j0 = 0; j0 < points.length; ++j0) {
  210. line.move_to(points[j0]);
  211. }
  212. }
  213. return arc;
  214. };
  215. // index.js
  216. function greatCircle(start, end, options) {
  217. options = options || {};
  218. if (typeof options !== "object") throw new Error("options is invalid");
  219. var properties = options.properties;
  220. var npoints = options.npoints;
  221. var offset = options.offset;
  222. start = _invariant.getCoord.call(void 0, start);
  223. end = _invariant.getCoord.call(void 0, end);
  224. properties = properties || {};
  225. npoints = npoints || 100;
  226. if (start[0] === end[0] && start[1] === end[1]) {
  227. const arr = Array(npoints);
  228. arr.fill([start[0], start[1]]);
  229. return _helpers.lineString.call(void 0, arr, properties);
  230. }
  231. offset = offset || 10;
  232. var generator = new GreatCircle(
  233. { x: start[0], y: start[1] },
  234. { x: end[0], y: end[1] },
  235. properties
  236. );
  237. var line = generator.Arc(npoints, { offset });
  238. return line.json();
  239. }
  240. var turf_great_circle_default = greatCircle;
  241. exports.default = turf_great_circle_default; exports.greatCircle = greatCircle;
  242. /*!
  243. * Copyright (c) 2019, Dane Springmeyer
  244. *
  245. * Redistribution and use in source and binary forms, with or without
  246. * modification, are permitted provided that the following conditions are
  247. * met:
  248. *
  249. * * Redistributions of source code must retain the above copyright
  250. * notice, this list of conditions and the following disclaimer.
  251. * * Redistributions in binary form must reproduce the above copyright
  252. * notice, this list of conditions and the following disclaimer in
  253. * the documentation and/or other materials provided with the
  254. * distribution.
  255. *
  256. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
  257. * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
  258. * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  259. * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  260. * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  261. * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  262. * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  263. * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
  264. * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  265. * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  266. * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  267. */
  268. //# sourceMappingURL=index.cjs.map