@droneblocks/node-red-dexi
Version:
You want to make sure you don't lose any of your flow development. Make sure to map the host "flows" directory to the container directory as shown below. This will store the flow on your host machine if/when the container is destroyed.
1,901 lines • 48 kB
JSON
[
{
"id": "e768c19cc0da9678",
"type": "tab",
"label": "PX4 Offboard Demo",
"disabled": false,
"info": "",
"env": []
},
{
"id": "29e53340ef49ce77",
"type": "ros2-publish",
"z": "e768c19cc0da9678",
"server": "27129f80a96ce509",
"topicname": "/fmu/in/offboard_control_mode",
"messagetype": "px4_msgs/msg/OffboardControlMode",
"stampheader": false,
"x": 790,
"y": 320,
"wires": [
[
"1c5fbcfced8f9252",
"04b22aa18610eeb5"
]
]
},
{
"id": "1c5fbcfced8f9252",
"type": "delay",
"z": "e768c19cc0da9678",
"name": "",
"pauseType": "delay",
"timeout": "100",
"timeoutUnits": "milliseconds",
"rate": "1",
"nbRateUnits": "1",
"rateUnits": "second",
"randomFirst": "1",
"randomLast": "5",
"randomUnits": "seconds",
"drop": false,
"allowrate": false,
"outputs": 1,
"x": 510,
"y": 400,
"wires": [
[
"e8aa4e2ceaea1f22"
]
]
},
{
"id": "e8aa4e2ceaea1f22",
"type": "function",
"z": "e768c19cc0da9678",
"name": "offboard heartbeat",
"func": "let offboardControlMode = {\n \"position\": true,\n}\n\n// Only send the heartbeat if flight mode is set to offboard\n// if (flow.get(\"current_flight_mode\") == 14) {\n msg.payload = offboardControlMode\n return msg\n// }",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 490,
"y": 320,
"wires": [
[
"29e53340ef49ce77"
]
]
},
{
"id": "86ea8d29eb6e3e9c",
"type": "ros2-publish",
"z": "e768c19cc0da9678",
"server": "27129f80a96ce509",
"topicname": "/fmu/in/vehicle_command",
"messagetype": "px4_msgs/msg/VehicleCommand",
"stampheader": false,
"x": 590,
"y": 680,
"wires": [
[]
]
},
{
"id": "51573c7cbe23531b",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "offboard",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "{\"command\":176,\"param1\":1,\"param2\":6}",
"payloadType": "json",
"x": 180,
"y": 600,
"wires": [
[]
]
},
{
"id": "7ba707f2050653d7",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "hold",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "{\"command\":176,\"param1\":1,\"param2\":4,\"param3\":3}",
"payloadType": "json",
"x": 190,
"y": 640,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "3d6920e4d5733888",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "stabilized",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "{\"command\":176,\"param1\":1,\"param2\":7}",
"payloadType": "json",
"x": 180,
"y": 560,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "41cf150f64cc4078",
"type": "comment",
"z": "e768c19cc0da9678",
"name": "https://github.com/PX4/PX4-Autopilot/blob/main/src/modules/commander/Commander.cpp#L388",
"info": "",
"x": 400,
"y": 460,
"wires": []
},
{
"id": "a0626b654553fea8",
"type": "comment",
"z": "e768c19cc0da9678",
"name": "https://discuss.px4.io/t/switching-modes-in-px4-using-ros2-and-uxrce-dds/37137/2",
"info": "",
"x": 350,
"y": 500,
"wires": []
},
{
"id": "e0d61e44670c2ae8",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "arm",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "{\"command\":400,\"param1\":1,\"param2\":0}",
"payloadType": "json",
"x": 190,
"y": 680,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "27cf97d74ed93ddd",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "disarm",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "{\"command\":400,\"param1\":0,\"param2\":0}",
"payloadType": "json",
"x": 190,
"y": 720,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "4a02d7e5afd462ee",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "land",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "{\"command\":21}",
"payloadType": "json",
"x": 190,
"y": 840,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "b5a7ac2a4b0caa1e",
"type": "comment",
"z": "e768c19cc0da9678",
"name": "Start sending the offboard heartbeat message so we can arm in offboard mode",
"info": "",
"x": 340,
"y": 260,
"wires": []
},
{
"id": "d3a675a7fdec0864",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 11,
"width": 0,
"height": 0,
"passthru": false,
"label": "Arm drone",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 370,
"y": 580,
"wires": [
[
"f1b214c36a44691b"
]
]
},
{
"id": "f3a9816e169032ce",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 10,
"width": 0,
"height": 0,
"passthru": false,
"label": "Offboard flight mode",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "{\"command\":176,\"param1\":1,\"param2\":6}",
"payloadType": "json",
"topic": "topic",
"topicType": "msg",
"x": 400,
"y": 540,
"wires": [
[
"9c7da5306de96025"
]
]
},
{
"id": "ea35d0e5ae1a6a18",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 19,
"width": 0,
"height": 0,
"passthru": false,
"label": "Land",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "{\"command\":21}",
"payloadType": "json",
"topic": "topic",
"topicType": "msg",
"x": 190,
"y": 880,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "43d0af16e9fd4786",
"type": "ros2-subscribe",
"z": "e768c19cc0da9678",
"server": "27129f80a96ce509",
"topicname": "/fmu/out/vehicle_local_position",
"messagetype": "px4_msgs/msg/VehicleLocalPosition",
"x": 910,
"y": 140,
"wires": [
[
"fb76f6ef6ab1088d",
"d781f7b43060a939",
"15b1e08659d29c42",
"32d31555c56c9a05"
]
]
},
{
"id": "fb76f6ef6ab1088d",
"type": "function",
"z": "e768c19cc0da9678",
"name": "set current heading",
"func": "let current_heading = msg.payload.heading\nmsg.payload = Math.round(current_heading * 100) / 100\nflow.set(\"current_heading\", current_heading)\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 1190,
"y": 240,
"wires": [
[
"ac34a5fb077829c6"
]
]
},
{
"id": "d781f7b43060a939",
"type": "function",
"z": "e768c19cc0da9678",
"name": "set current x",
"func": "let x = msg.payload.x\nmsg.payload = Math.round(x * 100) / 100\nflow.set(\"current_x\", x)\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 1170,
"y": 60,
"wires": [
[
"f10eb3165dda1bf0"
]
]
},
{
"id": "15b1e08659d29c42",
"type": "function",
"z": "e768c19cc0da9678",
"name": "set current y",
"func": "let y = msg.payload.y\nmsg.payload = Math.round(y * 100) / 100\nflow.set(\"current_y\", y)\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 1170,
"y": 120,
"wires": [
[
"ab94c08e491c6c7d"
]
]
},
{
"id": "32d31555c56c9a05",
"type": "function",
"z": "e768c19cc0da9678",
"name": "set current z",
"func": "let z = msg.payload.z\nmsg.payload = Math.round(z * 100) / 100\nflow.set(\"current_z\", z)\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 1170,
"y": 180,
"wires": [
[
"34a22118c0caf87f"
]
]
},
{
"id": "f10eb3165dda1bf0",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 2,
"width": 0,
"height": 0,
"name": "",
"label": "X",
"format": "{{msg.payload}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 1370,
"y": 60,
"wires": []
},
{
"id": "ab94c08e491c6c7d",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 4,
"width": 0,
"height": 0,
"name": "",
"label": "Y",
"format": "{{msg.payload}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 1370,
"y": 120,
"wires": []
},
{
"id": "34a22118c0caf87f",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 6,
"width": 0,
"height": 0,
"name": "",
"label": "Z",
"format": "{{msg.payload}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 1370,
"y": 180,
"wires": []
},
{
"id": "ac34a5fb077829c6",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 8,
"width": 0,
"height": 0,
"name": "",
"label": "Heading",
"format": "{{msg.payload}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 1380,
"y": 240,
"wires": []
},
{
"id": "e3dfb1cc46c3ae5f",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "takeoff",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 190,
"y": 760,
"wires": [
[
"be2b770ac31d638c"
]
]
},
{
"id": "be2b770ac31d638c",
"type": "function",
"z": "e768c19cc0da9678",
"name": "function 1",
"func": "let takeoff = {\n \"command\": 22,\n \"param1\": -1,\n \"param7\": flow.get(\"current_z\") + 5\n}\n\nmsg.payload = takeoff\nreturn msg\n\n\n// msg.command = VehicleCommand.VEHICLE_CMD_NAV_TAKEOFF\n// msg.param1 = float(-1)\n// msg.param2 = float(0)\n// msg.param3 = float(0)\n// msg.param4 = float('nan')\n// msg.param5 = float('nan')\n// msg.param6 = float('nan')\n// msg.param7 = float(alt + self.alt) \n// return msg;",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 440,
"y": 820,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "cacfbbf3845b4c4b",
"type": "function",
"z": "e768c19cc0da9678",
"name": "setpoint manager",
"func": "let position = {\n \"position\": [\n flow.get(\"setpoint_x\"),\n flow.get(\"setpoint_y\"),\n flow.get(\"setpoint_z\")\n ],\n \"yaw\": flow.get(\"setpoint_heading\")\n}\nmsg.payload = position\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 450,
"y": 1860,
"wires": [
[
"b4f471e7e1954462",
"631cf924412c0a25"
]
]
},
{
"id": "4f06bc67a9354850",
"type": "function",
"z": "e768c19cc0da9678",
"name": "forward",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\")) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\")) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 240,
"y": 1740,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "ad0fc481928caf4f",
"type": "function",
"z": "e768c19cc0da9678",
"name": "backward",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\") + Math.PI) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\") + Math.PI) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 240,
"y": 1800,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "05de19cc14adc2b6",
"type": "function",
"z": "e768c19cc0da9678",
"name": "left",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\") + -1 * (Math.PI / 2)) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\") + -1 * (Math.PI / 2)) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 250,
"y": 1860,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "11026dfc1cd09029",
"type": "function",
"z": "e768c19cc0da9678",
"name": "right",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\") + (Math.PI / 2)) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\") + (Math.PI / 2)) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 250,
"y": 1920,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "b4f471e7e1954462",
"type": "ros2-publish",
"z": "e768c19cc0da9678",
"server": "27129f80a96ce509",
"topicname": "/fmu/in/trajectory_setpoint",
"messagetype": "px4_msgs/msg/TrajectorySetpoint",
"stampheader": false,
"x": 760,
"y": 1860,
"wires": [
[]
]
},
{
"id": "2be381e5f550a017",
"type": "function",
"z": "e768c19cc0da9678",
"name": "up",
"func": "let distance = 1\nflow.set(\"setpoint_z\", flow.get(\"current_z\") + distance * -1)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 250,
"y": 1980,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "e7f8c4395b1d66b5",
"type": "function",
"z": "e768c19cc0da9678",
"name": "down",
"func": "let distance = 1\nflow.set(\"setpoint_z\", flow.get(\"current_z\") + distance)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 250,
"y": 2040,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "dd4f2eee2d25fae9",
"type": "function",
"z": "e768c19cc0da9678",
"name": "takeoff",
"func": "let distance = 2\n\nflow.set(\"setpoint_x\", flow.get(\"current_x\"))\nflow.set(\"setpoint_y\", flow.get(\"current_y\"))\nflow.set(\"setpoint_z\", flow.get(\"current_z\") - distance)\nflow.set(\"setpoint_heading\", flow.get(\"current_heading\"))\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 250,
"y": 1680,
"wires": [
[
"cacfbbf3845b4c4b"
]
]
},
{
"id": "f1b214c36a44691b",
"type": "function",
"z": "e768c19cc0da9678",
"name": "arm",
"func": "msg.payload = {\n \"command\": 400,\n \"param1\": 1,\n \"param2\": 0\n}\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 510,
"y": 580,
"wires": [
[
"9c7da5306de96025"
]
]
},
{
"id": "57279d179595d56c",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 1,
"width": 0,
"height": 0,
"name": "",
"label": "Current Flight Mode",
"format": "{{msg.payload.flight_mode}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 700,
"y": 80,
"wires": []
},
{
"id": "ee7ae77292d53306",
"type": "ros2-subscribe",
"z": "e768c19cc0da9678",
"server": "27129f80a96ce509",
"topicname": "/fmu/out/vehicle_status",
"messagetype": "",
"x": 180,
"y": 140,
"wires": [
[
"2c5a4d6ea290b29b"
]
]
},
{
"id": "2c5a4d6ea290b29b",
"type": "function",
"z": "e768c19cc0da9678",
"name": "get flight mode",
"func": "let flight_mode = msg.payload.nav_state\nflow.set(\"current_flight_mode\", flight_mode)\nmsg.payload.flight_mode = flight_mode\n// msg.payload.setpoint_x = flow.get(\"setpoint_x\").toFixed(2)\n// msg.payload.setpoint_y = flow.get(\"setpoint_y\").toFixed(2)\n// msg.payload.setpoint_z = flow.get(\"setpoint_z\").toFixed(2)\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 440,
"y": 140,
"wires": [
[
"57279d179595d56c",
"97ed472061216e5d",
"1890850bb897be32",
"66e9411049484047"
]
]
},
{
"id": "e5222c4dad4ea4ec",
"type": "comment",
"z": "e768c19cc0da9678",
"name": "Monitor current flight mode and begin offboard heartbeat if offboard enabled",
"info": "",
"x": 350,
"y": 40,
"wires": []
},
{
"id": "04b22aa18610eeb5",
"type": "debug",
"z": "e768c19cc0da9678",
"name": "debug 1",
"active": true,
"tosidebar": true,
"console": false,
"tostatus": false,
"complete": "false",
"statusVal": "",
"statusType": "auto",
"x": 1000,
"y": 380,
"wires": []
},
{
"id": "631cf924412c0a25",
"type": "debug",
"z": "e768c19cc0da9678",
"name": "debug 2",
"active": true,
"tosidebar": true,
"console": false,
"tostatus": false,
"complete": "false",
"statusVal": "",
"statusType": "auto",
"x": 640,
"y": 1760,
"wires": []
},
{
"id": "97ed472061216e5d",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 3,
"width": 0,
"height": 0,
"name": "",
"label": "Setpoint X",
"format": "{{msg.payload.setpoint_x}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 670,
"y": 120,
"wires": []
},
{
"id": "69d3d20809a89c5f",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 9,
"width": 0,
"height": 0,
"passthru": false,
"label": "Start offboard heartbeat",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 170,
"y": 360,
"wires": [
[
"e8aa4e2ceaea1f22"
]
]
},
{
"id": "24a03e61200a6f8d",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "Start offboard heartbeat",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 300,
"wires": [
[
"e8aa4e2ceaea1f22"
]
]
},
{
"id": "1890850bb897be32",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 5,
"width": 0,
"height": 0,
"name": "",
"label": "Setpoint Y",
"format": "{{msg.payload.setpoint_y}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 670,
"y": 160,
"wires": []
},
{
"id": "66e9411049484047",
"type": "ui_text",
"z": "e768c19cc0da9678",
"group": "5e97842196ee06b6",
"order": 7,
"width": 0,
"height": 0,
"name": "",
"label": "Setpoint Z",
"format": "{{msg.payload.setpoint_z}}",
"layout": "row-spread",
"className": "",
"style": false,
"font": "",
"fontSize": 16,
"color": "#000000",
"x": 670,
"y": 200,
"wires": []
},
{
"id": "9c7da5306de96025",
"type": "function",
"z": "e768c19cc0da9678",
"name": "initialize setpoints",
"func": "flow.set(\"setpoint_x\", flow.get(\"current_x\"))\nflow.set(\"setpoint_y\", flow.get(\"current_y\"))\nflow.set(\"setpoint_z\", flow.get(\"current_z\"))\nflow.set(\"setpoint_heading\", flow.get(\"current_heading\"))\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 690,
"y": 540,
"wires": [
[
"86ea8d29eb6e3e9c"
]
]
},
{
"id": "4ee3b6561e7b3b57",
"type": "function",
"z": "e768c19cc0da9678",
"name": "setpoint manager",
"func": "// Only send setpoints if we're in offboard mode\nif (flow.get(\"current_flight_mode\") == 14) {\n let position = {\n \"position\": [\n flow.get(\"setpoint_x\"),\n flow.get(\"setpoint_y\"),\n flow.get(\"setpoint_z\")\n ],\n \"yaw\": flow.get(\"setpoint_heading\")\n }\n msg.payload = position\n return msg\n}",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 650,
"y": 1240,
"wires": [
[
"a9121fb60aa7d30d"
]
]
},
{
"id": "d268e25e6cafab5a",
"type": "function",
"z": "e768c19cc0da9678",
"name": "forward",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\")) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\")) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 360,
"y": 1120,
"wires": [
[]
]
},
{
"id": "68c84c8092535827",
"type": "function",
"z": "e768c19cc0da9678",
"name": "backward",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\") + Math.PI) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\") + Math.PI) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 360,
"y": 1200,
"wires": [
[]
]
},
{
"id": "21bd06a3d3d57302",
"type": "function",
"z": "e768c19cc0da9678",
"name": "left",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\") + -1 * (Math.PI / 2)) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\") + -1 * (Math.PI / 2)) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 350,
"y": 1280,
"wires": [
[]
]
},
{
"id": "ff519fcd4338d292",
"type": "function",
"z": "e768c19cc0da9678",
"name": "right",
"func": "let distance = 1\nlet new_x = distance * Math.cos(flow.get(\"current_heading\") + (Math.PI / 2)) + flow.get(\"current_x\")\nlet new_y = distance * Math.sin(flow.get(\"current_heading\") + (Math.PI / 2)) + flow.get(\"current_y\")\n\nflow.set(\"setpoint_x\", new_x)\nflow.set(\"setpoint_y\", new_y)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 350,
"y": 1360,
"wires": [
[]
]
},
{
"id": "a9121fb60aa7d30d",
"type": "ros2-publish",
"z": "e768c19cc0da9678",
"server": "27129f80a96ce509",
"topicname": "/fmu/in/trajectory_setpoint",
"messagetype": "px4_msgs/msg/TrajectorySetpoint",
"stampheader": false,
"x": 960,
"y": 1240,
"wires": [
[
"e33a503624bdc29f"
]
]
},
{
"id": "36a57848fc40a563",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1140,
"wires": [
[
"d268e25e6cafab5a"
]
]
},
{
"id": "49af507655b18c6b",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1220,
"wires": [
[
"68c84c8092535827"
]
]
},
{
"id": "3b2f5f476c3e85cd",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1300,
"wires": [
[
"21bd06a3d3d57302"
]
]
},
{
"id": "803233882115069a",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1380,
"wires": [
[
"ff519fcd4338d292"
]
]
},
{
"id": "90a64faec87d3acd",
"type": "function",
"z": "e768c19cc0da9678",
"name": "up",
"func": "let distance = 1\nflow.set(\"setpoint_z\", flow.get(\"current_z\") + distance * -1)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 350,
"y": 1440,
"wires": [
[]
]
},
{
"id": "2f1641bdb39850dd",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1460,
"wires": [
[
"90a64faec87d3acd"
]
]
},
{
"id": "4f844fa7986fa111",
"type": "function",
"z": "e768c19cc0da9678",
"name": "down",
"func": "let distance = 1\nflow.set(\"setpoint_z\", flow.get(\"current_z\") + distance)\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 350,
"y": 1520,
"wires": [
[]
]
},
{
"id": "212d9351d62ea3bd",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1540,
"wires": [
[
"4f844fa7986fa111"
]
]
},
{
"id": "9e8a9c7bb90367ce",
"type": "function",
"z": "e768c19cc0da9678",
"name": "takeoff",
"func": "let distance = 2\n\nflow.set(\"setpoint_x\", flow.get(\"current_x\"))\nflow.set(\"setpoint_y\", flow.get(\"current_y\"))\nflow.set(\"setpoint_z\", flow.get(\"current_z\") - distance)\nflow.set(\"setpoint_heading\", flow.get(\"current_heading\"))\n\nreturn msg",
"outputs": 1,
"timeout": 0,
"noerr": 0,
"initialize": "",
"finalize": "",
"libs": [],
"x": 350,
"y": 1040,
"wires": [
[]
]
},
{
"id": "6a1a48532a01091e",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 180,
"y": 1060,
"wires": [
[
"9e8a9c7bb90367ce"
]
]
},
{
"id": "fed75f478dce5661",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 12,
"width": 0,
"height": 0,
"passthru": false,
"label": "Takeoff",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 180,
"y": 1020,
"wires": [
[
"9e8a9c7bb90367ce"
]
]
},
{
"id": "cde857ffff654e62",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 13,
"width": 0,
"height": 0,
"passthru": false,
"label": "Right",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 190,
"y": 1340,
"wires": [
[
"ff519fcd4338d292"
]
]
},
{
"id": "55888718c62b5b32",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 15,
"width": 0,
"height": 0,
"passthru": false,
"label": "Forward",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 180,
"y": 1100,
"wires": [
[
"d268e25e6cafab5a"
]
]
},
{
"id": "ca5a3bbce0e0be0b",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 16,
"width": 0,
"height": 0,
"passthru": false,
"label": "Back",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 190,
"y": 1180,
"wires": [
[
"68c84c8092535827"
]
]
},
{
"id": "0e1dbf4e7af42d83",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 14,
"width": 0,
"height": 0,
"passthru": false,
"label": "Left",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 190,
"y": 1260,
"wires": [
[
"21bd06a3d3d57302"
]
]
},
{
"id": "bf1d420bf352b5d0",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 17,
"width": 0,
"height": 0,
"passthru": false,
"label": "Up",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 190,
"y": 1420,
"wires": [
[
"90a64faec87d3acd"
]
]
},
{
"id": "d246496f9070d60a",
"type": "ui_button",
"z": "e768c19cc0da9678",
"name": "",
"group": "5e97842196ee06b6",
"order": 18,
"width": 0,
"height": 0,
"passthru": false,
"label": "Down",
"tooltip": "",
"color": "",
"bgcolor": "",
"className": "",
"icon": "",
"payload": "",
"payloadType": "date",
"topic": "topic",
"topicType": "msg",
"x": 190,
"y": 1500,
"wires": [
[
"4f844fa7986fa111"
]
]
},
{
"id": "2f5163c8cd3127a5",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "Start offboard control loop",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 650,
"y": 1040,
"wires": [
[
"4ee3b6561e7b3b57"
]
]
},
{
"id": "e33a503624bdc29f",
"type": "delay",
"z": "e768c19cc0da9678",
"name": "",
"pauseType": "delay",
"timeout": "100",
"timeoutUnits": "milliseconds",
"rate": "1",
"nbRateUnits": "1",
"rateUnits": "second",
"randomFirst": "1",
"randomLast": "5",
"randomUnits": "seconds",
"drop": false,
"allowrate": false,
"outputs": 1,
"x": 830,
"y": 1320,
"wires": [
[
"4ee3b6561e7b3b57"
]
]
},
{
"id": "1ff249ba4a85b00b",
"type": "comment",
"z": "e768c19cc0da9678",
"name": "Send offboard setpoints continously at 10Hz",
"info": "",
"x": 230,
"y": 960,
"wires": []
},
{
"id": "5cccfbcca625d925",
"type": "comment",
"z": "e768c19cc0da9678",
"name": "Send offboard setpoints one time (docs say we can do one time....need to verify)",
"info": "",
"x": 360,
"y": 1620,
"wires": []
},
{
"id": "9c0ac909dd06707e",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 1680,
"wires": [
[
"dd4f2eee2d25fae9"
]
]
},
{
"id": "caf98a4707675515",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 1740,
"wires": [
[
"4f06bc67a9354850"
]
]
},
{
"id": "cd5bfa83b6059c59",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 1800,
"wires": [
[
"ad0fc481928caf4f"
]
]
},
{
"id": "319e6e6d7e7f690c",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 1860,
"wires": [
[
"05de19cc14adc2b6"
]
]
},
{
"id": "ee4799da24ad9b25",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 1920,
"wires": [
[
"11026dfc1cd09029"
]
]
},
{
"id": "28ad59c9d9acf177",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 1980,
"wires": [
[
"2be381e5f550a017"
]
]
},
{
"id": "cff2ecd4ef265a01",
"type": "inject",
"z": "e768c19cc0da9678",
"name": "",
"props": [
{
"p": "payload"
},
{
"p": "topic",
"vt": "str"
}
],
"repeat": "",
"crontab": "",
"once": false,
"onceDelay": 0.1,
"topic": "",
"payload": "",
"payloadType": "date",
"x": 100,
"y": 2040,
"wires": [
[
"e7f8c4395b1d66b5"
]
]
},
{
"id": "27129f80a96ce509",
"type": "ros2-websocket-server",
"url": "ws://172.17.0.2:9090"
},
{
"id": "5e97842196ee06b6",
"type": "ui_group",
"name": "Main",
"tab": "02a0349dc0753d7c",
"order": 1,
"disp": true,
"width": "10",
"collapse": false,
"className": ""
},
{
"id": "02a0349dc0753d7c",
"type": "ui_tab",
"name": "Home",
"icon": "Tab 1",
"disabled": false,
"hidden": false
}
]