@idm-plugin/geo 2.1.8 → 2.1.9
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +368 -354
- package/dist/index.umd.cjs +6 -6
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import * as f from "@turf/turf";
|
|
2
|
-
import
|
|
3
|
-
import
|
|
2
|
+
import b from "moment";
|
|
3
|
+
import w from "@log4js-node/log4js-api";
|
|
4
4
|
import "moment-timezone";
|
|
5
|
-
import
|
|
6
|
-
import
|
|
5
|
+
import F from "tz-lookup";
|
|
6
|
+
import k from "shpjs";
|
|
7
7
|
class d {
|
|
8
8
|
/**
|
|
9
9
|
* 基于输入的经度,计算出时区
|
|
@@ -12,7 +12,7 @@ class d {
|
|
|
12
12
|
*/
|
|
13
13
|
static guessTimeZoneOffset(t, e) {
|
|
14
14
|
t = d.convertToStdLng(t);
|
|
15
|
-
const n =
|
|
15
|
+
const n = F(e, t), i = b().tz(n).utcOffset();
|
|
16
16
|
return d.roundPrecision(i / 60, 1);
|
|
17
17
|
}
|
|
18
18
|
/**
|
|
@@ -33,16 +33,16 @@ class d {
|
|
|
33
33
|
t = d.convertToStdLng(t, e);
|
|
34
34
|
let i = "E";
|
|
35
35
|
t < 0 && (i = "W"), t = Math.abs(t), n = n.toUpperCase();
|
|
36
|
-
let o = t * 3600,
|
|
37
|
-
|
|
38
|
-
const g = `${n.replace(/S+/gi,
|
|
36
|
+
let o = t * 3600, r, s, c, a, u, l;
|
|
37
|
+
r = o % 3600 % 60, n.indexOf("S") !== -1 && (o = o - r, s = d.padNumber(r, 2, 2)), c = o / 60 % 60, n.indexOf("M") !== -1 && (n.indexOf("S") !== -1 ? a = d.roundPrecision(c, e).toString().padStart(2, "0") : a = d.padNumber(c, 2, 3), o = o - c * 60), u = o / 3600, n.indexOf("M") !== -1 ? l = d.roundPrecision(u, e).toString().padStart(3, "0") : l = d.padNumber(u, 3, 6), Number(s) >= 60 && (a = Number(a) + 1, s = 0), Number(a) >= 60 && (l = Number(l) + 1, a = 0);
|
|
38
|
+
const g = `${n.replace(/S+/gi, s).replace(/M+/gi, a).replace(/H+/gi, l)}${i}`;
|
|
39
39
|
return {
|
|
40
40
|
direction: i,
|
|
41
41
|
degree: d.roundPrecision(u, e),
|
|
42
42
|
minute: d.roundPrecision(c, e),
|
|
43
|
-
second: d.roundPrecision(
|
|
43
|
+
second: d.roundPrecision(r, e),
|
|
44
44
|
pretty: g,
|
|
45
|
-
S:
|
|
45
|
+
S: s,
|
|
46
46
|
M: a,
|
|
47
47
|
H: l
|
|
48
48
|
};
|
|
@@ -57,16 +57,16 @@ class d {
|
|
|
57
57
|
t = t % 180;
|
|
58
58
|
let i = "N";
|
|
59
59
|
t < 0 && (i = "S"), t = Math.abs(t), n = n.toUpperCase();
|
|
60
|
-
let o = t * 3600,
|
|
61
|
-
|
|
62
|
-
const g = `${n.replace(/S+/gi,
|
|
60
|
+
let o = t * 3600, r, s, c, a, u, l;
|
|
61
|
+
r = o % 3600 % 60, n.indexOf("S") !== -1 && (o = o - r, s = d.padNumber(r, 2, 2)), c = o / 60 % 60, n.indexOf("M") !== -1 && (n.indexOf("S") !== -1 ? a = d.roundPrecision(c, e).toString().padStart(2, "0") : a = d.padNumber(c, 2, 3), o = o - c * 60), u = o / 3600, n.indexOf("M") !== -1 ? l = d.roundPrecision(u, e).toString().padStart(2, "0") : l = d.padNumber(u, 2, 6), Number(s) >= 60 && (a = Number(a) + 1, s = 0), Number(a) >= 60 && (l = Number(l) + 1, a = 0);
|
|
62
|
+
const g = `${n.replace(/S+/gi, s).replace(/M+/gi, a).replace(/H+/gi, l)}${i}`;
|
|
63
63
|
return {
|
|
64
64
|
direction: i,
|
|
65
65
|
degree: d.roundPrecision(u, e),
|
|
66
66
|
minute: d.roundPrecision(c, e),
|
|
67
|
-
second: d.roundPrecision(
|
|
67
|
+
second: d.roundPrecision(r, e),
|
|
68
68
|
pretty: g,
|
|
69
|
-
S:
|
|
69
|
+
S: s,
|
|
70
70
|
M: a,
|
|
71
71
|
H: l
|
|
72
72
|
};
|
|
@@ -78,12 +78,12 @@ class d {
|
|
|
78
78
|
const i = t[t.length - 1].toUpperCase();
|
|
79
79
|
t = t.substring(0, t.length - 1).trim();
|
|
80
80
|
const o = t.split(" ").filter((a) => a !== "").map((a) => Math.abs(Number(a)));
|
|
81
|
-
let [
|
|
82
|
-
if (
|
|
83
|
-
const a = this.roundPrecision(
|
|
84
|
-
|
|
81
|
+
let [r, s, c] = o;
|
|
82
|
+
if (s = s || 0, s = s > 60 ? s / Math.pow(10, String(s).length - 2) : s, c = c || 0, c = c > 60 ? c / Math.pow(10, String(c).length - 2) : c, r > 360 && !s) {
|
|
83
|
+
const a = this.roundPrecision(r / 100, 0);
|
|
84
|
+
s = r - a * 100, r = a;
|
|
85
85
|
}
|
|
86
|
-
n =
|
|
86
|
+
n = r + s / 60 + c / 3600, i === "W" && (n = n * -1);
|
|
87
87
|
} else
|
|
88
88
|
n = Number(t);
|
|
89
89
|
return d.convertToStdLng(n, e);
|
|
@@ -95,12 +95,12 @@ class d {
|
|
|
95
95
|
const i = t[t.length - 1].toUpperCase();
|
|
96
96
|
t = t.substring(0, t.length - 1).trim();
|
|
97
97
|
const o = t.split(" ").filter((a) => a !== "").map((a) => Math.abs(Number(a)));
|
|
98
|
-
let [
|
|
99
|
-
if (c = c || 0,
|
|
100
|
-
const a = this.roundPrecision(
|
|
101
|
-
|
|
98
|
+
let [r, s, c] = o;
|
|
99
|
+
if (c = c || 0, s = s || 0, s = s > 60 ? s / Math.pow(10, String(s).length - 2) : s, c = c > 60 ? c / Math.pow(10, String(c).length - 2) : c, r > 90 && !s) {
|
|
100
|
+
const a = this.roundPrecision(r / 100, 0);
|
|
101
|
+
s = r - a * 100, r = a;
|
|
102
102
|
}
|
|
103
|
-
if (n =
|
|
103
|
+
if (n = r + s / 60 + c / 3600, n > 90)
|
|
104
104
|
throw new Error(`latitude out of range: ${t}${i}`);
|
|
105
105
|
i === "S" && (n = n * -1);
|
|
106
106
|
} else
|
|
@@ -170,14 +170,14 @@ class W {
|
|
|
170
170
|
return `${t.lat}|${t.lng}|${t.positionTime}|${t.sog}|${t.cog}|${t.hdg}|${t.draught}|${e}|${JSON.stringify(t.meteo || {})}|${t.vendor}|${t.deleted}`;
|
|
171
171
|
}
|
|
172
172
|
static str2Json(t) {
|
|
173
|
-
const [e, n, i, o,
|
|
173
|
+
const [e, n, i, o, r, s, c, a, u, l, g] = t.split("|");
|
|
174
174
|
return {
|
|
175
175
|
lat: Number(e),
|
|
176
176
|
lng: Number(n),
|
|
177
177
|
positionTime: Number(i),
|
|
178
178
|
sog: Number(o),
|
|
179
|
-
cog: Number(
|
|
180
|
-
hdg: Number(
|
|
179
|
+
cog: Number(r),
|
|
180
|
+
hdg: Number(s),
|
|
181
181
|
//@ts-ignore
|
|
182
182
|
draught: isNaN(c) ? null : Number(c),
|
|
183
183
|
type: a,
|
|
@@ -191,7 +191,7 @@ class W {
|
|
|
191
191
|
const i = t.at(0).positionTime < t.at(-1).positionTime;
|
|
192
192
|
i || t.sort((c, a) => c.positionTime - a.positionTime);
|
|
193
193
|
const o = [];
|
|
194
|
-
let
|
|
194
|
+
let r, s;
|
|
195
195
|
for (let c = 0; c < t.length - 1; c++) {
|
|
196
196
|
const a = t[c];
|
|
197
197
|
if (!(n && ["N", "B", "E", "NOON", "BOSP", "EOSP"].includes(a.type))) {
|
|
@@ -201,33 +201,33 @@ class W {
|
|
|
201
201
|
continue;
|
|
202
202
|
const h = g.positionTime - l.positionTime;
|
|
203
203
|
if (v.calculateDistance(g, l, !0, 4) / (h / 3600) < e)
|
|
204
|
-
|
|
204
|
+
r || (r = a), u === t.length - 1 && (s = g, c = u);
|
|
205
205
|
else {
|
|
206
|
-
|
|
206
|
+
r && (s = t[u - 1], c = u);
|
|
207
207
|
break;
|
|
208
208
|
}
|
|
209
209
|
}
|
|
210
|
-
if ((
|
|
210
|
+
if ((s == null ? void 0 : s.positionTime) > (r == null ? void 0 : r.positionTime) && r) {
|
|
211
211
|
const u = {
|
|
212
212
|
start: {
|
|
213
|
-
lat: s.lat,
|
|
214
|
-
lng: s.lng,
|
|
215
|
-
sog: s.sog,
|
|
216
|
-
positionTime: s.positionTime,
|
|
217
|
-
utc: y.unix(s.positionTime).utc().format()
|
|
218
|
-
},
|
|
219
|
-
end: {
|
|
220
213
|
lat: r.lat,
|
|
221
214
|
lng: r.lng,
|
|
222
215
|
sog: r.sog,
|
|
223
216
|
positionTime: r.positionTime,
|
|
224
|
-
utc:
|
|
217
|
+
utc: b.unix(r.positionTime).utc().format()
|
|
218
|
+
},
|
|
219
|
+
end: {
|
|
220
|
+
lat: s.lat,
|
|
221
|
+
lng: s.lng,
|
|
222
|
+
sog: s.sog,
|
|
223
|
+
positionTime: s.positionTime,
|
|
224
|
+
utc: b.unix(s.positionTime).utc().format()
|
|
225
225
|
},
|
|
226
|
-
duration:
|
|
226
|
+
duration: s.positionTime - r.positionTime
|
|
227
227
|
}, l = t.filter((h) => h.positionTime >= u.start.positionTime && h.positionTime <= u.end.positionTime), g = v.divideAccordingToLng(l);
|
|
228
228
|
u.distance = v.calculateRouteDistance(g), u.hours = Math.round(u.duration / 3600 * 10) / 10, u.avgSog = Math.round(u.distance / u.hours * 10) / 10, o.push(u);
|
|
229
229
|
}
|
|
230
|
-
|
|
230
|
+
r = void 0, s = void 0;
|
|
231
231
|
}
|
|
232
232
|
}
|
|
233
233
|
return i || t.sort((c, a) => a.positionTime - c.positionTime), o;
|
|
@@ -239,21 +239,21 @@ class W {
|
|
|
239
239
|
* @param etm
|
|
240
240
|
*/
|
|
241
241
|
static inspectSummary(t, e, n) {
|
|
242
|
-
const i =
|
|
243
|
-
let
|
|
244
|
-
if (
|
|
245
|
-
for (let u = 0; u <
|
|
246
|
-
const l =
|
|
247
|
-
|
|
242
|
+
const i = b(e), o = b(n), r = t.filter((u) => u.positionTime >= i.unix() && u.positionTime <= o.unix());
|
|
243
|
+
let s = 0, c = 0;
|
|
244
|
+
if (r.length > 1)
|
|
245
|
+
for (let u = 0; u < r.length - 1; u++) {
|
|
246
|
+
const l = r[u], g = r[u + 1];
|
|
247
|
+
s += v.calculateDistance(l, g, !0, 4), c += Math.abs(g.positionTime - l.positionTime);
|
|
248
248
|
}
|
|
249
|
-
|
|
250
|
-
const a = c ? Math.round(
|
|
251
|
-
return { distance:
|
|
249
|
+
s = Math.round(s * 100) / 100, c = Math.round(c / 3600 * 100) / 100;
|
|
250
|
+
const a = c ? Math.round(s / c * 100) / 100 : 0;
|
|
251
|
+
return { distance: s, interval: c, avgSpd: a };
|
|
252
252
|
}
|
|
253
253
|
}
|
|
254
254
|
let I;
|
|
255
255
|
try {
|
|
256
|
-
I =
|
|
256
|
+
I = w.getLogger("meteo");
|
|
257
257
|
} catch {
|
|
258
258
|
} finally {
|
|
259
259
|
}
|
|
@@ -271,8 +271,8 @@ class v {
|
|
|
271
271
|
[t.lng, t.lat],
|
|
272
272
|
[e.lng, e.lat]
|
|
273
273
|
]);
|
|
274
|
-
let
|
|
275
|
-
return n ?
|
|
274
|
+
let r;
|
|
275
|
+
return n ? r = f.rhumbBearing(o.features[0], o.features[1]) : r = f.bearing(o.features[0], o.features[1]), r < 0 && (r += 360), d.roundPrecision(r, i);
|
|
276
276
|
}
|
|
277
277
|
/**
|
|
278
278
|
* 计算两点间距离
|
|
@@ -285,12 +285,12 @@ class v {
|
|
|
285
285
|
*/
|
|
286
286
|
static calculateDistance(t, e, n = !0, i = 4, o = "nauticalmiles") {
|
|
287
287
|
t = { ...t }, e = { ...e }, t.lng = d.convertToStdLng(t.lng, i), e.lng = d.convertToStdLng(e.lng, i);
|
|
288
|
-
const
|
|
288
|
+
const r = f.points([
|
|
289
289
|
[t.lng, t.lat],
|
|
290
290
|
[e.lng, e.lat]
|
|
291
291
|
]);
|
|
292
|
-
let
|
|
293
|
-
return n ?
|
|
292
|
+
let s;
|
|
293
|
+
return n ? s = f.rhumbDistance(r.features[0], r.features[1], { units: o }) : s = f.distance(r.features[0], r.features[1], { units: o }), d.roundPrecision(s, i);
|
|
294
294
|
}
|
|
295
295
|
/**
|
|
296
296
|
* 计算航线距离
|
|
@@ -300,11 +300,11 @@ class v {
|
|
|
300
300
|
*/
|
|
301
301
|
static calculateRouteDistance(t, e = 4, n = "nauticalmiles") {
|
|
302
302
|
let i = 0, o;
|
|
303
|
-
for (const
|
|
304
|
-
for (let
|
|
305
|
-
const c = { lng: s
|
|
306
|
-
|
|
307
|
-
const a = { lng: s
|
|
303
|
+
for (const r of t)
|
|
304
|
+
for (let s = 0; s < r.length - 1; s++) {
|
|
305
|
+
const c = { lng: r[s][0], lat: r[s][1] };
|
|
306
|
+
s === 0 && o && (i += this.calculateDistance(o, c, !0, e, n));
|
|
307
|
+
const a = { lng: r[s + 1][0], lat: r[s + 1][1] };
|
|
308
308
|
i += this.calculateDistance(c, a, !0, e, n), o = a;
|
|
309
309
|
}
|
|
310
310
|
return d.roundPrecision(i, e);
|
|
@@ -318,10 +318,10 @@ class v {
|
|
|
318
318
|
* @param rhumb
|
|
319
319
|
*/
|
|
320
320
|
static calculateCoordinate(t, e, n, i = "nauticalmiles", o = !0) {
|
|
321
|
-
const
|
|
322
|
-
let
|
|
323
|
-
o ?
|
|
324
|
-
const c =
|
|
321
|
+
const r = f.point([t.lng, t.lat]);
|
|
322
|
+
let s;
|
|
323
|
+
o ? s = f.rhumbDestination(r, n, e, { units: i }) : s = f.destination(r, n, e, { units: i });
|
|
324
|
+
const c = s.geometry.coordinates;
|
|
325
325
|
return { lng: d.convertToStdLng(c[0], 8), lat: d.roundPrecision(c[1], 8) };
|
|
326
326
|
}
|
|
327
327
|
/**
|
|
@@ -333,13 +333,13 @@ class v {
|
|
|
333
333
|
* @param includeTail true 包含终点 to
|
|
334
334
|
* @param units 单位,默认 nm(海里)
|
|
335
335
|
*/
|
|
336
|
-
static interpolateCoordinates(t, e, n, i = !0, o = !0,
|
|
337
|
-
const
|
|
338
|
-
i &&
|
|
336
|
+
static interpolateCoordinates(t, e, n, i = !0, o = !0, r = "nauticalmiles") {
|
|
337
|
+
const s = [], c = this.calculateBearing(t, e, !1), a = this.calculateDistance(t, e, !1, 8, r);
|
|
338
|
+
i && s.push({ lng: t.lng, lat: t.lat });
|
|
339
339
|
let u = 0;
|
|
340
340
|
for (; u < a; )
|
|
341
|
-
u += n, u < a &&
|
|
342
|
-
return o &&
|
|
341
|
+
u += n, u < a && s.push(this.calculateCoordinate(t, c, u, r, !1));
|
|
342
|
+
return o && s.push({ lng: e.lng, lat: e.lat }), s;
|
|
343
343
|
}
|
|
344
344
|
/**
|
|
345
345
|
* 分组坐标(如相邻两个坐标经度差超180度,需以180为界将坐标分为两组)
|
|
@@ -359,14 +359,14 @@ class v {
|
|
|
359
359
|
t = n ? this.deduplicateCoordinates(t) : t;
|
|
360
360
|
let i = [];
|
|
361
361
|
const o = [];
|
|
362
|
-
let
|
|
362
|
+
let r, s;
|
|
363
363
|
for (let c = 0; c < t.length - 1; c++) {
|
|
364
|
-
|
|
365
|
-
const a =
|
|
364
|
+
r = d.convertToStdLng(t[c].lng, 8), s = d.convertToStdLng(t[c + 1].lng, 8), t[c].lat = d.roundPrecision(t[c].lat, 8), t[c + 1].lat = d.roundPrecision(t[c + 1].lat, 8), i.push([r, t[c].lat]);
|
|
365
|
+
const a = r - s;
|
|
366
366
|
if (Math.abs(a) > 180) {
|
|
367
367
|
const u = d.convertToMonotonicLng2([
|
|
368
|
-
[
|
|
369
|
-
[
|
|
368
|
+
[r, t[c].lat],
|
|
369
|
+
[s, t[c + 1].lat]
|
|
370
370
|
]);
|
|
371
371
|
let l, g;
|
|
372
372
|
e ? (l = f.lineString(u), g = f.lineString([
|
|
@@ -382,7 +382,7 @@ class v {
|
|
|
382
382
|
p = t[c].lat;
|
|
383
383
|
a > 0 ? (i.push([180 - 1e-6, p]), o.push([...i]), i = [], i.push([-(180 - 1e-6), p])) : (i.push([-(180 - 1e-6), p]), o.push([...i]), i = [], i.push([180 - 1e-6, p]));
|
|
384
384
|
}
|
|
385
|
-
c === t.length - 2 && i.push([
|
|
385
|
+
c === t.length - 2 && i.push([s, t[c + 1].lat]);
|
|
386
386
|
}
|
|
387
387
|
return o.push(i), o;
|
|
388
388
|
}
|
|
@@ -393,7 +393,7 @@ class v {
|
|
|
393
393
|
static deduplicateRoute(t) {
|
|
394
394
|
const e = [];
|
|
395
395
|
for (const n of t) {
|
|
396
|
-
const i = n.reduce((o,
|
|
396
|
+
const i = n.reduce((o, r) => (o.findIndex((s) => s[0] === r[0] && s[1] === r[1]) === -1 && o.push(r), o), []);
|
|
397
397
|
e.push(i);
|
|
398
398
|
}
|
|
399
399
|
return e;
|
|
@@ -441,13 +441,13 @@ class v {
|
|
|
441
441
|
*/
|
|
442
442
|
static mergeCoordinateToRoute(t, e) {
|
|
443
443
|
t.lng = d.convertToStdLng(t.lng, 8);
|
|
444
|
-
let n = Number.MAX_VALUE, i = 0, o = 0,
|
|
444
|
+
let n = Number.MAX_VALUE, i = 0, o = 0, r, s;
|
|
445
445
|
return e.forEach((c, a) => {
|
|
446
446
|
for (let u = 0; u < c.length - 1; u++) {
|
|
447
447
|
const l = { lng: c[u][0], lat: c[u][1] }, g = { lng: c[u + 1][0], lat: c[u + 1][1] }, h = this.calculatePointToLineDistance(t, l, g);
|
|
448
|
-
n > h && (n = h, o = u, i = a,
|
|
448
|
+
n > h && (n = h, o = u, i = a, r = this.calculateDistance(l, t), s = this.calculateDistance(g, t));
|
|
449
449
|
}
|
|
450
|
-
}),
|
|
450
|
+
}), r !== 0 && s !== 0 ? e[i].splice(o + 1, 0, [t.lng, t.lat]) : r === 0 ? e[i].splice(o, 1, [t.lng, t.lat]) : s === 0 && e[i].splice(o + 1, 1, [t.lng, t.lat]), e;
|
|
451
451
|
}
|
|
452
452
|
/**
|
|
453
453
|
* 向Route尾加1个坐标
|
|
@@ -489,18 +489,18 @@ class v {
|
|
|
489
489
|
n = this.mergeWaypointsToRoute([t, e], n);
|
|
490
490
|
const i = [];
|
|
491
491
|
let o = 0;
|
|
492
|
-
return n.forEach((
|
|
492
|
+
return n.forEach((r) => {
|
|
493
493
|
if (o === 2)
|
|
494
494
|
return;
|
|
495
|
-
const
|
|
496
|
-
for (const c of
|
|
495
|
+
const s = [];
|
|
496
|
+
for (const c of r) {
|
|
497
497
|
if (d.roundPrecision(e.lng, 8) === d.roundPrecision(c[0], 8) && d.roundPrecision(e.lat, 8) === d.roundPrecision(c[1], 8)) {
|
|
498
|
-
|
|
498
|
+
s.push(c), o === 0 && s.push([t.lng, t.lat]), o = 2;
|
|
499
499
|
break;
|
|
500
500
|
}
|
|
501
|
-
o === 1 ?
|
|
501
|
+
o === 1 ? s.push(c) : d.roundPrecision(t.lng, 8) === d.roundPrecision(c[0], 8) && d.roundPrecision(t.lat, 8) === d.roundPrecision(c[1], 8) && (o = 1, s.push(c));
|
|
502
502
|
}
|
|
503
|
-
|
|
503
|
+
s.length && i.push(s);
|
|
504
504
|
}), i;
|
|
505
505
|
}
|
|
506
506
|
/**
|
|
@@ -512,12 +512,12 @@ class v {
|
|
|
512
512
|
* @return [{lng, lat}]
|
|
513
513
|
*/
|
|
514
514
|
static calculateRangeWaypoints(t, e, n, i = []) {
|
|
515
|
-
const o = this.convertRouteToCoordinates(n, 0),
|
|
515
|
+
const o = this.convertRouteToCoordinates(n, 0), r = this.mergeCoordinatesToWaypoints([t, e], o.length ? o : i), s = r.findIndex(
|
|
516
516
|
(u) => d.roundPrecision(t.lng, 8) === d.roundPrecision(u.lng, 8) && d.roundPrecision(t.lat, 8) === d.roundPrecision(u.lat, 8)
|
|
517
|
-
), c =
|
|
517
|
+
), c = r.findIndex(
|
|
518
518
|
(u) => d.roundPrecision(e.lng, 8) === d.roundPrecision(u.lng, 8) && d.roundPrecision(e.lat, 8) === d.roundPrecision(u.lat, 8)
|
|
519
519
|
);
|
|
520
|
-
return
|
|
520
|
+
return r.filter((u, l) => l >= s && l <= c);
|
|
521
521
|
}
|
|
522
522
|
/**
|
|
523
523
|
* 计算坐标到航路上的最短距离
|
|
@@ -526,10 +526,10 @@ class v {
|
|
|
526
526
|
*/
|
|
527
527
|
static calculateMinDistanceToRoute(t, e) {
|
|
528
528
|
let n = Number.MAX_VALUE, i = 0, o = 0;
|
|
529
|
-
return e.forEach((
|
|
530
|
-
for (let c = 0; c <
|
|
531
|
-
const a = { lng:
|
|
532
|
-
n > l && (n = l, i = c, o =
|
|
529
|
+
return e.forEach((r, s) => {
|
|
530
|
+
for (let c = 0; c < r.length - 1; c++) {
|
|
531
|
+
const a = { lng: r[c][0], lat: r[c][1] }, u = { lng: r[c + 1][0], lat: r[c + 1][1] }, l = this.calculatePointToLineDistance(t, a, u);
|
|
532
|
+
n > l && (n = l, i = c, o = s);
|
|
533
533
|
}
|
|
534
534
|
}), { minDist: n, segIndex: o, minIndex: i };
|
|
535
535
|
}
|
|
@@ -544,18 +544,18 @@ class v {
|
|
|
544
544
|
v.mergeCoordinateToWaypoints(t, n, !0), e = v.divideAccordingToLng(n);
|
|
545
545
|
const { segIndex: i, minIndex: o } = this.calculateMinDistanceToRoute({ ...t }, e);
|
|
546
546
|
t.lng = d.convertToStdLng(t.lng);
|
|
547
|
-
const
|
|
548
|
-
let
|
|
547
|
+
const r = [];
|
|
548
|
+
let s = !0;
|
|
549
549
|
for (let c = i; c < e.length; c++)
|
|
550
|
-
if (
|
|
550
|
+
if (s) {
|
|
551
551
|
const a = [];
|
|
552
552
|
a.push([t.lng, t.lat]);
|
|
553
553
|
for (let u = o + 1; u < e[c].length; u++)
|
|
554
554
|
t.lng === e[c][u][0] && t.lat === e[c][u][1] || a.push(e[c][u]);
|
|
555
|
-
|
|
555
|
+
r.push(a), s = !1;
|
|
556
556
|
} else
|
|
557
|
-
|
|
558
|
-
return
|
|
557
|
+
r.push([...e[c]]);
|
|
558
|
+
return r;
|
|
559
559
|
}
|
|
560
560
|
/**
|
|
561
561
|
* 计算子途经点
|
|
@@ -565,19 +565,19 @@ class v {
|
|
|
565
565
|
*/
|
|
566
566
|
static calculateSubWaypoints(t, e) {
|
|
567
567
|
let n = Number.MAX_VALUE, i = 0;
|
|
568
|
-
for (let
|
|
569
|
-
const
|
|
570
|
-
if (this.calculateDistance(t,
|
|
568
|
+
for (let r = 0; r < e.length - 1; r++) {
|
|
569
|
+
const s = e[r], c = e[r + 1];
|
|
570
|
+
if (this.calculateDistance(t, s) === 0)
|
|
571
571
|
return e;
|
|
572
572
|
if (this.calculateDistance(t, c) === 0)
|
|
573
573
|
return e.filter((u, l) => l > 0);
|
|
574
|
-
const a = this.calculatePointToLineDistance(t,
|
|
575
|
-
n > a && (n = a, i =
|
|
574
|
+
const a = this.calculatePointToLineDistance(t, s, c);
|
|
575
|
+
n > a && (n = a, i = r);
|
|
576
576
|
}
|
|
577
577
|
t.lng = d.convertToStdLng(t.lng);
|
|
578
578
|
const o = [t];
|
|
579
|
-
for (let
|
|
580
|
-
o.push(e[
|
|
579
|
+
for (let r = i + 1; r < e.length; r++)
|
|
580
|
+
o.push(e[r]);
|
|
581
581
|
return o;
|
|
582
582
|
}
|
|
583
583
|
/**
|
|
@@ -591,11 +591,11 @@ class v {
|
|
|
591
591
|
t.lng = d.convertToStdLng(t.lng, 8), e = { ...e }, n = { ...n }, e.lng = d.convertToStdLng(e.lng, 8), n.lng = d.convertToStdLng(n.lng, 8);
|
|
592
592
|
const o = d.convertToMonotonicLng([e, n]);
|
|
593
593
|
e = o[0], n = o[1];
|
|
594
|
-
const
|
|
594
|
+
const r = f.lineString([
|
|
595
595
|
[e.lng, e.lat],
|
|
596
596
|
[n.lng, n.lat]
|
|
597
|
-
]),
|
|
598
|
-
return d.roundPrecision(Math.min(
|
|
597
|
+
]), s = f.pointToLineDistance(f.point([t.lng, t.lat]), r, i), c = f.pointToLineDistance(f.point([t.lng > 0 ? t.lng - 360 : t.lng + 360, t.lat]), r, i);
|
|
598
|
+
return d.roundPrecision(Math.min(s, c), 6);
|
|
599
599
|
}
|
|
600
600
|
/**
|
|
601
601
|
* 计算途经点的COG, Distance等属性
|
|
@@ -605,8 +605,8 @@ class v {
|
|
|
605
605
|
static calculateWaypointsPropInRoute(t, e) {
|
|
606
606
|
e = this.mergeWaypointsToRoute(t, e);
|
|
607
607
|
for (let n = 0; n < t.length - 1; n++) {
|
|
608
|
-
const i = t[n], o = t[n + 1],
|
|
609
|
-
n === 0 && (i.distanceFromPrevious = 0, i.distanceFromStart = 0), o.distanceFromPrevious = this.calculateRouteDistance(
|
|
608
|
+
const i = t[n], o = t[n + 1], r = this.calculateRangeRoute(i, o, e);
|
|
609
|
+
n === 0 && (i.distanceFromPrevious = 0, i.distanceFromStart = 0), o.distanceFromPrevious = this.calculateRouteDistance(r), o.distanceFromStart = d.roundPrecision((i.distanceFromStart || 0) + o.distanceFromPrevious);
|
|
610
610
|
}
|
|
611
611
|
return t;
|
|
612
612
|
}
|
|
@@ -634,15 +634,15 @@ class v {
|
|
|
634
634
|
*/
|
|
635
635
|
static mergeCoordinateToWaypoints(t, e, n = !0) {
|
|
636
636
|
t.lng = d.convertToStdLng(t.lng, 8);
|
|
637
|
-
let i = Number.MAX_VALUE, o = 0,
|
|
637
|
+
let i = Number.MAX_VALUE, o = 0, r = 0, s = 0;
|
|
638
638
|
if (e.length < 2)
|
|
639
639
|
e.push(t);
|
|
640
640
|
else {
|
|
641
641
|
for (let c = 0; c < e.length - 1; c++) {
|
|
642
642
|
const a = { lng: e[c].lng, lat: e[c].lat }, u = { lng: e[c + 1].lng, lat: e[c + 1].lat }, l = this.calculatePointToLineDistance(t, a, u);
|
|
643
|
-
i >= l && (i = l, o = c,
|
|
643
|
+
i >= l && (i = l, o = c, r = this.calculateDistance(a, t, !1, 6), s = this.calculateDistance(u, t, !1, 6));
|
|
644
644
|
}
|
|
645
|
-
|
|
645
|
+
r !== 0 && s !== 0 ? r <= i && o === 0 ? e.unshift(t) : s <= i && o === e.length - 2 ? e.push(t) : e.splice(o + 1, 0, t) : r === 0 ? n ? e.splice(o, 1, t) : e.splice(o + 1, 0, t) : s === 0 && (n ? e.splice(o + 1, 1, t) : e.splice(o + 1, 0, t));
|
|
646
646
|
}
|
|
647
647
|
return e.map((c, a) => {
|
|
648
648
|
c.lng = d.convertToStdLng(c.lng);
|
|
@@ -664,12 +664,12 @@ class v {
|
|
|
664
664
|
static generateRouteAccordingToWaypoints(t, e = !0, n = !0) {
|
|
665
665
|
const i = [];
|
|
666
666
|
for (let o = 1; o < t.length; o++) {
|
|
667
|
-
const
|
|
668
|
-
if (o === 1 && i.push(
|
|
669
|
-
const c = this.interpolateCoordinates(
|
|
667
|
+
const r = t[o - 1], s = t[o];
|
|
668
|
+
if (o === 1 && i.push(r), s.gcToPrevious) {
|
|
669
|
+
const c = this.interpolateCoordinates(r, s, 200, !1, !0, "nauticalmiles");
|
|
670
670
|
i.push(...c);
|
|
671
671
|
} else
|
|
672
|
-
i.push(
|
|
672
|
+
i.push(s);
|
|
673
673
|
}
|
|
674
674
|
return this.divideAccordingToLng(i, e, n);
|
|
675
675
|
}
|
|
@@ -679,7 +679,7 @@ class v {
|
|
|
679
679
|
* @param route [[[lng, lat]]]
|
|
680
680
|
*/
|
|
681
681
|
static nearestCoordinateInRoute(t, e) {
|
|
682
|
-
const n = f.point([t.lng, t.lat]), o = this.convertRouteToCoordinates(e).map((a) => [a.lng, a.lat]),
|
|
682
|
+
const n = f.point([t.lng, t.lat]), o = this.convertRouteToCoordinates(e).map((a) => [a.lng, a.lat]), r = f.lineString(o), s = f.nearestPointOnLine(r, n), c = f.getCoord(s);
|
|
683
683
|
return { lng: d.roundPrecision(c[0], 8), lat: d.roundPrecision(c[1], 8) };
|
|
684
684
|
}
|
|
685
685
|
/**
|
|
@@ -691,12 +691,12 @@ class v {
|
|
|
691
691
|
let n = 0;
|
|
692
692
|
this.mergeCoordinateToWaypoints(t, e);
|
|
693
693
|
for (let i = 0; i < e.length - 1; i++) {
|
|
694
|
-
const o = e[i],
|
|
694
|
+
const o = e[i], r = e[i + 1];
|
|
695
695
|
if (this.calculateDistance(t, o) === 0) {
|
|
696
696
|
n = i;
|
|
697
697
|
break;
|
|
698
698
|
}
|
|
699
|
-
if (this.calculateDistance(t,
|
|
699
|
+
if (this.calculateDistance(t, r) === 0) {
|
|
700
700
|
n = i + 1;
|
|
701
701
|
break;
|
|
702
702
|
}
|
|
@@ -713,22 +713,22 @@ class v {
|
|
|
713
713
|
*/
|
|
714
714
|
static calculateNextCoordinateAlongRoute(t, e, n, i = "nauticalmiles") {
|
|
715
715
|
var g;
|
|
716
|
-
const o = t.speed || 12,
|
|
717
|
-
let
|
|
718
|
-
if (e && n.length ? (
|
|
716
|
+
const o = t.speed || 12, r = [];
|
|
717
|
+
let s = [], c = !1, a = 0, u = 0, l;
|
|
718
|
+
if (e && n.length ? (r.push(t), n.forEach((h, p) => {
|
|
719
719
|
if (c)
|
|
720
|
-
|
|
720
|
+
s.push(h);
|
|
721
721
|
else {
|
|
722
722
|
const T = [];
|
|
723
723
|
let m;
|
|
724
|
-
for (let
|
|
724
|
+
for (let y = 0; y < h.length; y++)
|
|
725
725
|
if (l)
|
|
726
|
-
T.push(h[
|
|
726
|
+
T.push(h[y]);
|
|
727
727
|
else {
|
|
728
|
-
m = { lng: h[
|
|
728
|
+
m = { lng: h[y][0], lat: h[y][1] };
|
|
729
729
|
const P = this.calculateDistance(t, m, !0, 8, i);
|
|
730
730
|
if (a += P, a < e)
|
|
731
|
-
u += P, P &&
|
|
731
|
+
u += P, P && r.push(m), t = m;
|
|
732
732
|
else {
|
|
733
733
|
if (u = e, a === e)
|
|
734
734
|
l = m, T.push([l.lng, l.lat]);
|
|
@@ -739,15 +739,15 @@ class v {
|
|
|
739
739
|
c = !0;
|
|
740
740
|
}
|
|
741
741
|
}
|
|
742
|
-
T.length &&
|
|
742
|
+
T.length && s.push(T), p === n.length - 1 && !l && (l = m);
|
|
743
743
|
}
|
|
744
|
-
})) : (
|
|
745
|
-
if (
|
|
746
|
-
const h = { lng:
|
|
744
|
+
})) : (s = n, l = { ...t }), l)
|
|
745
|
+
if (r.push(l), l.distanceFromPrevious = Math.round(u * 1e4) / 1e4, l.hourFromPrevious = Math.round(u / o * 1e4) / 1e4, ((g = s[0]) == null ? void 0 : g.length) > 1) {
|
|
746
|
+
const h = { lng: s[0][1][0], lat: s[0][1][1] };
|
|
747
747
|
l.bearing = this.calculateBearing(l, h);
|
|
748
748
|
} else
|
|
749
749
|
l.bearing = 0;
|
|
750
|
-
return { coordinate: l, nextRoute:
|
|
750
|
+
return { coordinate: l, nextRoute: s, prevRoute: r };
|
|
751
751
|
}
|
|
752
752
|
/**
|
|
753
753
|
* 返回最近点及其是否为垂足(最近点不是起点或终点)
|
|
@@ -756,11 +756,11 @@ class v {
|
|
|
756
756
|
* @param to {lng, lat}
|
|
757
757
|
*/
|
|
758
758
|
static nearestCoordinateInLine(t, e, n) {
|
|
759
|
-
const i = d.convertToStdLng(t.lng, 6), o = f.point([i, t.lat]),
|
|
760
|
-
[
|
|
761
|
-
[
|
|
759
|
+
const i = d.convertToStdLng(t.lng, 6), o = f.point([i, t.lat]), r = d.convertToStdLng(e.lng, 6), s = d.convertToStdLng(n.lng, 6), c = f.lineString([
|
|
760
|
+
[r, e.lat],
|
|
761
|
+
[s, n.lat]
|
|
762
762
|
]), a = f.nearestPointOnLine(c, o), u = f.getCoord(a), l = d.roundPrecision(u[0], 6), g = d.roundPrecision(u[1], 6);
|
|
763
|
-
return { lng: l, lat: g, inline: !(l ===
|
|
763
|
+
return { lng: l, lat: g, inline: !(l === r && g === e.lat) && !(l === s && g === n.lat) };
|
|
764
764
|
}
|
|
765
765
|
/**
|
|
766
766
|
* 将route转coordinate
|
|
@@ -770,9 +770,9 @@ class v {
|
|
|
770
770
|
static convertRouteToCoordinates(t, e = 0) {
|
|
771
771
|
const n = [];
|
|
772
772
|
let i, o;
|
|
773
|
-
return t.forEach((
|
|
774
|
-
|
|
775
|
-
const c = { lng: d.roundPrecision(
|
|
773
|
+
return t.forEach((r) => {
|
|
774
|
+
r.forEach((s) => {
|
|
775
|
+
const c = { lng: d.roundPrecision(s[0], 8), lat: d.roundPrecision(s[1], 8) };
|
|
776
776
|
if (!o)
|
|
777
777
|
n.push(c), o = c;
|
|
778
778
|
else if (o.bearing === void 0 || o.bearing === null)
|
|
@@ -805,17 +805,17 @@ class v {
|
|
|
805
805
|
this.mergeCoordinateToWaypoints(i, t, !0);
|
|
806
806
|
});
|
|
807
807
|
for (let i = 1; i < e.length; i++) {
|
|
808
|
-
const o = e[i - 1],
|
|
809
|
-
if (
|
|
810
|
-
const
|
|
811
|
-
for (let a = c - 1; a >
|
|
808
|
+
const o = e[i - 1], r = e[i];
|
|
809
|
+
if (r.gcToPrevious) {
|
|
810
|
+
const s = t.findIndex((a) => a.lng === o.lng && a.lat === o.lat), c = t.findIndex((a) => a.lng === r.lng && a.lat === r.lat);
|
|
811
|
+
for (let a = c - 1; a > s; a--)
|
|
812
812
|
t.splice(a, 1);
|
|
813
813
|
}
|
|
814
814
|
}
|
|
815
815
|
let n = 0;
|
|
816
816
|
for (let i = 1; i < t.length; i++) {
|
|
817
|
-
const o = t[i - 1],
|
|
818
|
-
|
|
817
|
+
const o = t[i - 1], r = t[i];
|
|
818
|
+
r.gcToPrevious ? (o.bearing = this.calculateBearing(o, r, !1), r.distanceFromPrevious = this.calculateDistance(o, r, !1)) : (o.bearing = this.calculateBearing(o, r, !0), r.distanceFromPrevious = this.calculateDistance(o, r, !0)), n = d.roundPrecision(n + r.distanceFromPrevious), r.distanceFromStart = n;
|
|
819
819
|
}
|
|
820
820
|
return t.map((i) => (i.lng = d.convertToStdLng(i.lng), i));
|
|
821
821
|
}
|
|
@@ -825,14 +825,14 @@ class v {
|
|
|
825
825
|
*/
|
|
826
826
|
static calculateCenter(t) {
|
|
827
827
|
const e = [];
|
|
828
|
-
for (const
|
|
829
|
-
for (const c of
|
|
828
|
+
for (const s of t)
|
|
829
|
+
for (const c of s)
|
|
830
830
|
e.push(c);
|
|
831
831
|
const n = f.featureCollection([]), i = d.convertToMonotonicLng2(e);
|
|
832
|
-
for (const
|
|
833
|
-
n.features.push(f.point(
|
|
834
|
-
const
|
|
835
|
-
return { lng: d.convertToStdLng(
|
|
832
|
+
for (const s of i)
|
|
833
|
+
n.features.push(f.point(s));
|
|
834
|
+
const r = f.center(n).geometry.coordinates;
|
|
835
|
+
return { lng: d.convertToStdLng(r[0], 8), lat: d.roundPrecision(r[1], 8) };
|
|
836
836
|
}
|
|
837
837
|
/**
|
|
838
838
|
* 计算中心点
|
|
@@ -849,8 +849,8 @@ class v {
|
|
|
849
849
|
static calculateBBox(t) {
|
|
850
850
|
const e = [];
|
|
851
851
|
for (const o of t)
|
|
852
|
-
for (const
|
|
853
|
-
e.push(
|
|
852
|
+
for (const r of o)
|
|
853
|
+
e.push(r);
|
|
854
854
|
const n = d.convertToMonotonicLng2(e), i = f.lineString(n);
|
|
855
855
|
return f.bbox(i);
|
|
856
856
|
}
|
|
@@ -871,11 +871,11 @@ class v {
|
|
|
871
871
|
static simplifyCoordinates(t, e = 1, n = 180) {
|
|
872
872
|
const i = [];
|
|
873
873
|
for (let o = 1; o < t.length; o++) {
|
|
874
|
-
const
|
|
874
|
+
const r = t[o - 1], s = t[o], c = t[o + 1];
|
|
875
875
|
let a = !1, u = !1;
|
|
876
|
-
if ((
|
|
877
|
-
const l = v.calculateDistance(
|
|
878
|
-
Math.round(Math.acos(p) * 180 / Math.PI) < n && h > e && !u && (i.push(
|
|
876
|
+
if ((r.velocity || r.suspend || r.important || r.pilot || o === 1) && (a = !0, i.push(r)), s.gcToPrevious && (a || (a = !0, i.push(r)), u = !0, i.push(s), o++), c) {
|
|
877
|
+
const l = v.calculateDistance(r, s, !0), g = v.calculateDistance(s, c, !0), h = v.calculateDistance(r, c, !0), p = (Math.pow(l, 2) + Math.pow(g, 2) - Math.pow(h, 2)) / (2 * l * g);
|
|
878
|
+
Math.round(Math.acos(p) * 180 / Math.PI) < n && h > e && !u && (i.push(s), o++);
|
|
879
879
|
}
|
|
880
880
|
if (o >= t.length - 1) {
|
|
881
881
|
const l = t.at(-1);
|
|
@@ -891,10 +891,10 @@ class v {
|
|
|
891
891
|
* @param waypoints 带时间的轨迹, 单位秒
|
|
892
892
|
*/
|
|
893
893
|
static nearestTSPointInWaypoints(t, e, n) {
|
|
894
|
-
const i =
|
|
895
|
-
(
|
|
894
|
+
const i = b.unix(t), o = n.filter(
|
|
895
|
+
(r) => i.clone().subtract(e, "hour").unix() <= (r.positionTime || 0) && i.clone().add(e, "h").unix() >= (r.positionTime || 0)
|
|
896
896
|
);
|
|
897
|
-
return o.sort((
|
|
897
|
+
return o.sort((r, s) => (r.positionTime || 0) - (s.positionTime || 0)), o.at(-1);
|
|
898
898
|
}
|
|
899
899
|
/**
|
|
900
900
|
* 推测船位
|
|
@@ -902,17 +902,17 @@ class v {
|
|
|
902
902
|
* @param positions 带时间(positionTime)的轨迹
|
|
903
903
|
*/
|
|
904
904
|
static deadReckoning(t, e) {
|
|
905
|
-
var o,
|
|
905
|
+
var o, r, s, c;
|
|
906
906
|
t > 1e12 && (t = Math.round(t / 1e3));
|
|
907
|
-
const n =
|
|
907
|
+
const n = b.unix(t);
|
|
908
908
|
let i = e.find((a) => a.positionTime === n.unix());
|
|
909
909
|
if (!i) {
|
|
910
|
-
const a = (
|
|
910
|
+
const a = (r = (o = e.filter((l) => (l == null ? void 0 : l.positionTime) < n.unix())) == null ? void 0 : o.sort((l, g) => (l.positionTime || 0) - (g.positionTime || 0))) == null ? void 0 : r.at(-1), u = (c = (s = e.filter((l) => (l == null ? void 0 : l.positionTime) > n.unix())) == null ? void 0 : s.sort((l, g) => (l.positionTime || 0) - (g.positionTime || 0))) == null ? void 0 : c.at(0);
|
|
911
911
|
if (a && u) {
|
|
912
912
|
const l = v.calculateBearing(a, u, !0), g = v.calculateDistance(a, u), h = (n.unix() - a.positionTime) / (u.positionTime - a.positionTime);
|
|
913
913
|
i = v.calculateCoordinate(a, l, g * h), i.positionTime = n.unix(), i.utc = n.utc().format(), i.cog = l, i.sog = Math.round(g / ((u.positionTime - a.positionTime) / 3600) * 100) / 100;
|
|
914
914
|
} else
|
|
915
|
-
i = a || u, i && (i.utc =
|
|
915
|
+
i = a || u, i && (i.utc = b.unix(i == null ? void 0 : i.positionTime).utc().format());
|
|
916
916
|
}
|
|
917
917
|
return i;
|
|
918
918
|
}
|
|
@@ -928,16 +928,16 @@ class v {
|
|
|
928
928
|
const u = e[a], l = e[a + 1], g = v.calculatePointToLineDistance(t, u, l);
|
|
929
929
|
g < n && (n = g, i = a);
|
|
930
930
|
}
|
|
931
|
-
const o = e[i],
|
|
932
|
-
if (
|
|
931
|
+
const o = e[i], r = e[i + 1], s = v.calculateDistance(o, t), c = v.calculateDistance(r, t);
|
|
932
|
+
if (s === 0)
|
|
933
933
|
t = o;
|
|
934
934
|
else if (c === 0)
|
|
935
|
-
t =
|
|
935
|
+
t = r;
|
|
936
936
|
else {
|
|
937
|
-
const a = o.positionTime || 0, u =
|
|
938
|
-
t.positionTime = Math.round(a + (u - a) * (
|
|
937
|
+
const a = o.positionTime || 0, u = r.positionTime || 0, l = v.calculateDistance(o, r);
|
|
938
|
+
t.positionTime = Math.round(a + (u - a) * (s / l));
|
|
939
939
|
}
|
|
940
|
-
return t.utc = t.positionTime ?
|
|
940
|
+
return t.utc = t.positionTime ? b.unix(t.positionTime).utc().format() : void 0, t.positionTime ? t : void 0;
|
|
941
941
|
}
|
|
942
942
|
/**
|
|
943
943
|
* 翻转轨迹
|
|
@@ -991,21 +991,21 @@ class v {
|
|
|
991
991
|
const i = [];
|
|
992
992
|
i.push(" <waypoints>");
|
|
993
993
|
for (let o = 0; o < t.length; o++) {
|
|
994
|
-
const
|
|
995
|
-
if (
|
|
996
|
-
const l =
|
|
994
|
+
const r = t[o], s = o + 1, c = (r.lat ?? "").toFixed ? r.lat.toFixed(e).padEnd(e + 2, "0") : r.lat, a = (r.lng ?? "").toFixed ? r.lng.toFixed(e).padEnd(e + 2, "0") : r.lng, u = [`id="${s}"`, 'revision="0"'];
|
|
995
|
+
if (r.name && u.push(`name="${v.xmlEscape(r.name)}"`), i.push(` <waypoint ${u.join(" ")}>`), i.push(` <position lat="${v.xmlEscape(c)}" lon="${v.xmlEscape(a)}" />`), o > 0) {
|
|
996
|
+
const l = r.gcToPrevious ? "Orthodrome" : "Loxodrome";
|
|
997
997
|
i.push(` <leg geometryType="${l}" />`);
|
|
998
998
|
}
|
|
999
999
|
if (n) {
|
|
1000
1000
|
const l = [];
|
|
1001
|
-
if (
|
|
1002
|
-
l.push(` <time>${v.xmlEscape(
|
|
1003
|
-
else if (
|
|
1001
|
+
if (r.description && l.push(` <description>${v.xmlEscape(r.description)}</description>`), r.utc)
|
|
1002
|
+
l.push(` <time>${v.xmlEscape(r.utc)}</time>`);
|
|
1003
|
+
else if (r.positionTime)
|
|
1004
1004
|
try {
|
|
1005
|
-
l.push(` <time>${v.xmlEscape(
|
|
1005
|
+
l.push(` <time>${v.xmlEscape(b.unix(r.positionTime).utc().format())}</time>`);
|
|
1006
1006
|
} catch {
|
|
1007
1007
|
}
|
|
1008
|
-
|
|
1008
|
+
r.cog !== void 0 && l.push(` <cog>${v.xmlEscape(r.cog)}</cog>`), r.sog !== void 0 && l.push(` <sog>${v.xmlEscape(r.sog)}</sog>`), l.length && (i.push(" <extensions>"), i.push(...l), i.push(" </extensions>"));
|
|
1009
1009
|
}
|
|
1010
1010
|
i.push(" </waypoint>");
|
|
1011
1011
|
}
|
|
@@ -1020,13 +1020,13 @@ class v {
|
|
|
1020
1020
|
*/
|
|
1021
1021
|
static waypoints2CSV(t, e, n) {
|
|
1022
1022
|
I.debug("keep name for waypoints2CSV for legacy compatibility only", t);
|
|
1023
|
-
const i = (n == null ? void 0 : n.precision) ?? 6, o = e.some((m) => m.name),
|
|
1024
|
-
o && p.push("Name"),
|
|
1023
|
+
const i = (n == null ? void 0 : n.precision) ?? 6, o = e.some((m) => m.name), r = e.some((m) => m.description), s = e.some((m) => m.port != null), c = e.some((m) => m.stbd != null), a = e.some((m) => m.arrRad != null), u = e.some((m) => m.speed != null), l = e.some((m, y) => y > 0 && m.gcToPrevious != null), g = e.some((m) => m.bearing != null), h = e.some((m) => m.distanceFromPrevious != null), p = ["WPT No.", "Latitude", "Longitude"];
|
|
1024
|
+
o && p.push("Name"), r && p.push("Description"), l && p.push("Leg"), g && p.push("Bearing[deg]"), h && p.push("Distance[NM]"), u && p.push("Speed[kn]"), s && p.push("PORT XTD[NM]"), c && p.push("STBD XTD[NM]"), a && p.push("Arr.Rad[NM]");
|
|
1025
1025
|
const T = [];
|
|
1026
1026
|
T.push(p.map((m) => v.csvEscapeField(m)).join(","));
|
|
1027
1027
|
for (let m = 0; m < e.length; m++) {
|
|
1028
|
-
const
|
|
1029
|
-
P.push((m + 1).toString()), P.push(
|
|
1028
|
+
const y = e[m], P = [];
|
|
1029
|
+
P.push((m + 1).toString()), P.push(y.lat.toFixed(i)), P.push(y.lng.toFixed(i)), o && P.push(y.name ?? ""), r && P.push(y.description ?? ""), l && P.push(m === 0 ? "" : y.gcToPrevious ? "GC" : "RL"), g && P.push(y.bearing != null ? String(y.bearing) : ""), h && P.push(y.distanceFromPrevious != null ? String(y.distanceFromPrevious) : ""), u && P.push(y.speed != null ? String(y.speed) : ""), s && P.push(y.port != null ? String(y.port) : ""), c && P.push(y.stbd != null ? String(y.stbd) : ""), a && P.push(y.arrRad != null ? String(y.arrRad) : ""), T.push(P.map((M) => v.csvEscapeField(M)).join(","));
|
|
1030
1030
|
}
|
|
1031
1031
|
return T.join(`
|
|
1032
1032
|
`);
|
|
@@ -1047,8 +1047,8 @@ class v {
|
|
|
1047
1047
|
* @param isLat true为纬度,false为经度
|
|
1048
1048
|
*/
|
|
1049
1049
|
static decimalToNmeaDm(t, e) {
|
|
1050
|
-
const n = Math.abs(t), i = Math.floor(n), o = (n - i) * 60,
|
|
1051
|
-
return { dm:
|
|
1050
|
+
const n = Math.abs(t), i = Math.floor(n), o = (n - i) * 60, r = e ? `${i.toString().padStart(2, "0")}${o.toFixed(2).padStart(5, "0")}` : `${i.toString().padStart(3, "0")}${o.toFixed(2).padStart(5, "0")}`, s = e ? t >= 0 ? "N" : "S" : t >= 0 ? "E" : "W";
|
|
1051
|
+
return { dm: r, dir: s };
|
|
1052
1052
|
}
|
|
1053
1053
|
/**
|
|
1054
1054
|
* 计算NMEA 0183校验和 ($与*之间所有字符的异或,两字符十六进制大写)
|
|
@@ -1068,7 +1068,7 @@ class v {
|
|
|
1068
1068
|
static waypoints2NMEA(t) {
|
|
1069
1069
|
const e = [];
|
|
1070
1070
|
for (let n = 0; n < t.length; n++) {
|
|
1071
|
-
const i = t[n], o = v.decimalToNmeaDm(i.lat, !0),
|
|
1071
|
+
const i = t[n], o = v.decimalToNmeaDm(i.lat, !0), r = v.decimalToNmeaDm(i.lng, !1), s = i.name ? String(i.name).slice(0, 6) : `WPT${(n + 1).toString().padStart(3, "0")}`, c = `GPWPL,${o.dm},${o.dir},${r.dm},${r.dir},${s}`, a = v.nmeaChecksum(c);
|
|
1072
1072
|
e.push(`$${c}*${a}`);
|
|
1073
1073
|
}
|
|
1074
1074
|
return e.join(`\r
|
|
@@ -1088,17 +1088,17 @@ class v {
|
|
|
1088
1088
|
*/
|
|
1089
1089
|
static coordinatesSummary(t, e = 3) {
|
|
1090
1090
|
if (t.length > 1) {
|
|
1091
|
-
const n = t[0], i = t[t.length - 1], o = (n == null ? void 0 : n.positionTime) < (i == null ? void 0 : i.positionTime) ?
|
|
1091
|
+
const n = t[0], i = t[t.length - 1], o = (n == null ? void 0 : n.positionTime) < (i == null ? void 0 : i.positionTime) ? b.unix(n == null ? void 0 : n.positionTime) : b.unix(i == null ? void 0 : i.positionTime), r = (n == null ? void 0 : n.positionTime) > (i == null ? void 0 : i.positionTime) ? b.unix(n == null ? void 0 : n.positionTime) : b.unix(i == null ? void 0 : i.positionTime), s = Math.round(r.diff(o, "hours", !0) * 100) / 100, c = this.generateRouteAccordingToWaypoints(t, !0, !0), a = this.calculateRouteDistance(c), l = W.inspectStoppages(t, e).reduce(
|
|
1092
1092
|
(h, p) => (h.duration += p.duration, h.distance += p.distance, h),
|
|
1093
1093
|
{ hours: 0, distance: 0, spd: 0, duration: 0 }
|
|
1094
1094
|
);
|
|
1095
1095
|
l.hours = Math.round(l.duration / 3600 * 100) / 100, l.distance = Math.round(l.distance * 100) / 100, l.spd = l.hours ? Math.round(l.distance / l.hours * 100) / 100 : 0;
|
|
1096
|
-
const g =
|
|
1096
|
+
const g = s ? Math.round((a - l.distance) / (s - l.hours) * 100) / 100 : 0;
|
|
1097
1097
|
return {
|
|
1098
1098
|
begin: o.utc().format(),
|
|
1099
|
-
end:
|
|
1099
|
+
end: r.utc().format(),
|
|
1100
1100
|
distance: Math.round((a - l.distance) * 100) / 100,
|
|
1101
|
-
hours: Math.round((
|
|
1101
|
+
hours: Math.round((s - l.hours) * 100) / 100,
|
|
1102
1102
|
avgSpeed: g,
|
|
1103
1103
|
stoppage: l
|
|
1104
1104
|
};
|
|
@@ -1124,30 +1124,30 @@ class v {
|
|
|
1124
1124
|
var u, l, g;
|
|
1125
1125
|
if (!((l = (u = e == null ? void 0 : e.sample) == null ? void 0 : u.hours) != null && l.length))
|
|
1126
1126
|
return { routes: [], hour: void 0 };
|
|
1127
|
-
const n = e.sample.hours.at(0), i =
|
|
1128
|
-
let
|
|
1129
|
-
if (!
|
|
1130
|
-
const h = e.sample.all.filter((N) =>
|
|
1131
|
-
|
|
1132
|
-
const { cFactor: T, cog: m, wxFactor:
|
|
1133
|
-
|
|
1134
|
-
...
|
|
1127
|
+
const n = e.sample.hours.at(0), i = b.utc(t), o = b.utc(e.eta), r = i.isAfter(o) ? o : i;
|
|
1128
|
+
let s = e.sample.all.find((h) => h.eta === r.format());
|
|
1129
|
+
if (!s) {
|
|
1130
|
+
const h = e.sample.all.filter((N) => b.utc(N.eta).isBefore(r)).at(-1), p = this.calculateSubRoute(h, e.route);
|
|
1131
|
+
s = (g = this.calculateNextCoordinateAlongRoute(h, h.speed * r.diff(b(h.etd), "hours", !0), p)) == null ? void 0 : g.coordinate;
|
|
1132
|
+
const { cFactor: T, cog: m, wxFactor: y, meteo: P } = h, M = Math.round(s.distanceFromPrevious * 1e4) / 1e4, S = Math.round((M + h.distanceFromStart) * 1e4) / 1e4;
|
|
1133
|
+
s = {
|
|
1134
|
+
...s,
|
|
1135
1135
|
cFactor: T,
|
|
1136
1136
|
cog: m,
|
|
1137
1137
|
speed: h.speed,
|
|
1138
|
-
wxFactor:
|
|
1138
|
+
wxFactor: y,
|
|
1139
1139
|
distanceFromStart: S,
|
|
1140
1140
|
distanceFromPrevious: M,
|
|
1141
1141
|
meteo: P,
|
|
1142
|
-
eta:
|
|
1143
|
-
etd:
|
|
1142
|
+
eta: r.format(),
|
|
1143
|
+
etd: r.format()
|
|
1144
1144
|
};
|
|
1145
1145
|
}
|
|
1146
|
-
|
|
1147
|
-
const c = this.calculateRangeWaypoints(n,
|
|
1146
|
+
s.distanceToGo = Math.round((e.distance - s.distanceFromStart) * 100) / 100, s.timeToGo = Math.round(o.diff(s.etd, "hours", !0) * 100) / 100;
|
|
1147
|
+
const c = this.calculateRangeWaypoints(n, s, e.route);
|
|
1148
1148
|
return {
|
|
1149
1149
|
routes: this.generateRouteAccordingToWaypoints(c),
|
|
1150
|
-
hour:
|
|
1150
|
+
hour: s
|
|
1151
1151
|
};
|
|
1152
1152
|
}
|
|
1153
1153
|
/**
|
|
@@ -1162,10 +1162,10 @@ class v {
|
|
|
1162
1162
|
*/
|
|
1163
1163
|
static pickUTCSampleFromRoute(t, e, n) {
|
|
1164
1164
|
var h;
|
|
1165
|
-
const i = this.calculateSubRoute(e, n), o = this.calculateRouteDistance(i),
|
|
1165
|
+
const i = this.calculateSubRoute(e, n), o = this.calculateRouteDistance(i), r = o / e.speed, s = b.utc(t), c = b(e.etd), a = (h = this.calculateNextCoordinateAlongRoute(e, e.speed * s.diff(b(e.etd), "hours", !0), i)) == null ? void 0 : h.coordinate;
|
|
1166
1166
|
a.speed = e.speed;
|
|
1167
1167
|
const u = c.clone().add(a.hourFromPrevious, "hour");
|
|
1168
|
-
a.eta = Math.abs(u.diff(
|
|
1168
|
+
a.eta = Math.abs(u.diff(s, "second")) < 2 ? s.format() : u.format(), a.etd = a.eta, a.distanceFromStart = Math.round(a.distanceFromPrevious * 100) / 100, a.distanceToGo = Math.round((o - a.distanceFromStart) * 100) / 100, a.timeToGo = Math.round(c.clone().add(r, "hour").diff(b(a.etd), "hour") * 100) / 100;
|
|
1169
1169
|
const l = this.calculateRangeWaypoints(e, a, n);
|
|
1170
1170
|
return {
|
|
1171
1171
|
routes: this.generateRouteAccordingToWaypoints(l),
|
|
@@ -1185,7 +1185,7 @@ class v {
|
|
|
1185
1185
|
}
|
|
1186
1186
|
let C;
|
|
1187
1187
|
try {
|
|
1188
|
-
C =
|
|
1188
|
+
C = w.getLogger("vessel");
|
|
1189
1189
|
} catch {
|
|
1190
1190
|
} finally {
|
|
1191
1191
|
}
|
|
@@ -1197,23 +1197,23 @@ class z {
|
|
|
1197
1197
|
static convert2Geojson(t) {
|
|
1198
1198
|
var n, i, o;
|
|
1199
1199
|
const e = f.featureCollection([]);
|
|
1200
|
-
for (const
|
|
1201
|
-
const
|
|
1202
|
-
if (
|
|
1203
|
-
|
|
1204
|
-
for (const c of
|
|
1200
|
+
for (const r of t) {
|
|
1201
|
+
const s = (n = r.history) == null ? void 0 : n[0];
|
|
1202
|
+
if (r.forecasts) {
|
|
1203
|
+
s && s.wind && (s.wind.kts = s.kts);
|
|
1204
|
+
for (const c of r.forecasts) {
|
|
1205
1205
|
let a;
|
|
1206
|
-
const u = [], l = [], g =
|
|
1206
|
+
const u = [], l = [], g = b(c.date).utc(), h = `${r.name}-${c.model}`;
|
|
1207
1207
|
for (const T in c == null ? void 0 : c.hours) {
|
|
1208
1208
|
const m = c.hours[T];
|
|
1209
1209
|
a = a || m;
|
|
1210
|
-
const
|
|
1210
|
+
const y = g.clone().add(Number(T), "hour"), P = f.point([m.lng, m.lat], {
|
|
1211
1211
|
model: c.model,
|
|
1212
|
-
name:
|
|
1213
|
-
nameCn:
|
|
1214
|
-
date:
|
|
1212
|
+
name: r.name,
|
|
1213
|
+
nameCn: r.nameCn,
|
|
1214
|
+
date: y.format(),
|
|
1215
1215
|
hour: Number(T),
|
|
1216
|
-
format:
|
|
1216
|
+
format: y.format("MMM-DD/HHmm[Z]"),
|
|
1217
1217
|
pressure: m.pressure > 1e4 ? d.roundPrecision(m.pressure / 100, 0) : d.roundPrecision(m.pressure, 0),
|
|
1218
1218
|
gusts: m.gusts,
|
|
1219
1219
|
wind: m.wind || {},
|
|
@@ -1227,21 +1227,21 @@ class z {
|
|
|
1227
1227
|
kts: void 0,
|
|
1228
1228
|
deg: void 0
|
|
1229
1229
|
};
|
|
1230
|
-
if (
|
|
1231
|
-
const T =
|
|
1230
|
+
if (s) {
|
|
1231
|
+
const T = b(s.updated).utc();
|
|
1232
1232
|
if (a) {
|
|
1233
|
-
const
|
|
1234
|
-
p.kts = Math.round(
|
|
1233
|
+
const y = v.calculateDistance(s, a), P = b(a.utc || a.updated).diff(T, "h", !0);
|
|
1234
|
+
p.kts = Math.round(y / P * 100) / 100, p.deg = v.calculateBearing(s, a, !0, 0);
|
|
1235
1235
|
}
|
|
1236
|
-
const m = f.point([
|
|
1236
|
+
const m = f.point([s.lng, s.lat], {
|
|
1237
1237
|
model: c.model,
|
|
1238
|
-
name:
|
|
1239
|
-
nameCn:
|
|
1238
|
+
name: r.name,
|
|
1239
|
+
nameCn: r.nameCn,
|
|
1240
1240
|
date: T.format(),
|
|
1241
1241
|
hour: 0,
|
|
1242
1242
|
format: T.format("MMM-DD/HHmm[Z]"),
|
|
1243
|
-
pressure:
|
|
1244
|
-
wind:
|
|
1243
|
+
pressure: s.pressure > 1e4 ? d.roundPrecision((s == null ? void 0 : s.pressure) / 100, 0) : d.roundPrecision(s.pressure, 0),
|
|
1244
|
+
wind: s.wind,
|
|
1245
1245
|
movement: p,
|
|
1246
1246
|
category: h,
|
|
1247
1247
|
type: "forecast",
|
|
@@ -1252,10 +1252,10 @@ class z {
|
|
|
1252
1252
|
}
|
|
1253
1253
|
if (e.features.push(...l), (u == null ? void 0 : u.length) > 1) {
|
|
1254
1254
|
const T = f.lineString(d.convertToMonotonicLng2(u), {
|
|
1255
|
-
date: (
|
|
1256
|
-
id:
|
|
1255
|
+
date: (s == null ? void 0 : s.updated) || (g == null ? void 0 : g.format()),
|
|
1256
|
+
id: r.id || r.name,
|
|
1257
1257
|
model: c.model,
|
|
1258
|
-
name:
|
|
1258
|
+
name: r.name,
|
|
1259
1259
|
category: h,
|
|
1260
1260
|
type: "forecast",
|
|
1261
1261
|
movement: p
|
|
@@ -1264,21 +1264,21 @@ class z {
|
|
|
1264
1264
|
}
|
|
1265
1265
|
}
|
|
1266
1266
|
}
|
|
1267
|
-
if (e.features.sort((c, a) => c.properties.type === "forecast" && a.properties.type === "forecast" && c.geometry.type === "Point" && a.geometry.type === "Point" ?
|
|
1268
|
-
const c = [], a =
|
|
1269
|
-
for (const g of
|
|
1270
|
-
const h =
|
|
1267
|
+
if (e.features.sort((c, a) => c.properties.type === "forecast" && a.properties.type === "forecast" && c.geometry.type === "Point" && a.geometry.type === "Point" ? b(c.properties.date).valueOf() - b(a.properties.date).valueOf() : 0), (i = r.history) != null && i.length) {
|
|
1268
|
+
const c = [], a = b(s == null ? void 0 : s.updated).utc(), u = b((o = r.history) == null ? void 0 : o.at(-1).updated).utc(), l = a.diff(u, "h") % 24 > 2 ? 24 : 12;
|
|
1269
|
+
for (const g of r.history) {
|
|
1270
|
+
const h = b(g.updated).utc(), p = h.isSameOrBefore(a) || h.isSame(u);
|
|
1271
1271
|
p && a.add(-l, "h");
|
|
1272
1272
|
const T = f.point([g.lng, g.lat], {
|
|
1273
|
-
name:
|
|
1274
|
-
nameCn:
|
|
1273
|
+
name: r.name,
|
|
1274
|
+
nameCn: r.nameCn,
|
|
1275
1275
|
date: h.format(),
|
|
1276
1276
|
format: h.format("MMM-DD/HHmm[Z]"),
|
|
1277
1277
|
pressure: g.pressure > 1e4 ? d.roundPrecision(g.pressure / 100, 0) : d.roundPrecision(g.pressure, 0),
|
|
1278
1278
|
kts: g.kts,
|
|
1279
1279
|
level: g.type,
|
|
1280
1280
|
type: "history",
|
|
1281
|
-
category: `${
|
|
1281
|
+
category: `${r.name}-history`,
|
|
1282
1282
|
wind: g.wind,
|
|
1283
1283
|
movement: g.movement,
|
|
1284
1284
|
important: p
|
|
@@ -1287,12 +1287,12 @@ class z {
|
|
|
1287
1287
|
}
|
|
1288
1288
|
if (c.length === 1 && c.push(c[0]), c.length > 1) {
|
|
1289
1289
|
const g = f.lineString(d.convertToMonotonicLng2(c), {
|
|
1290
|
-
name:
|
|
1290
|
+
name: r.name,
|
|
1291
1291
|
type: "history",
|
|
1292
|
-
updated:
|
|
1293
|
-
pressure: (
|
|
1294
|
-
kts:
|
|
1295
|
-
level:
|
|
1292
|
+
updated: s == null ? void 0 : s.updated,
|
|
1293
|
+
pressure: (s == null ? void 0 : s.pressure) > 1e4 ? d.roundPrecision((s == null ? void 0 : s.pressure) / 100, 0) : d.roundPrecision(s == null ? void 0 : s.pressure, 0),
|
|
1294
|
+
kts: s == null ? void 0 : s.kts,
|
|
1295
|
+
level: s == null ? void 0 : s.type
|
|
1296
1296
|
});
|
|
1297
1297
|
e.features.push(g);
|
|
1298
1298
|
}
|
|
@@ -1306,18 +1306,18 @@ class z {
|
|
|
1306
1306
|
* @param step
|
|
1307
1307
|
*/
|
|
1308
1308
|
static interpolate(t, e = 3) {
|
|
1309
|
-
var o,
|
|
1309
|
+
var o, r, s, c;
|
|
1310
1310
|
const n = (o = t == null ? void 0 : t.data) == null ? void 0 : o.features.filter((a) => a.geometry.type === "LineString" && a.properties.type === "forecast"), i = [];
|
|
1311
1311
|
for (const a of n) {
|
|
1312
|
-
const u = a.properties.name, l = a.properties.model, g = a.properties.showCircle, h = a.properties.disabled, p =
|
|
1312
|
+
const u = a.properties.name, l = a.properties.model, g = a.properties.showCircle, h = a.properties.disabled, p = b(a.properties.date).utc();
|
|
1313
1313
|
let T = e * 60;
|
|
1314
|
-
const m = (
|
|
1314
|
+
const m = (r = t == null ? void 0 : t.data) == null ? void 0 : r.features.filter(
|
|
1315
1315
|
(M) => M.geometry.type === "Point" && M.properties.type === "forecast" && M.properties.category === `${u}-${l}`
|
|
1316
1316
|
);
|
|
1317
|
-
let
|
|
1318
|
-
for (;
|
|
1319
|
-
if (
|
|
1320
|
-
const M = m[
|
|
1317
|
+
let y, P = p.clone().add(T, "minute").set({ minute: 0, second: 0, millisecond: 0 });
|
|
1318
|
+
for (; y = this.pickIndex(m, P), y <= m.length - 1; ) {
|
|
1319
|
+
if (y > 0) {
|
|
1320
|
+
const M = m[y], S = y === 0 ? void 0 : m[y - 1], N = (T / 60 - ((s = S == null ? void 0 : S.properties) == null ? void 0 : s.hour)) / (M.properties.hour - ((c = S == null ? void 0 : S.properties) == null ? void 0 : c.hour)), $ = this.computeNumber(S == null ? void 0 : S.geometry.coordinates[0], M.geometry.coordinates[0], N), O = this.computeNumber(S == null ? void 0 : S.geometry.coordinates[1], M.geometry.coordinates[1], N), A = f.point([$, O], {
|
|
1321
1321
|
name: u,
|
|
1322
1322
|
model: l,
|
|
1323
1323
|
category: M == null ? void 0 : M.properties.category,
|
|
@@ -1346,8 +1346,8 @@ class z {
|
|
|
1346
1346
|
* @param options
|
|
1347
1347
|
*/
|
|
1348
1348
|
static accelPassageAt(t, e) {
|
|
1349
|
-
const { t1: n, t2: i, hr: o, hours:
|
|
1350
|
-
return { t1: n, t2: i, hr: o, hours:
|
|
1349
|
+
const { t1: n, t2: i, hr: o, hours: r } = this.tropicalCenterTwin(t, 24, e);
|
|
1350
|
+
return { t1: n, t2: i, hr: o, hours: r };
|
|
1351
1351
|
}
|
|
1352
1352
|
/**
|
|
1353
1353
|
* 计算最佳绕航点
|
|
@@ -1361,31 +1361,31 @@ class z {
|
|
|
1361
1361
|
* @param options
|
|
1362
1362
|
*/
|
|
1363
1363
|
static diversionPassageAt(t, e, n, i = {}) {
|
|
1364
|
-
const { t1: o, t2:
|
|
1365
|
-
if (o &&
|
|
1364
|
+
const { t1: o, t2: r, hr: s, hours: c } = this.tropicalCenterTwin(e, 24, i);
|
|
1365
|
+
if (o && r) {
|
|
1366
1366
|
if (!i.debug) {
|
|
1367
|
-
const p = v.calculateDistance(t, o), T = v.calculateDistance(t,
|
|
1367
|
+
const p = v.calculateDistance(t, o), T = v.calculateDistance(t, r);
|
|
1368
1368
|
if (p > 2 * n && T > 2 * n)
|
|
1369
1369
|
return C == null || C.info("[%s] the distance between from and t1(%d) and t2(%d) is enough, no need diversion: %j", i.requestId, p, T, {
|
|
1370
1370
|
from: t,
|
|
1371
1371
|
t1: o,
|
|
1372
|
-
t2:
|
|
1373
|
-
hr:
|
|
1372
|
+
t2: r,
|
|
1373
|
+
hr: s
|
|
1374
1374
|
}), {};
|
|
1375
1375
|
}
|
|
1376
|
-
const a = v.calculateBearing(t, o), u = v.calculateBearing(o,
|
|
1376
|
+
const a = v.calculateBearing(t, o), u = v.calculateBearing(o, r), l = Math.abs(a - u);
|
|
1377
1377
|
let g = 0;
|
|
1378
1378
|
l < 180 ? g = l + 90 : l >= 180 && (g = l - 90);
|
|
1379
1379
|
const h = v.calculateCoordinate(o, g, n);
|
|
1380
1380
|
return C == null || C.info("[%s] the right tangent position: %j", i.requestId, {
|
|
1381
1381
|
from: t,
|
|
1382
1382
|
t1: o,
|
|
1383
|
-
t2:
|
|
1383
|
+
t2: r,
|
|
1384
1384
|
radius: n,
|
|
1385
1385
|
bearing1: a,
|
|
1386
1386
|
bearing2: u,
|
|
1387
1387
|
right: h
|
|
1388
|
-
}), { at: h, t1: o, t2:
|
|
1388
|
+
}), { at: h, t1: o, t2: r, hr: Number(s), hours: c };
|
|
1389
1389
|
}
|
|
1390
1390
|
return {};
|
|
1391
1391
|
}
|
|
@@ -1400,22 +1400,22 @@ class z {
|
|
|
1400
1400
|
* @param options
|
|
1401
1401
|
*/
|
|
1402
1402
|
static driftPassageAt(t, e, n, i = {}) {
|
|
1403
|
-
const { t1: o, t2:
|
|
1404
|
-
if (o &&
|
|
1403
|
+
const { t1: o, t2: r, hr: s, hours: c } = this.tropicalCenterTwin(e, 24, i);
|
|
1404
|
+
if (o && r) {
|
|
1405
1405
|
if (!i.debug) {
|
|
1406
|
-
const h = v.calculateDistance(t, o), p = v.calculateDistance(t,
|
|
1406
|
+
const h = v.calculateDistance(t, o), p = v.calculateDistance(t, r);
|
|
1407
1407
|
if (h > 2 * n && p > 2 * n)
|
|
1408
1408
|
return C == null || C.info("[%s] the distance between from and t1(%d) and t2(%d) is enough, no need drifting: %j", i.requestId, h, p, {
|
|
1409
1409
|
from: t,
|
|
1410
1410
|
t1: o,
|
|
1411
|
-
t2:
|
|
1412
|
-
hr:
|
|
1411
|
+
t2: r,
|
|
1412
|
+
hr: s
|
|
1413
1413
|
}), {};
|
|
1414
1414
|
}
|
|
1415
|
-
const a = v.calculateBearing(t, o), u = v.calculateBearing(o,
|
|
1416
|
-
return { at: v.calculateCoordinate(o, a - u + 180, n < l ? n : l), t1: o, t2:
|
|
1415
|
+
const a = v.calculateBearing(t, o), u = v.calculateBearing(o, r), l = v.calculateDistance(t, o);
|
|
1416
|
+
return { at: v.calculateCoordinate(o, a - u + 180, n < l ? n : l), t1: o, t2: r, hr: Number(s), hours: c };
|
|
1417
1417
|
} else
|
|
1418
|
-
return C == null || C.info("[%s] no need drift: %j", i.requestId, { from: t, t1: o, t2:
|
|
1418
|
+
return C == null || C.info("[%s] no need drift: %j", i.requestId, { from: t, t1: o, t2: r, hr: s }), {};
|
|
1419
1419
|
}
|
|
1420
1420
|
/**
|
|
1421
1421
|
* 获取台风中心点对
|
|
@@ -1433,19 +1433,19 @@ class z {
|
|
|
1433
1433
|
});
|
|
1434
1434
|
const o = ((l = t == null ? void 0 : t.history) == null ? void 0 : l[0]) || (i == null ? void 0 : i[(g = Object.keys(i)) == null ? void 0 : g[0]]);
|
|
1435
1435
|
C == null || C.info("[%s] the first tropical center: %j", n.requestId, o);
|
|
1436
|
-
let
|
|
1437
|
-
|
|
1438
|
-
const
|
|
1439
|
-
C == null || C.info("[%s] the second tropical center: %j in %d hrs", n.requestId,
|
|
1440
|
-
const c = Object.keys(i || {}).filter((T) => Number(T) <= Number(
|
|
1436
|
+
let r = (h = Object.keys(i || {}).filter((T) => Number(T) <= (e < 0 ? 24 : e))) == null ? void 0 : h.at(-1);
|
|
1437
|
+
r || (r = (p = Object.keys(i || {}).filter((T) => Number(T) <= (e < 0 ? 24 : 2 * e))) == null ? void 0 : p.at(-1));
|
|
1438
|
+
const s = i == null ? void 0 : i[r || -1];
|
|
1439
|
+
C == null || C.info("[%s] the second tropical center: %j in %d hrs", n.requestId, s, r);
|
|
1440
|
+
const c = Object.keys(i || {}).filter((T) => Number(T) <= Number(r)), a = { 0: o };
|
|
1441
1441
|
for (const T of c)
|
|
1442
1442
|
a[T] = i[T];
|
|
1443
|
-
return { t1: o, t2:
|
|
1443
|
+
return { t1: o, t2: s, hr: Number(r), hours: a };
|
|
1444
1444
|
}
|
|
1445
1445
|
static pickIndex(t, e) {
|
|
1446
1446
|
let n = 0;
|
|
1447
1447
|
for (const i of t) {
|
|
1448
|
-
if (
|
|
1448
|
+
if (b(i.properties.date).isAfter(e))
|
|
1449
1449
|
return n === 0 ? -1 : n;
|
|
1450
1450
|
n++;
|
|
1451
1451
|
}
|
|
@@ -1467,19 +1467,33 @@ class z {
|
|
|
1467
1467
|
return e;
|
|
1468
1468
|
}
|
|
1469
1469
|
}
|
|
1470
|
+
typeof globalThis < "u" && typeof globalThis.Buffer > "u" && (globalThis.Buffer = {
|
|
1471
|
+
isBuffer(D) {
|
|
1472
|
+
return D instanceof Uint8Array;
|
|
1473
|
+
},
|
|
1474
|
+
from(D, t) {
|
|
1475
|
+
if (typeof D == "string")
|
|
1476
|
+
return new TextEncoder().encode(D);
|
|
1477
|
+
if (D instanceof ArrayBuffer)
|
|
1478
|
+
return new Uint8Array(D);
|
|
1479
|
+
if (Array.isArray(D))
|
|
1480
|
+
return new Uint8Array(D);
|
|
1481
|
+
throw new TypeError("Buffer.from: unsupported source type");
|
|
1482
|
+
}
|
|
1483
|
+
});
|
|
1470
1484
|
let x;
|
|
1471
1485
|
try {
|
|
1472
|
-
x =
|
|
1486
|
+
x = w.getLogger("meteo");
|
|
1473
1487
|
} catch {
|
|
1474
1488
|
} finally {
|
|
1475
1489
|
}
|
|
1476
1490
|
function q() {
|
|
1477
1491
|
if (typeof DOMParser < "u")
|
|
1478
1492
|
return new DOMParser();
|
|
1479
|
-
const { JSDOM:
|
|
1493
|
+
const { JSDOM: D } = require("jsdom"), { DOMParser: t } = new D("").window;
|
|
1480
1494
|
return new t();
|
|
1481
1495
|
}
|
|
1482
|
-
class
|
|
1496
|
+
class R {
|
|
1483
1497
|
/**
|
|
1484
1498
|
* Buffer to ArrayBuffer
|
|
1485
1499
|
* 将 Node.js Buffer 转换为独立的 ArrayBuffer(byteOffset=0)。
|
|
@@ -1498,10 +1512,10 @@ class $ {
|
|
|
1498
1512
|
* @param options 步数、单位等选项
|
|
1499
1513
|
*/
|
|
1500
1514
|
static drawCircle(t, e, n, i = {}) {
|
|
1501
|
-
const o = (i == null ? void 0 : i.steps) ?? 64,
|
|
1502
|
-
|
|
1515
|
+
const o = (i == null ? void 0 : i.steps) ?? 64, r = (i == null ? void 0 : i.units) ?? "nauticalmiles", s = (i == null ? void 0 : i.properties) ?? {}, c = f.point([t, e]), a = f.destination(c, n, 90, { units: r }), u = b.utc();
|
|
1516
|
+
s.id = (i == null ? void 0 : i.id) || u.valueOf().toString();
|
|
1503
1517
|
const l = "circle";
|
|
1504
|
-
return
|
|
1518
|
+
return s.name = (i == null ? void 0 : i.name) || `${l}_${u.format()}`, s.radius = n, s.center = [t, e], s.end = a.geometry.coordinates.map((g) => d.roundPrecision(g, 9)), s.units = r, s.steps = o, s.shape = "circle", x.info("[%s] draw circle with %j", i == null ? void 0 : i.requestId, s), f.circle(c, n, { steps: o, units: r, properties: s });
|
|
1505
1519
|
}
|
|
1506
1520
|
/**
|
|
1507
1521
|
* 基于turf画矩形,返回GeoJSON Feature<Polygon>
|
|
@@ -1510,11 +1524,11 @@ class $ {
|
|
|
1510
1524
|
* @param options 选项
|
|
1511
1525
|
*/
|
|
1512
1526
|
static drawRect(t, e, n = {}) {
|
|
1513
|
-
const i = (n == null ? void 0 : n.properties) ?? {}, o =
|
|
1527
|
+
const i = (n == null ? void 0 : n.properties) ?? {}, o = b.utc();
|
|
1514
1528
|
i.id = (n == null ? void 0 : n.id) || o.valueOf().toString();
|
|
1515
|
-
const
|
|
1516
|
-
i.name = (n == null ? void 0 : n.name) || `${
|
|
1517
|
-
const [
|
|
1529
|
+
const r = "rect";
|
|
1530
|
+
i.name = (n == null ? void 0 : n.name) || `${r}_${o.format()}`, i.start = t.map((u) => d.roundPrecision(u, 9)), i.end = e.map((u) => d.roundPrecision(u, 9)), i.shape = "rect", x.info("[%s] draw rect with %j", n == null ? void 0 : n.requestId, i);
|
|
1531
|
+
const [s, c] = d.convertToMonotonicLng2([t, e]), a = [Math.min(s[0], c[0]), Math.min(s[1], c[1]), Math.max(s[0], c[0]), Math.max(s[1], c[1])];
|
|
1518
1532
|
return f.bboxPolygon(a, { properties: i });
|
|
1519
1533
|
}
|
|
1520
1534
|
/**
|
|
@@ -1525,12 +1539,12 @@ class $ {
|
|
|
1525
1539
|
* @returns
|
|
1526
1540
|
*/
|
|
1527
1541
|
static drawLine(t, e = {}) {
|
|
1528
|
-
const n = (e == null ? void 0 : e.properties) ?? {}, i =
|
|
1542
|
+
const n = (e == null ? void 0 : e.properties) ?? {}, i = b.utc();
|
|
1529
1543
|
n.id = (e == null ? void 0 : e.id) || i.valueOf().toString();
|
|
1530
1544
|
const o = "line";
|
|
1531
1545
|
n.name = (e == null ? void 0 : e.name) || `${o}_${i.format()}`, n.shape = "line", x.info("[%s] draw line with %j", e == null ? void 0 : e.requestId, n);
|
|
1532
|
-
const
|
|
1533
|
-
return f.lineString(
|
|
1546
|
+
const r = d.convertToMonotonicLng2(t);
|
|
1547
|
+
return f.lineString(r, n);
|
|
1534
1548
|
}
|
|
1535
1549
|
/**
|
|
1536
1550
|
* 基于turf画多边形,返回GeoJSON Feature<Polygon>
|
|
@@ -1539,12 +1553,12 @@ class $ {
|
|
|
1539
1553
|
* @returns
|
|
1540
1554
|
*/
|
|
1541
1555
|
static drawPolygon(t, e = {}) {
|
|
1542
|
-
const n = (e == null ? void 0 : e.properties) ?? {}, i =
|
|
1556
|
+
const n = (e == null ? void 0 : e.properties) ?? {}, i = b.utc();
|
|
1543
1557
|
n.id = (e == null ? void 0 : e.id) || i.valueOf().toString();
|
|
1544
1558
|
const o = "polygon";
|
|
1545
|
-
n.name = (e == null ? void 0 : e.name) || `${o}_${i.format()}`, n.coordinates = t.map((
|
|
1546
|
-
const
|
|
1547
|
-
return f.polygon([
|
|
1559
|
+
n.name = (e == null ? void 0 : e.name) || `${o}_${i.format()}`, n.coordinates = t.map((s) => s.map((c) => d.roundPrecision(c, 9))), n.shape = "polygon", x.info("[%s] draw polygon with %j", e == null ? void 0 : e.requestId, n);
|
|
1560
|
+
const r = d.convertToMonotonicLng2(t);
|
|
1561
|
+
return f.polygon([r], n);
|
|
1548
1562
|
}
|
|
1549
1563
|
/**
|
|
1550
1564
|
* 基于turf画点,返回GeoJSON Feature<Point>
|
|
@@ -1554,10 +1568,10 @@ class $ {
|
|
|
1554
1568
|
* @returns
|
|
1555
1569
|
*/
|
|
1556
1570
|
static drawPoint(t, e, n = {}) {
|
|
1557
|
-
const i = (n == null ? void 0 : n.properties) ?? {}, o =
|
|
1571
|
+
const i = (n == null ? void 0 : n.properties) ?? {}, o = b.utc();
|
|
1558
1572
|
i.id = (n == null ? void 0 : n.id) || o.valueOf().toString();
|
|
1559
|
-
const
|
|
1560
|
-
return i.name = (n == null ? void 0 : n.name) || `${
|
|
1573
|
+
const r = "point";
|
|
1574
|
+
return i.name = (n == null ? void 0 : n.name) || `${r}_${o.format()}`, i.shape = "point", x.info("[%s] draw point with %j", n == null ? void 0 : n.requestId, i), f.point([e, t], i);
|
|
1561
1575
|
}
|
|
1562
1576
|
/**
|
|
1563
1577
|
* 解析ORM GeoJSON Feature (圆), 返回FeatureCollection
|
|
@@ -1571,11 +1585,11 @@ class $ {
|
|
|
1571
1585
|
x.info("[%s] parse circle with %j", e == null ? void 0 : e.requestId, t.properties);
|
|
1572
1586
|
const n = t.properties || {};
|
|
1573
1587
|
if (n.shape == "circle") {
|
|
1574
|
-
const
|
|
1575
|
-
n.id = (n == null ? void 0 : n.id) ||
|
|
1576
|
-
const
|
|
1588
|
+
const r = b.utc();
|
|
1589
|
+
n.id = (n == null ? void 0 : n.id) || r.valueOf().toString();
|
|
1590
|
+
const s = n == null ? void 0 : n.id, c = ((i = n == null ? void 0 : n.center) == null ? void 0 : i.length) == 2 ? f.point(n.center) : f.centroid(t);
|
|
1577
1591
|
let a = "center";
|
|
1578
|
-
c.properties = { id: `${a}_${
|
|
1592
|
+
c.properties = { id: `${a}_${s}`, parentId: s, name: a };
|
|
1579
1593
|
const u = (n == null ? void 0 : n.units) || "nauticalmiles";
|
|
1580
1594
|
let l = n == null ? void 0 : n.radius;
|
|
1581
1595
|
if (!l) {
|
|
@@ -1584,9 +1598,9 @@ class $ {
|
|
|
1584
1598
|
}
|
|
1585
1599
|
a = "end";
|
|
1586
1600
|
const g = ((o = n == null ? void 0 : n.end) == null ? void 0 : o.length) == 2 ? f.point(n.end) : f.destination(c, l, 90, { units: u });
|
|
1587
|
-
g.properties = { id: `${a}_${
|
|
1601
|
+
g.properties = { id: `${a}_${s}`, parentId: s, name: a, radius: l, units: u };
|
|
1588
1602
|
const h = f.lineString([c.geometry.coordinates, g.geometry.coordinates]);
|
|
1589
|
-
return a = "edge", h.properties = { id: `${a}_${
|
|
1603
|
+
return a = "edge", h.properties = { id: `${a}_${s}`, parentId: s, name: a, radius: l, units: u }, f.featureCollection([c, g, h, t]);
|
|
1590
1604
|
} else
|
|
1591
1605
|
return x.warn("[%s] not a orm-std circle, just return the original feature", e == null ? void 0 : e.requestId), f.featureCollection([t]);
|
|
1592
1606
|
}
|
|
@@ -1601,10 +1615,10 @@ class $ {
|
|
|
1601
1615
|
x.info("[%s] parse rect with %j", e == null ? void 0 : e.requestId, t.properties);
|
|
1602
1616
|
const n = t.properties || {};
|
|
1603
1617
|
if (n.shape == "rect") {
|
|
1604
|
-
const i =
|
|
1618
|
+
const i = b.utc();
|
|
1605
1619
|
n.id = (n == null ? void 0 : n.id) || i.valueOf().toString();
|
|
1606
|
-
const o = n == null ? void 0 : n.id,
|
|
1607
|
-
const l = f.point(
|
|
1620
|
+
const o = n == null ? void 0 : n.id, r = t.geometry.coordinates[0], c = ["sw", "nw", "ne", "se"].map((a, u) => {
|
|
1621
|
+
const l = f.point(r[u]);
|
|
1608
1622
|
return l.properties = { id: `${a}_${o}`, parentId: o, name: a }, l;
|
|
1609
1623
|
});
|
|
1610
1624
|
return f.featureCollection([...c, t]);
|
|
@@ -1622,13 +1636,13 @@ class $ {
|
|
|
1622
1636
|
x.info("[%s] parse line with %j", e == null ? void 0 : e.requestId, t.properties);
|
|
1623
1637
|
const n = t.properties || {};
|
|
1624
1638
|
if (n.shape == "line") {
|
|
1625
|
-
const i =
|
|
1639
|
+
const i = b.utc();
|
|
1626
1640
|
n.id = (n == null ? void 0 : n.id) || i.valueOf().toString();
|
|
1627
|
-
const o = n == null ? void 0 : n.id,
|
|
1641
|
+
const o = n == null ? void 0 : n.id, s = t.geometry.coordinates.map((c, a) => {
|
|
1628
1642
|
const u = `point_${a}`, l = f.point(c);
|
|
1629
1643
|
return l.properties = { id: `${u}_${o}`, parentId: o, name: u, index: a }, l;
|
|
1630
1644
|
});
|
|
1631
|
-
return f.featureCollection([...
|
|
1645
|
+
return f.featureCollection([...s, t]);
|
|
1632
1646
|
} else
|
|
1633
1647
|
return x.warn("[%s] not a orm-std line, just return the original feature", e == null ? void 0 : e.requestId), f.featureCollection([t]);
|
|
1634
1648
|
}
|
|
@@ -1643,13 +1657,13 @@ class $ {
|
|
|
1643
1657
|
x.info("[%s] parse polygon with %j", e == null ? void 0 : e.requestId, t.properties);
|
|
1644
1658
|
const n = t.properties || {};
|
|
1645
1659
|
if (n.shape == "polygon") {
|
|
1646
|
-
const i =
|
|
1660
|
+
const i = b.utc();
|
|
1647
1661
|
n.id = (n == null ? void 0 : n.id) || i.valueOf().toString();
|
|
1648
|
-
const o = n == null ? void 0 : n.id,
|
|
1662
|
+
const o = n == null ? void 0 : n.id, s = t.geometry.coordinates[0].map((c, a) => {
|
|
1649
1663
|
const u = f.point(c), l = `corner_${a}`;
|
|
1650
1664
|
return u.properties = { id: `${l}_${o}`, parentId: o, name: l, index: a }, u;
|
|
1651
1665
|
});
|
|
1652
|
-
return f.featureCollection([...
|
|
1666
|
+
return f.featureCollection([...s, t]);
|
|
1653
1667
|
} else
|
|
1654
1668
|
return x.warn("[%s] not a orm-std polygon, just return the original feature", e == null ? void 0 : e.requestId), f.featureCollection([t]);
|
|
1655
1669
|
}
|
|
@@ -1673,38 +1687,38 @@ class $ {
|
|
|
1673
1687
|
*/
|
|
1674
1688
|
static async _parseZipEntries(t) {
|
|
1675
1689
|
var c;
|
|
1676
|
-
const e = new Uint8Array(t), n = e.buffer.slice(e.byteOffset, e.byteOffset + e.byteLength), i = new DataView(n), o = new Uint8Array(n),
|
|
1677
|
-
let
|
|
1678
|
-
for (;
|
|
1679
|
-
const u = i.getUint16(
|
|
1690
|
+
const e = new Uint8Array(t), n = e.buffer.slice(e.byteOffset, e.byteOffset + e.byteLength), i = new DataView(n), o = new Uint8Array(n), r = /* @__PURE__ */ new Map();
|
|
1691
|
+
let s = 0;
|
|
1692
|
+
for (; s + 4 <= n.byteLength && i.getUint32(s, !0) === 67324752; ) {
|
|
1693
|
+
const u = i.getUint16(s + 8, !0), l = i.getUint32(s + 18, !0), g = i.getUint16(s + 26, !0), h = i.getUint16(s + 28, !0), p = o.slice(s + 30, s + 30 + g), T = new TextDecoder().decode(p), m = s + 30 + g + h, y = o.slice(m, m + l);
|
|
1680
1694
|
if (u === 0)
|
|
1681
|
-
|
|
1695
|
+
r.set(T, y);
|
|
1682
1696
|
else if (u === 8) {
|
|
1683
1697
|
if (typeof DecompressionStream < "u") {
|
|
1684
1698
|
const P = new DecompressionStream("deflate-raw"), M = P.writable.getWriter(), S = P.readable.getReader();
|
|
1685
|
-
M.write(
|
|
1699
|
+
M.write(y), M.close();
|
|
1686
1700
|
const N = [];
|
|
1687
|
-
let
|
|
1701
|
+
let $ = 0;
|
|
1688
1702
|
for (; ; ) {
|
|
1689
|
-
const { done: E, value:
|
|
1703
|
+
const { done: E, value: B } = await S.read();
|
|
1690
1704
|
if (E)
|
|
1691
1705
|
break;
|
|
1692
|
-
N.push(
|
|
1706
|
+
N.push(B), $ += B.length;
|
|
1693
1707
|
}
|
|
1694
|
-
const O = new Uint8Array(
|
|
1708
|
+
const O = new Uint8Array($);
|
|
1695
1709
|
let A = 0;
|
|
1696
1710
|
for (const E of N)
|
|
1697
1711
|
O.set(E, A), A += E.length;
|
|
1698
|
-
|
|
1712
|
+
r.set(T, O);
|
|
1699
1713
|
} else if (typeof process < "u" && ((c = process.versions) != null && c.node))
|
|
1700
1714
|
try {
|
|
1701
|
-
|
|
1715
|
+
r.set(T, R._inflateRawSync(y));
|
|
1702
1716
|
} catch {
|
|
1703
1717
|
}
|
|
1704
1718
|
}
|
|
1705
|
-
|
|
1719
|
+
s = m + l;
|
|
1706
1720
|
}
|
|
1707
|
-
return
|
|
1721
|
+
return r;
|
|
1708
1722
|
}
|
|
1709
1723
|
// ---------------------------------------------------------------------------
|
|
1710
1724
|
// KMZ / ZIP → GeoJSON
|
|
@@ -1716,24 +1730,24 @@ class $ {
|
|
|
1716
1730
|
* @returns
|
|
1717
1731
|
*/
|
|
1718
1732
|
static async convertKML2GeoJSON(t, e = {}) {
|
|
1719
|
-
var
|
|
1733
|
+
var s, c;
|
|
1720
1734
|
x.info("[%s] convert kml to geojson", e == null ? void 0 : e.requestId);
|
|
1721
|
-
const i = q().parseFromString(t, "application/xml"), o = Array.from(i.querySelectorAll("Placemark")),
|
|
1735
|
+
const i = q().parseFromString(t, "application/xml"), o = Array.from(i.querySelectorAll("Placemark")), r = [];
|
|
1722
1736
|
for (const a of o) {
|
|
1723
1737
|
const u = {}, l = Array.from(a.querySelectorAll("ExtendedData > Data"));
|
|
1724
1738
|
for (const S of l) {
|
|
1725
|
-
const N = S.getAttribute("name"),
|
|
1726
|
-
N &&
|
|
1739
|
+
const N = S.getAttribute("name"), $ = (c = (s = S.querySelector("value")) == null ? void 0 : s.textContent) == null ? void 0 : c.trim();
|
|
1740
|
+
N && $ !== void 0 && $ !== null && (u[N] = $);
|
|
1727
1741
|
}
|
|
1728
|
-
const g =
|
|
1729
|
-
const
|
|
1730
|
-
return [
|
|
1731
|
-
}),
|
|
1732
|
-
if (
|
|
1733
|
-
const S = m(
|
|
1742
|
+
const g = b.utc(), h = Object.keys(u).find((S) => S.toLowerCase().indexOf("name") !== -1), p = h ? u[h] : void 0, T = `${g.valueOf().toString()}_${Math.random().toString(36).slice(2, 8)}`, m = (S) => S.trim().split(/[\s\n]+/).filter((N) => N.length > 0).map((N) => {
|
|
1743
|
+
const $ = N.split(",").map(Number);
|
|
1744
|
+
return [$[0], $[1]];
|
|
1745
|
+
}), y = a.querySelector("LineString > coordinates");
|
|
1746
|
+
if (y) {
|
|
1747
|
+
const S = m(y.textContent || "");
|
|
1734
1748
|
if (S.length >= 2) {
|
|
1735
1749
|
const N = f.lineString(S, { ...u, shape: "line", id: T, name: p });
|
|
1736
|
-
|
|
1750
|
+
r.push(N);
|
|
1737
1751
|
}
|
|
1738
1752
|
continue;
|
|
1739
1753
|
}
|
|
@@ -1741,8 +1755,8 @@ class $ {
|
|
|
1741
1755
|
if (P) {
|
|
1742
1756
|
const S = m(P.textContent || "");
|
|
1743
1757
|
if (S.length >= 4) {
|
|
1744
|
-
const N = S[0][0] === S[S.length - 1][0] && S[0][1] === S[S.length - 1][1] ? S : [...S, S[0]],
|
|
1745
|
-
|
|
1758
|
+
const N = S[0][0] === S[S.length - 1][0] && S[0][1] === S[S.length - 1][1] ? S : [...S, S[0]], $ = f.polygon([N], { ...u, shape: "polygon", id: T, name: p });
|
|
1759
|
+
r.push($);
|
|
1746
1760
|
}
|
|
1747
1761
|
continue;
|
|
1748
1762
|
}
|
|
@@ -1751,12 +1765,12 @@ class $ {
|
|
|
1751
1765
|
const S = m(M.textContent || "");
|
|
1752
1766
|
if (S.length >= 1) {
|
|
1753
1767
|
const N = f.point(S[0], { ...u, shape: "point", id: T, name: p });
|
|
1754
|
-
|
|
1768
|
+
r.push(N);
|
|
1755
1769
|
}
|
|
1756
1770
|
continue;
|
|
1757
1771
|
}
|
|
1758
1772
|
}
|
|
1759
|
-
return f.featureCollection(
|
|
1773
|
+
return f.featureCollection(r);
|
|
1760
1774
|
}
|
|
1761
1775
|
/**
|
|
1762
1776
|
* 将 KMZ(ZIP 内含 doc.kml 或首个 .kml 文件)异步转换为 GeoJSON。
|
|
@@ -1768,13 +1782,13 @@ class $ {
|
|
|
1768
1782
|
* @param options
|
|
1769
1783
|
*/
|
|
1770
1784
|
static async convertKMZ2GeoJSON(t, e = {}) {
|
|
1771
|
-
var
|
|
1772
|
-
x.info("[%s] convert kmz to geojson (async)", e == null ? void 0 : e.requestId), Buffer.isBuffer(t) && (t =
|
|
1773
|
-
const n = await
|
|
1785
|
+
var r;
|
|
1786
|
+
x.info("[%s] convert kmz to geojson (async)", e == null ? void 0 : e.requestId), typeof Buffer < "u" && Buffer.isBuffer(t) && (t = R.toArrayBuffer(t));
|
|
1787
|
+
const n = await R._parseZipEntries(t), i = n.get("doc.kml") ?? ((r = [...n.entries()].find(([s]) => s.toLowerCase().endsWith(".kml"))) == null ? void 0 : r[1]);
|
|
1774
1788
|
if (!i)
|
|
1775
1789
|
return x.warn("[%s] no .kml file found in kmz", e == null ? void 0 : e.requestId), f.featureCollection([]);
|
|
1776
1790
|
const o = new TextDecoder().decode(i);
|
|
1777
|
-
return
|
|
1791
|
+
return R.convertKML2GeoJSON(o, e);
|
|
1778
1792
|
}
|
|
1779
1793
|
/**
|
|
1780
1794
|
* 将 ZIP 文件中所有 .kml 文件合并转换为一个 GeoJSON FeatureCollection(异步)。
|
|
@@ -1786,12 +1800,12 @@ class $ {
|
|
|
1786
1800
|
* @param options
|
|
1787
1801
|
*/
|
|
1788
1802
|
static async convertZIP2GeoJSON(t, e = {}) {
|
|
1789
|
-
x.info("[%s] convert zip to geojson (async)", e == null ? void 0 : e.requestId), Buffer.isBuffer(t) && (t =
|
|
1790
|
-
const n = await
|
|
1791
|
-
for (const [o,
|
|
1803
|
+
x.info("[%s] convert zip to geojson (async)", e == null ? void 0 : e.requestId), typeof Buffer < "u" && Buffer.isBuffer(t) && (t = R.toArrayBuffer(t));
|
|
1804
|
+
const n = await R._parseZipEntries(t), i = [];
|
|
1805
|
+
for (const [o, r] of n) {
|
|
1792
1806
|
if (!o.toLowerCase().endsWith(".kml"))
|
|
1793
1807
|
continue;
|
|
1794
|
-
const
|
|
1808
|
+
const s = new TextDecoder().decode(r), c = await R.convertKML2GeoJSON(s, e);
|
|
1795
1809
|
i.push(...c.features);
|
|
1796
1810
|
}
|
|
1797
1811
|
return i.length === 0 ? (x.warn("[%s] no .kml files found in zip", e == null ? void 0 : e.requestId), this.convertSHP2GeoJSON(t, e)) : f.featureCollection(i);
|
|
@@ -1807,10 +1821,10 @@ class $ {
|
|
|
1807
1821
|
static async convertSHP2GeoJSON(t, e = {}) {
|
|
1808
1822
|
x.info("[%s] convert shp zip to geojson", e == null ? void 0 : e.requestId);
|
|
1809
1823
|
try {
|
|
1810
|
-
Buffer.isBuffer(t) && (t =
|
|
1811
|
-
const n = await
|
|
1824
|
+
typeof Buffer < "u" && Buffer.isBuffer(t) && (t = R.toArrayBuffer(t));
|
|
1825
|
+
const n = await k(t);
|
|
1812
1826
|
if (Array.isArray(n)) {
|
|
1813
|
-
const i = n.flatMap((c) => c.features || []), o =
|
|
1827
|
+
const i = n.flatMap((c) => c.features || []), o = b.utc(), r = (e == null ? void 0 : e.id) || o.valueOf().toString(), s = {
|
|
1814
1828
|
Point: "point",
|
|
1815
1829
|
MultiPoint: "point",
|
|
1816
1830
|
LineString: "line",
|
|
@@ -1820,8 +1834,8 @@ class $ {
|
|
|
1820
1834
|
};
|
|
1821
1835
|
return i.forEach((c, a) => {
|
|
1822
1836
|
var p;
|
|
1823
|
-
const u = ((p = c.geometry) == null ? void 0 : p.type) || "", l =
|
|
1824
|
-
c.properties = c.properties || {}, c.properties.shape = l, c.properties.parentId =
|
|
1837
|
+
const u = ((p = c.geometry) == null ? void 0 : p.type) || "", l = s[u] || u.toLowerCase();
|
|
1838
|
+
c.properties = c.properties || {}, c.properties.shape = l, c.properties.parentId = r, c.properties.id = `${r}_${a}`;
|
|
1825
1839
|
const g = Object.keys(c.properties).find((T) => T.toLowerCase().indexOf("name") !== -1), h = g ? c.properties[g] : void 0;
|
|
1826
1840
|
c.properties.name = h || `${l}_${o.format()}_${a}`;
|
|
1827
1841
|
}), f.featureCollection(i);
|
|
@@ -1834,7 +1848,7 @@ class $ {
|
|
|
1834
1848
|
}
|
|
1835
1849
|
export {
|
|
1836
1850
|
W as AisHelper,
|
|
1837
|
-
|
|
1851
|
+
R as GeoJsonHelper,
|
|
1838
1852
|
v as LaneHelper,
|
|
1839
1853
|
d as LngLatHelper,
|
|
1840
1854
|
z as TropicalHelper
|