UI (src/hooks/useCamera.js, src/components/CameraViewer.jsx):
- 7 camera sources: front/left/rear/right CSI, D435i RGB/depth, panoramic
- Compressed image subscription via rosbridge (sensor_msgs/CompressedImage)
- Client-side 15fps gate (drops excess frames, reduces JS pressure)
- Per-camera FPS indicator with quality badge (FULL/GOOD/LOW/NO SIGNAL)
- Detection overlays: face boxes + names (/social/faces/detections),
gesture icons (/social/gestures), scene object labels + hazard colours
(/social/scene/objects); overlay mode selector (off/faces/gestures/objects/all)
- 360° panoramic equirect viewer with mouse/touch drag azimuth pan
- Picture-in-picture: up to 3 pinned cameras via ⊕ button
- One-click recording (MediaRecorder → MP4/WebM download)
- Snapshot to PNG with detection overlay composite + timestamp watermark
- Cameras tab added to TELEMETRY group in App.jsx
Jetson (rosbridge bringup):
- rosbridge_params.yaml: whitelist + /camera/depth/image_rect_raw/compressed,
/camera/panoramic/compressed, /social/faces/detections,
/social/gestures, /social/scene/objects
- rosbridge.launch.py: D435i colour republisher (JPEG 75%) +
depth republisher (compressedDepth/PNG16 preserving uint16 values)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
72 lines
3.7 KiB
YAML
72 lines
3.7 KiB
YAML
# rosbridge_params.yaml — rosbridge_websocket server configuration
|
||
#
|
||
# WebSocket endpoint: ws://<jetson-ip>:9090
|
||
# Browser client lib: roslibjs (cdn.jsdelivr.net/npm/roslib)
|
||
#
|
||
# Topic whitelist limits bandwidth and prevents unintended exposure.
|
||
# Glob patterns follow Python fnmatch: * matches everything (incl. /).
|
||
#
|
||
# Bandwidth budget (worst case, all subscriptions active):
|
||
# /map ~100 KB/update × 0.2 Hz = ~20 KB/s
|
||
# /scan ~5 KB/scan × 5.5 Hz = ~28 KB/s
|
||
# /saltybot/imu ~0.2 KB/msg × 50 Hz = ~10 KB/s
|
||
# /tf ~1 KB/msg × 10 Hz = ~10 KB/s
|
||
# 4× cameras ~20 KB/frame × 5 Hz = ~400 KB/s (JPEG quality 75)
|
||
# ─────────────────────────────────────────────────────
|
||
# Total ~470 KB/s ≈ 3.8 Mbps
|
||
#
|
||
# Use throttle_rate in roslibjs subscribe() calls to cap per-topic rates:
|
||
# viewer.subscribe({ topic: '/map', throttle_rate: 5000 }) // 0.2 Hz
|
||
|
||
rosbridge_websocket:
|
||
ros__parameters:
|
||
# ── Network ──────────────────────────────────────────────────────────────
|
||
port: 9090
|
||
host: "0.0.0.0" # bind all interfaces (Jetson LAN + USB-C)
|
||
address: ""
|
||
|
||
# ── Authentication ────────────────────────────────────────────────────────
|
||
authenticate: false # no auth on local network; enable if exposed
|
||
|
||
# ── Message size ──────────────────────────────────────────────────────────
|
||
# OccupancyGrid /map can exceed 1 MB for large environments.
|
||
max_message_size: 10000000 # 10 MB
|
||
|
||
# ── Topic/service/param whitelists ────────────────────────────────────────
|
||
# JSON-encoded glob list. "*" in a glob matches any chars including "/".
|
||
# Only topics matching at least one pattern are accessible to clients.
|
||
topics_glob: >-
|
||
["/map",
|
||
"/person/target",
|
||
"/person/detections",
|
||
"/camera/*/image_raw/compressed",
|
||
"/camera/depth/image_rect_raw/compressed",
|
||
"/camera/panoramic/compressed",
|
||
"/social/faces/detections",
|
||
"/social/gestures",
|
||
"/social/scene/objects",
|
||
"/scan",
|
||
"/cmd_vel",
|
||
"/saltybot/imu",
|
||
"/saltybot/balance_state",
|
||
"/tf",
|
||
"/tf_static"]
|
||
|
||
services_glob: "[]" # no service calls via WebSocket
|
||
params_glob: "[]" # no parameter access via WebSocket
|
||
|
||
# ── Connection management ─────────────────────────────────────────────────
|
||
# Time (s) before dropping a client that stops responding.
|
||
unregister_timeout: 10.0
|
||
|
||
# Fragment timeout: max seconds to wait for all fragments of a large message.
|
||
fragment_timeout: 600
|
||
|
||
# Delay between consecutive outgoing messages (ms). 0 = unlimited.
|
||
# Set > 0 (e.g. 10) if browser JS event loop is overwhelmed.
|
||
delay_between_messages: 0
|
||
|
||
# ── Logging ───────────────────────────────────────────────────────────────
|
||
# Set to true to log every publish/subscribe call (verbose, dev only).
|
||
bson_only_mode: false
|