Plateforme populaire pour les robots sur ROS

L'article est écrit uniquement pour ceux qui font partie de ROS lui-même et qui ont besoin de construire un vrai robot pour s'entraîner ou effectuer de vraies tâches.







Lorsque vous commencez à apprendre ROS, vous souhaitez généralement travailler avec des plates-formes physiques, et non avec des modèles dans un simulateur. En fait, Gazebo suffit à étudier uniquement les algorithmes de mouvement ou simplement à enseigner ROS lui-même, mais travailler avec une vraie plate-forme permet immédiatement de comprendre en pratique tous les problèmes de mouvement des roues. Eh bien, et souvent, la plate-forme est nécessaire simplement comme une condition préalable au projet.



Pour l'avenir, il vaut mieux commencer par un tour, car pour des raisons évidentes, une telle configuration peut tourner autour de l'axe sans tenir compte de la taille de la partie en saillie. Le rectangle demi-tour est beaucoup moins pratique, par exemple, dans les couloirs étroits - il devient parfois nécessaire de déployer 3 tours ou plus, je pense que les automobilistes comprendront.



Acheter des plateformes prêtes à l'emploi



Il n'y a pas beaucoup de plates-formes prêtes à l'emploi sur le marché, elles sont répertoriées sur le site Web de ROS .



Dans le même temps, leur coût en Russie est suffisamment élevé pour commencer à travailler; l'option la moins chère est Turtlebot Burger 3 - 549 $. Nous avons trouvé des revendeurs directement en Russie pour environ 90 000 roubles.







En Chine, vous pouvez acheter pour 45-50 tr ... Dans tous les cas, ce seront des plates-formes de petite taille et de capacité de charge, pas capables d'effectuer de vraies tâches.



Vous pouvez créer la plate-forme vous-même, il existe de nombreux guides et configurations différents. Mais en moyenne, il s'avère quelque chose comme:



  • Lidar de classe Slamtech A1-A2
  • Roues bon marché basées sur des moteurs collecteurs avec réducteurs
  • , PWM , UART + rosserial.
  • Single Board Computer — Raspberry, Jetson Nano
  • 2
  • gmapping + amcl/rosbot_ekf + move_base






Nous n'avons pas aimé les moteurs collecteurs car ils sont bruyants, ont une consommation élevée et une boîte de vitesses est nécessaire. Ici, il faut dire que les plates-formes sont considérées comme assez lourdes - i.e. boîtes de vitesses + moteurs verrouillés quelque chose comme le moteur de la photo ne fonctionnera pas.



En conséquence, les moteurs de roue BLDC ont été choisis comme moteurs. L'option la plus abordable pour le moment est les roues hoverboard 6.5. Il ne reste plus qu'à les gérer depuis ROS.



Mais alors un problème est apparu: même en travaillant avec des robots de golf , un problème important a été remarqué avec la rotation d'une telle plate-forme à basse vitesse - le robot s'est retourné plutôt saccadé.



Les raisons de ce comportement sont simples: les forces de frottement de glissement jouent un rôle important dans la résistance au mouvement dans le virage. Et ils ont une particularité - la résistance dépend de la masse et de la nature des surfaces elles-mêmes - c'est pourquoi un petit boulon tient de grandes structures avec les 2-3 premiers tours.



Par conséquent, rendre les roues étroites au centre pour qu'elles tournent devient plutôt inutile - la résistance changera très peu. La roue en caoutchouc frotte contre l'herbe et le sol, qui ne sont pas du tout uniformes et la force peut changer radicalement, en conséquence, quelque chose comme une boîte de vitesses a été fabriqué - à basse vitesse, nous contrôlons le moment sur la roue et avec un mouvement direct - la vitesse elle-même.





Il semblerait que lors de la conduite sur parquet ou linoléum, la situation devrait être meilleure, mais hélas, le coefficient de frottement est presque le même (rappelez-vous que les chaussures antidérapantes sont également en caoutchouc).







En conséquence, un robot pesant 10-15 kilogrammes commence déjà à se déplier avec des secousses tangibles.



La deuxième partie du problème est ajoutée par le package ROS diff_drive en combinaison avec des cartes SBC plutôt faibles.



Voici une liste de ce que j'ai réussi à comprendre



La gestion est effectuée à l'aide d'une implémentation en temps réel, mais elle ne tient pas compte du fait que d'autres packages devraient s'attendre à cette approche lorsqu'ils travaillent avec la direction.



Ici, nous devons nous rappeler que le temps réel n'est pas une réaction instantanée à un événement, mais une garantie que l'événement sera traité à des intervalles de temps physique garantis. Ceux. La centrale hydroélectrique conditionnelle, régulée toutes les minutes (forcément toutes) est aussi un système en temps réel.

Il est possible que les messages obstruent les rubriques du planificateur d'itinéraire, et pour les sous-systèmes de positionnement et de planification d'itinéraire, ce comportement conduit généralement à l'arrêt et au redémarrage du traitement du flux, ou à des tentatives d'ajuster le processus à la volée.







En conséquence, sur les SBC faibles une situation survient avec un recalcul continu du chemin , ou la recherche de localisation consomme un temps processeur suffisamment important - et plus on essaie de suivre le composant RT, plus le temps de démarrage s'accumule. Dans sa forme pure, une rétroaction positive, qui dans ce cas n'est pas du tout nécessaire.



En plus de cela, gmapping ne commence pas à fonctionner très rapidement avec des changements brusques de la position de la plate-forme et un lidar faible - il y a eu des pauses allant jusqu'à une demi-seconde, ce qui intrigue également grandement le planificateur d'itinéraire.



Les moteurs sont contrôlés séparément, donc lors de l'utilisation de SBC et de l'implémentation naïve des pilotes, les roues seront contrôlées avec un certain retard.



Ici, le problème est encore plus simple - nous devons contrôler 2-4 roues via le canal de communication, qui. En conséquence, les signaux de commande s'alignent et commencent à être transmis les uns après les autres - roue gauche, roue droite, roue gauche, roue droite.



En conséquence, les roues elles-mêmes, et pire encore, les positions des roues des encodeurs commencent à contribuer à la formation du PIC entre la planification du trajet et le contrôle des moteurs.



L'odométrie intégrée est très simpliste.



Comme nous ne cherchions pas un moyen simple de synchroniser la commande et le retour de l'odométrie, je ne l'ai pas trouvé. La synchronisation est toujours associée à l'attente de certaines commandes à l'entrée, mais elles ne sont pas régulières dans le temps et, par conséquent, l'odométrie commence à s'attarder en sortie. Peut-être que les lecteurs proposeront un moyen facile - ici, nous ne nous considérons pas comme un gourou de ROS.



Nous n'avons pas réussi à faire en sorte qu'une telle assemblée se comporte bien. Plus précisément, il a été possible de sous-estimer l'accélération du déplacement à 0,05-0,1 m / s ^ 2 et la vitesse angulaire à 0,03 rad / s.



J'ai pensé que ce serait bien d'avoir:



  • Plateforme bon marché
  • Direction de roue synchrone
  • Calcul d'odométrie basé sur le comportement et la maniabilité des roues
  • Modes de rotation avec différentes commandes
  • Différentes restrictions dans différents modes


Ce qui est arrivé à la fin



Le contrôleur a été pris sur les planches du gyro-scooter et la commande de roue a été écrite de telle manière que la commande de couple est utilisée lors du démarrage du mouvement et des virages. Et si le chariot va tout droit et accélère à une certaine vitesse, alors le mode de contrôle de vitesse est activé. Dans les deux modes, les données des encodeurs sont traitées à l'intérieur du contrôleur, en tenant compte de la vitesse et du mode, et les données sont émises avec une certaine prédiction avant 10-15 ms.



Les codeurs sont toujours lus dans le contrôleur, s'accumulent dans un tampon de 2-3 éléments et sont transmis avec un retard. L'essentiel est que lorsque le contrôle est reçu, la réponse ne va qu'après l'exécution de la commande - c.-à-d. le tampon est bloqué jusqu'à ce que les valeurs modifiées du codeur soient reçues. Mais l'odométrie est en cours d'émission, elle utilise juste la dernière valeur déjà transmise.



Car Tous les problèmes ci-dessus se résument au fait qu'il est nécessaire dans tous les cas de synchroniser le contrôle sur réception-transmission synchrone depuis le port UART, puis nous avons considéré qu'il était déraisonnable d'introduire un synchroniseur forcé dans le package diff_drive, nous avons donc écrit notre propre package de contrôle.



Il se trouve ici github.com/Shadowru/hoverboard_driver et est actuellement en cours de développement actif:



launch :



<node name="hoverboard_driver" pkg="hoverboard_driver" type="node" output="screen">
        <param name="uart" value="{ }"/>
        <param name="baudrate" value="115200"/>
        <param name="wheel_radius" value="0.116"/>
        <param name="base_width”  value="0.43"/>
        <param name="odom_frame”  value="odom"/>
        <param name="base_frame”  value="base_link"/>
    </node>
      
      





Le port uart lui-même doit disposer des droits d'accès appropriés, sur certaines plates-formes, il n'a pas toujours accès pour l'utilisateur. Par exemple, pour le Jetson Nano dans le répertoire hoverboard_driver / scripts / jetson_nano_serial.sh, un script est attaché qui définit les droits au démarrage du système d'exploitation.



Le paquet lui-même contient la lecture du flux de données du contrôleur et l'émission des informations pertinentes aux sujets:



hoverboard_driver / hoverboard_msg avec un paquet comme hoverboard_msg



La structure du message est la suivante:



int16 state1 - informations internes sur la roue 1

int16 state2 - informations internes sur la roue 2

int16 speed1 - vitesse instantanée de la roue 1

int16 speed2 - vitesse instantanée de la roue 2

int16 batVoltage - tension de la batterie

int16 boardTemp - température du contrôleur

int16 error1 - roue 1 erreur

int16 error2 - roue 2 erreur

int32 pulseCount1 - roue 1 du compteur du codeur

int32 pulseCount2 - roue 2 compteur de codeur



En outre, un message typique nav_msgs :: Odométrie est sortie au sujet de hoverboard_driver / odométrie



La position est calculée comme suit:



Sur la base des paramètres wheel_radius - le rayon de la roue en mètres, base_width - la distance entre les centres des roues, nous calculons combien chaque roue a bougé pendant le temps entre la position précédente et la lecture.



double curr_wheel_L_ang_pos = getAngularPos((double) feedback.pulseCount1);
double curr_wheel_R_ang_pos = getAngularPos((double) feedback.pulseCount2);

double dtime = (current_time - last_time).toSec();

double delta_L_ang_pos = curr_wheel_L_ang_pos - raw_wheel_L_ang_pos;
double delta_R_ang_pos = -1.0 * (curr_wheel_R_ang_pos - raw_wheel_R_ang_pos);
      
      





Ensuite, nous calculons l'accélération de chacune des roues



wheel_L_ang_vel = delta_L_ang_pos / (dtime);
wheel_R_ang_vel = delta_R_ang_pos / (dtime);
      
      





Ensuite, nous calculons l'accélération linéaire du robot le long de chacun des axes



robot_angular_vel = (((wheel_R_ang_pos - wheel_L_ang_pos) * wheel_radius / base_width) - robot_angular_pos) / dtime;
robot_angular_pos = (wheel_R_ang_pos - wheel_L_ang_pos) * wheel_radius / base_width;

robot_x_vel = ((wheel_L_ang_vel * wheel_radius + robot_angular_vel * (base_width / 2.0)) * cos(robot_angular_pos));
robot_y_vel = ((wheel_L_ang_vel * wheel_radius + robot_angular_vel * (base_width / 2.0)) * sin(robot_angular_pos));
      
      





En conséquence, un ensemble complet est obtenu - accélération linéaire, accélération angulaire et en les multipliant par le temps - le déplacement de la position du robot.



robot_x_pos = robot_x_pos + robot_x_vel * dtime;
robot_y_pos = robot_y_pos + robot_y_vel * dtime;
      
      





Après cela, le message d'odométrie est envoyé, plus une traduction tf entre le cadre d'odométrie et la base.



Le contrôleur à l'entrée est contrôlé par un paquet avec 2 paramètres - vitesse et tour, le paquet est transmis de torsion presque nativement - la vitesse est divisée par la circonférence et les tours sont obtenus.



double v = vel.linear.x;
double rps = v / rpm_per_meter;
double rpm = rps * 60;
int16_t speed = static_cast(rpm);

      
      





et l'accélération angulaire est convertie en différence de vitesse de roue sous forme de multiplication par un coefficient, un nouveau calcul sera ajouté en tenant compte de l'empattement, mais en pratique cela n'est nécessaire que pour des robots suffisamment grands et lourds.



double w = vel.angular.z;
int16_t steer = static_cast<int>(-1 * w * 30);

      
      





En conséquence, il était possible d'obtenir une commande de chariot très stable sur des composants bon marché.







Nous créons des robots, comme la grande majorité d'entre vous. Nous avons notre produit principal, que nous développons activement. Testé par pilote et prêt pour la production. Il s'agit d'un robot pour collecter des balles de golf.



Nous développons des robots personnalisés et des solutions dérivées. Parfois, il s'agit d'un travail allant de la mission technique et du croquis au produit fini, parfois une partie du travail.







Dans la plupart des cas, le robot a besoin de roues pour interagir avec le monde extérieur. Le plus souvent, il s'agit de moteurs sans balais, en raison de la capacité de contrôler avec précision la vitesse et la position.



Pour les petits robots, les roues d'un gyro-scooter sont souvent utilisées, cela se justifie par la production de masse et le prix de cette solution. Quiconque a vu la liste des prix des moteurs russes comprend l'importance de la production de masse.







En ce qui concerne le contrôleur, il s'agit le plus souvent de modèles esc, vesc, odrive, BLD-300B ou de solutions maison.



Pour entrer facilement dans la création de vrais robots et briser la malédiction Gazebo, la plupart des développeurs ont besoin d'une baleine pour une entrée facile. Beaucoup de choses dans le monde réel sont différentes de l'idéal.



Parfois, des choses imprévisibles se produisent, des capteurs bruyants, en temps réel, un débordement de la mémoire tampon. Sur cet appareil vidéo, que nous avons testé précédemment avec un contacteur et un interrupteur à distance.





Nous proposons quelque chose qui nous aiderait à économiser les nerfs en temps voulu, il s'agit d'un kit pour assembler le boîtier (parallélépipède et un cylindre), deux roues motrices, une batterie, un chargeur et un contrôleur flash qui donne l'odométrie et fonctionne avec notre package ROS prêt à l'emploi pour 19.000 frotter. C'est moins cher que le fraisage, le coût du matériau composite, des fixations et une roue pivotante rembourrée.







Appelez-nous ou demandez une plateforme pour ROS en ligne . Faisons ensemble des robots. Nous vous en dirons



plus sur la plateforme lors du meetup Robot Operating System le 5 décembre. L'inscription des participants est déjà ouverte.



→ Inscription pour les téléspectateurs



All Articles