Posts da série:
8. Nós controlamos a partir do telefone-ROS Control, GPS-node7. Localização do robô: gmapping, AMCL, pontos de referência no mapa da sala6. Odometria com codificadores de roda, mapa da sala, lidar5. Trabalhamos em rviz e gazebo: xacro, novos sensores.4. Crie uma simulação de robô usando os editores rviz e gazebo.3. Acelere, troque a câmera, conserte a marcha2. Software1. FerroNa última vez, projetamos o projeto na forma de módulos xacro separados, adicionamos uma câmera de vídeo virtual e imu (giroscópio).
Neste post, trabalharemos com a odometria dos codificadores ópticos montados nos eixos das rodas, carregaremos um mapa da sala e o montaremos em um carrinho de robô real.
Odometria e tf
O que é odometria e tf e como eles geralmente são implementados no ROS já está bem descrito no recurso, portanto, nos referimos aos artigos relevantes na parte da teoria, por exemplo,
aqui .
Partindo da base teórica, trabalharemos com a prática.
Vamos começar trabalhando em um robô de carrinho conectando-o via VNC.
Vá para a pasta rosbots_driver e crie um nó de arquivo. Este arquivo gera odometria, recebendo-o de codificadores ópticos, que por sua vez o enviam para o arduino uno e, em seguida, para o raspberry pi.
cd /home/pi/rosbots_catkin_ws/src/rosbots_driver/scripts/rosbots_driver touch diff-tf.py
Colocamos o código no arquivo:
Salve o arquivo e torne-o executável:
CTRL+X
chmod +x diff-tf.py
Agora, no robô, execute os 2º nós - driver e diff-tf:
1º terminal:
python diff_tf.py
2º:
rosrun rosbots_driver part2_cmr.py
No terceiro terminal, verificaremos se há novos tópicos odom e tf:

Vamos ver com o comando rostopic echo odom o que é publicado no tópico (e se ele é publicado).
A saída será aproximadamente da seguinte maneira:

Agora, sem fechar os nós em execução no robô, lançaremos o computador de controle com os ambientes gráficos rviz e gazebo.
* Uma imagem (máquina virtual VMWare com Ubuntu 16.04 + ROS Kinetic), oferecida anteriormente para download, contém tudo o que você precisa.
No computador de controle (doravante denominado "Computador"), execute o modelo em rviz:
roslaunch rosbots_description rviz.launch
O modelo do robô carregado com o qual funcionou nas postagens anteriores carregará:

Adicione duas telas ao rviz clicando em Adicionar. A tela com odometria e a tela com tf, marque as caixas para visualizá-las.
Na janela em que o modelo do robô é representado, gráficos característicos aparecerão:

* Para torná-lo mais visível, você pode desativar a tela Robotmodel.
Controlamos o robô a partir do teclado do computador e vemos como a visualização de tf e odometria muda.
Sem fechar o rviz no 2º terminal, iniciaremos o controle a partir do teclado:
rosrun teleop_twist_keyboard teleop_twist_keyboard.py /cmd_vel:=/part2_cmr/cmd_vel
Ao controlar o robô, a janela com visualização mostrará: seta vermelha (visualização do tópico odom), linhas vetoriais (tópico tf).
Se a seta vermelha do tópico odom mostra a direção do movimento do robô, as linhas vetoriais tf mostram como os elementos individuais do robô estão localizados no espaço:
Agora, para seguir em frente, você precisa "ajustar" a odometria.
Para fazer isso, feche o editor rviz e inicie-o novamente, apenas sem visualizar o modelo com o comando:
rosrun rviz rviz
Isso é necessário para que apenas base_link e odom permaneçam nos vetores do tópico tf:

No rviz, uma célula tem 1 metro. Portanto, na realidade, o robô também deve passar 1 metro para que os dados sejam comparáveis.
Passaremos 1 metro no robô, controlando-o pelo teclado. No rviz, o robô também precisa dirigir 1 metro - uma célula.
Se o robô viaja mais tempo do que deveria no rviz, ou vice-versa, a uma distância menor do que na realidade, é necessário editar o arquivo diff_tf.py que foi criado anteriormente, ou seja, este bloco:
diff_tf.py #### parameters ####### #Wheel radius : 0.0325 # wheel circum = 2* 3.14 * 0.0325 = 0.2041 # One rotation encoder ticks : 8 ticks # For 1 meter: 8 * ( 1 / 0.2041) = 39 ticks self.rate = rospy.get_param('~rate',10.0) # the rate at which to publish the transform self.ticks_meter = float(rospy.get_param('ticks_meter', 190)) # The number of wheel encoder ticks per meter of travel self.base_width = float(rospy.get_param('~base_width', 0.11)) # The wheel base width in meters
Mapa
Para ir a algum lugar, você precisa de um mapa. Para os propósitos do nosso robô - precisamos de um mapa da sala.
Vamos trabalhar com ela.
Para fazer upload de um mapa para o rviz, você precisa criar uma pasta de mapa no projeto (rosbots_description) no Computador (não no robô) e colocar dois arquivos nele que compõem o mapa: map.pgm e map.yaml.
* De fato, pode haver vários arquivos de mapa em uma pasta, mas você só pode enviar um para o assistente.
Um mapa no ROS consiste em dois arquivos, um dos quais é uma imagem PGM, em que cada pixel é:
- espaço em branco é livre;
- espaço negro é ocupado por um obstáculo;
- espaço cinza ainda não foi explorado.
O segundo arquivo .yaml é um arquivo com as configurações do mapa, onde são indicadas suas dimensões, ocupação de pixels com diferentes tipos (listados acima) e outros parâmetros.
Execute o nó no computador que publicará o cartão:
rosrun map_server map_server /home/pi/catkin_ws/src/rosbots_description/maps/rail_lab.pgm 0.05
No terminal vizinho, execute o modelo em rviz:
roslaunch rosbots_description rviz.launch
No rviz, adicione uma exibição de mapa.
No rviz, o robô mostrou-se desproporcionalmente grande e está localizado fora do mapa:

Para corrigir isso, você precisa executar um mapa em que o tamanho da célula seja de 1 metro. Reinicie o cartão com o parâmetro 1 no final:
rosrun map_server map_server /home/pi/catkin_ws/src/rosbots_description/maps/rail_lab.pgm 1
Agora você pode montar o mapa no rviz, controlando o robô a partir do teclado:
Então, o que foi alcançado :
- receber dados de odometria dos codificadores ópticos das rodas do robô e enviá-los aos tópicos para exibição no rviz;
- configurar a odometria do robô para corresponder à distância percorrida ao vivo e virtualmente;
- carregar e exibir um mapa da sala.
No entanto, apesar do mapa ser exibido e o robô poder andar com uma odometria “sintonizada”, na realidade o robô é cego. Ele não vê obstáculos e tropeçará neles. O segundo ponto negativo é o mapa da sala virtual carregado no rviz, que permite que você viaje sozinho em todas as direções, mesmo naquelas em que os obstáculos são claramente mostrados.
Como fazer o robô "ver" obstáculos na realidade e virtualmente?
Com um ambiente virtual é mais simples. Tudo aqui é baseado no emulador-editor de gazebo. E nos posts anteriores isso foi mencionado.
É mais complicado com a realidade. Precisamos de um elemento (sensor) que indique obstáculos e relate isso ao sistema.
Uma opção é colocar o lidar no robô.
Lidar RPlidar A1
Usaremos a solução de orçamento acessível e colocaremos o lidar no robô. Talvez essa solução seja mais cara do que usar o mesmo Kinect, mas, como a prática demonstrou, é mais eficaz em termos de velocidade, precisão e facilidade de instalação (menos complicada). Além disso, é mais fácil começar a trabalhar com o lidar, como Nenhuma reflexão é necessária sobre como alimentá-lo e conectá-lo ao projeto (https://habr.com/en/company/tod/blog/210252/).
Nós precisaremos do pacote ros para trabalhar com o lidar -
wiki.ros.org/rplidar .
Com a ajuda do lidar, construiremos um mapa da sala e também o usaremos na navegação.
Como instalar o rplidar no ROS tem muitos artigos, por exemplo
aqui .
Usaremos o conhecimento de idosos de cabelos grisalhos e instalaremos pacotes com o lidar no sistema
no robô :
cd /home/pi/rosbots_catkin_ws/src git clone https://github.com/robopeak/rplidar_ros.git cd .. catkin_make
No
computador, instale o pacote para trabalhar com a placa:
cd /home/pi/rosbots_catkin_ws/src git clone https://github.com/tu-darmstadt-ros-pkg/hector_slam </code> cd .. catkin_make
Execute o pacote no robô e verifique se o lidar está funcionando:
sudo chmod a+rw /dev/ttyUSB0 roslaunch rplidar_ros rplidar.launch
* O primeiro comando dá acesso à porta usb onde o lidar está conectado.
Se tudo correu bem, ele produzirá linhas para o console:
[ INFO] [1570900184.874891236]: RPLIDAR running on ROS package rplidar_ros. SDK Version:1.9.0 RPLIDAR S/N: ---------------- [ INFO] [1570900187.397858270]: Firmware Ver: 1.24 [ INFO] [1570900187.398081809]: Hardware Rev: 5 [ INFO] [1570900187.401749476]: RPLidar health status : 0 [ INFO] [1570900188.014285166]: current scan mode: Express, max_distance: 12.0 m, Point number: 4.0K , angle_compensate: 1
Aqui configuramos imediatamente um pouco de lidar, porque o
site oficial diz que (lidar) pode funcionar melhor.
Precisamos obter a saída quando a digitalização não é de 4,0K pontos, que são emitidos por padrão, mas de 8,0K. Esta opção melhorará um pouco a qualidade da digitalização.
Para isso, definiremos mais um parâmetro no pacote rplidar - modo de verificação:
cd /rosbots_catkin_ws/src/rplidar_ros/launch nano nano rplidar.launch
E depois
<param name="angle_compensate" type="bool" value="true"/>
adicione a linha:
<param name="scan_mode" type="string" value="Boost"/>
A segunda linha que precisa ser corrigida aqui:
<param name="frame_id" type="string" value="laser"/>
Substitua o valor do laser por base_link.
* Agora, se você reiniciar o nó com o comando roslaunch rplidar_ros rplidar.launch, a saída será diferente:
[ INFO] [1570900188.014285166]: current scan mode: Boost, max_distance: 12.0 m, Point number: 8.0K , angle_compensate: 1
Dê uma olhada. que exibe lidar em rviz.
Para fazer isso, execute o robô:
roslaunch rplidar_ros rplidar.launch
Em um computador:
roslaunch rosbots_description rviz.launch
No rviz, adicione a tela LaserScan e selecione o tópico de digitalização. Além disso, será visto que as mensagens estão caindo no tópico:

Na janela com a visualização do robô, o robô acabou sendo um gigante. Com seu tamanho, descobriremos mais tarde. Agora vamos construir um mapa da sala.
Para fazer isso, crie um pacote com um nó:
catkin_create_pkg my_hector_mapping rospy cd my_hector_mapping mkdir launch cd launch nano hector.launch
hector.launch <?xml version="1.0"?> <launch> <node pkg="tf" type="static_transform_publisher" name="laser_link" args="0.0 0.0 0.0 0.0 0.0 0.0 /base_link /laser 50" /> <node pkg="hector_mapping" type="hector_mapping" name="hector_mapping" output="screen"> <!-- Frame names --> <param name="map_frame" value="map" /> <param name="odom_frame" value="base_link" /> <!-- Map size / start point --> <param name="map_resolution" value="0.050"/> <param name="map_size" value="1024"/> <param name="map_start_x" value="0.5"/> // <param name="map_start_y" value="0.5" /> <param name="map_multi_res_levels" value="2" /> <!-- Map update parameters --> <param name="update_factor_free" value="0.4"/> <param name="update_factor_occupied" value="0.9" /> <param name="map_update_distance_thresh" value="0.4"/> <param name="map_update_angle_thresh" value="0.06" /> <param name="laser_z_min_value" value="-1.0" /> <param name="laser_z_max_value" value="1.0" /> <!-- Advertising config --> <param name="advertise_map_service" value="true"/> <param name="scan_subscriber_queue_size" value="5"/> <param name="scan_topic" value="scan"/> </node> </launch>
cd ~/rosbots_catkin_ws catkin_make
Vamos correr.
No robô:
1º terminal:
roslaunch rplidar_ros rplidar.launch
2nd:
rosrun rosbots_driver part2_cmr.py
Em um computador:
1º terminal:
roslaunch my_hector_mapping hector.launch
2nd:
roslaunch rosbots_description rviz.launch
3º:
rosrun teleop_twist_keyboard teleop_twist_keyboard.py /cmd_vel:=/part2_cmr/cmd_vel
Nos monitores, você precisa adicionar o mapa, e Quadro fixo, selecione base_link. Então você pode observar em tempo real como o lidar "ilumina" o espaço ao seu redor:

Na etapa atual, para construir um mapa, você precisa andar pela sala, “parando” em diferentes ângulos para que o lidar os marque no mapa.
Portanto, recomende livros didáticos. Mas nosso conselho é pegar o robô e andar com ele, segurando-o na sua frente. Portanto, a velocidade de construção de um mapa será maior no sentido de que você não precisará se distrair e olhar para onde o robô dirigiu na próxima sala na ausência de contato visual.
Além disso, ao girar o robô em torno de seu eixo durante uma viagem, o lidar deixa artefatos pretos característicos nos locais onde não há realmente obstáculos:

Após criar o mapa, salve-o com o comando:
rosrun map_server map_saver -f map-1
Construir o mapa perfeito com um orçamento lidar é um mito. Portanto, ajudaremos o lidar no Photoshop. Removeremos os artefatos pretos do mapa, onde realmente não há obstáculos, e alinharemos as paredes com linhas pretas:

Não esqueça de salvar o mapa no formato .pgm.
Agora repetimos no computador os comandos que estavam no início do post, mas com um novo mapa:
1º terminal:
rosrun map_server maserver /home/pi/catkin_ws/src/rosbots_description/maps/map-1.pgm 0.05
2nd:
roslaunch rosbots_description rviz.launch
Resultado em rviz:

O novo mapa foi carregado, como o modelo do robô, mas o robô está fora do mapa.
Falaremos sobre isso mais tarde, mas, por enquanto, vamos resumir:
- dominando o lidar RP-lidar A1
- construindo um mapa de sala usando um lidar, ajustando-o e carregando-o no editor visual rviz.
Arquivos para download:
mapa da sala .