node-red-contrib-web-worldmap 2.31.3 → 2.32.0

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/CHANGELOG.md CHANGED
@@ -1,6 +1,9 @@
1
1
  ### Change Log for Node-RED Worldmap
2
2
 
3
- - v2.33.3 - Undo previous fix as while more technically correct - doesn't look so good. Issue #217
3
+ - v2.32.0 - Change || to nullish operator ?? to fix numerous dodgy assignments. Issue #219
4
+ Delete marker now also removes from heatmap layer. Issue #218
5
+
6
+ - v2.31.3 - Undo previous fix as while more technically correct - doesn't look so good. Issue #217
4
7
  - v2.31.2 = Fix more antimeridian crossing wrinkles. Issue #216
5
8
  - v2.31.1 - Fix missing type property for drawings, and pass back feedback value. Add route distance. Issue #213, Issue #212, PR #215
6
9
  - v2.31.0 - Better handling of KML files. Issue #211
package/README.md CHANGED
@@ -11,7 +11,9 @@ map web page for plotting "things" on.
11
11
 
12
12
  ### Updates
13
13
 
14
- - v2.33.3 - Undo previous fix as while more technically correct - doesn't look so good. Issue #217
14
+ - v2.32.0 - Change || to nullish operator ?? to fix numerous dodgy assignments. Issue #219
15
+ Delete marker now also removes from heatmap layer. Issue #218
16
+ - v2.31.3 - Undo previous fix as while more technically correct - doesn't look so good. Issue #217
15
17
  - v2.31.2 = Fix more antimeridian crossing wrinkles. Issue #216
16
18
  - v2.31.1 - Fix missing type property for drawings, and pass back feedback value. Add route distance. Issue #213, Issue #212, PR #215
17
19
  - v2.31.0 - Better handling of KML files. Issue #211
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "node-red-contrib-web-worldmap",
3
- "version": "2.31.3",
3
+ "version": "2.32.0",
4
4
  "description": "A Node-RED node to provide a web page of a world map for plotting things on.",
5
5
  "dependencies": {
6
6
  "@turf/bezier-spline": "~6.5.0",
@@ -266,11 +266,11 @@ var errRing;
266
266
  function onLocationFound(e) {
267
267
  if (followState === true) { map.panTo(e.latlng); }
268
268
  if (followMode.icon) {
269
- var self = {name:followMode.name || "self", lat:e.latlng.lat, lon:e.latlng.lng, hdg:e.heading, speed:(e.speed*3.6 || undefined), layer:followMode.layer, icon:followMode.icon, iconColor:followMode.iconColor || "#910000" };
269
+ var self = {name:followMode.name || "self", lat:e.latlng.lat, lon:e.latlng.lng, hdg:e.heading, speed:(e.speed*3.6 ?? undefined), layer:followMode.layer, icon:followMode.icon, iconColor:followMode.iconColor ?? "#910000" };
270
270
  setMarker(self);
271
271
  }
272
272
  if (followMode.accuracy) {
273
- errRing = L.circle(e.latlng, e.accuracy, {color:followMode.color || "cyan", weight:3, opacity:0.6, fill:false, clickable:false});
273
+ errRing = L.circle(e.latlng, e.accuracy, {color:followMode.color ?? "cyan", weight:3, opacity:0.6, fill:false, clickable:false});
274
274
  errRing.addTo(map);
275
275
  // if (e.hasOwnProperty("heading")) {
276
276
  // var lengthAsDegrees = e.speed * 60 / 110540;
@@ -280,7 +280,7 @@ function onLocationFound(e) {
280
280
  // L.polygon([ e.latlng, lla ], {color:"cyan", weight:3, opacity:0.5, clickable:false}).addTo(map);
281
281
  // }
282
282
  }
283
- ws.send(JSON.stringify({action:"point", lat:e.latlng.lat.toFixed(5), lon:e.latlng.lng.toFixed(5), point:"self", hdg:e.heading, speed:(e.speed*3.6 || undefined)}));
283
+ ws.send(JSON.stringify({action:"point", lat:e.latlng.lat.toFixed(5), lon:e.latlng.lng.toFixed(5), point:"self", hdg:e.heading, speed:(e.speed*3.6 ?? undefined)}));
284
284
  }
285
285
 
286
286
  function onLocationError(e) { console.log(e.message); }
@@ -702,7 +702,7 @@ var addThing = function() {
702
702
  var bits = thing.split(",");
703
703
  var icon = (bits[1] || "circle").trim();
704
704
  var lay = (bits[2] || "_drawing").trim();
705
- var colo = (bits[3] || "#910000").trim();
705
+ var colo = (bits[3] ?? "#910000").trim();
706
706
  var hdg = parseFloat(bits[4] || 0);
707
707
  var drag = true;
708
708
  var regi = /^[S,G,E,I,O][A-Z]{3}.*/i; // if it looks like a SIDC code
@@ -1214,9 +1214,13 @@ var addOverlays = function(overlist) {
1214
1214
  });
1215
1215
  }
1216
1216
 
1217
- // Add the heatmap layer
1217
+ // Add the heatmap layer (and add delete LatLng function)
1218
1218
  if (overlist.indexOf("HM")!==-1) {
1219
1219
  heat = L.heatLayer([], {radius:60, gradient:{0.2:'blue', 0.4:'lime', 0.6:'red', 0.8:'yellow', 1:'white'}});
1220
+ heat.delLatLng = function(ll) {
1221
+ heat._latlngs = heat._latlngs.filter(v => { return v != ll; } );
1222
+ heat._redraw();
1223
+ }
1220
1224
  layers["_heat"] = new L.LayerGroup().addLayer(heat);
1221
1225
  overlays["heatmap"] = layers["_heat"];
1222
1226
  }
@@ -1276,6 +1280,9 @@ var delMarker = function(dname,note) {
1276
1280
  delete polygons[dname+"_"];
1277
1281
  }
1278
1282
  if (typeof markers[dname] != "undefined") {
1283
+ if (heat && markers[dname].hasOwnProperty("_latlng")) {
1284
+ heat.delLatLng(markers[dname]._latlng);
1285
+ }
1279
1286
  layers[markers[dname].lay].removeLayer(markers[dname]);
1280
1287
  map.removeLayer(markers[dname]);
1281
1288
  delete markers[dname];
@@ -1325,7 +1332,7 @@ var rangerings = function(latlng, options) {
1325
1332
  radius: options.ranges[i],
1326
1333
  fill: false,
1327
1334
  color: options.color,
1328
- weight: options.weight || 1
1335
+ weight: options.weight ?? 1
1329
1336
  }).setDirection(options.pan, options.fov).addTo(rings);
1330
1337
  }
1331
1338
  return rings;
@@ -1333,7 +1340,6 @@ var rangerings = function(latlng, options) {
1333
1340
 
1334
1341
  // the MAIN add something to map function
1335
1342
  function setMarker(data) {
1336
-
1337
1343
  var rightmenu = function(m) {
1338
1344
  // customise right click context menu
1339
1345
  var rightcontext = "";
@@ -1376,8 +1382,8 @@ function setMarker(data) {
1376
1382
  var ll;
1377
1383
  var lli = null;
1378
1384
  var opt = {};
1379
- opt.color = data.color || data.lineColor || "#910000";
1380
- opt.fillColor = data.fillColor || "#910000";
1385
+ opt.color = data.color ?? data.lineColor ?? "#910000";
1386
+ opt.fillColor = data.fillColor ?? "#910000";
1381
1387
  opt.stroke = (data.hasOwnProperty("stroke")) ? data.stroke : true;
1382
1388
  opt.weight = data.weight;
1383
1389
  opt.opacity = data.opacity;
@@ -1407,7 +1413,7 @@ function setMarker(data) {
1407
1413
  if (markers.hasOwnProperty(data.name) && markers[data.name].hasOwnProperty("lay")) {
1408
1414
  lll = markers[data.name].lay;
1409
1415
  }
1410
- var lay = data.layer || lll;
1416
+ var lay = data.layer ?? lll;
1411
1417
  if (!data.hasOwnProperty("action") || data.action.indexOf("layer") === -1) {
1412
1418
  if (typeof layers[lay] == "undefined") { // add layer if if doesn't exist
1413
1419
  if (clusterAt > 0) {
@@ -1564,11 +1570,11 @@ function setMarker(data) {
1564
1570
  if (data.draggable === true) { drag = true; }
1565
1571
 
1566
1572
  if (data.hasOwnProperty("icon")) {
1567
- var dir = parseFloat(data.hdg || data.heading || data.bearing || "0");
1573
+ var dir = parseFloat(data.hdg ?? data.heading ?? data.bearing ?? "0");
1568
1574
  if (data.icon === "ship") {
1569
1575
  marker = L.boatMarker(ll, {
1570
1576
  title: data.name,
1571
- color: (data.iconColor || "blue")
1577
+ color: (data.iconColor ?? "blue")
1572
1578
  });
1573
1579
  marker.setHeading(dir);
1574
1580
  q = 'https://www.bing.com/images/search?q='+data.icon+'%20%2B"'+encodeURIComponent(data.name)+'"';
@@ -1592,7 +1598,7 @@ function setMarker(data) {
1592
1598
  marker = L.marker(ll, {title:data.name, icon:myMarker, draggable:drag});
1593
1599
  }
1594
1600
  else if (data.icon === "smallplane") {
1595
- data.iconColor = data.iconColor || "black";
1601
+ data.iconColor = data.iconColor ?? "black";
1596
1602
  icon = '<svg xmlns="http://www.w3.org/2000/svg" version="1.0" width="20" height="20">';
1597
1603
  icon += '<path d="M15.388 4.781c.068.068.061.154-.171.656-.028.06-.18.277-.18.277s.102.113.13.14c.054.055.078.175.056.27-.068.295-.89 1.47-1.35 1.93-.285.286-.432.481-.422.56.009.068.117.356.24.64.219.5.3.599 2.762 3.339 1.95 2.169 2.546 2.87 2.582 3.028.098.439-.282.847-1.264 1.356l-.507.263-7.389-5.29-4.43 3.365.102.18c.056.099.519.676 1.029 1.283.51.607.933 1.161.94 1.232.026.284-1.111 1.177-1.282 1.006-.27-.27-1.399-1.131-1.494-1.14-.068-.007-1.04-.747-1.37-1.077-.329-.33-1.07-1.301-1.076-1.37-.01-.094-.871-1.224-1.14-1.493-.171-.171.722-1.308 1.006-1.282.07.007.625.43 1.231.94.607.51 1.185.973 1.283 1.029l.18.101 3.365-4.43-5.29-7.388.263-.507c.51-.982.918-1.362 1.357-1.264.158.035.859.632 3.028 2.581 2.74 2.462 2.838 2.544 3.339 2.762.284.124.572.232.639.24.08.01.274-.136.56-.422.46-.46 1.635-1.282 1.93-1.35.095-.022.216.003.27.057.028.028.139.129.139.129s.217-.153.277-.18c.502-.233.59-.238.657-.17z" fill="'+data.iconColor+'"/></svg>';
1598
1604
  var svgplane = "data:image/svg+xml;base64," + btoa(icon);
@@ -1607,7 +1613,7 @@ function setMarker(data) {
1607
1613
  dir = dir - 90;
1608
1614
  var sc = 1;
1609
1615
  if (dir < -90 || dir >= 90) { sc = -1; }
1610
- data.iconColor = data.iconColor || "#910000";
1616
+ data.iconColor = data.iconColor ?? "#910000";
1611
1617
  var p = "m595.5 97.332-30.898-68.199c-11.141-24.223-35.344-39.762-62.004-39.801h-443.3c-32.738 0.035157-59.266 26.562-59.301 59.305v148.2c0 17.949 14.551 32.5 32.5 32.5h48.5c4.7344 23.309 25.219 40.051 49 40.051s44.266-16.742 49-40.051h242c4.7344 23.309 25.219 40.051 49 40.051s44.266-16.742 49-40.051h53.203c12.348-0.003906 23.219-8.1484 26.699-20 0.72266-2.5391 1.0898-5.1602 1.0977-7.7969v-83.5c-0.003906-7.1445-1.5391-14.203-4.5-20.703zm-545.5 12c-5.5234 0-10-4.4766-10-10v-80c0-5.5195 4.4766-10 10-10h70c5.5234 0 10 4.4805 10 10v80c0 5.5234-4.4766 10-10 10zm80 140c-16.566 0-30-13.43-30-30 0-16.566 13.434-30 30-30s30 13.434 30 30c-0.046875 16.551-13.453 29.953-30 30zm110-150c0 5.5234-4.4766 10-10 10h-70c-5.5234 0-10-4.4766-10-10v-80c0-5.5195 4.4766-10 10-10h70c5.5234 0 10 4.4805 10 10zm110 0c0 5.5234-4.4766 10-10 10h-70c-5.5234 0-10-4.4766-10-10v-80c0-5.5195 4.4766-10 10-10h70c5.5234 0 10 4.4805 10 10zm30 10c-5.5234 0-10-4.4766-10-10v-80c0-5.5195 4.4766-10 10-10h70c5.5234 0 10 4.4805 10 10v80c0 5.5234-4.4766 10-10 10zm90 140c-16.566 0-30-13.43-30-30 0-16.566 13.434-30 30-30s30 13.434 30 30c-0.046875 16.551-13.453 29.953-30 30zm19.199-140c-5.1836-0.46094-9.168-4.793-9.1992-10v-80.086c0-5.4727 4.4375-9.9141 9.9141-9.9141h12.684c18.824 0.050781 35.914 11.012 43.805 28.102l30.898 68.199c1.6133 3.5547 2.5 7.3984 2.6016 11.297z";
1612
1618
  icon = '<svg width="640pt" height="640pt" viewBox="-20 -180 640 640" xmlns="http://www.w3.org/2000/svg">';
1613
1619
  icon += '<path d="'+p+'" fill="'+data.iconColor+'"/></svg>';
@@ -1620,7 +1626,7 @@ function setMarker(data) {
1620
1626
  marker = L.marker(ll, {title:data.name, icon:myMarker, draggable:drag});
1621
1627
  }
1622
1628
  else if (data.icon === "helicopter") {
1623
- data.iconColor = data.iconColor || "black";
1629
+ data.iconColor = data.iconColor ?? "black";
1624
1630
  if (data.hasOwnProperty("squawk")) {
1625
1631
  if (data.squawk == 7500 || data.squawk == 7600 || data.squawk == 7700) {
1626
1632
  data.iconColor = "red";
@@ -1772,7 +1778,7 @@ function setMarker(data) {
1772
1778
  }
1773
1779
  else if (data.icon.match(/^:.*:$/g)) {
1774
1780
  var em = emojify(data.icon);
1775
- var col = data.iconColor || "#910000";
1781
+ var col = data.iconColor ?? "#910000";
1776
1782
  myMarker = L.divIcon({
1777
1783
  className:"emicon",
1778
1784
  html: '<center><span style="font-size:2em; color:'+col+'">'+em+'</span></center>',
@@ -1782,7 +1788,7 @@ function setMarker(data) {
1782
1788
  labelOffset = [12,-4];
1783
1789
  }
1784
1790
  else if (data.icon.match(/^https?:.*$/)) {
1785
- var sz = data.iconSize || 32;
1791
+ var sz = data.iconSize ?? 32;
1786
1792
  myMarker = L.icon({
1787
1793
  iconUrl: data.icon,
1788
1794
  iconSize: [sz, sz],
@@ -1794,7 +1800,7 @@ function setMarker(data) {
1794
1800
  delete data.iconSize;
1795
1801
  }
1796
1802
  else if (data.icon.substr(0,3) === "fa-") {
1797
- var col = data.iconColor || "#910000";
1803
+ var col = data.iconColor ?? "#910000";
1798
1804
  var imod = "";
1799
1805
  if (data.icon.indexOf(" ") === -1) { imod = "fa-2x "; }
1800
1806
  myMarker = L.divIcon({
@@ -1808,7 +1814,7 @@ function setMarker(data) {
1808
1814
  labelOffset = [8,-8];
1809
1815
  }
1810
1816
  else if (data.icon.substr(0,3) === "wi-") {
1811
- var col = data.iconColor || "#910000";
1817
+ var col = data.iconColor ?? "#910000";
1812
1818
  var imod = "";
1813
1819
  if (data.icon.indexOf(" ") === -1) { imod = "wi-2x "; }
1814
1820
  myMarker = L.divIcon({
@@ -1823,8 +1829,8 @@ function setMarker(data) {
1823
1829
  }
1824
1830
  else {
1825
1831
  myMarker = L.VectorMarkers.icon({
1826
- icon: data.icon || "circle",
1827
- markerColor: (data.iconColor || "#910000"),
1832
+ icon: data.icon ?? "circle",
1833
+ markerColor: (data.iconColor ?? "#910000"),
1828
1834
  prefix: 'fa',
1829
1835
  iconColor: 'white'
1830
1836
  });
@@ -1863,7 +1869,7 @@ function setMarker(data) {
1863
1869
  else {
1864
1870
  myMarker = L.VectorMarkers.icon({
1865
1871
  icon: "circle",
1866
- markerColor: (data.iconColor || "#910000"),
1872
+ markerColor: (data.iconColor ?? "#910000"),
1867
1873
  prefix: 'fa',
1868
1874
  iconColor: 'white'
1869
1875
  });
@@ -2451,7 +2457,7 @@ function doCommand(cmd) {
2451
2457
  }
2452
2458
 
2453
2459
  var custIco = function() {
2454
- var col = cmd.map.iconColor || "#910000";
2460
+ var col = cmd.map.iconColor ?? "#910000";
2455
2461
  var myMarker = L.VectorMarkers.icon({
2456
2462
  icon: "circle",
2457
2463
  markerColor: col,
@@ -2692,17 +2698,17 @@ function doCommand(cmd) {
2692
2698
  // handle any incoming GEOJSON directly - may style badly
2693
2699
  function doGeojson(n,g,l,o) {
2694
2700
  //console.log("GEOJSON",n,g,l,o)
2695
- var lay = l || g.name || "unknown";
2701
+ var lay = l ?? g.name ?? "unknown";
2696
2702
  // if (!basemaps[lay]) {
2697
2703
  var opt = { style: function(feature) {
2698
2704
  var st = { stroke:true, color:"#910000", weight:1, fill:true, fillColor:"#910000", fillOpacity:0.15 };
2699
2705
  st = Object.assign(st,o);
2700
2706
  if (feature.hasOwnProperty("properties")) {
2701
2707
  //console.log("GPROPS", feature.properties)
2702
- st.color = feature.properties["stroke"] || st.color;
2703
- st.weight = feature.properties["stroke-width"] || st.weight;
2704
- st.fillColor = feature.properties["fill-color"] || feature.properties["fill"] || st.fillColor;
2705
- st.fillOpacity = feature.properties["fill-opacity"] || st.fillOpacity;
2708
+ st.color = feature.properties["stroke"] ?? st.color;
2709
+ st.weight = feature.properties["stroke-width"] ?? st.weight;
2710
+ st.fillColor = feature.properties["fill-color"] ?? feature.properties["fill"] ?? st.fillColor;
2711
+ st.fillOpacity = feature.properties["fill-opacity"] ?? st.fillOpacity;
2706
2712
  delete feature.properties["stroke"];
2707
2713
  delete feature.properties["stroke-width"];
2708
2714
  delete feature.properties["fill-color"];
@@ -2712,10 +2718,10 @@ function doGeojson(n,g,l,o) {
2712
2718
  }
2713
2719
  if (feature.hasOwnProperty("style")) {
2714
2720
  //console.log("GSTYLE", feature.style)
2715
- st.color = feature.style["stroke"] || st.color;
2716
- st.weight = feature.style["stroke-width"] || st.weight;
2717
- st.fillColor = feature.style["fill-color"] || feature.style["fill"] || st.fillColor;
2718
- st.fillOpacity = feature.style["fill-opacity"] || st.fillOpacity;
2721
+ st.color = feature.style["stroke"] ?? st.color;
2722
+ st.weight = feature.style["stroke-width"] ?? st.weight;
2723
+ st.fillColor = feature.style["fill-color"] ?? feature.style["fill"] ?? st.fillColor;
2724
+ st.fillOpacity = feature.style["fill-opacity"] ?? st.fillOpacity;
2719
2725
  }
2720
2726
  if (feature.hasOwnProperty("geometry") && feature.geometry.hasOwnProperty("type") && (feature.geometry.type === "LineString" || feature.geometry.type === "MultiLineString") ) {
2721
2727
  st.fill = false;
@@ -2751,8 +2757,8 @@ function doGeojson(n,g,l,o) {
2751
2757
  }
2752
2758
  else {
2753
2759
  myMarker = L.VectorMarkers.icon({
2754
- icon: feature.properties["marker-symbol"] || "circle",
2755
- markerColor: (feature.properties["marker-color"] || "#910000"),
2760
+ icon: feature.properties["marker-symbol"] ?? "circle",
2761
+ markerColor: (feature.properties["marker-color"] ?? "#910000"),
2756
2762
  prefix: 'fa',
2757
2763
  iconColor: 'white'
2758
2764
  });
@@ -2768,7 +2774,7 @@ function doGeojson(n,g,l,o) {
2768
2774
  delete feature.properties["marker-size"];
2769
2775
  var nf = {title:feature.properties.title, name:feature.properties.name};
2770
2776
  feature.properties = Object.assign(nf, feature.properties);
2771
- return L.marker(latlng, {title:feature.properties.title || "", icon:myMarker});
2777
+ return L.marker(latlng, {title:feature.properties.title ?? "", icon:myMarker});
2772
2778
  }
2773
2779
  opt.onEachFeature = function (f,l) {
2774
2780
  if (f.properties && Object.keys(f.properties).length > 0) {