@idm-plugin/geo 2.2.3 → 2.2.5
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 +30 -30
- package/dist/index.umd.cjs +2 -2
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -1093,21 +1093,21 @@ class v {
|
|
|
1093
1093
|
const p = (P) => P == null ? "" : String(P).replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """);
|
|
1094
1094
|
let x = `<row r="1">${m.map((P, I) => `<c r="${z(I)}1" s="1" t="inlineStr"><is><t>${p(P)}</t></is></c>`).join("")}</row>`;
|
|
1095
1095
|
for (let P = 0; P < e.length; P++) {
|
|
1096
|
-
const I = e[P],
|
|
1097
|
-
j != null ? Z(W, j) :
|
|
1096
|
+
const I = e[P], E = P + 2, B = [], Z = (W, j) => B.push(`<c r="${z(W)}${E}"><v>${j}</v></c>`), A = (W, j) => B.push(`<c r="${z(W)}${E}" t="inlineStr"><is><t>${p(j)}</t></is></c>`), k = (W, j) => {
|
|
1097
|
+
j != null ? Z(W, j) : A(W, "");
|
|
1098
1098
|
};
|
|
1099
|
-
Z(0, P + 1),
|
|
1099
|
+
Z(0, P + 1), A(1, d.lat2pretty(I.lat, s).pretty), A(2, d.lng2pretty(I.lng, s).pretty);
|
|
1100
1100
|
let D = 3;
|
|
1101
|
-
r && (
|
|
1101
|
+
r && (A(D, I.name ?? ""), D++), i && (A(D, I.description ?? ""), D++), f && (A(D, P === 0 ? "" : I.gcToPrevious ? "GC" : "RL"), D++), h && (k(D, I.bearing), D++), g && (k(D, I.distanceFromPrevious), D++), u && (k(D, I.speed), D++), c && (k(D, I.port), D++), a && (k(D, I.stbd), D++), l && (k(D, I.arrRad), D++), x += `<row r="${E}">${B.join("")}</row>`;
|
|
1102
1102
|
}
|
|
1103
|
-
const M = "0." + "0".repeat(s), y = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><worksheet xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main"><sheetData>' + x + "</sheetData></worksheet>", N = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Types xmlns="http://schemas.openxmlformats.org/package/2006/content-types"><Default Extension="rels" ContentType="application/vnd.openxmlformats-package.relationships+xml"/><Default Extension="xml" ContentType="application/xml"/><Override PartName="/xl/workbook.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"/><Override PartName="/xl/worksheets/sheet1.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml"/><Override PartName="/xl/styles.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml"/></Types>', w = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships"><Relationship Id="rId1" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument" Target="xl/workbook.xml"/></Relationships>', q = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><workbook xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main" xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"><sheets><sheet name="' + p(o) + '" sheetId="1" r:id="rId1"/></sheets></workbook>',
|
|
1103
|
+
const M = "0." + "0".repeat(s), y = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><worksheet xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main"><sheetData>' + x + "</sheetData></worksheet>", N = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Types xmlns="http://schemas.openxmlformats.org/package/2006/content-types"><Default Extension="rels" ContentType="application/vnd.openxmlformats-package.relationships+xml"/><Default Extension="xml" ContentType="application/xml"/><Override PartName="/xl/workbook.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"/><Override PartName="/xl/worksheets/sheet1.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml"/><Override PartName="/xl/styles.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml"/></Types>', w = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships"><Relationship Id="rId1" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument" Target="xl/workbook.xml"/></Relationships>', q = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><workbook xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main" xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"><sheets><sheet name="' + p(o) + '" sheetId="1" r:id="rId1"/></sheets></workbook>', U = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships"><Relationship Id="rId1" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet" Target="worksheets/sheet1.xml"/><Relationship Id="rId2" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles" Target="styles.xml"/></Relationships>', L = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?><styleSheet xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main"><numFmts count="1"><numFmt numFmtId="164" formatCode="' + M + '"/></numFmts><fonts count="2"><font><sz val="11"/><name val="Arial"/></font><font><b/><sz val="11"/><name val="Arial"/></font></fonts><fills count="2"><fill><patternFill patternType="none"/></fill><fill><patternFill patternType="gray125"/></fill></fills><borders count="2"><border><left/><right/><top/><bottom/><diagonal/></border><border><bottom style="thin"><color auto="1"/></bottom></border></borders><cellStyleXfs count="1"><xf/></cellStyleXfs><cellXfs count="3"><xf/><xf fontId="1" fillId="0" borderId="1" applyFont="1" applyBorder="1"/><xf numFmtId="164" fontId="0" applyNumberFormat="1"/></cellXfs></styleSheet>', O = new TextEncoder();
|
|
1104
1104
|
return _([
|
|
1105
|
-
{ name: "[Content_Types].xml", data:
|
|
1106
|
-
{ name: "_rels/.rels", data:
|
|
1107
|
-
{ name: "xl/workbook.xml", data:
|
|
1108
|
-
{ name: "xl/_rels/workbook.xml.rels", data:
|
|
1109
|
-
{ name: "xl/worksheets/sheet1.xml", data:
|
|
1110
|
-
{ name: "xl/styles.xml", data:
|
|
1105
|
+
{ name: "[Content_Types].xml", data: O.encode(N) },
|
|
1106
|
+
{ name: "_rels/.rels", data: O.encode(w) },
|
|
1107
|
+
{ name: "xl/workbook.xml", data: O.encode(q) },
|
|
1108
|
+
{ name: "xl/_rels/workbook.xml.rels", data: O.encode(U) },
|
|
1109
|
+
{ name: "xl/worksheets/sheet1.xml", data: O.encode(y) },
|
|
1110
|
+
{ name: "xl/styles.xml", data: O.encode(L) }
|
|
1111
1111
|
]);
|
|
1112
1112
|
}
|
|
1113
1113
|
/**
|
|
@@ -1396,7 +1396,7 @@ class it {
|
|
|
1396
1396
|
let S, x = g.clone().add(m, "minute").set({ minute: 0, second: 0, millisecond: 0 });
|
|
1397
1397
|
for (; S = this.pickIndex(p, x), S <= p.length - 1; ) {
|
|
1398
1398
|
if (S > 0) {
|
|
1399
|
-
const M = p[S], y = S === 0 ? void 0 : p[S - 1], N = (m / 60 - ((i = y == null ? void 0 : y.properties) == null ? void 0 : i.hour)) / (M.properties.hour - ((c = y == null ? void 0 : y.properties) == null ? void 0 : c.hour)), w = this.computeNumber(y == null ? void 0 : y.geometry.coordinates[0], M.geometry.coordinates[0], N), q = this.computeNumber(y == null ? void 0 : y.geometry.coordinates[1], M.geometry.coordinates[1], N),
|
|
1399
|
+
const M = p[S], y = S === 0 ? void 0 : p[S - 1], N = (m / 60 - ((i = y == null ? void 0 : y.properties) == null ? void 0 : i.hour)) / (M.properties.hour - ((c = y == null ? void 0 : y.properties) == null ? void 0 : c.hour)), w = this.computeNumber(y == null ? void 0 : y.geometry.coordinates[0], M.geometry.coordinates[0], N), q = this.computeNumber(y == null ? void 0 : y.geometry.coordinates[1], M.geometry.coordinates[1], N), U = T.point([w, q], {
|
|
1400
1400
|
name: l,
|
|
1401
1401
|
model: u,
|
|
1402
1402
|
category: M == null ? void 0 : M.properties.category,
|
|
@@ -1411,7 +1411,7 @@ class it {
|
|
|
1411
1411
|
disabled: h,
|
|
1412
1412
|
showCircle: f
|
|
1413
1413
|
});
|
|
1414
|
-
s.push(
|
|
1414
|
+
s.push(U);
|
|
1415
1415
|
}
|
|
1416
1416
|
m += e * 60, x = g.clone().add(m, "minute").set({ minute: 0, second: 0, millisecond: 0 });
|
|
1417
1417
|
}
|
|
@@ -1572,7 +1572,7 @@ function H() {
|
|
|
1572
1572
|
const { JSDOM: C } = require("jsdom"), { DOMParser: t } = new C("").window;
|
|
1573
1573
|
return new t();
|
|
1574
1574
|
}
|
|
1575
|
-
class
|
|
1575
|
+
class F {
|
|
1576
1576
|
/**
|
|
1577
1577
|
* Buffer to ArrayBuffer
|
|
1578
1578
|
* 将 Node.js Buffer 转换为独立的 ArrayBuffer(byteOffset=0)。
|
|
@@ -1783,29 +1783,29 @@ class A {
|
|
|
1783
1783
|
for (; l < u; ) {
|
|
1784
1784
|
if (s.getUint32(l, !0) !== 33639248)
|
|
1785
1785
|
throw new Error(`Invalid ZIP file: Central Directory signature mismatch at offset ${l}`);
|
|
1786
|
-
const g = s.getUint16(l + 10, !0), m = s.getUint32(l + 20, !0), p = s.getUint16(l + 28, !0), S = s.getUint16(l + 30, !0), x = s.getUint16(l + 32, !0), M = s.getUint32(l + 42, !0), y = o.slice(l + 46, l + 46 + p), N = new TextDecoder().decode(y), w = s.getUint16(M + 26, !0), q = s.getUint16(M + 28, !0),
|
|
1786
|
+
const g = s.getUint16(l + 10, !0), m = s.getUint32(l + 20, !0), p = s.getUint16(l + 28, !0), S = s.getUint16(l + 30, !0), x = s.getUint16(l + 32, !0), M = s.getUint32(l + 42, !0), y = o.slice(l + 46, l + 46 + p), N = new TextDecoder().decode(y), w = s.getUint16(M + 26, !0), q = s.getUint16(M + 28, !0), U = M + 30 + w + q, L = o.slice(U, U + m);
|
|
1787
1787
|
if (g === 0)
|
|
1788
1788
|
r.set(N, L);
|
|
1789
1789
|
else if (g === 8) {
|
|
1790
1790
|
if (typeof DecompressionStream < "u") {
|
|
1791
|
-
const
|
|
1791
|
+
const O = new DecompressionStream("deflate-raw"), P = O.writable.getWriter(), I = O.readable.getReader();
|
|
1792
1792
|
P.write(L), P.close();
|
|
1793
|
-
const
|
|
1793
|
+
const E = [];
|
|
1794
1794
|
let B = 0;
|
|
1795
1795
|
for (; ; ) {
|
|
1796
1796
|
const { done: k, value: D } = await I.read();
|
|
1797
1797
|
if (k)
|
|
1798
1798
|
break;
|
|
1799
|
-
|
|
1799
|
+
E.push(D), B += D.length;
|
|
1800
1800
|
}
|
|
1801
1801
|
const Z = new Uint8Array(B);
|
|
1802
|
-
let
|
|
1803
|
-
for (const k of
|
|
1804
|
-
Z.set(k,
|
|
1802
|
+
let A = 0;
|
|
1803
|
+
for (const k of E)
|
|
1804
|
+
Z.set(k, A), A += k.length;
|
|
1805
1805
|
r.set(N, Z);
|
|
1806
1806
|
} else if (typeof process < "u" && ((f = process.versions) != null && f.node))
|
|
1807
1807
|
try {
|
|
1808
|
-
r.set(N,
|
|
1808
|
+
r.set(N, F._inflateRawSync(L));
|
|
1809
1809
|
} catch {
|
|
1810
1810
|
}
|
|
1811
1811
|
}
|
|
@@ -1876,12 +1876,12 @@ class A {
|
|
|
1876
1876
|
*/
|
|
1877
1877
|
static async convertKMZ2GeoJSON(t, e = {}) {
|
|
1878
1878
|
var r;
|
|
1879
|
-
R.info("[%s] convert kmz to geojson (async)", e == null ? void 0 : e.requestId), typeof Buffer < "u" && Buffer.isBuffer(t) && (t =
|
|
1880
|
-
const n = await
|
|
1879
|
+
R.info("[%s] convert kmz to geojson (async)", e == null ? void 0 : e.requestId), typeof Buffer < "u" && Buffer.isBuffer(t) && (t = F.toArrayBuffer(t));
|
|
1880
|
+
const n = await F._parseZipEntries(t), s = n.get("doc.kml") ?? ((r = [...n.entries()].find(([i]) => i.toLowerCase().endsWith(".kml"))) == null ? void 0 : r[1]);
|
|
1881
1881
|
if (!s)
|
|
1882
1882
|
return R.warn("[%s] no .kml file found in kmz", e == null ? void 0 : e.requestId), T.featureCollection([]);
|
|
1883
1883
|
const o = new TextDecoder().decode(s);
|
|
1884
|
-
return
|
|
1884
|
+
return F.convertKML2GeoJSON(o, e);
|
|
1885
1885
|
}
|
|
1886
1886
|
/**
|
|
1887
1887
|
* 将 ZIP 文件中所有 .kml 文件合并转换为一个 GeoJSON FeatureCollection(异步)。
|
|
@@ -1893,12 +1893,12 @@ class A {
|
|
|
1893
1893
|
* @param options
|
|
1894
1894
|
*/
|
|
1895
1895
|
static async convertZIP2GeoJSON(t, e = {}) {
|
|
1896
|
-
R.info("[%s] convert zip to geojson (async)", e == null ? void 0 : e.requestId), typeof Buffer < "u" && Buffer.isBuffer(t) && (t =
|
|
1897
|
-
const n = await
|
|
1896
|
+
R.info("[%s] convert zip to geojson (async)", e == null ? void 0 : e.requestId), typeof Buffer < "u" && Buffer.isBuffer(t) && (t = F.toArrayBuffer(t));
|
|
1897
|
+
const n = await F._parseZipEntries(t), s = [];
|
|
1898
1898
|
for (const [o, r] of n) {
|
|
1899
1899
|
if (!o.toLowerCase().endsWith(".kml"))
|
|
1900
1900
|
continue;
|
|
1901
|
-
const i = new TextDecoder().decode(r), c = await
|
|
1901
|
+
const i = new TextDecoder().decode(r), c = await F.convertKML2GeoJSON(i, e);
|
|
1902
1902
|
s.push(...c.features);
|
|
1903
1903
|
}
|
|
1904
1904
|
return s.length === 0 ? (R.warn("[%s] no .kml files found in zip", e == null ? void 0 : e.requestId), this.convertSHP2GeoJSON(t, e)) : T.featureCollection(s);
|
|
@@ -1914,7 +1914,7 @@ class A {
|
|
|
1914
1914
|
static async convertSHP2GeoJSON(t, e = {}) {
|
|
1915
1915
|
R.info("[%s] convert shp zip to geojson", e == null ? void 0 : e.requestId);
|
|
1916
1916
|
try {
|
|
1917
|
-
typeof Buffer < "u" && Buffer.isBuffer(t) && (t =
|
|
1917
|
+
typeof Buffer < "u" && Buffer.isBuffer(t) && (t = F.toArrayBuffer(t));
|
|
1918
1918
|
const n = await J(t);
|
|
1919
1919
|
if (Array.isArray(n)) {
|
|
1920
1920
|
const s = n.flatMap((c) => c.features || []), o = b.utc(), r = (e == null ? void 0 : e.id) || o.valueOf().toString(), i = {
|
|
@@ -1941,7 +1941,7 @@ class A {
|
|
|
1941
1941
|
}
|
|
1942
1942
|
export {
|
|
1943
1943
|
K as AisHelper,
|
|
1944
|
-
|
|
1944
|
+
F as GeoJsonHelper,
|
|
1945
1945
|
v as LaneHelper,
|
|
1946
1946
|
d as LngLatHelper,
|
|
1947
1947
|
it as TropicalHelper
|
package/dist/index.umd.cjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
(function(w,L){typeof exports=="object"&&typeof module<"u"?L(exports,require("@turf/turf"),require("moment"),require("@log4js-node/log4js-api"),require("moment-timezone"),require("tz-lookup"),require("shpjs")):typeof define=="function"&&define.amd?define(["exports","@turf/turf","moment","@log4js-node/log4js-api","moment-timezone","tz-lookup","shpjs"],L):(w=typeof globalThis<"u"?globalThis:w||self,L(w["idm-plugin-rabbitmq"]={},w["@turf/turf"],w.moment,w["@log4js-node/log4js-api"],w["moment-timezone"],w["tz-lookup"],w.shpjs))})(this,function(w,L,b,V,ie,Q,Y){"use strict";function _(M){const e=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(M){for(const t in M)if(t!=="default"){const n=Object.getOwnPropertyDescriptor(M,t);Object.defineProperty(e,t,n.get?n:{enumerable:!0,get:()=>M[t]})}}return e.default=M,Object.freeze(e)}const p=_(L);class d{static guessTimeZoneOffset(e,t){e=d.convertToStdLng(e);const n=Q(t,e),s=b().tz(n).utcOffset();return d.roundPrecision(s/60,1)}static prettyTimeZoneOffset(e){let t=Math.floor(Math.abs(e)),n=Math.round((Math.abs(e)-t)*60);return n=n>9?n:`0${n}`,t=t>9?t:`0${t}`,e>0?`+${t}:${n}`:`-${t}:${n}`}static lng2pretty(e,t=6,n="H°M′"){e=d.convertToStdLng(e,t);let s="E";e<0&&(s="W"),e=Math.abs(e),n=n.toUpperCase();let o=e*3600,i,r,c,a,l,u;i=o%3600%60,n.indexOf("S")!==-1&&(o=o-i,r=d.padNumber(i,2,2)),c=o/60%60,n.indexOf("M")!==-1&&(n.indexOf("S")!==-1?a=d.roundPrecision(c,t).toString().padStart(2,"0"):a=d.padNumber(c,2,3),o=o-c*60),l=o/3600,n.indexOf("M")!==-1?u=d.roundPrecision(l,t).toString().padStart(3,"0"):u=d.padNumber(l,3,6),Number(r)>=60&&(a=Number(a)+1,r=0),Number(a)>=60&&(u=Number(u)+1,a=0);const h=`${n.replace(/S+/gi,r).replace(/M+/gi,a).replace(/H+/gi,u)}${s}`;return{direction:s,degree:d.roundPrecision(l,t),minute:d.roundPrecision(c,t),second:d.roundPrecision(i,t),pretty:h,S:r,M:a,H:u}}static lat2pretty(e,t=6,n="H°M′"){e=e%180;let s="N";e<0&&(s="S"),e=Math.abs(e),n=n.toUpperCase();let o=e*3600,i,r,c,a,l,u;i=o%3600%60,n.indexOf("S")!==-1&&(o=o-i,r=d.padNumber(i,2,2)),c=o/60%60,n.indexOf("M")!==-1&&(n.indexOf("S")!==-1?a=d.roundPrecision(c,t).toString().padStart(2,"0"):a=d.padNumber(c,2,3),o=o-c*60),l=o/3600,n.indexOf("M")!==-1?u=d.roundPrecision(l,t).toString().padStart(2,"0"):u=d.padNumber(l,2,6),Number(r)>=60&&(a=Number(a)+1,r=0),Number(a)>=60&&(u=Number(u)+1,a=0);const h=`${n.replace(/S+/gi,r).replace(/M+/gi,a).replace(/H+/gi,u)}${s}`;return{direction:s,degree:d.roundPrecision(l,t),minute:d.roundPrecision(c,t),second:d.roundPrecision(i,t),pretty:h,S:r,M:a,H:u}}static str2Lng(e,t=6){let n;if(isNaN(e)){e=d.strReplace(e,"LNG");const s=e[e.length-1].toUpperCase();e=e.substring(0,e.length-1).trim();const o=e.split(" ").filter(a=>a!=="").map(a=>Math.abs(Number(a)));let[i,r,c]=o;if(r=r||0,r=r>60?r/Math.pow(10,String(r).length-2):r,c=c||0,c=c>60?c/Math.pow(10,String(c).length-2):c,i>360&&!r){const a=this.roundPrecision(i/100,0);r=i-a*100,i=a}n=i+r/60+c/3600,s==="W"&&(n=n*-1)}else n=Number(e);return d.convertToStdLng(n,t)}static str2Lat(e,t=6){let n;if(isNaN(e)){e=d.strReplace(e,"LAT");const s=e[e.length-1].toUpperCase();e=e.substring(0,e.length-1).trim();const o=e.split(" ").filter(a=>a!=="").map(a=>Math.abs(Number(a)));let[i,r,c]=o;if(c=c||0,r=r||0,r=r>60?r/Math.pow(10,String(r).length-2):r,c=c>60?c/Math.pow(10,String(c).length-2):c,i>90&&!r){const a=this.roundPrecision(i/100,0);r=i-a*100,i=a}if(n=i+r/60+c/3600,n>90)throw new Error(`latitude out of range: ${e}${s}`);s==="S"&&(n=n*-1)}else n=Number(e);return d.roundPrecision(n,t)}static str2LngOrLat(e,t=6,n="LAT"){e=d.strReplace(e,n);const s=e[e.length-1].toUpperCase();return["N","S"].includes(s)?{lat:d.str2Lat(e,t)}:{lng:d.str2Lng(e,t)}}static convertToStdLng(e,t=6){return e>180?(e=e%360,e=e>180?e-360:e):e<-180&&(e=e%360,e=e<-180?e+360:e),d.roundPrecision(e,t)}static roundPrecision(e,t=6){const n=Number("1".padEnd(t+1,"0"));return Math.round(e*n)/n}static convertToMonotonicLng2(e){for(let t=1;t<e.length;t++)e[t][0]+=Math.round((e[t-1][0]-e[t][0])/360)*360;return e}static convertToMonotonicLng(e){for(let t=1;t<e.length;t++)e[t].lng+=Math.round((e[t-1].lng-e[t].lng)/360)*360;return e}static strReplace(e,t="LAT"){e=e.replace(/([0-9]+)\.([0-9]+\.[0-9]+)/g,"$1 $2").replace(/([0-9]+)-([0-9]+\.[0-9]+)/g,"$1 $2").replace(/°/," ").replace(/(\d+)-(\d?)/g,"$1 $2").replace(/'/g," ").replace(/′/g," ").replace(/"/g," ").replace(/∼/g," ").replace(/°/g," ").replace(/,/g,".").replace(/^ /g,"").replace(/ $/g,"").trim();const n=e[e.length-1].toUpperCase();if(!["N","S","E","W"].includes(n)){const s=e,o=Number(s.split(" ")[0]);if(isNaN(o))throw new Error(`invalid Lat/Lng: ${e}`);o>=90?e=`${s}E`:o<=-90?e=`${s}W`:["LAN","LNG"].includes(t==null?void 0:t.toUpperCase())?e=`${s}${o>0?"E":"W"}`:e=`${s}${o>0?"N":"S"}`}return e}static padNumber(e,t=2,n=2){const s=d.roundPrecision(e-Math.trunc(e),n),o=s>=1?Math.trunc(e+1).toString().padStart(t,"0"):Math.trunc(e).toString().padStart(t,"0");return s>=1?o:n>0?`${o}.${Math.trunc(s*Math.pow(10,n)).toString().padStart(n,"0")}`:o}}class K{static json2Str(e){const t=e.type?e.type[0].toUpperCase():"A";return`${e.lat}|${e.lng}|${e.positionTime}|${e.sog}|${e.cog}|${e.hdg}|${e.draught}|${t}|${JSON.stringify(e.meteo||{})}|${e.vendor}|${e.deleted}`}static str2Json(e){const[t,n,s,o,i,r,c,a,l,u,h]=e.split("|");return{lat:Number(t),lng:Number(n),positionTime:Number(s),sog:Number(o),cog:Number(i),hdg:Number(r),draught:isNaN(c)?null:Number(c),type:a,important:a!=="A",meteo:l?JSON.parse(l):void 0,vendor:u,deleted:h==="true"}}static inspectStoppages(e,t=1,n=!0){const s=e.at(0).positionTime<e.at(-1).positionTime;s||e.sort((c,a)=>c.positionTime-a.positionTime);const o=[];let i,r;for(let c=0;c<e.length-1;c++){const a=e[c];if(!(n&&["N","B","E","NOON","BOSP","EOSP"].includes(a.type))){for(let l=c+1;l<e.length;l++){const u=e[l-1],h=e[l];if(n&&["N","B","E","NOON","BOSP","EOSP"].includes(a.type))continue;const f=h.positionTime-u.positionTime;if(S.calculateDistance(h,u,!0,4)/(f/3600)<t)i||(i=a),l===e.length-1&&(r=h,c=l);else{i&&(r=e[l-1],c=l);break}}if((r==null?void 0:r.positionTime)>(i==null?void 0:i.positionTime)&&i){const l={start:{lat:i.lat,lng:i.lng,sog:i.sog,positionTime:i.positionTime,utc:b.unix(i.positionTime).utc().format()},end:{lat:r.lat,lng:r.lng,sog:r.sog,positionTime:r.positionTime,utc:b.unix(r.positionTime).utc().format()},duration:r.positionTime-i.positionTime},u=e.filter(f=>f.positionTime>=l.start.positionTime&&f.positionTime<=l.end.positionTime),h=S.divideAccordingToLng(u);l.distance=S.calculateRouteDistance(h),l.hours=Math.round(l.duration/3600*10)/10,l.avgSog=Math.round(l.distance/l.hours*10)/10,o.push(l)}i=void 0,r=void 0}}return s||e.sort((c,a)=>a.positionTime-c.positionTime),o}static inspectSummary(e,t,n){const s=b(t),o=b(n),i=e.filter(l=>l.positionTime>=s.unix()&&l.positionTime<=o.unix());let r=0,c=0;if(i.length>1)for(let l=0;l<i.length-1;l++){const u=i[l],h=i[l+1];r+=S.calculateDistance(u,h,!0,4),c+=Math.abs(h.positionTime-u.positionTime)}r=Math.round(r*100)/100,c=Math.round(c/3600*100)/100;const a=c?Math.round(r/c*100)/100:0;return{distance:r,interval:c,avgSpd:a}}}let z;try{z=V.getLogger("meteo")}catch{}finally{}const H=(()=>{const M=new Uint32Array(256);for(let e=0;e<256;e++){let t=e;for(let n=0;n<8;n++)t=t&1?3988292384^t>>>1:t>>>1;M[e]=t}return M})();function ee(M){let e=4294967295;for(let t=0;t<M.length;t++)e=H[(e^M[t])&255]^e>>>8;return(e^4294967295)>>>0}function te(M){const e=new TextEncoder,t=[],n=[];let s=0;for(const f of M){const m=e.encode(f.name),g=ee(f.data),T=new Uint8Array(30+m.length),v=new DataView(T.buffer);v.setUint32(0,67324752,!0),v.setUint16(4,20,!0),v.setUint16(8,0,!0),v.setUint32(14,g,!0),v.setUint32(18,f.data.length,!0),v.setUint32(22,f.data.length,!0),v.setUint16(26,m.length,!0),T.set(m,30),t.push({nameBytes:m,data:f.data,crc:g,offset:s}),s+=T.length+f.data.length,n.push(T,f.data)}const o=s,i=[];let r=0;for(const f of t){const m=new Uint8Array(46+f.nameBytes.length),g=new DataView(m.buffer);g.setUint32(0,33639248,!0),g.setUint16(4,20,!0),g.setUint16(6,20,!0),g.setUint16(10,0,!0),g.setUint32(16,f.crc,!0),g.setUint32(20,f.data.length,!0),g.setUint32(24,f.data.length,!0),g.setUint16(28,f.nameBytes.length,!0),g.setUint32(42,f.offset,!0),m.set(f.nameBytes,46),r+=m.length,i.push(m)}const c=new Uint8Array(22),a=new DataView(c.buffer);a.setUint32(0,101010256,!0),a.setUint16(8,t.length,!0),a.setUint16(10,t.length,!0),a.setUint32(12,r,!0),a.setUint32(16,o,!0);const l=n.reduce((f,m)=>f+m.length,0)+r+22,u=new Uint8Array(l);let h=0;for(const f of n)u.set(f,h),h+=f.length;for(const f of i)u.set(f,h),h+=f.length;return u.set(c,h),u}function J(M){let e="",t=M;for(;t>=0;)e=String.fromCharCode(65+t%26)+e,t=Math.floor(t/26)-1;return e}class S{static calculateBearing(e,t,n=!0,s=4){const o=p.points([[e.lng,e.lat],[t.lng,t.lat]]);let i;return n?i=p.rhumbBearing(o.features[0],o.features[1]):i=p.bearing(o.features[0],o.features[1]),i<0&&(i+=360),d.roundPrecision(i,s)}static calculateDistance(e,t,n=!0,s=4,o="nauticalmiles"){e={...e},t={...t},e.lng=d.convertToStdLng(e.lng,s),t.lng=d.convertToStdLng(t.lng,s);const i=p.points([[e.lng,e.lat],[t.lng,t.lat]]);let r;return n?r=p.rhumbDistance(i.features[0],i.features[1],{units:o}):r=p.distance(i.features[0],i.features[1],{units:o}),d.roundPrecision(r,s)}static calculateRouteDistance(e,t=4,n="nauticalmiles"){let s=0,o;for(const i of e)for(let r=0;r<i.length-1;r++){const c={lng:i[r][0],lat:i[r][1]};r===0&&o&&(s+=this.calculateDistance(o,c,!0,t,n));const a={lng:i[r+1][0],lat:i[r+1][1]};s+=this.calculateDistance(c,a,!0,t,n),o=a}return d.roundPrecision(s,t)}static calculateCoordinate(e,t,n,s="nauticalmiles",o=!0){const i=p.point([e.lng,e.lat]);let r;o?r=p.rhumbDestination(i,n,t,{units:s}):r=p.destination(i,n,t,{units:s});const c=r.geometry.coordinates;return{lng:d.convertToStdLng(c[0],8),lat:d.roundPrecision(c[1],8)}}static interpolateCoordinates(e,t,n,s=!0,o=!0,i="nauticalmiles"){const r=[],c=this.calculateBearing(e,t,!1),a=this.calculateDistance(e,t,!1,8,i);s&&r.push({lng:e.lng,lat:e.lat});let l=0;for(;l<a;)l+=n,l<a&&r.push(this.calculateCoordinate(e,c,l,i,!1));return o&&r.push({lng:t.lng,lat:t.lat}),r}static divideAccordingToLng(e,t=!1,n=!0){if((e==null?void 0:e.length)<2)return[];e=n?this.deduplicateCoordinates(e):e;let s=[];const o=[];let i,r;for(let c=0;c<e.length-1;c++){i=d.convertToStdLng(e[c].lng,8),r=d.convertToStdLng(e[c+1].lng,8),e[c].lat=d.roundPrecision(e[c].lat,8),e[c+1].lat=d.roundPrecision(e[c+1].lat,8),s.push([i,e[c].lat]);const a=i-r;if(Math.abs(a)>180){const l=d.convertToMonotonicLng2([[i,e[c].lat],[r,e[c+1].lat]]);let u,h;t?(u=p.lineString(l),h=p.lineString([[a>0?180:-180,89],[a>0?180:-180,-89]])):(u=p.greatCircle(l[0],l[1]),h=p.greatCircle([a>0?180:-180,89],[a>0?180:-180,-89]));const f=p.lineIntersect(u,h);let m;if(f.features.length){const g=p.getCoord(f.features[0]);m=d.roundPrecision(g[1],8)}else m=e[c].lat;a>0?(s.push([180-1e-6,m]),o.push([...s]),s=[],s.push([-(180-1e-6),m])):(s.push([-(180-1e-6),m]),o.push([...s]),s=[],s.push([180-1e-6,m]))}c===e.length-2&&s.push([r,e[c+1].lat])}return o.push(s),o}static deduplicateRoute(e){const t=[];for(const n of e){const s=n.reduce((o,i)=>(o.findIndex(r=>r[0]===i[0]&&r[1]===i[1])===-1&&o.push(i),o),[]);t.push(s)}return t}static deduplicateCoordinates(e){return e.reduce((t,n)=>(t.findIndex(s=>s.lat===n.lat&&s.lng===n.lng)===-1&&t.push(n),t),[])}static removeCoordinateFromRoute(e,t){e.lng=d.convertToStdLng(e.lng,8);for(const n of t)for(let s=n.length-1;s>=0;s--)d.roundPrecision(n[s][0],8)===e.lng&&d.roundPrecision(n[s][1],8)===d.roundPrecision(e.lat,8)&&n.splice(s,1);return t}static removeCoordinateFromWaypoints(e,t){e.lng=d.convertToStdLng(e.lng,8);for(let n=t.length-1;n>=0;n--)d.roundPrecision(t[n].lng,8)===e.lng&&d.roundPrecision(t[n].lat,8)===d.roundPrecision(e.lat,8)&&t.splice(n,1);return t}static mergeCoordinateToRoute(e,t){e.lng=d.convertToStdLng(e.lng,8);let n=Number.MAX_VALUE,s=0,o=0,i,r;return t.forEach((c,a)=>{for(let l=0;l<c.length-1;l++){const u={lng:c[l][0],lat:c[l][1]},h={lng:c[l+1][0],lat:c[l+1][1]},f=this.calculatePointToLineDistance(e,u,h);n>f&&(n=f,o=l,s=a,i=this.calculateDistance(u,e),r=this.calculateDistance(h,e))}}),i!==0&&r!==0?t[s].splice(o+1,0,[e.lng,e.lat]):i===0?t[s].splice(o,1,[e.lng,e.lat]):r===0&&t[s].splice(o+1,1,[e.lng,e.lat]),t}static appendCoordinateToRoute(e,t){e.lng=d.convertToStdLng(e.lng,8);const n=S.convertRouteToCoordinates(t);return n.push(e),S.divideAccordingToLng(n)}static unshiftCoordinateToRoute(e,t){const n=S.convertRouteToCoordinates(t);return n.unshift(e),S.divideAccordingToLng(n)}static mergeWaypointsToRoute(e,t){for(const n of e)t=this.mergeCoordinateToRoute(n,t);return t}static calculateRangeRoute(e,t,n){n=this.mergeWaypointsToRoute([e,t],n);const s=[];let o=0;return n.forEach(i=>{if(o===2)return;const r=[];for(const c of i){if(d.roundPrecision(t.lng,8)===d.roundPrecision(c[0],8)&&d.roundPrecision(t.lat,8)===d.roundPrecision(c[1],8)){r.push(c),o===0&&r.push([e.lng,e.lat]),o=2;break}o===1?r.push(c):d.roundPrecision(e.lng,8)===d.roundPrecision(c[0],8)&&d.roundPrecision(e.lat,8)===d.roundPrecision(c[1],8)&&(o=1,r.push(c))}r.length&&s.push(r)}),s}static calculateRangeWaypoints(e,t,n,s=[]){const o=this.convertRouteToCoordinates(n,0),i=this.mergeCoordinatesToWaypoints([e,t],o.length?o:s),r=i.findIndex(l=>d.roundPrecision(e.lng,8)===d.roundPrecision(l.lng,8)&&d.roundPrecision(e.lat,8)===d.roundPrecision(l.lat,8)),c=i.findIndex(l=>d.roundPrecision(t.lng,8)===d.roundPrecision(l.lng,8)&&d.roundPrecision(t.lat,8)===d.roundPrecision(l.lat,8));return i.filter((l,u)=>u>=r&&u<=c)}static calculateMinDistanceToRoute(e,t){let n=Number.MAX_VALUE,s=0,o=0;return t.forEach((i,r)=>{for(let c=0;c<i.length-1;c++){const a={lng:i[c][0],lat:i[c][1]},l={lng:i[c+1][0],lat:i[c+1][1]},u=this.calculatePointToLineDistance(e,a,l);n>u&&(n=u,s=c,o=r)}}),{minDist:n,segIndex:o,minIndex:s}}static calculateSubRoute(e,t){const n=S.convertRouteToCoordinates(t);S.mergeCoordinateToWaypoints(e,n,!0),t=S.divideAccordingToLng(n);const{segIndex:s,minIndex:o}=this.calculateMinDistanceToRoute({...e},t);e.lng=d.convertToStdLng(e.lng);const i=[];let r=!0;for(let c=s;c<t.length;c++)if(r){const a=[];a.push([e.lng,e.lat]);for(let l=o+1;l<t[c].length;l++)e.lng===t[c][l][0]&&e.lat===t[c][l][1]||a.push(t[c][l]);i.push(a),r=!1}else i.push([...t[c]]);return i}static calculateSubWaypoints(e,t){let n=Number.MAX_VALUE,s=0;for(let i=0;i<t.length-1;i++){const r=t[i],c=t[i+1];if(this.calculateDistance(e,r)===0)return t;if(this.calculateDistance(e,c)===0)return t.filter((l,u)=>u>0);const a=this.calculatePointToLineDistance(e,r,c);n>a&&(n=a,s=i)}e.lng=d.convertToStdLng(e.lng);const o=[e];for(let i=s+1;i<t.length;i++)o.push(t[i]);return o}static calculatePointToLineDistance(e,t,n,s={units:"nauticalmiles",method:"geodesic"}){e.lng=d.convertToStdLng(e.lng,8),t={...t},n={...n},t.lng=d.convertToStdLng(t.lng,8),n.lng=d.convertToStdLng(n.lng,8);const o=d.convertToMonotonicLng([t,n]);t=o[0],n=o[1];const i=p.lineString([[t.lng,t.lat],[n.lng,n.lat]]),r=p.pointToLineDistance(p.point([e.lng,e.lat]),i,s),c=p.pointToLineDistance(p.point([e.lng>0?e.lng-360:e.lng+360,e.lat]),i,s);return d.roundPrecision(Math.min(r,c),6)}static calculateWaypointsPropInRoute(e,t){t=this.mergeWaypointsToRoute(e,t);for(let n=0;n<e.length-1;n++){const s=e[n],o=e[n+1],i=this.calculateRangeRoute(s,o,t);n===0&&(s.distanceFromPrevious=0,s.distanceFromStart=0),o.distanceFromPrevious=this.calculateRouteDistance(i),o.distanceFromStart=d.roundPrecision((s.distanceFromStart||0)+o.distanceFromPrevious)}return e}static mergeCoordinatesToWaypoints(e,t,n=!0){for(const s of e)this.mergeCoordinateToWaypoints(s,t,n);return t}static mergeCoordinateToWaypoints(e,t,n=!0){e.lng=d.convertToStdLng(e.lng,8);let s=Number.MAX_VALUE,o=0,i=0,r=0;if(t.length<2)t.push(e);else{for(let c=0;c<t.length-1;c++){const a={lng:t[c].lng,lat:t[c].lat},l={lng:t[c+1].lng,lat:t[c+1].lat},u=this.calculatePointToLineDistance(e,a,l);s>=u&&(s=u,o=c,i=this.calculateDistance(a,e,!1,6),r=this.calculateDistance(l,e,!1,6))}i!==0&&r!==0?i<=s&&o===0?t.unshift(e):r<=s&&o===t.length-2?t.push(e):t.splice(o+1,0,e):i===0?n?t.splice(o,1,e):t.splice(o+1,0,e):r===0&&(n?t.splice(o+1,1,e):t.splice(o+1,0,e))}return t.map((c,a)=>{c.lng=d.convertToStdLng(c.lng);const l=t[a+1];if(l&&((c.bearing===null||c.bearing===void 0)&&((c.positionTime||0)>(l.positionTime||0)?c.bearing=this.calculateBearing(l,c,!0):c.bearing=this.calculateBearing(c,l,!0)),c.cog=c.cog||c.bearing,!c.sog&&c.positionTime&&l.positionTime)){const u=this.calculateDistance(c,l,!0),h=Math.abs(l.positionTime-c.positionTime)/3600;c.sog=d.roundPrecision(u/h,2)}return c})}static generateRouteAccordingToWaypoints(e,t=!0,n=!0){const s=[];for(let o=1;o<e.length;o++){const i=e[o-1],r=e[o];if(o===1&&s.push(i),r.gcToPrevious){const c=this.interpolateCoordinates(i,r,200,!1,!0,"nauticalmiles");s.push(...c)}else s.push(r)}return this.divideAccordingToLng(s,t,n)}static nearestCoordinateInRoute(e,t){const n=p.point([e.lng,e.lat]),o=this.convertRouteToCoordinates(t).map(a=>[a.lng,a.lat]),i=p.lineString(o),r=p.nearestPointOnLine(i,n),c=p.getCoord(r);return{lng:d.roundPrecision(c[0],8),lat:d.roundPrecision(c[1],8)}}static calculatePrevWaypoint(e,t){let n=0;this.mergeCoordinateToWaypoints(e,t);for(let s=0;s<t.length-1;s++){const o=t[s],i=t[s+1];if(this.calculateDistance(e,o)===0){n=s;break}if(this.calculateDistance(e,i)===0){n=s+1;break}}return t[n===0?0:n-1]}static calculateNextCoordinateAlongRoute(e,t,n,s="nauticalmiles"){var h;const o=e.speed||12,i=[];let r=[],c=!1,a=0,l=0,u;if(t&&n.length?(i.push(e),n.forEach((f,m)=>{if(c)r.push(f);else{const g=[];let T;for(let v=0;v<f.length;v++)if(u)g.push(f[v]);else{T={lng:f[v][0],lat:f[v][1]};const x=this.calculateDistance(e,T,!0,8,s);if(a+=x,a<t)l+=x,x&&i.push(T),e=T;else{if(l=t,a===t)u=T,g.push([u.lng,u.lat]);else{const N=a-t,y=this.calculateBearing(T,e);u=this.calculateCoordinate(T,y,N,s),g.push([u.lng,u.lat]),g.push([T.lng,T.lat])}c=!0}}g.length&&r.push(g),m===n.length-1&&!u&&(u=T)}})):(r=n,u={...e}),u)if(i.push(u),u.distanceFromPrevious=Math.round(l*1e4)/1e4,u.hourFromPrevious=Math.round(l/o*1e4)/1e4,((h=r[0])==null?void 0:h.length)>1){const f={lng:r[0][1][0],lat:r[0][1][1]};u.bearing=this.calculateBearing(u,f)}else u.bearing=0;return{coordinate:u,nextRoute:r,prevRoute:i}}static nearestCoordinateInLine(e,t,n){const s=d.convertToStdLng(e.lng,6),o=p.point([s,e.lat]),i=d.convertToStdLng(t.lng,6),r=d.convertToStdLng(n.lng,6),c=p.lineString([[i,t.lat],[r,n.lat]]),a=p.nearestPointOnLine(c,o),l=p.getCoord(a),u=d.roundPrecision(l[0],6),h=d.roundPrecision(l[1],6);return{lng:u,lat:h,inline:!(u===i&&h===t.lat)&&!(u===r&&h===n.lat)}}static convertRouteToCoordinates(e,t=0){const n=[];let s,o;return e.forEach(i=>{i.forEach(r=>{const c={lng:d.roundPrecision(r[0],8),lat:d.roundPrecision(r[1],8)};if(!o)n.push(c),o=c;else if(o.bearing===void 0||o.bearing===null)o.bearing=this.calculateBearing(o,c,!0);else{const a=this.calculateDistance(s,c,!0);a&&a>=t&&(s.bearing=this.calculateBearing(s,c,!0),n.push(s),o=s)}s=c})}),s&&n.push(s),n}static simplifyRouteToCoordinates(e,t,n=1){let s=this.convertRouteToCoordinates(e,n);return s=this.simplifyGCCoordinates(s,t),s}static simplifyGCCoordinates(e,t){t.forEach(s=>{this.mergeCoordinateToWaypoints(s,e,!0)});for(let s=1;s<t.length;s++){const o=t[s-1],i=t[s];if(i.gcToPrevious){const r=e.findIndex(a=>a.lng===o.lng&&a.lat===o.lat),c=e.findIndex(a=>a.lng===i.lng&&a.lat===i.lat);for(let a=c-1;a>r;a--)e.splice(a,1)}}let n=0;for(let s=1;s<e.length;s++){const o=e[s-1],i=e[s];i.gcToPrevious?(o.bearing=this.calculateBearing(o,i,!1),i.distanceFromPrevious=this.calculateDistance(o,i,!1)):(o.bearing=this.calculateBearing(o,i,!0),i.distanceFromPrevious=this.calculateDistance(o,i,!0)),n=d.roundPrecision(n+i.distanceFromPrevious),i.distanceFromStart=n}return e.map(s=>(s.lng=d.convertToStdLng(s.lng),s))}static calculateCenter(e){const t=[];for(const r of e)for(const c of r)t.push(c);const n=p.featureCollection([]),s=d.convertToMonotonicLng2(t);for(const r of s)n.features.push(p.point(r));const i=p.center(n).geometry.coordinates;return{lng:d.convertToStdLng(i[0],8),lat:d.roundPrecision(i[1],8)}}static calculateCenter2(e){const t=this.generateRouteAccordingToWaypoints(e);return this.calculateCenter(t)}static calculateBBox(e){const t=[];for(const o of e)for(const i of o)t.push(i);const n=d.convertToMonotonicLng2(t),s=p.lineString(n);return p.bbox(s)}static calculateBBox2(e){const t=this.generateRouteAccordingToWaypoints(e);return this.calculateBBox(t)}static simplifyCoordinates(e,t=1,n=180){const s=[];for(let o=1;o<e.length;o++){const i=e[o-1],r=e[o],c=e[o+1];let a=!1,l=!1;if((i.velocity||i.suspend||i.important||i.pilot||o===1)&&(a=!0,s.push(i)),r.gcToPrevious&&(a||(a=!0,s.push(i)),l=!0,s.push(r),o++),c){const u=S.calculateDistance(i,r,!0),h=S.calculateDistance(r,c,!0),f=S.calculateDistance(i,c,!0),m=(Math.pow(u,2)+Math.pow(h,2)-Math.pow(f,2))/(2*u*h);Math.round(Math.acos(m)*180/Math.PI)<n&&f>t&&!l&&(s.push(r),o++)}if(o>=e.length-1){const u=e.at(-1);u&&s.push(u)}}return s}static nearestTSPointInWaypoints(e,t,n){const s=b.unix(e),o=n.filter(i=>s.clone().subtract(t,"hour").unix()<=(i.positionTime||0)&&s.clone().add(t,"h").unix()>=(i.positionTime||0));return o.sort((i,r)=>(i.positionTime||0)-(r.positionTime||0)),o.at(-1)}static deadReckoning(e,t){var o,i,r,c;e>1e12&&(e=Math.round(e/1e3));const n=b.unix(e);let s=t.find(a=>a.positionTime===n.unix());if(!s){const a=(i=(o=t.filter(u=>(u==null?void 0:u.positionTime)<n.unix()))==null?void 0:o.sort((u,h)=>(u.positionTime||0)-(h.positionTime||0)))==null?void 0:i.at(-1),l=(c=(r=t.filter(u=>(u==null?void 0:u.positionTime)>n.unix()))==null?void 0:r.sort((u,h)=>(u.positionTime||0)-(h.positionTime||0)))==null?void 0:c.at(0);if(a&&l){const u=S.calculateBearing(a,l,!0),h=S.calculateDistance(a,l),f=(n.unix()-a.positionTime)/(l.positionTime-a.positionTime);s=S.calculateCoordinate(a,u,h*f),s.positionTime=n.unix(),s.utc=n.utc().format(),s.cog=u,s.sog=Math.round(h/((l.positionTime-a.positionTime)/3600)*100)/100}else s=a||l,s&&(s.utc=b.unix(s==null?void 0:s.positionTime).utc().format())}return s}static deadReckoningTime(e,t){t=JSON.parse(JSON.stringify(t)),t.sort((a,l)=>(a.positionTime||0)-(l.positionTime||0));let n=Number.MAX_SAFE_INTEGER,s=Number.MAX_SAFE_INTEGER;for(let a=0;a<t.length-1;a++){const l=t[a],u=t[a+1],h=S.calculatePointToLineDistance(e,l,u);h<n&&(n=h,s=a)}const o=t[s],i=t[s+1],r=S.calculateDistance(o,e),c=S.calculateDistance(i,e);if(r===0)e=o;else if(c===0)e=i;else{const a=o.positionTime||0,l=i.positionTime||0,u=S.calculateDistance(o,i);e.positionTime=Math.round(a+(l-a)*(r/u))}return e.utc=e.positionTime?b.unix(e.positionTime).utc().format():void 0,e.positionTime?e:void 0}static reverseRoute(e){const t=[];for(const n of e)t.push(n.reverse());return t}static reverseCoordinates(e){return e.reverse()}static xmlEscape(e){return e==null?"":String(e).trim().replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">").replace(/"/g,""").replace(/'/g,"'")}static waypoints2RTZ(e,t){const s=[];return s.push('<?xml version="1.0" encoding="UTF-8"?>'),s.push('<route xmlns="http://www.cirm.org/RTZ/1/2" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.2">'),s.push(` <routeInfo routeName="${S.xmlEscape(e)}"></routeInfo>`),s.push(...S.toRTZWaypoints(t,6)),s.push("</route>"),s.join(`
|
|
2
2
|
`)}static waypoints2RTZ10(e,t,n=!0){const o=[];return o.push('<?xml version="1.0" encoding="UTF-8"?>'),o.push('<route xmlns="http://www.cirm.org/RTZ/1/0" version="1.0">'),o.push(` <routeInfo routeName="${S.xmlEscape(e)}"></routeInfo>`),o.push(...S.toRTZWaypoints(t,6,n)),o.push("</route>"),o.join(`
|
|
3
3
|
`)}static toRTZWaypoints(e,t=6,n=!0){const s=[];s.push(" <waypoints>");for(let o=0;o<e.length;o++){const i=e[o],r=o+1,c=(i.lat??"").toFixed?i.lat.toFixed(t).padEnd(t+2,"0"):i.lat,a=(i.lng??"").toFixed?i.lng.toFixed(t).padEnd(t+2,"0"):i.lng,l=[`id="${r}"`,'revision="0"'];if(i.name&&l.push(`name="${S.xmlEscape(i.name)}"`),s.push(` <waypoint ${l.join(" ")}>`),s.push(` <position lat="${S.xmlEscape(c)}" lon="${S.xmlEscape(a)}" />`),o>0){const u=i.gcToPrevious?"Orthodrome":"Loxodrome";s.push(` <leg geometryType="${u}" />`)}if(n){const u=[];if(i.description&&u.push(` <description>${S.xmlEscape(i.description)}</description>`),i.utc)u.push(` <time>${S.xmlEscape(i.utc)}</time>`);else if(i.positionTime)try{u.push(` <time>${S.xmlEscape(b.unix(i.positionTime).utc().format())}</time>`)}catch{}i.cog!==void 0&&u.push(` <cog>${S.xmlEscape(i.cog)}</cog>`),i.sog!==void 0&&u.push(` <sog>${S.xmlEscape(i.sog)}</sog>`),u.length&&(s.push(" <extensions>"),s.push(...u),s.push(" </extensions>"))}s.push(" </waypoint>")}return s.push(" </waypoints>"),s}static waypoints2CSV(e,t,n){z.debug("keep name for waypoints2CSV for legacy compatibility only",e);const s=(n==null?void 0:n.precision)??6,o=t.some(T=>T.name),i=t.some(T=>T.description),r=t.some(T=>T.port!=null),c=t.some(T=>T.stbd!=null),a=t.some(T=>T.arrRad!=null),l=t.some(T=>T.speed!=null),u=t.some((T,v)=>v>0&&T.gcToPrevious!=null),h=t.some(T=>T.bearing!=null),f=t.some(T=>T.distanceFromPrevious!=null),m=["WPT No.","Latitude","Longitude"];o&&m.push("Name"),i&&m.push("Description"),u&&m.push("Leg"),h&&m.push("Bearing[deg]"),f&&m.push("Distance[NM]"),l&&m.push("Speed[kn]"),r&&m.push("PORT XTD[NM]"),c&&m.push("STBD XTD[NM]"),a&&m.push("Arr.Rad[NM]");const g=[];g.push(m.map(T=>S.csvEscapeField(T)).join(","));for(let T=0;T<t.length;T++){const v=t[T],x=[];x.push((T+1).toString()),x.push(v.lat.toFixed(s)),x.push(v.lng.toFixed(s)),o&&x.push(v.name??""),i&&x.push(v.description??""),u&&x.push(T===0?"":v.gcToPrevious?"GC":"RL"),h&&x.push(v.bearing!=null?String(v.bearing):""),f&&x.push(v.distanceFromPrevious!=null?String(v.distanceFromPrevious):""),l&&x.push(v.speed!=null?String(v.speed):""),r&&x.push(v.port!=null?String(v.port):""),c&&x.push(v.stbd!=null?String(v.stbd):""),a&&x.push(v.arrRad!=null?String(v.arrRad):""),g.push(x.map(N=>S.csvEscapeField(N)).join(","))}return g.join(`
|
|
4
|
-
`)}static waypoints2XLSX(e,t,n){const s=(n==null?void 0:n.precision)??6,o=e||"Route",i=t.some(P=>P.name),r=t.some(P=>P.description),c=t.some(P=>P.port!=null),a=t.some(P=>P.stbd!=null),l=t.some(P=>P.arrRad!=null),u=t.some(P=>P.speed!=null),h=t.some((P,I)=>I>0&&P.gcToPrevious!=null),f=t.some(P=>P.bearing!=null),m=t.some(P=>P.distanceFromPrevious!=null),g=["WPT No.","Latitude","Longitude"];i&&g.push("Name"),r&&g.push("Description"),h&&g.push("Leg"),f&&g.push("Bearing[deg]"),m&&g.push("Distance[NM]"),u&&g.push("Speed[kn]"),c&&g.push("PORT XTD[NM]"),a&&g.push("STBD XTD[NM]"),l&&g.push("Arr.Rad[NM]");const T=P=>P==null?"":String(P).replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">").replace(/"/g,""");let x=`<row r="1">${g.map((P,I)=>`<c r="${J(I)}1" s="1" t="inlineStr"><is><t>${T(P)}</t></is></c>`).join("")}</row>`;for(let P=0;P<t.length;P++){const I=t[P],B=P+2,j=[],G=(q,W)=>j.push(`<c r="${J(q)}${B}"><v>${W}</v></c>`),
|
|
4
|
+
`)}static waypoints2XLSX(e,t,n){const s=(n==null?void 0:n.precision)??6,o=e||"Route",i=t.some(P=>P.name),r=t.some(P=>P.description),c=t.some(P=>P.port!=null),a=t.some(P=>P.stbd!=null),l=t.some(P=>P.arrRad!=null),u=t.some(P=>P.speed!=null),h=t.some((P,I)=>I>0&&P.gcToPrevious!=null),f=t.some(P=>P.bearing!=null),m=t.some(P=>P.distanceFromPrevious!=null),g=["WPT No.","Latitude","Longitude"];i&&g.push("Name"),r&&g.push("Description"),h&&g.push("Leg"),f&&g.push("Bearing[deg]"),m&&g.push("Distance[NM]"),u&&g.push("Speed[kn]"),c&&g.push("PORT XTD[NM]"),a&&g.push("STBD XTD[NM]"),l&&g.push("Arr.Rad[NM]");const T=P=>P==null?"":String(P).replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">").replace(/"/g,""");let x=`<row r="1">${g.map((P,I)=>`<c r="${J(I)}1" s="1" t="inlineStr"><is><t>${T(P)}</t></is></c>`).join("")}</row>`;for(let P=0;P<t.length;P++){const I=t[P],B=P+2,j=[],G=(q,W)=>j.push(`<c r="${J(q)}${B}"><v>${W}</v></c>`),U=(q,W)=>j.push(`<c r="${J(q)}${B}" t="inlineStr"><is><t>${T(W)}</t></is></c>`),O=(q,W)=>{W!=null?G(q,W):U(q,"")};G(0,P+1),U(1,d.lat2pretty(I.lat,s).pretty),U(2,d.lng2pretty(I.lng,s).pretty);let R=3;i&&(U(R,I.name??""),R++),r&&(U(R,I.description??""),R++),h&&(U(R,P===0?"":I.gcToPrevious?"GC":"RL"),R++),f&&(O(R,I.bearing),R++),m&&(O(R,I.distanceFromPrevious),R++),u&&(O(R,I.speed),R++),c&&(O(R,I.port),R++),a&&(O(R,I.stbd),R++),l&&(O(R,I.arrRad),R++),x+=`<row r="${B}">${j.join("")}</row>`}const N="0."+"0".repeat(s),y='<?xml version="1.0" encoding="UTF-8" standalone="yes"?><worksheet xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main"><sheetData>'+x+"</sheetData></worksheet>",C='<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Types xmlns="http://schemas.openxmlformats.org/package/2006/content-types"><Default Extension="rels" ContentType="application/vnd.openxmlformats-package.relationships+xml"/><Default Extension="xml" ContentType="application/xml"/><Override PartName="/xl/workbook.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml"/><Override PartName="/xl/worksheets/sheet1.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml"/><Override PartName="/xl/styles.xml" ContentType="application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml"/></Types>',k='<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships"><Relationship Id="rId1" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument" Target="xl/workbook.xml"/></Relationships>',Z='<?xml version="1.0" encoding="UTF-8" standalone="yes"?><workbook xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main" xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"><sheets><sheet name="'+T(o)+'" sheetId="1" r:id="rId1"/></sheets></workbook>',E='<?xml version="1.0" encoding="UTF-8" standalone="yes"?><Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships"><Relationship Id="rId1" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet" Target="worksheets/sheet1.xml"/><Relationship Id="rId2" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles" Target="styles.xml"/></Relationships>',X='<?xml version="1.0" encoding="UTF-8" standalone="yes"?><styleSheet xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main"><numFmts count="1"><numFmt numFmtId="164" formatCode="'+N+'"/></numFmts><fonts count="2"><font><sz val="11"/><name val="Arial"/></font><font><b/><sz val="11"/><name val="Arial"/></font></fonts><fills count="2"><fill><patternFill patternType="none"/></fill><fill><patternFill patternType="gray125"/></fill></fills><borders count="2"><border><left/><right/><top/><bottom/><diagonal/></border><border><bottom style="thin"><color auto="1"/></bottom></border></borders><cellStyleXfs count="1"><xf/></cellStyleXfs><cellXfs count="3"><xf/><xf fontId="1" fillId="0" borderId="1" applyFont="1" applyBorder="1"/><xf numFmtId="164" fontId="0" applyNumberFormat="1"/></cellXfs></styleSheet>',F=new TextEncoder;return te([{name:"[Content_Types].xml",data:F.encode(C)},{name:"_rels/.rels",data:F.encode(k)},{name:"xl/workbook.xml",data:F.encode(Z)},{name:"xl/_rels/workbook.xml.rels",data:F.encode(E)},{name:"xl/worksheets/sheet1.xml",data:F.encode(y)},{name:"xl/styles.xml",data:F.encode(X)}])}static csvEscapeField(e){if(e==null)return"";const t=String(e);return t.includes(",")||t.includes('"')||t.includes(`
|
|
5
5
|
`)||t.includes("\r")?`"${t.replace(/"/g,'""')}"`:t}static decimalToNmeaDm(e,t){const n=Math.abs(e),s=Math.floor(n),o=(n-s)*60,i=t?`${s.toString().padStart(2,"0")}${o.toFixed(2).padStart(5,"0")}`:`${s.toString().padStart(3,"0")}${o.toFixed(2).padStart(5,"0")}`,r=t?e>=0?"N":"S":e>=0?"E":"W";return{dm:i,dir:r}}static nmeaChecksum(e){let t=0;for(let n=0;n<e.length;n++)t^=e.charCodeAt(n);return t.toString(16).toUpperCase().padStart(2,"0")}static waypoints2NMEA(e){const t=[];for(let n=0;n<e.length;n++){const s=e[n],o=S.decimalToNmeaDm(s.lat,!0),i=S.decimalToNmeaDm(s.lng,!1),r=s.name?String(s.name).slice(0,6):`WPT${(n+1).toString().padStart(3,"0")}`,c=`GPWPL,${o.dm},${o.dir},${i.dm},${i.dir},${r}`,a=S.nmeaChecksum(c);t.push(`$${c}*${a}`)}return t.join(`\r
|
|
6
|
-
`)}static coordinatesSummary(e,t=3){if(e.length>1){const n=e[0],s=e[e.length-1],o=(n==null?void 0:n.positionTime)<(s==null?void 0:s.positionTime)?b.unix(n==null?void 0:n.positionTime):b.unix(s==null?void 0:s.positionTime),i=(n==null?void 0:n.positionTime)>(s==null?void 0:s.positionTime)?b.unix(n==null?void 0:n.positionTime):b.unix(s==null?void 0:s.positionTime),r=Math.round(i.diff(o,"hours",!0)*100)/100,c=this.generateRouteAccordingToWaypoints(e,!0,!0),a=this.calculateRouteDistance(c),u=K.inspectStoppages(e,t).reduce((f,m)=>(f.duration+=m.duration,f.distance+=m.distance,f),{hours:0,distance:0,spd:0,duration:0});u.hours=Math.round(u.duration/3600*100)/100,u.distance=Math.round(u.distance*100)/100,u.spd=u.hours?Math.round(u.distance/u.hours*100)/100:0;const h=r?Math.round((a-u.distance)/(r-u.hours)*100)/100:0;return{begin:o.utc().format(),end:i.utc().format(),distance:Math.round((a-u.distance)*100)/100,hours:Math.round((r-u.hours)*100)/100,avgSpeed:h,stoppage:u}}return{begin:void 0,end:void 0,distance:0,hours:0,avgSpeed:0}}static pickUTCSampleFromSpeed(e,t){var l,u,h;if(!((u=(l=t==null?void 0:t.sample)==null?void 0:l.hours)!=null&&u.length))return{routes:[],hour:void 0};const n=t.sample.hours.at(0),s=b.utc(e),o=b.utc(t.eta),i=s.isAfter(o)?o:s;let r=t.sample.all.find(f=>f.eta===i.format());if(!r){const f=t.sample.all.filter(C=>b.utc(C.eta).isBefore(i)).at(-1),m=this.calculateSubRoute(f,t.route);r=(h=this.calculateNextCoordinateAlongRoute(f,f.speed*i.diff(b(f.etd),"hours",!0),m))==null?void 0:h.coordinate;const{cFactor:g,cog:T,wxFactor:v,meteo:x}=f,N=Math.round(r.distanceFromPrevious*1e4)/1e4,y=Math.round((N+f.distanceFromStart)*1e4)/1e4;r={...r,cFactor:g,cog:T,speed:f.speed,wxFactor:v,distanceFromStart:y,distanceFromPrevious:N,meteo:x,eta:i.format(),etd:i.format()}}r.distanceToGo=Math.round((t.distance-r.distanceFromStart)*100)/100,r.timeToGo=Math.round(o.diff(r.etd,"hours",!0)*100)/100;const c=this.calculateRangeWaypoints(n,r,t.route);return{routes:this.generateRouteAccordingToWaypoints(c),hour:r}}static pickUTCSampleFromRoute(e,t,n){var f;const s=this.calculateSubRoute(t,n),o=this.calculateRouteDistance(s),i=o/t.speed,r=b.utc(e),c=b(t.etd),a=(f=this.calculateNextCoordinateAlongRoute(t,t.speed*r.diff(b(t.etd),"hours",!0),s))==null?void 0:f.coordinate;a.speed=t.speed;const l=c.clone().add(a.hourFromPrevious,"hour");a.eta=Math.abs(l.diff(r,"second"))<2?r.format():l.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(i,"hour").diff(b(a.etd),"hour")*100)/100;const u=this.calculateRangeWaypoints(t,a,n);return{routes:this.generateRouteAccordingToWaypoints(u),hour:a}}static includedAngle(e,t){z==null||z.debug("calculate bearing via: %j",{bearing:e,degree:t});let n=Math.abs(e%360-(t%360||0));return n=n>180?360-n:n,n}}let $;try{$=V.getLogger("vessel")}catch{}finally{}class ne{static convert2Geojson(e){var n,s,o;const t=p.featureCollection([]);for(const i of e){const r=(n=i.history)==null?void 0:n[0];if(i.forecasts){r&&r.wind&&(r.wind.kts=r.kts);for(const c of i.forecasts){let a;const l=[],u=[],h=b(c.date).utc(),f=`${i.name}-${c.model}`;for(const g in c==null?void 0:c.hours){const T=c.hours[g];a=a||T;const v=h.clone().add(Number(g),"hour"),x=p.point([T.lng,T.lat],{model:c.model,name:i.name,nameCn:i.nameCn,date:v.format(),hour:Number(g),format:v.format("MMM-DD/HHmm[Z]"),pressure:T.pressure>1e4?d.roundPrecision(T.pressure/100,0):d.roundPrecision(T.pressure,0),gusts:T.gusts,wind:T.wind||{},movement:T.movement,category:f,type:"forecast"});u.push(x),l.push(x.geometry.coordinates)}const m={kts:void 0,deg:void 0};if(r){const g=b(r.updated).utc();if(a){const v=S.calculateDistance(r,a),x=b(a.utc||a.updated).diff(g,"h",!0);m.kts=Math.round(v/x*100)/100,m.deg=S.calculateBearing(r,a,!0,0)}const T=p.point([r.lng,r.lat],{model:c.model,name:i.name,nameCn:i.nameCn,date:g.format(),hour:0,format:g.format("MMM-DD/HHmm[Z]"),pressure:r.pressure>1e4?d.roundPrecision((r==null?void 0:r.pressure)/100,0):d.roundPrecision(r.pressure,0),wind:r.wind,movement:m,category:f,type:"forecast",important:!0});u.unshift(T),l.unshift(T.geometry.coordinates)}if(t.features.push(...u),(l==null?void 0:l.length)>1){const g=p.lineString(d.convertToMonotonicLng2(l),{date:(r==null?void 0:r.updated)||(h==null?void 0:h.format()),id:i.id||i.name,model:c.model,name:i.name,category:f,type:"forecast",movement:m});t.features.push(g)}}}if(t.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),(s=i.history)!=null&&s.length){const c=[],a=b(r==null?void 0:r.updated).utc(),l=b((o=i.history)==null?void 0:o.at(-1).updated).utc(),u=a.diff(l,"h")%24>2?24:12;for(const h of i.history){const f=b(h.updated).utc(),m=f.isSameOrBefore(a)||f.isSame(l);m&&a.add(-u,"h");const g=p.point([h.lng,h.lat],{name:i.name,nameCn:i.nameCn,date:f.format(),format:f.format("MMM-DD/HHmm[Z]"),pressure:h.pressure>1e4?d.roundPrecision(h.pressure/100,0):d.roundPrecision(h.pressure,0),kts:h.kts,level:h.type,type:"history",category:`${i.name}-history`,wind:h.wind,movement:h.movement,important:m});t.features.push(g),c.push(g.geometry.coordinates)}if(c.length===1&&c.push(c[0]),c.length>1){const h=p.lineString(d.convertToMonotonicLng2(c),{name:i.name,type:"history",updated:r==null?void 0:r.updated,pressure:(r==null?void 0:r.pressure)>1e4?d.roundPrecision((r==null?void 0:r.pressure)/100,0):d.roundPrecision(r==null?void 0:r.pressure,0),kts:r==null?void 0:r.kts,level:r==null?void 0:r.type});t.features.push(h)}}}return t}static interpolate(e,t=3){var o,i,r,c;const n=(o=e==null?void 0:e.data)==null?void 0:o.features.filter(a=>a.geometry.type==="LineString"&&a.properties.type==="forecast"),s=[];for(const a of n){const l=a.properties.name,u=a.properties.model,h=a.properties.showCircle,f=a.properties.disabled,m=b(a.properties.date).utc();let g=t*60;const T=(i=e==null?void 0:e.data)==null?void 0:i.features.filter(N=>N.geometry.type==="Point"&&N.properties.type==="forecast"&&N.properties.category===`${l}-${u}`);let v,x=m.clone().add(g,"minute").set({minute:0,second:0,millisecond:0});for(;v=this.pickIndex(T,x),v<=T.length-1;){if(v>0){const N=T[v],y=v===0?void 0:T[v-1],C=(g/60-((r=y==null?void 0:y.properties)==null?void 0:r.hour))/(N.properties.hour-((c=y==null?void 0:y.properties)==null?void 0:c.hour)),k=this.computeNumber(y==null?void 0:y.geometry.coordinates[0],N.geometry.coordinates[0],C),Z=this.computeNumber(y==null?void 0:y.geometry.coordinates[1],N.geometry.coordinates[1],C),U=p.point([k,Z],{name:l,model:u,category:N==null?void 0:N.properties.category,date:x.format(),format:x.format("MMM-DD/HHmm[Z]"),gusts:this.computeNumber(y==null?void 0:y.properties.gusts,N.properties.gusts,C),hour:this.computeNumber(y==null?void 0:y.properties.hour,N.properties.hour,C),movement:this.computeNumber(y==null?void 0:y.properties.movement,N.properties.movement,C),pressure:this.computeNumber(y==null?void 0:y.properties.pressure,N.properties.pressure,C),wind:this.computeNumber(y==null?void 0:y.properties.wind,N.properties.wind,C),type:"forecast",disabled:f,showCircle:h});s.push(U)}g+=t*60,x=m.clone().add(g,"minute").set({minute:0,second:0,millisecond:0})}}return s}static accelPassageAt(e,t){const{t1:n,t2:s,hr:o,hours:i}=this.tropicalCenterTwin(e,24,t);return{t1:n,t2:s,hr:o,hours:i}}static diversionPassageAt(e,t,n,s={}){const{t1:o,t2:i,hr:r,hours:c}=this.tropicalCenterTwin(t,24,s);if(o&&i){if(!s.debug){const m=S.calculateDistance(e,o),g=S.calculateDistance(e,i);if(m>2*n&&g>2*n)return $==null||$.info("[%s] the distance between from and t1(%d) and t2(%d) is enough, no need diversion: %j",s.requestId,m,g,{from:e,t1:o,t2:i,hr:r}),{}}const a=S.calculateBearing(e,o),l=S.calculateBearing(o,i),u=Math.abs(a-l);let h=0;u<180?h=u+90:u>=180&&(h=u-90);const f=S.calculateCoordinate(o,h,n);return $==null||$.info("[%s] the right tangent position: %j",s.requestId,{from:e,t1:o,t2:i,radius:n,bearing1:a,bearing2:l,right:f}),{at:f,t1:o,t2:i,hr:Number(r),hours:c}}return{}}static driftPassageAt(e,t,n,s={}){const{t1:o,t2:i,hr:r,hours:c}=this.tropicalCenterTwin(t,24,s);if(o&&i){if(!s.debug){const f=S.calculateDistance(e,o),m=S.calculateDistance(e,i);if(f>2*n&&m>2*n)return $==null||$.info("[%s] the distance between from and t1(%d) and t2(%d) is enough, no need drifting: %j",s.requestId,f,m,{from:e,t1:o,t2:i,hr:r}),{}}const a=S.calculateBearing(e,o),l=S.calculateBearing(o,i),u=S.calculateDistance(e,o);return{at:S.calculateCoordinate(o,a-l+180,n<u?n:u),t1:o,t2:i,hr:Number(r),hours:c}}else return $==null||$.info("[%s] no need drift: %j",s.requestId,{from:e,t1:o,t2:i,hr:r}),{}}static tropicalCenterTwin(e,t=24,n={}){var l,u,h,f,m;let s={};(l=e.forecasts)==null||l.forEach(g=>{s={...g.hours,...s}});const o=((u=e==null?void 0:e.history)==null?void 0:u[0])||(s==null?void 0:s[(h=Object.keys(s))==null?void 0:h[0]]);$==null||$.info("[%s] the first tropical center: %j",n.requestId,o);let i=(f=Object.keys(s||{}).filter(g=>Number(g)<=(t<0?24:t)))==null?void 0:f.at(-1);i||(i=(m=Object.keys(s||{}).filter(g=>Number(g)<=(t<0?24:2*t)))==null?void 0:m.at(-1));const r=s==null?void 0:s[i||-1];$==null||$.info("[%s] the second tropical center: %j in %d hrs",n.requestId,r,i);const c=Object.keys(s||{}).filter(g=>Number(g)<=Number(i)),a={0:o};for(const g of c)a[g]=s[g];return{t1:o,t2:r,hr:Number(i),hours:a}}static pickIndex(e,t){let n=0;for(const s of e){if(b(s.properties.date).isAfter(t))return n===0?-1:n;n++}return n}static computeNumber(e,t,n){if(e)if(t){if(isNaN(e)&&isNaN(t)&&typeof e!="string"&&typeof t!="string"){const s={};for(const o in e)s[o]=this.computeNumber(e[o],t[o],n);return s}return Math.round((e+(t-e)*n)*100)/100}else return e;else return t}}typeof globalThis<"u"&&typeof globalThis.Buffer>"u"&&(globalThis.Buffer={isBuffer(M){return M instanceof Uint8Array},from(M,e){if(typeof M=="string")return new TextEncoder().encode(M);if(M instanceof ArrayBuffer)return new Uint8Array(M);if(Array.isArray(M))return new Uint8Array(M);throw new TypeError("Buffer.from: unsupported source type")}});let D;try{D=V.getLogger("meteo")}catch{}finally{}function se(){if(typeof DOMParser<"u")return new DOMParser;const{JSDOM:M}=require("jsdom"),{DOMParser:e}=new M("").window;return new e}class F{static toArrayBuffer(e){return e.buffer.slice(e.byteOffset,e.byteOffset+e.byteLength)}static drawCircle(e,t,n,s={}){const o=(s==null?void 0:s.steps)??64,i=(s==null?void 0:s.units)??"nauticalmiles",r=(s==null?void 0:s.properties)??{},c=p.point([e,t]),a=p.destination(c,n,90,{units:i}),l=b.utc();r.id=(s==null?void 0:s.id)||l.valueOf().toString();const u="circle";return r.name=(s==null?void 0:s.name)||`${u}_${l.format()}`,r.radius=n,r.center=[e,t],r.end=a.geometry.coordinates.map(h=>d.roundPrecision(h,9)),r.units=i,r.steps=o,r.shape="circle",D.info("[%s] draw circle with %j",s==null?void 0:s.requestId,r),p.circle(c,n,{steps:o,units:i,properties:r})}static drawRect(e,t,n={}){const s=(n==null?void 0:n.properties)??{},o=b.utc();s.id=(n==null?void 0:n.id)||o.valueOf().toString();const i="rect";s.name=(n==null?void 0:n.name)||`${i}_${o.format()}`,s.start=e.map(l=>d.roundPrecision(l,9)),s.end=t.map(l=>d.roundPrecision(l,9)),s.shape="rect",D.info("[%s] draw rect with %j",n==null?void 0:n.requestId,s);const[r,c]=d.convertToMonotonicLng2([e,t]),a=[Math.min(r[0],c[0]),Math.min(r[1],c[1]),Math.max(r[0],c[0]),Math.max(r[1],c[1])];return p.bboxPolygon(a,{properties:s})}static drawLine(e,t={}){const n=(t==null?void 0:t.properties)??{},s=b.utc();n.id=(t==null?void 0:t.id)||s.valueOf().toString();const o="line";n.name=(t==null?void 0:t.name)||`${o}_${s.format()}`,n.shape="line",D.info("[%s] draw line with %j",t==null?void 0:t.requestId,n);const i=d.convertToMonotonicLng2(e);return p.lineString(i,n)}static drawPolygon(e,t={}){const n=(t==null?void 0:t.properties)??{},s=b.utc();n.id=(t==null?void 0:t.id)||s.valueOf().toString();const o="polygon";n.name=(t==null?void 0:t.name)||`${o}_${s.format()}`,n.coordinates=e.map(r=>r.map(c=>d.roundPrecision(c,9))),n.shape="polygon",D.info("[%s] draw polygon with %j",t==null?void 0:t.requestId,n);const i=d.convertToMonotonicLng2(e);return p.polygon([i],n)}static drawPoint(e,t,n={}){const s=(n==null?void 0:n.properties)??{},o=b.utc();s.id=(n==null?void 0:n.id)||o.valueOf().toString();const i="point";return s.name=(n==null?void 0:n.name)||`${i}_${o.format()}`,s.shape="point",D.info("[%s] draw point with %j",n==null?void 0:n.requestId,s),p.point([t,e],s)}static parseCircle(e,t={}){var s,o;D.info("[%s] parse circle with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="circle"){const i=b.utc();n.id=(n==null?void 0:n.id)||i.valueOf().toString();const r=n==null?void 0:n.id,c=((s=n==null?void 0:n.center)==null?void 0:s.length)==2?p.point(n.center):p.centroid(e);let a="center";c.properties={id:`${a}_${r}`,parentId:r,name:a};const l=(n==null?void 0:n.units)||"nauticalmiles";let u=n==null?void 0:n.radius;if(!u){const m=p.polygonToLine(e);u=p.pointToLineDistance(c,m,{units:l})}a="end";const h=((o=n==null?void 0:n.end)==null?void 0:o.length)==2?p.point(n.end):p.destination(c,u,90,{units:l});h.properties={id:`${a}_${r}`,parentId:r,name:a,radius:u,units:l};const f=p.lineString([c.geometry.coordinates,h.geometry.coordinates]);return a="edge",f.properties={id:`${a}_${r}`,parentId:r,name:a,radius:u,units:l},p.featureCollection([c,h,f,e])}else return D.warn("[%s] not a orm-std circle, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static parseRect(e,t={}){D.info("[%s] parse rect with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="rect"){const s=b.utc();n.id=(n==null?void 0:n.id)||s.valueOf().toString();const o=n==null?void 0:n.id,i=e.geometry.coordinates[0],c=["sw","nw","ne","se"].map((a,l)=>{const u=p.point(i[l]);return u.properties={id:`${a}_${o}`,parentId:o,name:a},u});return p.featureCollection([...c,e])}else return D.warn("[%s] not a orm-std rect, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static parseLine(e,t={}){D.info("[%s] parse line with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="line"){const s=b.utc();n.id=(n==null?void 0:n.id)||s.valueOf().toString();const o=n==null?void 0:n.id,r=e.geometry.coordinates.map((c,a)=>{const l=`point_${a}`,u=p.point(c);return u.properties={id:`${l}_${o}`,parentId:o,name:l,index:a},u});return p.featureCollection([...r,e])}else return D.warn("[%s] not a orm-std line, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static parsePolygon(e,t={}){D.info("[%s] parse polygon with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="polygon"){const s=b.utc();n.id=(n==null?void 0:n.id)||s.valueOf().toString();const o=n==null?void 0:n.id,r=e.geometry.coordinates[0].map((c,a)=>{const l=p.point(c),u=`corner_${a}`;return l.properties={id:`${u}_${o}`,parentId:o,name:u,index:a},l});return p.featureCollection([...r,e])}else return D.warn("[%s] not a orm-std polygon, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static _inflateRawSync(e){var t;if(typeof process<"u"&&((t=process.versions)!=null&&t.node)){const n=require("zlib");return new Uint8Array(n.inflateRawSync(Buffer.from(e)))}throw new Error("Sync inflate is not supported in browser; use the async convertKMZ2GeoJSONAsync / convertZIP2GeoJSONAsync instead")}static async _parseZipEntries(e){var h;const t=new Uint8Array(e),n=t.buffer.slice(t.byteOffset,t.byteOffset+t.byteLength),s=new DataView(n),o=new Uint8Array(n),i=new Map;let r=-1;for(let f=n.byteLength-22;f>=0;f--)if(s.getUint32(f,!0)===101010256){r=f;break}if(r<0)throw new Error("Invalid ZIP file: EOCD not found");s.getUint16(r+8,!0);const c=s.getUint32(r+12,!0),a=s.getUint32(r+16,!0);let l=a;const u=a+c;for(;l<u;){if(s.getUint32(l,!0)!==33639248)throw new Error(`Invalid ZIP file: Central Directory signature mismatch at offset ${l}`);const m=s.getUint16(l+10,!0),g=s.getUint32(l+20,!0),T=s.getUint16(l+28,!0),v=s.getUint16(l+30,!0),x=s.getUint16(l+32,!0),N=s.getUint32(l+42,!0),y=o.slice(l+46,l+46+T),C=new TextDecoder().decode(y),k=s.getUint16(N+26,!0),Z=s.getUint16(N+28,!0),U=N+30+k+Z,X=o.slice(U,U+g);if(m===0)i.set(C,X);else if(m===8){if(typeof DecompressionStream<"u"){const A=new DecompressionStream("deflate-raw"),P=A.writable.getWriter(),I=A.readable.getReader();P.write(X),P.close();const B=[];let j=0;for(;;){const{done:O,value:R}=await I.read();if(O)break;B.push(R),j+=R.length}const G=new Uint8Array(j);let E=0;for(const O of B)G.set(O,E),E+=O.length;i.set(C,G)}else if(typeof process<"u"&&((h=process.versions)!=null&&h.node))try{i.set(C,F._inflateRawSync(X))}catch{}}l+=46+T+v+x}return i}static async convertKML2GeoJSON(e,t={}){var r,c;D.info("[%s] convert kml to geojson",t==null?void 0:t.requestId);const s=se().parseFromString(e,"application/xml"),o=Array.from(s.querySelectorAll("Placemark")),i=[];for(const a of o){const l={},u=Array.from(a.querySelectorAll("ExtendedData > Data"));for(const y of u){const C=y.getAttribute("name"),k=(c=(r=y.querySelector("value"))==null?void 0:r.textContent)==null?void 0:c.trim();C&&k!==void 0&&k!==null&&(l[C]=k)}const h=b.utc(),f=Object.keys(l).find(y=>y.toLowerCase().indexOf("name")!==-1),m=f?l[f]:void 0,g=`${h.valueOf().toString()}_${Math.random().toString(36).slice(2,8)}`,T=y=>y.trim().split(/[\s\n]+/).filter(C=>C.length>0).map(C=>{const k=C.split(",").map(Number);return[k[0],k[1]]}),v=a.querySelector("LineString > coordinates");if(v){const y=T(v.textContent||"");if(y.length>=2){const C=p.lineString(y,{...l,shape:"line",id:g,name:m});i.push(C)}continue}const x=a.querySelector("Polygon outerBoundaryIs LinearRing > coordinates");if(x){const y=T(x.textContent||"");if(y.length>=4){const C=y[0][0]===y[y.length-1][0]&&y[0][1]===y[y.length-1][1]?y:[...y,y[0]],k=p.polygon([C],{...l,shape:"polygon",id:g,name:m});i.push(k)}continue}const N=a.querySelector("Point > coordinates");if(N){const y=T(N.textContent||"");if(y.length>=1){const C=p.point(y[0],{...l,shape:"point",id:g,name:m});i.push(C)}continue}}return p.featureCollection(i)}static async convertKMZ2GeoJSON(e,t={}){var i;D.info("[%s] convert kmz to geojson (async)",t==null?void 0:t.requestId),typeof Buffer<"u"&&Buffer.isBuffer(e)&&(e=F.toArrayBuffer(e));const n=await F._parseZipEntries(e),s=n.get("doc.kml")??((i=[...n.entries()].find(([r])=>r.toLowerCase().endsWith(".kml")))==null?void 0:i[1]);if(!s)return D.warn("[%s] no .kml file found in kmz",t==null?void 0:t.requestId),p.featureCollection([]);const o=new TextDecoder().decode(s);return F.convertKML2GeoJSON(o,t)}static async convertZIP2GeoJSON(e,t={}){D.info("[%s] convert zip to geojson (async)",t==null?void 0:t.requestId),typeof Buffer<"u"&&Buffer.isBuffer(e)&&(e=F.toArrayBuffer(e));const n=await F._parseZipEntries(e),s=[];for(const[o,i]of n){if(!o.toLowerCase().endsWith(".kml"))continue;const r=new TextDecoder().decode(i),c=await F.convertKML2GeoJSON(r,t);s.push(...c.features)}return s.length===0?(D.warn("[%s] no .kml files found in zip",t==null?void 0:t.requestId),this.convertSHP2GeoJSON(e,t)):p.featureCollection(s)}static async convertSHP2GeoJSON(e,t={}){D.info("[%s] convert shp zip to geojson",t==null?void 0:t.requestId);try{typeof Buffer<"u"&&Buffer.isBuffer(e)&&(e=F.toArrayBuffer(e));const n=await Y(e);if(Array.isArray(n)){const s=n.flatMap(c=>c.features||[]),o=b.utc(),i=(t==null?void 0:t.id)||o.valueOf().toString(),r={Point:"point",MultiPoint:"point",LineString:"line",MultiLineString:"line",Polygon:"polygon",MultiPolygon:"polygon"};return s.forEach((c,a)=>{var m;const l=((m=c.geometry)==null?void 0:m.type)||"",u=r[l]||l.toLowerCase();c.properties=c.properties||{},c.properties.shape=u,c.properties.parentId=i,c.properties.id=`${i}_${a}`;const h=Object.keys(c.properties).find(g=>g.toLowerCase().indexOf("name")!==-1),f=h?c.properties[h]:void 0;c.properties.name=f||`${u}_${o.format()}_${a}`}),p.featureCollection(s)}return n}catch(n){return D.warn("[%s] failed to convert shp zip: %s",t==null?void 0:t.requestId,n),p.featureCollection([])}}}w.AisHelper=K,w.GeoJsonHelper=F,w.LaneHelper=S,w.LngLatHelper=d,w.TropicalHelper=ne,Object.defineProperty(w,Symbol.toStringTag,{value:"Module"})});
|
|
6
|
+
`)}static coordinatesSummary(e,t=3){if(e.length>1){const n=e[0],s=e[e.length-1],o=(n==null?void 0:n.positionTime)<(s==null?void 0:s.positionTime)?b.unix(n==null?void 0:n.positionTime):b.unix(s==null?void 0:s.positionTime),i=(n==null?void 0:n.positionTime)>(s==null?void 0:s.positionTime)?b.unix(n==null?void 0:n.positionTime):b.unix(s==null?void 0:s.positionTime),r=Math.round(i.diff(o,"hours",!0)*100)/100,c=this.generateRouteAccordingToWaypoints(e,!0,!0),a=this.calculateRouteDistance(c),u=K.inspectStoppages(e,t).reduce((f,m)=>(f.duration+=m.duration,f.distance+=m.distance,f),{hours:0,distance:0,spd:0,duration:0});u.hours=Math.round(u.duration/3600*100)/100,u.distance=Math.round(u.distance*100)/100,u.spd=u.hours?Math.round(u.distance/u.hours*100)/100:0;const h=r?Math.round((a-u.distance)/(r-u.hours)*100)/100:0;return{begin:o.utc().format(),end:i.utc().format(),distance:Math.round((a-u.distance)*100)/100,hours:Math.round((r-u.hours)*100)/100,avgSpeed:h,stoppage:u}}return{begin:void 0,end:void 0,distance:0,hours:0,avgSpeed:0}}static pickUTCSampleFromSpeed(e,t){var l,u,h;if(!((u=(l=t==null?void 0:t.sample)==null?void 0:l.hours)!=null&&u.length))return{routes:[],hour:void 0};const n=t.sample.hours.at(0),s=b.utc(e),o=b.utc(t.eta),i=s.isAfter(o)?o:s;let r=t.sample.all.find(f=>f.eta===i.format());if(!r){const f=t.sample.all.filter(C=>b.utc(C.eta).isBefore(i)).at(-1),m=this.calculateSubRoute(f,t.route);r=(h=this.calculateNextCoordinateAlongRoute(f,f.speed*i.diff(b(f.etd),"hours",!0),m))==null?void 0:h.coordinate;const{cFactor:g,cog:T,wxFactor:v,meteo:x}=f,N=Math.round(r.distanceFromPrevious*1e4)/1e4,y=Math.round((N+f.distanceFromStart)*1e4)/1e4;r={...r,cFactor:g,cog:T,speed:f.speed,wxFactor:v,distanceFromStart:y,distanceFromPrevious:N,meteo:x,eta:i.format(),etd:i.format()}}r.distanceToGo=Math.round((t.distance-r.distanceFromStart)*100)/100,r.timeToGo=Math.round(o.diff(r.etd,"hours",!0)*100)/100;const c=this.calculateRangeWaypoints(n,r,t.route);return{routes:this.generateRouteAccordingToWaypoints(c),hour:r}}static pickUTCSampleFromRoute(e,t,n){var f;const s=this.calculateSubRoute(t,n),o=this.calculateRouteDistance(s),i=o/t.speed,r=b.utc(e),c=b(t.etd),a=(f=this.calculateNextCoordinateAlongRoute(t,t.speed*r.diff(b(t.etd),"hours",!0),s))==null?void 0:f.coordinate;a.speed=t.speed;const l=c.clone().add(a.hourFromPrevious,"hour");a.eta=Math.abs(l.diff(r,"second"))<2?r.format():l.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(i,"hour").diff(b(a.etd),"hour")*100)/100;const u=this.calculateRangeWaypoints(t,a,n);return{routes:this.generateRouteAccordingToWaypoints(u),hour:a}}static includedAngle(e,t){z==null||z.debug("calculate bearing via: %j",{bearing:e,degree:t});let n=Math.abs(e%360-(t%360||0));return n=n>180?360-n:n,n}}let $;try{$=V.getLogger("vessel")}catch{}finally{}class ne{static convert2Geojson(e){var n,s,o;const t=p.featureCollection([]);for(const i of e){const r=(n=i.history)==null?void 0:n[0];if(i.forecasts){r&&r.wind&&(r.wind.kts=r.kts);for(const c of i.forecasts){let a;const l=[],u=[],h=b(c.date).utc(),f=`${i.name}-${c.model}`;for(const g in c==null?void 0:c.hours){const T=c.hours[g];a=a||T;const v=h.clone().add(Number(g),"hour"),x=p.point([T.lng,T.lat],{model:c.model,name:i.name,nameCn:i.nameCn,date:v.format(),hour:Number(g),format:v.format("MMM-DD/HHmm[Z]"),pressure:T.pressure>1e4?d.roundPrecision(T.pressure/100,0):d.roundPrecision(T.pressure,0),gusts:T.gusts,wind:T.wind||{},movement:T.movement,category:f,type:"forecast"});u.push(x),l.push(x.geometry.coordinates)}const m={kts:void 0,deg:void 0};if(r){const g=b(r.updated).utc();if(a){const v=S.calculateDistance(r,a),x=b(a.utc||a.updated).diff(g,"h",!0);m.kts=Math.round(v/x*100)/100,m.deg=S.calculateBearing(r,a,!0,0)}const T=p.point([r.lng,r.lat],{model:c.model,name:i.name,nameCn:i.nameCn,date:g.format(),hour:0,format:g.format("MMM-DD/HHmm[Z]"),pressure:r.pressure>1e4?d.roundPrecision((r==null?void 0:r.pressure)/100,0):d.roundPrecision(r.pressure,0),wind:r.wind,movement:m,category:f,type:"forecast",important:!0});u.unshift(T),l.unshift(T.geometry.coordinates)}if(t.features.push(...u),(l==null?void 0:l.length)>1){const g=p.lineString(d.convertToMonotonicLng2(l),{date:(r==null?void 0:r.updated)||(h==null?void 0:h.format()),id:i.id||i.name,model:c.model,name:i.name,category:f,type:"forecast",movement:m});t.features.push(g)}}}if(t.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),(s=i.history)!=null&&s.length){const c=[],a=b(r==null?void 0:r.updated).utc(),l=b((o=i.history)==null?void 0:o.at(-1).updated).utc(),u=a.diff(l,"h")%24>2?24:12;for(const h of i.history){const f=b(h.updated).utc(),m=f.isSameOrBefore(a)||f.isSame(l);m&&a.add(-u,"h");const g=p.point([h.lng,h.lat],{name:i.name,nameCn:i.nameCn,date:f.format(),format:f.format("MMM-DD/HHmm[Z]"),pressure:h.pressure>1e4?d.roundPrecision(h.pressure/100,0):d.roundPrecision(h.pressure,0),kts:h.kts,level:h.type,type:"history",category:`${i.name}-history`,wind:h.wind,movement:h.movement,important:m});t.features.push(g),c.push(g.geometry.coordinates)}if(c.length===1&&c.push(c[0]),c.length>1){const h=p.lineString(d.convertToMonotonicLng2(c),{name:i.name,type:"history",updated:r==null?void 0:r.updated,pressure:(r==null?void 0:r.pressure)>1e4?d.roundPrecision((r==null?void 0:r.pressure)/100,0):d.roundPrecision(r==null?void 0:r.pressure,0),kts:r==null?void 0:r.kts,level:r==null?void 0:r.type});t.features.push(h)}}}return t}static interpolate(e,t=3){var o,i,r,c;const n=(o=e==null?void 0:e.data)==null?void 0:o.features.filter(a=>a.geometry.type==="LineString"&&a.properties.type==="forecast"),s=[];for(const a of n){const l=a.properties.name,u=a.properties.model,h=a.properties.showCircle,f=a.properties.disabled,m=b(a.properties.date).utc();let g=t*60;const T=(i=e==null?void 0:e.data)==null?void 0:i.features.filter(N=>N.geometry.type==="Point"&&N.properties.type==="forecast"&&N.properties.category===`${l}-${u}`);let v,x=m.clone().add(g,"minute").set({minute:0,second:0,millisecond:0});for(;v=this.pickIndex(T,x),v<=T.length-1;){if(v>0){const N=T[v],y=v===0?void 0:T[v-1],C=(g/60-((r=y==null?void 0:y.properties)==null?void 0:r.hour))/(N.properties.hour-((c=y==null?void 0:y.properties)==null?void 0:c.hour)),k=this.computeNumber(y==null?void 0:y.geometry.coordinates[0],N.geometry.coordinates[0],C),Z=this.computeNumber(y==null?void 0:y.geometry.coordinates[1],N.geometry.coordinates[1],C),E=p.point([k,Z],{name:l,model:u,category:N==null?void 0:N.properties.category,date:x.format(),format:x.format("MMM-DD/HHmm[Z]"),gusts:this.computeNumber(y==null?void 0:y.properties.gusts,N.properties.gusts,C),hour:this.computeNumber(y==null?void 0:y.properties.hour,N.properties.hour,C),movement:this.computeNumber(y==null?void 0:y.properties.movement,N.properties.movement,C),pressure:this.computeNumber(y==null?void 0:y.properties.pressure,N.properties.pressure,C),wind:this.computeNumber(y==null?void 0:y.properties.wind,N.properties.wind,C),type:"forecast",disabled:f,showCircle:h});s.push(E)}g+=t*60,x=m.clone().add(g,"minute").set({minute:0,second:0,millisecond:0})}}return s}static accelPassageAt(e,t){const{t1:n,t2:s,hr:o,hours:i}=this.tropicalCenterTwin(e,24,t);return{t1:n,t2:s,hr:o,hours:i}}static diversionPassageAt(e,t,n,s={}){const{t1:o,t2:i,hr:r,hours:c}=this.tropicalCenterTwin(t,24,s);if(o&&i){if(!s.debug){const m=S.calculateDistance(e,o),g=S.calculateDistance(e,i);if(m>2*n&&g>2*n)return $==null||$.info("[%s] the distance between from and t1(%d) and t2(%d) is enough, no need diversion: %j",s.requestId,m,g,{from:e,t1:o,t2:i,hr:r}),{}}const a=S.calculateBearing(e,o),l=S.calculateBearing(o,i),u=Math.abs(a-l);let h=0;u<180?h=u+90:u>=180&&(h=u-90);const f=S.calculateCoordinate(o,h,n);return $==null||$.info("[%s] the right tangent position: %j",s.requestId,{from:e,t1:o,t2:i,radius:n,bearing1:a,bearing2:l,right:f}),{at:f,t1:o,t2:i,hr:Number(r),hours:c}}return{}}static driftPassageAt(e,t,n,s={}){const{t1:o,t2:i,hr:r,hours:c}=this.tropicalCenterTwin(t,24,s);if(o&&i){if(!s.debug){const f=S.calculateDistance(e,o),m=S.calculateDistance(e,i);if(f>2*n&&m>2*n)return $==null||$.info("[%s] the distance between from and t1(%d) and t2(%d) is enough, no need drifting: %j",s.requestId,f,m,{from:e,t1:o,t2:i,hr:r}),{}}const a=S.calculateBearing(e,o),l=S.calculateBearing(o,i),u=S.calculateDistance(e,o);return{at:S.calculateCoordinate(o,a-l+180,n<u?n:u),t1:o,t2:i,hr:Number(r),hours:c}}else return $==null||$.info("[%s] no need drift: %j",s.requestId,{from:e,t1:o,t2:i,hr:r}),{}}static tropicalCenterTwin(e,t=24,n={}){var l,u,h,f,m;let s={};(l=e.forecasts)==null||l.forEach(g=>{s={...g.hours,...s}});const o=((u=e==null?void 0:e.history)==null?void 0:u[0])||(s==null?void 0:s[(h=Object.keys(s))==null?void 0:h[0]]);$==null||$.info("[%s] the first tropical center: %j",n.requestId,o);let i=(f=Object.keys(s||{}).filter(g=>Number(g)<=(t<0?24:t)))==null?void 0:f.at(-1);i||(i=(m=Object.keys(s||{}).filter(g=>Number(g)<=(t<0?24:2*t)))==null?void 0:m.at(-1));const r=s==null?void 0:s[i||-1];$==null||$.info("[%s] the second tropical center: %j in %d hrs",n.requestId,r,i);const c=Object.keys(s||{}).filter(g=>Number(g)<=Number(i)),a={0:o};for(const g of c)a[g]=s[g];return{t1:o,t2:r,hr:Number(i),hours:a}}static pickIndex(e,t){let n=0;for(const s of e){if(b(s.properties.date).isAfter(t))return n===0?-1:n;n++}return n}static computeNumber(e,t,n){if(e)if(t){if(isNaN(e)&&isNaN(t)&&typeof e!="string"&&typeof t!="string"){const s={};for(const o in e)s[o]=this.computeNumber(e[o],t[o],n);return s}return Math.round((e+(t-e)*n)*100)/100}else return e;else return t}}typeof globalThis<"u"&&typeof globalThis.Buffer>"u"&&(globalThis.Buffer={isBuffer(M){return M instanceof Uint8Array},from(M,e){if(typeof M=="string")return new TextEncoder().encode(M);if(M instanceof ArrayBuffer)return new Uint8Array(M);if(Array.isArray(M))return new Uint8Array(M);throw new TypeError("Buffer.from: unsupported source type")}});let D;try{D=V.getLogger("meteo")}catch{}finally{}function se(){if(typeof DOMParser<"u")return new DOMParser;const{JSDOM:M}=require("jsdom"),{DOMParser:e}=new M("").window;return new e}class A{static toArrayBuffer(e){return e.buffer.slice(e.byteOffset,e.byteOffset+e.byteLength)}static drawCircle(e,t,n,s={}){const o=(s==null?void 0:s.steps)??64,i=(s==null?void 0:s.units)??"nauticalmiles",r=(s==null?void 0:s.properties)??{},c=p.point([e,t]),a=p.destination(c,n,90,{units:i}),l=b.utc();r.id=(s==null?void 0:s.id)||l.valueOf().toString();const u="circle";return r.name=(s==null?void 0:s.name)||`${u}_${l.format()}`,r.radius=n,r.center=[e,t],r.end=a.geometry.coordinates.map(h=>d.roundPrecision(h,9)),r.units=i,r.steps=o,r.shape="circle",D.info("[%s] draw circle with %j",s==null?void 0:s.requestId,r),p.circle(c,n,{steps:o,units:i,properties:r})}static drawRect(e,t,n={}){const s=(n==null?void 0:n.properties)??{},o=b.utc();s.id=(n==null?void 0:n.id)||o.valueOf().toString();const i="rect";s.name=(n==null?void 0:n.name)||`${i}_${o.format()}`,s.start=e.map(l=>d.roundPrecision(l,9)),s.end=t.map(l=>d.roundPrecision(l,9)),s.shape="rect",D.info("[%s] draw rect with %j",n==null?void 0:n.requestId,s);const[r,c]=d.convertToMonotonicLng2([e,t]),a=[Math.min(r[0],c[0]),Math.min(r[1],c[1]),Math.max(r[0],c[0]),Math.max(r[1],c[1])];return p.bboxPolygon(a,{properties:s})}static drawLine(e,t={}){const n=(t==null?void 0:t.properties)??{},s=b.utc();n.id=(t==null?void 0:t.id)||s.valueOf().toString();const o="line";n.name=(t==null?void 0:t.name)||`${o}_${s.format()}`,n.shape="line",D.info("[%s] draw line with %j",t==null?void 0:t.requestId,n);const i=d.convertToMonotonicLng2(e);return p.lineString(i,n)}static drawPolygon(e,t={}){const n=(t==null?void 0:t.properties)??{},s=b.utc();n.id=(t==null?void 0:t.id)||s.valueOf().toString();const o="polygon";n.name=(t==null?void 0:t.name)||`${o}_${s.format()}`,n.coordinates=e.map(r=>r.map(c=>d.roundPrecision(c,9))),n.shape="polygon",D.info("[%s] draw polygon with %j",t==null?void 0:t.requestId,n);const i=d.convertToMonotonicLng2(e);return p.polygon([i],n)}static drawPoint(e,t,n={}){const s=(n==null?void 0:n.properties)??{},o=b.utc();s.id=(n==null?void 0:n.id)||o.valueOf().toString();const i="point";return s.name=(n==null?void 0:n.name)||`${i}_${o.format()}`,s.shape="point",D.info("[%s] draw point with %j",n==null?void 0:n.requestId,s),p.point([t,e],s)}static parseCircle(e,t={}){var s,o;D.info("[%s] parse circle with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="circle"){const i=b.utc();n.id=(n==null?void 0:n.id)||i.valueOf().toString();const r=n==null?void 0:n.id,c=((s=n==null?void 0:n.center)==null?void 0:s.length)==2?p.point(n.center):p.centroid(e);let a="center";c.properties={id:`${a}_${r}`,parentId:r,name:a};const l=(n==null?void 0:n.units)||"nauticalmiles";let u=n==null?void 0:n.radius;if(!u){const m=p.polygonToLine(e);u=p.pointToLineDistance(c,m,{units:l})}a="end";const h=((o=n==null?void 0:n.end)==null?void 0:o.length)==2?p.point(n.end):p.destination(c,u,90,{units:l});h.properties={id:`${a}_${r}`,parentId:r,name:a,radius:u,units:l};const f=p.lineString([c.geometry.coordinates,h.geometry.coordinates]);return a="edge",f.properties={id:`${a}_${r}`,parentId:r,name:a,radius:u,units:l},p.featureCollection([c,h,f,e])}else return D.warn("[%s] not a orm-std circle, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static parseRect(e,t={}){D.info("[%s] parse rect with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="rect"){const s=b.utc();n.id=(n==null?void 0:n.id)||s.valueOf().toString();const o=n==null?void 0:n.id,i=e.geometry.coordinates[0],c=["sw","nw","ne","se"].map((a,l)=>{const u=p.point(i[l]);return u.properties={id:`${a}_${o}`,parentId:o,name:a},u});return p.featureCollection([...c,e])}else return D.warn("[%s] not a orm-std rect, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static parseLine(e,t={}){D.info("[%s] parse line with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="line"){const s=b.utc();n.id=(n==null?void 0:n.id)||s.valueOf().toString();const o=n==null?void 0:n.id,r=e.geometry.coordinates.map((c,a)=>{const l=`point_${a}`,u=p.point(c);return u.properties={id:`${l}_${o}`,parentId:o,name:l,index:a},u});return p.featureCollection([...r,e])}else return D.warn("[%s] not a orm-std line, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static parsePolygon(e,t={}){D.info("[%s] parse polygon with %j",t==null?void 0:t.requestId,e.properties);const n=e.properties||{};if(n.shape=="polygon"){const s=b.utc();n.id=(n==null?void 0:n.id)||s.valueOf().toString();const o=n==null?void 0:n.id,r=e.geometry.coordinates[0].map((c,a)=>{const l=p.point(c),u=`corner_${a}`;return l.properties={id:`${u}_${o}`,parentId:o,name:u,index:a},l});return p.featureCollection([...r,e])}else return D.warn("[%s] not a orm-std polygon, just return the original feature",t==null?void 0:t.requestId),p.featureCollection([e])}static _inflateRawSync(e){var t;if(typeof process<"u"&&((t=process.versions)!=null&&t.node)){const n=require("zlib");return new Uint8Array(n.inflateRawSync(Buffer.from(e)))}throw new Error("Sync inflate is not supported in browser; use the async convertKMZ2GeoJSONAsync / convertZIP2GeoJSONAsync instead")}static async _parseZipEntries(e){var h;const t=new Uint8Array(e),n=t.buffer.slice(t.byteOffset,t.byteOffset+t.byteLength),s=new DataView(n),o=new Uint8Array(n),i=new Map;let r=-1;for(let f=n.byteLength-22;f>=0;f--)if(s.getUint32(f,!0)===101010256){r=f;break}if(r<0)throw new Error("Invalid ZIP file: EOCD not found");s.getUint16(r+8,!0);const c=s.getUint32(r+12,!0),a=s.getUint32(r+16,!0);let l=a;const u=a+c;for(;l<u;){if(s.getUint32(l,!0)!==33639248)throw new Error(`Invalid ZIP file: Central Directory signature mismatch at offset ${l}`);const m=s.getUint16(l+10,!0),g=s.getUint32(l+20,!0),T=s.getUint16(l+28,!0),v=s.getUint16(l+30,!0),x=s.getUint16(l+32,!0),N=s.getUint32(l+42,!0),y=o.slice(l+46,l+46+T),C=new TextDecoder().decode(y),k=s.getUint16(N+26,!0),Z=s.getUint16(N+28,!0),E=N+30+k+Z,X=o.slice(E,E+g);if(m===0)i.set(C,X);else if(m===8){if(typeof DecompressionStream<"u"){const F=new DecompressionStream("deflate-raw"),P=F.writable.getWriter(),I=F.readable.getReader();P.write(X),P.close();const B=[];let j=0;for(;;){const{done:O,value:R}=await I.read();if(O)break;B.push(R),j+=R.length}const G=new Uint8Array(j);let U=0;for(const O of B)G.set(O,U),U+=O.length;i.set(C,G)}else if(typeof process<"u"&&((h=process.versions)!=null&&h.node))try{i.set(C,A._inflateRawSync(X))}catch{}}l+=46+T+v+x}return i}static async convertKML2GeoJSON(e,t={}){var r,c;D.info("[%s] convert kml to geojson",t==null?void 0:t.requestId);const s=se().parseFromString(e,"application/xml"),o=Array.from(s.querySelectorAll("Placemark")),i=[];for(const a of o){const l={},u=Array.from(a.querySelectorAll("ExtendedData > Data"));for(const y of u){const C=y.getAttribute("name"),k=(c=(r=y.querySelector("value"))==null?void 0:r.textContent)==null?void 0:c.trim();C&&k!==void 0&&k!==null&&(l[C]=k)}const h=b.utc(),f=Object.keys(l).find(y=>y.toLowerCase().indexOf("name")!==-1),m=f?l[f]:void 0,g=`${h.valueOf().toString()}_${Math.random().toString(36).slice(2,8)}`,T=y=>y.trim().split(/[\s\n]+/).filter(C=>C.length>0).map(C=>{const k=C.split(",").map(Number);return[k[0],k[1]]}),v=a.querySelector("LineString > coordinates");if(v){const y=T(v.textContent||"");if(y.length>=2){const C=p.lineString(y,{...l,shape:"line",id:g,name:m});i.push(C)}continue}const x=a.querySelector("Polygon outerBoundaryIs LinearRing > coordinates");if(x){const y=T(x.textContent||"");if(y.length>=4){const C=y[0][0]===y[y.length-1][0]&&y[0][1]===y[y.length-1][1]?y:[...y,y[0]],k=p.polygon([C],{...l,shape:"polygon",id:g,name:m});i.push(k)}continue}const N=a.querySelector("Point > coordinates");if(N){const y=T(N.textContent||"");if(y.length>=1){const C=p.point(y[0],{...l,shape:"point",id:g,name:m});i.push(C)}continue}}return p.featureCollection(i)}static async convertKMZ2GeoJSON(e,t={}){var i;D.info("[%s] convert kmz to geojson (async)",t==null?void 0:t.requestId),typeof Buffer<"u"&&Buffer.isBuffer(e)&&(e=A.toArrayBuffer(e));const n=await A._parseZipEntries(e),s=n.get("doc.kml")??((i=[...n.entries()].find(([r])=>r.toLowerCase().endsWith(".kml")))==null?void 0:i[1]);if(!s)return D.warn("[%s] no .kml file found in kmz",t==null?void 0:t.requestId),p.featureCollection([]);const o=new TextDecoder().decode(s);return A.convertKML2GeoJSON(o,t)}static async convertZIP2GeoJSON(e,t={}){D.info("[%s] convert zip to geojson (async)",t==null?void 0:t.requestId),typeof Buffer<"u"&&Buffer.isBuffer(e)&&(e=A.toArrayBuffer(e));const n=await A._parseZipEntries(e),s=[];for(const[o,i]of n){if(!o.toLowerCase().endsWith(".kml"))continue;const r=new TextDecoder().decode(i),c=await A.convertKML2GeoJSON(r,t);s.push(...c.features)}return s.length===0?(D.warn("[%s] no .kml files found in zip",t==null?void 0:t.requestId),this.convertSHP2GeoJSON(e,t)):p.featureCollection(s)}static async convertSHP2GeoJSON(e,t={}){D.info("[%s] convert shp zip to geojson",t==null?void 0:t.requestId);try{typeof Buffer<"u"&&Buffer.isBuffer(e)&&(e=A.toArrayBuffer(e));const n=await Y(e);if(Array.isArray(n)){const s=n.flatMap(c=>c.features||[]),o=b.utc(),i=(t==null?void 0:t.id)||o.valueOf().toString(),r={Point:"point",MultiPoint:"point",LineString:"line",MultiLineString:"line",Polygon:"polygon",MultiPolygon:"polygon"};return s.forEach((c,a)=>{var m;const l=((m=c.geometry)==null?void 0:m.type)||"",u=r[l]||l.toLowerCase();c.properties=c.properties||{},c.properties.shape=u,c.properties.parentId=i,c.properties.id=`${i}_${a}`;const h=Object.keys(c.properties).find(g=>g.toLowerCase().indexOf("name")!==-1),f=h?c.properties[h]:void 0;c.properties.name=f||`${u}_${o.format()}_${a}`}),p.featureCollection(s)}return n}catch(n){return D.warn("[%s] failed to convert shp zip: %s",t==null?void 0:t.requestId,n),p.featureCollection([])}}}w.AisHelper=K,w.GeoJsonHelper=A,w.LaneHelper=S,w.LngLatHelper=d,w.TropicalHelper=ne,Object.defineProperty(w,Symbol.toStringTag,{value:"Module"})});
|