Files
ExoMy_Cuno/ExoMy_Software-master/README.md
T
2026-05-25 16:36:21 +02:00

5.9 KiB

ExoMy CUNO — Software

ExoMy Mars-Rover auf Basis eines Raspberry Pi mit ROS1 Melodic, betrieben vollständig in einem Docker-Container.


Zugang zum Raspberry Pi

Modell Raspberry Pi 4 Model B Rev 1.4
Hostname cuno
Benutzer pi
LAN-IP 192.168.1.83
WLAN-IP 192.168.1.9 (bevorzugt)
Fallback-AP SSID CUNO, IP 192.168.50.1, Passwort astr0cun042
ssh pi@192.168.1.9

Architektur

Web-GUI (Port 8000)
    │ WebSocket (Port 9090)
    ▼
rosbridge_websocket ──► /joy ──► joystick_parser_node ──► /rover_command
                                                                │
f710_joy_node ──────────────────────────────────────────────────┘
(Logitech F710, /dev/input/js0)

/rover_command ──► robot_node ──► /motor_commands ──► motor_node ──► PCA9685 PWM ──► Motoren

Software auf dem Pi: /home/pi/ExoMy_Software/
ROS-Workspace im Container: /root/exomy_ws/src/exomy/


Systemd-Services auf dem Pi

Service Beschreibung
exomy-admin-api.service Admin-API (exomy_admin_api.py)
exomy-camera-stream.service MJPEG Kamera-Stream
exomy-wifi-fallback.service WLAN-Fallback auf eigenen Access Point
# Status prüfen
systemctl status exomy-admin-api.service

Docker-Container

Der Container exomy_autostart (Image: exomy) startet automatisch beim Booten.

# Status
docker ps

# Logs
docker logs exomy_autostart --tail=50

# Shell im Container
docker exec -it exomy_autostart bash

ROS-Nodes im Container

Node Beschreibung
f710_joy_node.py Liest Logitech F710 von /dev/input/js0, publiziert auf /joy mit 20 Hz — auch wenn der Joystick in Ruhe liegt
joystick_parser_node.py Konvertiert /joy → /rover_command; priorisiert Web-GUI über physischen Controller
gps_node.py Liest den GPS-Empfänger, publiziert Fix- und Diagnosedaten und kann über die Admin-Seite gezielt neu gestartet oder per Kaltstart zur Neuinitialisierung gezwungen werden
robot_node.py Berechnet Lenkwinkel und Geschwindigkeiten aus /rover_command
motor_node.py Setzt PWM-Werte über PCA9685; Watchdog stoppt Motoren nach 5 s ohne Befehl
rosbridge_websocket WebSocket-Bridge für die Web-GUI (Port 9090)
rosapi_node ROS-API für die Web-GUI

Admin-Funktionen

  • Admin-Seite: http://<IP>:8000/admin.html
  • Kamera-Tab nur mit 4:3-Profilen:
    • 640 x 480
    • 1024 x 768
    • 1296 x 972
  • Systemstatus mit zusätzlicher WLAN-Signalstärke in Prozent
  • GPS-Aktionen:
    • GPS neu starten
    • GPS-Kaltstart für den GlobalSat BU-353N5

Ports

Port Verwendung
8000 Web-GUI
9090 ROSBridge WebSocket
8082 Admin-API

Deploy-Workflow

Dateien lokal bearbeiten, dann auf den Pi und in den laufenden Container übertragen:

# Datei auf den Pi kopieren
scp ExoMy_Software-master/src/meine_datei.py pi@192.168.1.9:/home/pi/ExoMy_Software/src/

# In den Container kopieren
ssh pi@192.168.1.9 "docker cp /home/pi/ExoMy_Software/src/meine_datei.py exomy_autostart:/root/exomy_ws/src/exomy/src/"

# Container neu starten
ssh pi@192.168.1.9 "docker restart exomy_autostart"

GUI-Dateien:

scp ExoMy_Software-master/gui/index.html pi@192.168.1.9:/home/pi/ExoMy_Software/gui/
ssh pi@192.168.1.9 "docker cp /home/pi/ExoMy_Software/gui/index.html exomy_autostart:/root/exomy_ws/src/exomy/gui/"
# Kein Neustart nötig — Browser-Reload genügt

Bekannte Probleme & Fixes

Web-GUI: Ruckartige Bewegung bei angeschlossenem Controller

Problem: Der f710_joy_node sendet permanent mit 20 Hz auf /joy, auch wenn der Logitech F710 in Ruhe liegt (Nullwerte). Wenn die Web-GUI gleichzeitig steuert, wechseln sich Fahr- und Stopp-Befehle im 50-ms-Takt ab — der Rover bewegt sich ruckartig.

Fix: joystick_parser_node.py ignoriert Nachrichten des physischen Controllers für 2 Sekunden, sobald eine Web-GUI-Nachricht eintrifft (erkennbar an frame_id == "webgui"). Danach übernimmt der physische Controller automatisch wieder.

SyntaxError in rover.py (Point-Turn-Modus)

Problem: Überzählige schließende Klammer in rover.py Zeile 157 ließ robot_node.py beim Start abstürzen — der Rover war nicht steuerbar.

# Falsch:
math.atan((self.wheel_rx + self.wheel_fx) / self.wheel_ry)))
# Richtig:
math.atan((self.wheel_rx + self.wheel_fx) / self.wheel_ry))

Fahrmodi

Modus Taste (Controller) Taste (Web-GUI)
Ackermann A Schaltfläche „Ackermann"
Point Turn (Drehen auf der Stelle) X Schaltfläche „Turn on Point"
Crab (Seitwärtsfahrt) Y Schaltfläche „Crab"
Motoren ein/aus START Schaltfläche „Motoren"

Latenz-Simulation

Die Latenz-Simulation wird über die Admin-Seite eingestellt und wirkt gleichzeitig auf Steuerung und Kamerabild.

  • Bereich: Admin-Seite http://<IP>:8000/admin.html
  • Einstellbereich: 0 bis 10 Sekunden
  • Steuerbefehle: werden im ROS-Node delay_node gepuffert
  • Kamerabild: läuft über den Delay-Proxy auf Port 8083
  • Rohstream: Port 8081 bleibt ohne Verzögerung für Debug und interne Vorschau
  • Hauptseite: nutzt bewusst 8083, damit die eingestellte Verzögerung auch im Fahrbild sichtbar ist

Signalweg:

Kamera -> 8081 Rohstream -> 8083 Delay-Proxy -> Web-GUI
Joystick/Websteuerung -> /joy -> /delay_node -> /joy_delayed -> Rover-Steuerung

Damit lässt sich eine künstliche Laufzeit simulieren, ohne den eigentlichen Kameradienst umzubauen.


Originales ESA-Projekt