feat(bringup): add foxglove_bridge and MCAP recording
This commit is contained in:
parent
6aea0c24a6
commit
559f60dfd8
74
src/rov_bringup/launch/foxglove_mcap.launch.py
Normal file
74
src/rov_bringup/launch/foxglove_mcap.launch.py
Normal file
@ -0,0 +1,74 @@
|
||||
"""
|
||||
foxglove_mcap.launch.py
|
||||
Launches foxglove_bridge (WebSocket :8765) and MCAP bag recording.
|
||||
Included automatically by rov_full.launch.py.
|
||||
|
||||
Standalone:
|
||||
ros2 launch rov_bringup foxglove_mcap.launch.py
|
||||
ros2 launch rov_bringup foxglove_mcap.launch.py record:=false
|
||||
|
||||
Foxglove connection from Edge PC:
|
||||
Foxglove Studio -> Open Connection -> Foxglove WebSocket -> ws://rov-brain.local:8765
|
||||
|
||||
Storage:
|
||||
Bags written to /data/bags/ on NVMe. Create before first launch:
|
||||
sudo mkdir -p /data/bags && sudo chown ubuntu:ubuntu /data/bags
|
||||
"""
|
||||
from launch import LaunchDescription
|
||||
from launch.actions import DeclareLaunchArgument, ExecuteProcess, LogInfo
|
||||
from launch.conditions import IfCondition
|
||||
from launch.substitutions import LaunchConfiguration
|
||||
from launch_ros.actions import Node
|
||||
|
||||
|
||||
def generate_launch_description():
|
||||
|
||||
bag_output_arg = DeclareLaunchArgument(
|
||||
'bag_output_dir',
|
||||
default_value='/data/bags/dive',
|
||||
description='Base path for MCAP bag. Timestamp appended automatically.',
|
||||
)
|
||||
|
||||
record_arg = DeclareLaunchArgument(
|
||||
'record',
|
||||
default_value='true',
|
||||
description='Set false to run foxglove_bridge without recording.',
|
||||
)
|
||||
|
||||
# Exposes all ROS2 topics over WebSocket
|
||||
# Edge PC connects via Foxglove Studio -> ws://rov-brain.local:8765
|
||||
foxglove_bridge_node = Node(
|
||||
package='foxglove_bridge',
|
||||
executable='foxglove_bridge',
|
||||
name='foxglove_bridge',
|
||||
parameters=[{
|
||||
'port': 8765,
|
||||
'address': '0.0.0.0', # all interfaces — required for tether access
|
||||
'tls': False,
|
||||
'send_buffer_limit': 10000000, # 10MB — headroom for image topics
|
||||
'max_update_ms': 100, # 10Hz cap — prevents WebSocket flooding
|
||||
}],
|
||||
output='screen',
|
||||
)
|
||||
|
||||
# Records all topics to NVMe in MCAP format (Foxglove native)
|
||||
# Output dir is auto-timestamped, e.g.: /data/bags/dive_2026_05_07-14_22_05/
|
||||
mcap_recorder = ExecuteProcess(
|
||||
cmd=[
|
||||
'ros2', 'bag', 'record',
|
||||
'--all',
|
||||
'--storage', 'mcap',
|
||||
'--output', LaunchConfiguration('bag_output_dir'),
|
||||
'--max-bag-size', '0', # no size limit — one bag per dive
|
||||
],
|
||||
output='screen',
|
||||
condition=IfCondition(LaunchConfiguration('record')),
|
||||
)
|
||||
|
||||
return LaunchDescription([
|
||||
bag_output_arg,
|
||||
record_arg,
|
||||
LogInfo(msg='foxglove_bridge: connect Foxglove Studio to ws://<RPi5-IP>:8765'),
|
||||
foxglove_bridge_node,
|
||||
mcap_recorder,
|
||||
])
|
||||
@ -79,4 +79,11 @@ def generate_launch_description():
|
||||
os.path.join(mission_pkg, 'launch', 'mission.launch.py')
|
||||
),
|
||||
),
|
||||
|
||||
# Foxglove bridge + MCAP recording (Prong 2 + 3)
|
||||
IncludeLaunchDescription(
|
||||
PythonLaunchDescriptionSource(
|
||||
os.path.join(bringup_pkg, 'launch', 'foxglove_mcap.launch.py')
|
||||
),
|
||||
),
|
||||
])
|
||||
|
||||
@ -14,4 +14,5 @@
|
||||
<export>
|
||||
<build_type>ament_cmake</build_type>
|
||||
</export>
|
||||
<exec_depend>foxglove_bridge</exec_depend>
|
||||
</package>
|
||||
|
||||
Loading…
Reference in New Issue
Block a user