How to save waypoints in node-red-worldmap upon refresh or redirect?

Hello I have this project that requires users to add waypoints onto a world map dashboard which will send coordinates to a small vehicle powered by a Jetson Nano which would then navigate to those coordinates. It will also contain a UI group that will have gauges connected to external sensors to display environmental information.
So far it seems to be working fine, however there are two issues I'm dealing with. The first being that if I switch between the different groups (Sensors and World Map) any of the waypoints I made on the map are removed when I go to the sensor group and back to the world map group.

Here is my flow to test out:

[{"id":"2e76b3c6.13b85c","type":"tab","label":"Default Flow","disabled":false,"info":""},{"id":"fa913f62.527d5","type":"serial in","z":"2e76b3c6.13b85c","name":"Uno","serial":"8a11e895.023138","x":50,"y":620,"wires":[["1b347714.4a2769"]]},{"id":"7c19eb52.800184","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":2,"width":5,"height":4,"gtype":"gage","title":"Temperature","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":570,"y":200,"wires":[]},{"id":"e09e7acc.4d3cc8","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":3,"width":5,"height":4,"gtype":"gage","title":"Humidity","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":560,"y":240,"wires":[]},{"id":"fc6c927.7266b7","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":4,"width":5,"height":4,"gtype":"gage","title":"Oxygen","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":560,"y":280,"wires":[]},{"id":"4a07774b.755e98","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":5,"width":5,"height":4,"gtype":"gage","title":"CO2","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":550,"y":320,"wires":[]},{"id":"57847025.3455","type":"ui_template","z":"2e76b3c6.13b85c","group":"248ec348.cf595c","name":"Logo / Clock","order":1,"width":0,"height":0,"format":"<script id=\"clockScript1\" type=\"text/javascript\">\n    var clockInterval;\n    $(function () {\n        if (clockInterval) return;\n\n        //add logo\n        var div1 = $('<div/>');\n        var logo = new Image();\n\n        logo.src = 'https://www.ucf.edu/brand/files/2016/07/UCF-tab-NoBleed_vert-KG-7406.png'\n        logo.height = 45;\n        div1[0].style.margin = '10px auto';\n\n        div1.append(logo);\n\n        //add clock\n        var div2 = $('<div/>');\n        var p = $('<p/>');\n\n        div2.append(p);\n        div2[0].style.margin = '5px';\n\n        function displayTime() {\n            p.text(new Date().toLocaleString());\n        }\n        \n        clockInterval = setInterval(displayTime, 1000);\n\n        //add to toolbar when it's available\n        var addToToolbarTimer;\n        \n        function addToToolbar() {\n            var toolbar = $('.md-toolbar-tools');\n            \n            if(!toolbar.length) return;\n            \n            toolbar.append(div1);\n            toolbar.append(div2);\n            clearInterval(addToToolbarTimer);\n        }\n        addToToolbarTimer = setInterval(addToToolbar, 100);\n    });\n</script>","storeOutMessages":true,"fwdInMessages":true,"resendOnRefresh":false,"templateScope":"local","className":"","x":70,"y":460,"wires":[[]]},{"id":"5271f6a0.938c48","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":6,"width":5,"height":4,"gtype":"gage","title":"Light","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":550,"y":360,"wires":[]},{"id":"2f3b3c56.6e34c4","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":7,"width":5,"height":4,"gtype":"gage","title":"UV","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":550,"y":400,"wires":[]},{"id":"81778df8.f97ba","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":8,"width":5,"height":4,"gtype":"gage","title":"Particulate Matter","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":590,"y":440,"wires":[]},{"id":"9304bc7a.fdb0e","type":"ui_gauge","z":"2e76b3c6.13b85c","name":"","group":"248ec348.cf595c","order":9,"width":5,"height":4,"gtype":"gage","title":"VOC","label":"units","format":"{{value}}","min":0,"max":10,"colors":["#00b500","#e6e600","#ca3838"],"seg1":"","seg2":"","className":"","x":550,"y":480,"wires":[]},{"id":"ca12ebb0.f99368","type":"ui_worldmap","z":"2e76b3c6.13b85c","group":"c519da4c.f6bf9","order":9,"width":"0","height":"0","name":"","lat":"","lon":"","zoom":"16","layer":"OSM","cluster":"","maxage":"","usermenu":"show","layers":"hide","panit":"true","panlock":"false","zoomlock":"false","hiderightclick":"false","coords":"dms","showgrid":"false","allowFileDrop":"false","path":"/worldmap","mapname":"","mapurl":"","mapopt":"","mapwms":false,"x":800,"y":840,"wires":[]},{"id":"d9bbf301.8154f","type":"function","z":"2e76b3c6.13b85c","name":"Get Current Location","func":"var current_lat = msg.payload.latitude;\nvar current_lon = msg.payload.longitude;\n\nreturn {\n    payload: {\n        lat : current_lat,\n        lon: current_lon,\n        name: \"Vehicle\",\n        icon: \"car\",\n        iconColor: \"red\"\n    }\n}","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":660,"y":700,"wires":[["ca12ebb0.f99368"]]},{"id":"4b3d60b1.dda66","type":"change","z":"2e76b3c6.13b85c","name":"Latitude","rules":[{"t":"change","p":"payload","pt":"msg","from":"Lat=","fromt":"str","to":"","tot":"str"},{"t":"set","p":"topic","pt":"msg","to":"latitude","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":400,"y":580,"wires":[["cdcb5858.d2ea78"]]},{"id":"1b347714.4a2769","type":"switch","z":"2e76b3c6.13b85c","name":"Lat/Lon","property":"payload","propertyType":"msg","rules":[{"t":"cont","v":"Lat","vt":"str"},{"t":"cont","v":"Lon","vt":"str"}],"checkall":"true","repair":false,"outputs":2,"x":240,"y":620,"wires":[["4b3d60b1.dda66"],["faaf0555.51c6d8"]]},{"id":"faaf0555.51c6d8","type":"change","z":"2e76b3c6.13b85c","name":"Longitude","rules":[{"t":"change","p":"payload","pt":"msg","from":"Lon=","fromt":"str","to":"","tot":"str"},{"t":"set","p":"topic","pt":"msg","to":"longitude","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":400,"y":660,"wires":[["cdcb5858.d2ea78"]]},{"id":"cdcb5858.d2ea78","type":"join","z":"2e76b3c6.13b85c","name":"","mode":"custom","build":"object","property":"payload","propertyType":"msg","key":"topic","joiner":"\\n","joinerType":"str","accumulate":false,"timeout":"","count":"2","reduceRight":false,"reduceExp":"","reduceInit":"","reduceInitType":"","reduceFixup":"","x":570,"y":620,"wires":[["d9bbf301.8154f"]]},{"id":"6f62eeb0.9ded8","type":"worldmap in","z":"2e76b3c6.13b85c","name":"","path":"/worldmap","events":"all","x":60,"y":860,"wires":[["85fb0dd1.d16e","763f29e4.75ce38"]]},{"id":"2326142.34db5ec","type":"function","z":"2e76b3c6.13b85c","name":"","func":"var menu ='Enter Waypoint</br>'; \nmenu +='<center>'\nmenu += '<input type=\"text\" name=\"name\" onchange=\\'addToForm(this.name,this.value)\\'></input><br/>'\nmenu +='</center>'\nmenu +='<center>'\nmenu +='<button name=\"waypoint\" onclick=\\'feedback(this.name,\"$form\",null,true)\\'>Submit</button>'\nmenu +='</center>'\nmsg.payload = { command: { \"contextmenu\":menu } }\nreturn msg;\n","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":500,"y":980,"wires":[["ca12ebb0.f99368"]]},{"id":"85fb0dd1.d16e","type":"switch","z":"2e76b3c6.13b85c","name":"action: connected?","property":"payload.action","propertyType":"msg","rules":[{"t":"eq","v":"connected","vt":"str"}],"checkall":"true","repair":false,"outputs":1,"x":290,"y":980,"wires":[["2326142.34db5ec"]]},{"id":"763f29e4.75ce38","type":"switch","z":"2e76b3c6.13b85c","name":"action: feedback?","property":"payload.action","propertyType":"msg","rules":[{"t":"eq","v":"feedback","vt":"str"}],"checkall":"true","repair":false,"outputs":1,"x":290,"y":900,"wires":[["3752b989.f675c6"]]},{"id":"3752b989.f675c6","type":"function","z":"2e76b3c6.13b85c","name":"Add Waypoint","func":"var latitude = msg.payload.lat;\nvar longitude = msg.payload.lon;\nvar name = msg.payload.value.name;\nreturn {\n    payload: {\n        lat : latitude,\n        lon: longitude,\n        name: name\n    }\n}","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":480,"y":900,"wires":[["ca12ebb0.f99368","f190f162.08f27","44db7d04.edd1e4"]]},{"id":"f190f162.08f27","type":"ui_template","z":"2e76b3c6.13b85c","group":"c519da4c.f6bf9","name":"Waypoint Notification","order":1,"width":"8","height":"1","format":"<div>Traveling to : {{msg.payload.name}}</div>\n","storeOutMessages":true,"fwdInMessages":true,"resendOnRefresh":true,"templateScope":"local","className":"","x":780,"y":980,"wires":[[]]},{"id":"44db7d04.edd1e4","type":"serial out","z":"2e76b3c6.13b85c","name":"Send Waypoint Out","serial":"8a11e895.023138","x":770,"y":1040,"wires":[]},{"id":"cf87b249.a939e","type":"debug","z":"2e76b3c6.13b85c","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":350,"y":300,"wires":[]},{"id":"e3875d07.dc839","type":"inject","z":"2e76b3c6.13b85c","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":60,"y":120,"wires":[["e5122ebf.4c75d"]]},{"id":"590deaea.c11944","type":"debug","z":"2e76b3c6.13b85c","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","x":210,"y":180,"wires":[]},{"id":"e5122ebf.4c75d","type":"i2c in","z":"2e76b3c6.13b85c","name":"","busno":"1","address":"8","command":"","count":"31","x":70,"y":200,"wires":[["dc8e10c1.46873","590deaea.c11944"]]},{"id":"dc8e10c1.46873","type":"buffer-parser","z":"2e76b3c6.13b85c","name":"I2C Package Parser","data":"payload","dataType":"msg","specification":"spec","specificationType":"ui","items":[{"type":"int16le","name":"DistanceFL","offset":0,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"int16le","name":"DistanceRL","offset":2,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"int16le","name":"DistanceFR","offset":4,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"int16le","name":"DistanceRR","offset":6,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"floatle","name":"Oxygen","offset":8,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"floatle","name":"Lux","offset":12,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"uint16le","name":"UV","offset":14,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"int32le","name":"VOC_Index","offset":18,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"floatle","name":"Temp","offset":22,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"floatle","name":"Humidity","offset":26,"length":1,"offsetbit":0,"scale":"1","mask":""},{"type":"bool","name":"Unlocked","offset":27,"length":1,"offsetbit":0,"scale":"1","mask":""}],"swap1":"","swap2":"","swap3":"","swap1Type":"swap","swap2Type":"swap","swap3Type":"swap","msgProperty":"payload","msgPropertyType":"str","resultType":"keyvalue","resultTypeType":"output","multipleResult":false,"fanOutMultipleResult":false,"setTopic":true,"outputs":1,"x":220,"y":240,"wires":[["cf87b249.a939e"]]},{"id":"5e387e43.32158","type":"function","z":"2e76b3c6.13b85c","name":"Deleted","func":"var latitude = msg.payload.lat;\nvar longitude = msg.payload.lon;\nvar name = msg.payload.name;\nreturn {\n    payload: {\n        lat : latitude,\n        lon: longitude,\n        name: name,\n        deleted: true\n    }\n}","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":420,"y":800,"wires":[[]]},{"id":"58d7996.db4dc68","type":"function","z":"2e76b3c6.13b85c","name":"","func":"\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":670,"y":1120,"wires":[[]]},{"id":"8a11e895.023138","type":"serial-port","serialport":"/dev/ttyACM0","serialbaud":"9600","databits":"8","parity":"none","stopbits":"1","waitfor":"","dtr":"none","rts":"none","cts":"none","dsr":"none","newline":"\\n","bin":"false","out":"char","addchar":"","responsetimeout":"10000"},{"id":"248ec348.cf595c","type":"ui_group","name":"Sensor Gauges","tab":"f0ad5670.9ce5c8","order":1,"disp":false,"width":20,"collapse":false,"className":""},{"id":"c519da4c.f6bf9","type":"ui_group","name":"World Map","tab":"89d4bd9a.635d3","order":1,"disp":false,"width":"16","collapse":false,"className":""},{"id":"f0ad5670.9ce5c8","type":"ui_tab","name":"UCF Auto Vehicle","icon":"dashboard","disabled":false,"hidden":false},{"id":"89d4bd9a.635d3","type":"ui_tab","name":"World Map","icon":"dashboard","disabled":false,"hidden":false}]

Is there any way to fix this?

As you have found the worldmap is not a track store. If you need to save points you need to do that at the server side (when they are sent with a click). And then they can be replayed from however you choose to store whenever the map connects by using a connect event from the worldmap in node to trigger it

Here is an example on storing stuff with the worldmap

1 Like

Alright I’ll work around with that and see what I can get. Thank you!

From what I'm testing in that example I noticed a few things: the first is when I put waypoints onto that map and refresh the page the flow should be injecting the waypoints back into the map upon refresh. However, when I refresh my waypoints don't show up so I manually inject the waypoints, but get an error saying: "Unexpected token [ in JSON at position 120", and doesn't put the waypoints back into the map.

But if I add a new waypoint onto the worldmap-markers map, all the waypoints show up again. Is this supposed to be happening?

Also is there anyway I can access the .dat file to see the waypoints that are already stored? I know the in the debug console, it displays each waypoint that is being added to that file, as well as the length of the array after each addition of a waypoint.

I'll take a look at it and see if there is an issue with the flow. I wrote it a while ago and time marches forward.

No problem, I appreciate the help

Were you able to tinker with it? I found the file location and tried removing the brackets that were causing the issues and it did not seem to work. My guess it has something to do with the functions that contain this line of code:

var flowMarkersObjectArray = flow.get('MarkersObjectArray')||[];

It's not really making sense to me though since the payload objects are being saved into an array and this should be the proper format for them as show here:

[{"name":"New","layer":"_drawing","lat":51.14169580579338,"lon":-1.6136169433593752,"icon":"circle","iconColor":"#910000"},{"name":"Hello","layer":"_drawing","lat":51.16232830172301,"lon":-1.5243530273437502,"icon":"circle","iconColor":"#910000"},{"name":"New Two","layer":"_drawing","lat":51.056489224826656,"lon":-1.5270996093750002,"icon":"circle","iconColor":"#910000"}]

Sorry got tied up with life.......

Spinning up a new enviroment with a fresh copy of node-red I got a few hrs to poke at it.

Example all fixed and working.

[
    {
        "id": "c2bcf0f3792ab738",
        "type": "tab",
        "label": "worldmap-markers",
        "disabled": false,
        "info": ""
    },
    {
        "id": "615c21e76ad1381f",
        "type": "worldmap",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "lat": "",
        "lon": "",
        "zoom": "",
        "layer": "OSMG",
        "cluster": "",
        "maxage": "",
        "usermenu": "show",
        "layers": "show",
        "panit": "false",
        "panlock": "false",
        "zoomlock": "false",
        "hiderightclick": "false",
        "coords": "none",
        "showgrid": "false",
        "allowFileDrop": "false",
        "path": "/worldmap-markers",
        "overlist": "DR,CO,RA,DN,HM",
        "maplist": "OSMG,OSMC,EsriC,EsriS,EsriT,EsriO,EsriDG,NatGeo,UKOS,OpTop,SW",
        "mapname": "",
        "mapurl": "",
        "mapopt": "",
        "mapwms": false,
        "x": 1050,
        "y": 420,
        "wires": []
    },
    {
        "id": "5011ed6cde079651",
        "type": "worldmap in",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "path": "/worldmap-markers",
        "events": "connect,disconnect,point,bounds,files,draw,other",
        "x": 130,
        "y": 280,
        "wires": [
            [
                "52f4244d3fbc43f1",
                "14ddae6d25df93bd",
                "49097396821160db"
            ]
        ]
    },
    {
        "id": "06dbca3997e278ba",
        "type": "inject",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": true,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "",
        "payloadType": "date",
        "x": 130,
        "y": 100,
        "wires": [
            [
                "ca08d6a7163345d1"
            ]
        ]
    },
    {
        "id": "ca08d6a7163345d1",
        "type": "file in",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "filename": "worldmap-icon-example.dat",
        "format": "utf8",
        "chunk": false,
        "sendError": false,
        "encoding": "none",
        "allProps": false,
        "x": 360,
        "y": 100,
        "wires": [
            [
                "d36baf9d5a6a4a41"
            ]
        ]
    },
    {
        "id": "502590cb73e0f19c",
        "type": "debug",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "true",
        "targetType": "full",
        "statusVal": "",
        "statusType": "auto",
        "x": 1150,
        "y": 100,
        "wires": []
    },
    {
        "id": "0ab7143ee833f8df",
        "type": "comment",
        "z": "c2bcf0f3792ab738",
        "name": "Load stored Markers from file to flow.markers, We only want to call on the file once at start/deploy of node-red",
        "info": "",
        "x": 430,
        "y": 60,
        "wires": []
    },
    {
        "id": "d36baf9d5a6a4a41",
        "type": "json",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "property": "payload",
        "action": "obj",
        "pretty": false,
        "x": 570,
        "y": 100,
        "wires": [
            [
                "4d68522054ab174c"
            ]
        ]
    },
    {
        "id": "4d68522054ab174c",
        "type": "change",
        "z": "c2bcf0f3792ab738",
        "name": "set flow.MarkersObjectArray to msg.payload",
        "rules": [
            {
                "t": "set",
                "p": "MarkersObjectArray",
                "pt": "flow",
                "to": "payload",
                "tot": "msg"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 850,
        "y": 100,
        "wires": [
            [
                "502590cb73e0f19c"
            ]
        ]
    },
    {
        "id": "f80df7052901ec0f",
        "type": "function",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "func": "//Check if stored markers in MarkersObjectArray exists, if not create it\nvar flowMarkersObjectArray = flow.get('MarkersObjectArray')||[];\n//Send the markers to msg payload to be processed by split node\n\n\nmsg.payload = flowMarkersObjectArray;\nreturn msg;\n",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 560,
        "y": 280,
        "wires": [
            [
                "557e814c9451af3d"
            ]
        ]
    },
    {
        "id": "52f4244d3fbc43f1",
        "type": "switch",
        "z": "c2bcf0f3792ab738",
        "name": "connected?",
        "property": "payload.action",
        "propertyType": "msg",
        "rules": [
            {
                "t": "eq",
                "v": "connected",
                "vt": "str"
            }
        ],
        "checkall": "true",
        "repair": false,
        "outputs": 1,
        "x": 350,
        "y": 280,
        "wires": [
            [
                "f80df7052901ec0f"
            ]
        ]
    },
    {
        "id": "557e814c9451af3d",
        "type": "split",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "splt": "\\n",
        "spltType": "str",
        "arraySplt": 1,
        "arraySpltType": "len",
        "stream": false,
        "addname": "",
        "x": 790,
        "y": 280,
        "wires": [
            [
                "615c21e76ad1381f",
                "417ccacb0ec3c456"
            ]
        ]
    },
    {
        "id": "14ddae6d25df93bd",
        "type": "switch",
        "z": "c2bcf0f3792ab738",
        "name": "point?",
        "property": "payload.action",
        "propertyType": "msg",
        "rules": [
            {
                "t": "eq",
                "v": "point",
                "vt": "str"
            }
        ],
        "checkall": "true",
        "repair": false,
        "outputs": 1,
        "x": 330,
        "y": 420,
        "wires": [
            [
                "9d75237f227b57c9"
            ]
        ]
    },
    {
        "id": "9d75237f227b57c9",
        "type": "function",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "func": "//Check if stored markers in MarkersObjectArray exists, if not create it\nvar flowMarkersObjectArray = flow.get('MarkersObjectArray')||[];\n\n//Check if marker name is already used\nif (flowMarkersObjectArray.some(element => element.name === msg.payload.name)) {\n    //flowMarkersObjectArray contains msg.payload.name value that is already in use\n    //warn user and don't add it to the flowMarkersObjectArray\n    node.warn(\"Marker name: \" + msg.payload.name + \" is already used. Please use a diffrent name or Delete current marker with that name\");\n    \n    //send msg\n    msg.payload = flowMarkersObjectArray;\n    return msg;\n}\n\nelse {\n    //append new marker object to flowMarkersObjectArray\n    var newMarker = {\n        \"name\" : msg.payload.name, \n        \"layer\": \"myWayPoint\", \n        \"draggable\":msg.payload.draggable,\n        \"lat\" : msg.payload.lat, \n        \"lon\" : msg.payload.lon, \n        \"icon\" : msg.payload.icon, \n        \"iconColor\" : msg.payload.iconColor\n        };\n    // append new value to the array\n    flowMarkersObjectArray.push(newMarker);\n\n    //update the flow.MarkersObjectArray\n    flow.set('MarkersObjectArray',flowMarkersObjectArray);\n\n    //send msg\n    msg.payload = flowMarkersObjectArray;\n    return msg;\n}\n\n",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 520,
        "y": 420,
        "wires": [
            [
                "a1887bcbf12463de",
                "beb59b256d283376"
            ]
        ]
    },
    {
        "id": "a1887bcbf12463de",
        "type": "split",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "splt": "\\n",
        "spltType": "str",
        "arraySplt": 1,
        "arraySpltType": "len",
        "stream": false,
        "addname": "",
        "x": 790,
        "y": 420,
        "wires": [
            [
                "615c21e76ad1381f",
                "2f4e2052f8104945"
            ]
        ]
    },
    {
        "id": "beb59b256d283376",
        "type": "json",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "property": "payload",
        "action": "str",
        "pretty": false,
        "x": 510,
        "y": 380,
        "wires": [
            [
                "dfb949577659254b"
            ]
        ]
    },
    {
        "id": "dfb949577659254b",
        "type": "file",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "filename": "worldmap-icon-example.dat",
        "appendNewline": false,
        "createDir": false,
        "overwriteFile": "true",
        "encoding": "none",
        "x": 720,
        "y": 380,
        "wires": [
            []
        ]
    },
    {
        "id": "49097396821160db",
        "type": "switch",
        "z": "c2bcf0f3792ab738",
        "name": "delete?",
        "property": "payload.action",
        "propertyType": "msg",
        "rules": [
            {
                "t": "eq",
                "v": "delete",
                "vt": "str"
            }
        ],
        "checkall": "true",
        "repair": false,
        "outputs": 1,
        "x": 340,
        "y": 560,
        "wires": [
            [
                "2a327773da8add97"
            ]
        ]
    },
    {
        "id": "2a327773da8add97",
        "type": "function",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "func": "//Check if stored markers in MarkersObjectArray exists, if not create it\nvar flowMarkersObjectArray = flow.get('MarkersObjectArray')||[];\n\n//Get the index in the array that the marker name is located\nvar index = flowMarkersObjectArray.findIndex(element => element.name === msg.payload.name);\n\n//Delete marker from flowMarkersObjectArray if its in the array\nif (index > -1) {\n    flowMarkersObjectArray.splice(index, 1);\n    //update the flow.MarkersObjectArray\n    flow.set('MarkersObjectArray',flowMarkersObjectArray);\n\n    //send msg\n    msg.payload = flowMarkersObjectArray;\n    return msg;\n}\n\n\nelse {\n    //warn user and don't add it to the flowMarkersObjectArray\n    node.warn(\"Unable to Delete Marker name: \" + msg.payload.name + \"as it was not found in the MarkersObjectArray\");\n    \n    //send msg\n    msg.payload = flowMarkersObjectArray;\n    return msg;\n}\n\n",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 520,
        "y": 560,
        "wires": [
            [
                "d3d5f6d8839eb541",
                "1eabb97e4bd98a3e"
            ]
        ]
    },
    {
        "id": "d3d5f6d8839eb541",
        "type": "json",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "property": "payload",
        "action": "str",
        "pretty": false,
        "x": 510,
        "y": 520,
        "wires": [
            [
                "47a6e65a2fca43ad"
            ]
        ]
    },
    {
        "id": "47a6e65a2fca43ad",
        "type": "file",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "filename": "worldmap-icon-example.dat",
        "appendNewline": false,
        "createDir": false,
        "overwriteFile": "true",
        "encoding": "none",
        "x": 720,
        "y": 520,
        "wires": [
            []
        ]
    },
    {
        "id": "1eabb97e4bd98a3e",
        "type": "split",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "splt": "\\n",
        "spltType": "str",
        "arraySplt": 1,
        "arraySpltType": "len",
        "stream": false,
        "addname": "",
        "x": 790,
        "y": 560,
        "wires": [
            [
                "615c21e76ad1381f",
                "48888de5deec1a22"
            ]
        ]
    },
    {
        "id": "a022674d0404e763",
        "type": "comment",
        "z": "c2bcf0f3792ab738",
        "name": "Load Markers from flow",
        "info": "",
        "x": 600,
        "y": 240,
        "wires": []
    },
    {
        "id": "5aa9f183ab84247e",
        "type": "comment",
        "z": "c2bcf0f3792ab738",
        "name": "Add a new marker to the map/flow/storage",
        "info": "",
        "x": 620,
        "y": 340,
        "wires": []
    },
    {
        "id": "499a2357334ed199",
        "type": "comment",
        "z": "c2bcf0f3792ab738",
        "name": "Delete marker from the map/flow/storage",
        "info": "",
        "x": 620,
        "y": 480,
        "wires": []
    },
    {
        "id": "2f4e2052f8104945",
        "type": "debug",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "true",
        "targetType": "full",
        "statusVal": "",
        "statusType": "auto",
        "x": 1030,
        "y": 380,
        "wires": []
    },
    {
        "id": "f32af760ec9f23ce",
        "type": "function",
        "z": "c2bcf0f3792ab738",
        "name": "create empty array if err",
        "func": "msg.payload = [];\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 450,
        "y": 140,
        "wires": [
            [
                "4d68522054ab174c"
            ]
        ]
    },
    {
        "id": "26f7bdd84f26ae99",
        "type": "catch",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "scope": [
            "ca08d6a7163345d1",
            "d36baf9d5a6a4a41"
        ],
        "uncaught": false,
        "x": 270,
        "y": 140,
        "wires": [
            [
                "f32af760ec9f23ce"
            ]
        ]
    },
    {
        "id": "48888de5deec1a22",
        "type": "debug",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "true",
        "targetType": "full",
        "statusVal": "",
        "statusType": "auto",
        "x": 1030,
        "y": 520,
        "wires": []
    },
    {
        "id": "417ccacb0ec3c456",
        "type": "debug",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "active": false,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "true",
        "targetType": "full",
        "statusVal": "",
        "statusType": "auto",
        "x": 1070,
        "y": 280,
        "wires": []
    },
    {
        "id": "b997e475d74739ec",
        "type": "inject",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "",
        "payloadType": "date",
        "x": 120,
        "y": 700,
        "wires": [
            [
                "e4b9a79bd4f709e8"
            ]
        ]
    },
    {
        "id": "88b096346ca80876",
        "type": "inject",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "",
        "payloadType": "date",
        "x": 130,
        "y": 800,
        "wires": [
            [
                "6bf853c967fd8318"
            ]
        ]
    },
    {
        "id": "e4b9a79bd4f709e8",
        "type": "function",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "func": "//Check if stored markers in MarkersObjectArray exists, if not create it\nvar flowMarkersObjectArray = flow.get('MarkersObjectArray')||[];\n\nmsg.payload = flowMarkersObjectArray.length;\n\n  return msg;",
        "outputs": 1,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 320,
        "y": 700,
        "wires": [
            [
                "8367b82cbd5ada62"
            ]
        ]
    },
    {
        "id": "8367b82cbd5ada62",
        "type": "debug",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "active": true,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "true",
        "targetType": "full",
        "statusVal": "",
        "statusType": "auto",
        "x": 670,
        "y": 700,
        "wires": []
    },
    {
        "id": "6f50e7140ae653bd",
        "type": "comment",
        "z": "c2bcf0f3792ab738",
        "name": "Length of array containg waypoints ",
        "info": "",
        "x": 200,
        "y": 660,
        "wires": []
    },
    {
        "id": "aee4d8ebbb7983af",
        "type": "comment",
        "z": "c2bcf0f3792ab738",
        "name": "raw dat file contents",
        "info": "",
        "x": 150,
        "y": 760,
        "wires": []
    },
    {
        "id": "6bf853c967fd8318",
        "type": "file in",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "filename": "worldmap-icon-example.dat",
        "format": "utf8",
        "chunk": false,
        "sendError": false,
        "encoding": "none",
        "allProps": false,
        "x": 360,
        "y": 800,
        "wires": [
            [
                "698285d26d2b73f6"
            ]
        ]
    },
    {
        "id": "698285d26d2b73f6",
        "type": "debug",
        "z": "c2bcf0f3792ab738",
        "name": "",
        "active": true,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "true",
        "targetType": "full",
        "statusVal": "",
        "statusType": "auto",
        "x": 670,
        "y": 800,
        "wires": []
    }
]

I had an issue with a missed labled context var that caused the no load markers on redeploy.
The other issue was using the layer: "_drawing" insted of creating a new layer.

As per your request I added the ability to get the array length of the markers and a raw output to the dat file.

Hope this helps. I will be driving 8 hrs to a camp spot today in 5hrs then the next day 6hr drive to where my motor home is at. So I will not be able to help you again until tuesday when I get internet and laptop set up.

Thanks for understanding life, over free time fun, in node-red.

Let me know if you have another issue.

2 Likes

Wow just want to say you're a legend for this. Thanks for the fix and previous help you've provided. This should be enough for my purposes.

I'll keep at it in the morning. Enjoy your trip!

I'm not sure where I'm going wrong with this. But I'm still having errors with the flow. I'm pretty sure I'm doing something wrong, but the any waypoints I add on the map doesn't get saved into the .dat file.

Not only that, any waypoints that I hard code into the file doesn't get loaded either. I tried changing layer/removed it entirely and it didn't work.

I was thinking maybe it's not properly reading the file, but whenever I inject to load stored markers, it returns the correct debug message with all the waypoints. Also length of array and the raw file contents inject returns a correct message too.

Sorry that I keep having issues with this, especially since you've able to get it. Any ideas why I'm getting this error?

hmmmm. are you using a docker instance??? if its docker the dir needs to be changed.
what is your setup your using for hosting node-red.

I can spin up a server later this week that I can give you access to and show you a working copy if you like.

I'm running it off a Pi using Raspbian.

So I messed around with what you gave in your flow and integrated some of it into my flow. It does successfully load the waypoints from the dat file onto the map correctly which is great news.

Also because of this, any waypoint I add shows up on the map even if I redirect despite not being written to that dat file, which solves that initial issue I had. I'm not really sure why it's working like this though but I'll take it I guess haha