Le monde warehouse
Le projet final se déroule dans un entrepôt simulé (Gazebo Ionic, gz-sim 9) où le manipulateur
mobile LeKiwi + SO-101 détecte un objet, le saisit sur une station de prélèvement, puis le
transporte vers une zone de dépôt liée à sa classe. Cette page décrit le monde et son outillage —
les interfaces, le detector et le coordinateur restent à votre charge (Jours 1, 4 et 5).
Plan du monde
Section intitulée « Plan du monde »Entrepôt de 15 × 12 m, murs d’enceinte + cloison (obstacles pour le LiDAR / Nav2), rayonnages, piliers et caisses (décor de navigation), plus :
| Élément | Rôle | Position (monde) |
|---|---|---|
pick_station | Table basse où apparaissent les objets à saisir. | (0, 4.6), plateau à z ≈ 0.15 m |
zone_a (rouge) | Dépôt — classe metal (exemple) | (-5, 3.5) |
zone_b (vert) | Dépôt — classe plastic (exemple) | (5, 3.5) |
zone_c (bleu) | Dépôt — classe paper (exemple) | (0, -3.5) |
Les trois zones sont éloignées les unes des autres pour forcer la navigation Nav2 entre la station et
le dépôt. Le mapping classe → zone ci-dessus n’est qu’une proposition : c’est votre
mission_coordinator qui le fixe (via un YAML).
La caméra eye-in-hand
Section intitulée « La caméra eye-in-hand »Une caméra RGB-D est montée sur le poignet du SO-101 (arm_wrist_link) et regarde vers la pince. Elle
est pontée automatiquement par sim_full.launch.py :
| Topic | Type |
|---|---|
/wrist_camera/image (alias /camera/image_raw) | sensor_msgs/Image |
/wrist_camera/camera_info (alias /camera/camera_info) | sensor_msgs/CameraInfo |
/wrist_camera/depth_image (alias /camera/depth_image) | sensor_msgs/Image |
/wrist_camera/points | sensor_msgs/PointCloud2 |
L’alias /camera/* (option camera_alias:=true, activée par défaut) republie la même caméra sous le nom
d’interface attendu par votre detector du Jour 4. Le frame_id est wrist_camera_optical_frame
(convention REP-103), relié au TF du bras.
Démarrer le monde
Section intitulée « Démarrer le monde »-
Compiler & sourcer :
Fenêtre de terminal cd ~/ros2_bootcamp_ws && colcon build --packages-select lekiwi_bringupsource install/setup.bash -
Lancer le monde + le robot + la caméra :
Fenêtre de terminal ros2 launch lekiwi_bringup warehouse_sim.launch.py# variantes : headless:=true (sans GUI) | camera_alias:=false | spawn:=true -
Vérifier les flux (autre terminal) :
Fenêtre de terminal ros2 topic hz /scanros2 topic hz /camera/image_rawros2 topic echo /camera/camera_info --once
Options de lancement (MoveIt, Nav2, RViz)
Section intitulée « Options de lancement (MoveIt, Nav2, RViz) »warehouse_sim.launch.py est le point d’entrée unique. Les options sont combinables :
| Argument | Défaut | Effet |
|---|---|---|
headless:=true | false | Gazebo sans GUI |
camera_alias:=false | true | ne pas republier /camera/* |
spawn:=true | false | poser un objet au démarrage (avec object_type:=…) |
moveit:=true | false | démarrer MoveIt (move_group) |
rviz:=true | false | RViz MoveIt (nécessite moveit:=true) |
nav2:=true | false | démarrer localisation + Nav2 |
slam_mode:=… | map | map (SLAM live) | localize | amcl (cf. ci-dessous) |
map_name:=… | — | carte pour localize / amcl (ex. warehouse) |
# Tout-en-un : sim + MoveIt + RViz + Nav2 (AMCL sur la carte warehouse)ros2 launch lekiwi_bringup warehouse_sim.launch.py \ moveit:=true rviz:=true nav2:=true slam_mode:=amcl map_name:=warehouseNavigation : SLAM live ou AMCL
Section intitulée « Navigation : SLAM live ou AMCL »nav2:=true démarre Nav2 (planner + controller) et la localisation choisie par slam_mode :
slam_mode | Localisation | Carte |
|---|---|---|
map (défaut) | slam_toolbox mapping | construite en direct |
localize | slam_toolbox localization | carte sauvegardée (map_name) |
amcl | nav2_map_server + AMCL | carte statique (map_name) |
Une carte warehouse est fournie (lekiwi_navigation/maps/warehouse/). En mode amcl / localize,
donnez la pose initiale dans RViz (« 2D Pose Estimate ») ou via /initialpose : tant qu’AMCL
n’est pas localisé, des avertissements costmap « odom → base_footprint » au démarrage sont normaux.
Faire apparaître des objets
Section intitulée « Faire apparaître des objets »Les objets ne sont pas pré-placés : on les spawne à la demande avec spawn_object.launch.py (qui
démarre le pont de services gz et le nœud de spawn). Le monde doit déjà tourner.
# Cube de couleur (détection HSV) — classe = couleurros2 launch lekiwi_bringup spawn_object.launch.py object_type:=cube_color color:=green
# Cube ArUco (pose 6D + classe = ID du marqueur)ros2 launch lekiwi_bringup spawn_object.launch.py object_type:=cube_aruco aruco_id:=1
# Déchets simples (scénario de tri) : can=metal, bottle=plastic, carton=paperros2 launch lekiwi_bringup spawn_object.launch.py object_type:=waste_canros2 launch lekiwi_bringup spawn_object.launch.py object_type:=waste_bottle count:=2
# Rejouer une mission proprement : supprime puis re-spawneros2 launch lekiwi_bringup spawn_object.launch.py action:=respawn name:=pick_object_0
# Modèle arbitraire (SDF/URDF) — branchez vos propres objetsros2 launch lekiwi_bringup spawn_object.launch.py object_type:=sdf model_path:=/chemin/model.sdfBibliothèque d’objets
Section intitulée « Bibliothèque d’objets »object_type | Description | Classe par défaut |
|---|---|---|
cube_color | Cube 4 cm coloré (color:=red/green/blue/yellow ou "r g b a") | la couleur |
cube_aruco | Cube 4 cm, marqueur ArUco DICT_4X4_50 sur le dessus | l’aruco_id |
waste_can | Canette (cylindre métal) | metal |
waste_bottle | Bouteille plastique (cylindre + col) | plastic |
waste_carton | Carton (boîte brune) | paper |
sdf | Modèle arbitraire via model_path | nom du fichier |
Tout est paramétrable
Section intitulée « Tout est paramétrable »| Pour… | …éditer | Où |
|---|---|---|
| Changer d’objet | object_type / color / aruco_id / model_path | argument de launch |
| Poser à un endroit précis | pose:="x y z [yaw]" (vide ⇒ aléatoire sur la station) | argument de launch |
| Forcer la classe | class_id:=… (sinon dérivée du type / couleur / aruco_id) | argument de launch |
| Changer la zone d’apparition | station_xy, station_z, jitter | paramètres du spawn |
| Repositionner la station | la <pose> du modèle pick_station + station_xy | worlds/warehouse.sdf |
| Déplacer / ajouter une zone | la <pose> (ou un nouveau modèle) zone_* | worlds/warehouse.sdf |
| Générer un nouveau marqueur ArUco | ros2 run lekiwi_bringup generate_aruco.py --id N | — |
Et ensuite ?
Section intitulée « Et ensuite ? »Le monde fournit tout le terrain de jeu ; à vous de brancher vos briques du Jour 1 :
-
Detector (Jour 4) : s’abonne à
/camera/image_raw, publieDetection.msg(class_name+class_id+score+ boîte 2D +geometry_msgs/Pose pose) sur/detections. -
Bras (Jour 3) : service
PickRequest.srv(Pose target→bool success) avec MoveIt 2 (lekiwi_manipulation_moveit_config, groupearm, poseshome/ready/gripper_open/gripper_close). -
Navigation (Jour 2) : action
NavigateToPose(Nav2 sur LeKiwi) vers la zone liée à la classe. -
Coordinateur (Jour 5) : orchestre détection → pick → navigation → dépôt, piloté par un YAML classe → zone.
Cours conçu et animé par Etienne Schmitz