ROS2 Programming Basics Using Python

ROS2 Programming Basics Using Python

What we are going to learn:

How to send a message using Topic Publisher and Subscriber using Python

To ensure stability, I’ll guide you through ROS2 Foxy on Ubuntu 20.04 system. I’ll be using Docker images for installation, but the process is similar to a local Ubuntu setup.

Prerequisites:

Ubuntu 20.04 installed on your computer.

We will actually create and run a ROS2 package that sends and receives messages through Publisher and Subscriber.

If you want to learn ROS 2 Python in a practical, hands-on way, check out the course ROS 2 Basics in 5 Days: https://app.theconstruct.ai/courses/132

In this course, you’ll cover the foundational concepts needed to start working with ROS 2, as well as more advanced topics, all while engaging in hands-on practice.

1. Make Package:


The command to create a package is as follows:

ros2 pkg create [package_name] --build-type [build_type] --dependencies [dependent package1][dependent package2]

Lets’ make ros2_ws and create the ros_topic_pkg package

mkdir ~/ros2_ws/src
cd ~/ros2_ws/src
ros2 pkg create ros_topic_pkg --build-type ament_python --dependencies rclpy std_msgs

2. Write Publisher and Subscriber script

Firstly, we will make empty script publisher.py, subscriber.py in ros_topic_pkg_folder

cd ~/ros2_ws/src/ros_topic_pkg/ros_topic_pkg
touch publisher.py
touch subscriber.py

After make empty script, Using Vim or VsCode, write down this publisher and subscriber code

publihser.py
import rclpy
from rclpy.node import Node
from rclpy.qos import QoSProfile
from std_msgs.msg import String

class Publisher(Node):
def __init__(self):
super().__init__('Publisher')
qos_profile = QoSProfile(depth=10)
self.publisher = self.create_publisher(String, 'topic', qos_profile)
self.timer = self.create_timer(1, self.publish_msg)
self.count = 0

def publish_msg(self):
msg = String()
msg.data = 'Number: {0}'.format(self.count)
self.publisher.publish(msg)
self.get_logger().info('Published message: {0}'.format(msg.data))
self.count += 1

def main(args=None):
rclpy.init(args=args)
node = Publisher()
try:
rclpy.spin(node)
except KeyboardInterrupt:
node.get_logger().info('Keyboard Interrupt')
finally:
node.destroy_node()
rclpy.shutdown()

if __name__ == '__main__':
main()

subscriber.py
import rclpy
from rclpy.node import Node
from rclpy.qos import QoSProfile
from std_msgs.msg import String​

class Subscriber(Node):

def __init__(self):
super().__init__('Subscriber')
qos_profile = QoSProfile(depth=10)
self.subscriber = self.create_subscription(
String,
'topic',
self.subscribe_topic_message,
qos_profile)

def subscribe_topic_message(self, msg):
self.get_logger().info('Received message: {0}'.format(msg.data))​

def main(args=None):
rclpy.init(args=args)
node = Subscriber()
try:
rclpy.spin(node)
except KeyboardInterrupt:
node.get_logger().info('Keyboard Interrupt')
finally:
node.destroy_node()
rclpy.shutdown()​

if __name__ == '__main__':
main()


3. Write a Python package configuration file

Lastly, we have to write down this setup.py file to build Ros2 package

from setuptools import find_packages, setup

package_name = 'ros_topic_pkg'

setup(
name=package_name,
version='0.0.0',
packages=find_packages(exclude=['test']),
data_files=[
('share/ament_index/resource_index/packages',
['resource/' + package_name]),
('share/' + package_name, ['package.xml']),
],
install_requires=['setuptools'],
zip_safe=True,
maintainer='user',
maintainer_email='user@todo.todo',
description='TODO: Package description',
license='TODO: License declaration',
tests_require=['pytest'],
entry_points={
'console_scripts': [
'publisher = ros_topic_pkg.publisher:main',
'subscriber = ros_topic_pkg.subscriber:main'
],
},
)

4 Build package:

If you write down all the code correctly, Now we will build ros2_topic pkg

cd ~/ros2_ws && colcon build --symlink-install

If the build is completely normal, you must load the configuration file and set the node for the executable package to run the build node

You can see the file that writes a lot of commands, at the end of the file, Input i to change insert mode and write
source install/setup.bash

Now let’s run the publisher and subscriber we created

First, run publisher to issue a topic

ros2 run ros_topic_pkg publisher

Then Run a new terminal and run the Subscriber after proceeding with the configuration file load

source install/setup.bash


If you wrote the code correctly, you can see that the subscriber is properly subscribing to the numbers issued by the publisher.

Congratulations. You have now learned how to send a message using Topic Publisher and Subscriber using Python.

To learn more about ROS 2, have a look at the course below:

We hope this tutorial was really helpful to you.

This tutorial is created by Robotics Ambassador Park.

Criação de Serviços Personalizados no ROS 2 e Controle de Movimento do Robô em Python – Portuguese ROS Tutorial

Criação de Serviços Personalizados no ROS 2 e Controle de Movimento do Robô em Python – Portuguese ROS Tutorial

This tutorial is created by Robotics Ambassador – Anderson

Robotics Ambassador: theconstruct.ai/robotics-ambassador/

 

O que nós vamos aprender:

  1. Criação de um serviço personalizado no ROS2.
  2. Configuração do ambiente ROS2 para garantir que todas as dependências estão corretamente instaladas e atualizadas.
  3. Criação de um pacote ROS2 incluindo a estrutura de diretórios e os arquivos necessários para o projeto.
  4. Implementação de um servidor e cliente de serviço para controle de movimento do robô.
  5. Criação e edição de arquivos de lançamento (launch files) no ROS2.
  6. Compilação e execução dos pacotes ROS2.
  7. Teste e verificação do serviço para controlar o movimento do robô em diferentes direções.

 

Lista de recursos usados neste post:

  1. Use este rosject: https://app.theconstruct.ai/l/639df241/
  2. The Construct: https://app.theconstructsim.com/
  3. ROS Courses: ROS Basics in 5 Days (C++) https://app.theconstructsim.com/courses/132

 

Panorama

Neste tutorial, vamos aprender a criar serviços personalizados no ROS2 e desenvolver um pacote de controle de movimento para um robô. Vamos passar pelos passos de criação e configuração de serviços, desenvolvimento de um pacote de movimento, implementação do servidor e cliente de serviço, e a criação de arquivos de lançamento. Este tutorial é ideal para quem deseja aprimorar suas habilidades em ROS2 e programação robótica.

 

Abrindo o rosject

Clique no link abaixo para ter acesso ao rosject deste tutorial. Em seguida, clique no botão “RUN”.

https://app.theconstruct.ai/l/639df241/

<figure1>

Criando o Serviço Personalizado

Criação do Pacote de Interfaces Personalizadas

Primeiro, vamos criar um pacote de interfaces personalizadas que conterá nosso serviço. Este pacote será responsável por definir e gerenciar a interface do serviço que iremos usar para controlar o robô.

Copie este bloco de comandos no primeiro terminal:

cd ~/ros2_ws/src
ros2 pkg create --build-type ament_cmake custom_interfaces --dependencies rclcpp std_msgs

Esses comandos criam um novo pacote chamado custom_interfaces com as dependências rclcpp e std_msgs.

Definição do Serviço

Em seguida, vamos definir o serviço que será utilizado para controlar o robô. Para isso, crie uma pasta chamada srv dentro do pacote custom_interfaces e um arquivo Move.srv. Use os comandos:

cd ~/ros2_ws/src/custom_interfaces
mkdir srv
cd srv
touch Move.srv

Edite o arquivo Move.srv com o seguinte conteúdo:

string direction               # Direção para girar (direita ou esquerda)
float64 velocity               # Velocidade angular (em rad/s) ou linear (em m/s)
int32 time                     # Duração do giro (em segundos)
---
bool success                   # O comando foi bem-sucedido?

Esse arquivo define a estrutura do serviço. Ele recebe a direção, velocidade e tempo como entrada, e retorna um booleano indicando se a operação foi bem-sucedida.

Atualizando os Arquivos CMakeLists.txt e package.xml

Agora, precisamos configurar os arquivos CMakeLists.txt e package.xml para que o ROS2 possa construir e utilizar nosso serviço.

No arquivo CMakeLists.txt, adicione:

find_package(rosidl_default_generators REQUIRED)
.
.
.
rosidl_generate_interfaces(${PROJECT_NAME}
"srv/Move.srv"
)

Essas linhas garantem que o gerador de interfaces do ROS2 processe nosso arquivo Move.srv.

No arquivo package.xml, adicione:

<build_depend>rosidl_default_generators</build_depend>
<exec_depend>rosidl_default_runtime</exec_depend>
<member_of_group>rosidl_interface_packages</member_of_group>

Essas dependências são necessárias para a construção e execução do nosso serviço.

Compilação e Verificação

Agora, compile o pacote e verifique se o serviço foi criado corretamente.

cd ~/ros2_ws
colcon build --packages-select custom_interfaces
source ~/ros2_ws/install/setup.bash

Para verificar se a mensagem de serviço foi criada:

ros2 interface show custom_interfaces/srv/Move

Criando o Pacote de Movimento

Vamos criar um pacote que implementará a lógica de movimento do robô, incluindo um servidor e um cliente de serviço.

cd ~/ros2_ws/src
ros2 pkg create --build-type ament_python movement_pkg --dependencies rclpy custom_interfaces std_msgs geometry_msgs sensor_msgs

Este comando cria um pacote chamado movement_pkg com as dependências necessárias.

Crie os arquivos necessários com os comandos:
cd ~/ros2_ws/src/movement_pkg/movement_pkg
touch movement_server.py movement_client.py

Implementação do Servidor de Serviço

Crie e edite o arquivo movement_server.py com o seguinte conteúdo:


from geometry_msgs.msg import Twist
from custom_interfaces.srv import Move
import rclpy
from rclpy.node import Node
import time

class Service(Node):
    def __init__(self):
        super().__init__('move_server')
        self.srv = self.create_service(Move, 'move', self.custom_service_callback)
        self.publisher_ = self.create_publisher(Twist, 'cmd_vel', 10)

    def custom_service_callback(self, request, response):
        msg = Twist()
        if request.direction == "right":
            msg.angular.z = -request.velocity
        elif request.direction == "left":
            msg.angular.z = request.velocity
        elif request.direction == "forward":
            msg.linear.x = request.velocity
        elif request.direction == "backward":
            msg.linear.x = -request.velocity
        elif request.direction == "stop":
            msg.linear.x = 0.0
            msg.angular.z = 0.0
            self.publisher_.publish(msg)
            response.success = True
            return response
        else:
            response.success = False
            return response

        self.publisher_.publish(msg)
        time.sleep(request.time)
        msg.linear.x = 0.0
        msg.angular.z = 0.0
        self.publisher_.publish(msg)
        response.success = True
        return response

def main(args=None):
    rclpy.init(args=args)
    service = Service()
    rclpy.spin(service)
    rclpy.shutdown()

if __name__ == '__main__':
    main()

Explicação do código:

  • Importamos as bibliotecas necessárias.
  • Definimos a classe Service, que herda de Node.
  • No método __init__, criamos o serviço e o publicador.
  • O método custom_service_callback define a lógica de controle do robô com base nos parâmetros recebidos.
  • No final, iniciamos e rodamos o nó ROS2.

Implementação do Cliente de Serviço

Crie e edite o arquivo movement_client.py com o seguinte conteúdo:


from custom_interfaces.srv import Move
import rclpy
from rclpy.node import Node
import sys

class ClientAsync(Node):
    def __init__(self):
        super().__init__('move_client')
        self.client = self.create_client(Move, 'move')
        while not self.client.wait_for_service(timeout_sec=1.0):
            self.get_logger().info('service not available, waiting again...')
        self.req = Move.Request()

    def send_request(self):
        self.req.direction = str(sys.argv[1])
        self.req.velocity = float(sys.argv[2])
        self.req.time = int(sys.argv[3])
        self.future = self.client.call_async(self.req)

def main(args=None):
    rclpy.init(args=args)
    client = ClientAsync()
    client.send_request()

    while rclpy.ok():
        rclpy.spin_once(client)
        if client.future.done():
            try:
                response = client.future.result()
            except Exception as e:
                client.get_logger().info('Service call failed %r' % (e,))
            else:
                client.get_logger().info('Response state %r' % (response.success,))
            break

    client.destroy_node()
    rclpy.shutdown()

if __name__ == '__main__':
    main()

Explicação do código:

  • Importamos as bibliotecas necessárias.
  • Definimos a classe ClientAsync, que herda de Node.
  • No método __init__, criamos o cliente de serviço e esperamos que o serviço esteja disponível.
  • O método send_request envia a solicitação ao serviço com os parâmetros fornecidos.
  • No final, iniciamos e rodamos o nó ROS2.

Criando o Arquivo de Lançamento

cd ~/ros2_ws/src/movement_pkg
mkdir launch
cd launch
touch movement_server_launch_file.launch.py
chmod +x movement_server_launch_file.launch.py

Edite o arquivo movement_server_launch_file.launch.py com o seguinte conteúdo:


from launch import LaunchDescription
from launch_ros.actions import Node

def generate_launch_description():
    return LaunchDescription([
        Node(
            package='movement_pkg',
            executable='movement_server',
            output='screen'),
    ])

Este arquivo de lançamento define um nó que executa o servidor de movimento.

Então sua estrutura de pastas e arquivos deve ficar assim:

Modificação do arquivo setup.py

Atualize o arquivo setup.py com o seguinte conteúdo:


from setuptools import setup
import os
from glob import glob

package_name = 'movement_pkg'

setup(
    name=package_name,
    version='0.0.0',
    packages=[package_name],
    data_files=[
        ('share/ament_index/resource_index/packages',
            ['resource/' + package_name]),
        ('share/' + package_name, ['package.xml']),
        (os.path.join('share', package_name), glob('launch/*.launch.py'))
    ],
    install_requires=['setuptools'],
    zip_safe=True,
    maintainer='user',
    maintainer_email='user@todo.todo',
    description='TODO: Package description',
    license='TODO: License declaration',
    tests_require=['pytest'],
    entry_points={
        'console_scripts': [
        'movement_server = movement_pkg.movement_server:main',
        'movement_client = movement_pkg.movement_client:main'
        ],
    },
)

Este arquivo define a configuração do pacote, incluindo as entradas do console que apontam para nossos scripts Python.

Compilação e Execução

Compile o pacote movement_pkg:

cd ~/ros2_ws
colcon build --packages-select movement_pkg
source ~/ros2_ws/install/setup.bash

Lançando o Servidor

No primeiro terminal, execute:

ros2 launch movement_pkg movement_server_launch_file.launch.py

Executando o Cliente

No segundo terminal, execute:

source ~/ros2_ws/install/setup.bash
ros2 run movement_pkg movement_client left 0.2 5

No segundo terminal você verá:

Enquanto no primeiro terminal aparecerá:

Isso indica que o serviço foi realizado corretamente.

Na janela do Gazebo, você pode ver o robô se movimentando pelo ambiente.

<figure7>

Outras opções, além de left, são right, forward, backward. Experimente mudar os parametros do comando anterior variando também a velocidade e a duraçao do movimento do robô (respectivamente segundo e terceiro parametros do comando).

Conclusão

Esperamos que este tutorial tenha sido útil e que você tenha aprendido como criar serviços personalizados no ROS2 e controlar o movimento de um robô. Se você gostou deste conteúdo, considere explorar mais recursos do ROS2 e experimentar novas possibilidades para expandir suas habilidades em robótica.

 Vídeo no YouTube

Este foi o post de hoje. Lembre-se que nós temos uma versão deste post em vídeo no YouTube.

Se você gostou do conteúdo, por favor, considere se inscrever no nosso canal do YouTube. Estamos publicando novos conteúdos quase todos os dias.

Continue avançando no seu aprendizado de ROS.

 

Comment utiliser ROSlibjs avec ROS2 – French ROS2 Tutorial

Comment utiliser ROSlibjs avec ROS2 – French ROS2 Tutorial

This tutorial is created by Robotics Ambassador 023 Enzo

Rosbotics Ambassador Program https://www.theconstruct.ai/rosbotics-ambassador/
Cours: ROS2 Basics in 5 Days C++: https://app.theconstructsim.com/courses/133

Dans ce tutoriel, nous allons voir comment utiliser ROSLibjs avec ROS2 pour tirer parti de la puissance de ROS dans des applications web et JavaScript. Nous allons mettre en place un exemple simple d’une page HTML utilisant ROSLibjs pour communiquer avec un système ROS2. L’objectif du tutoriel sera d’utiliser un publisher et un subscriber depuis notre page web pour interagir avec un turtlebot3 simulé dans Gazebo.

Prérequis: Utiliser une installation ROS2 avec Gazebo

ROS2

Vous pouvez vous connecter au site TheConstruct pour acceder à des machines virtuelles préconfigurées avec une installation ROS. Ce tutoriel est realisé avec ROS Humble.

Si vous voulez effectuer le tutoriel sur votre installation local, vous devez avoir ROS2 installé (https://docs.ros.org/en/humble/Installation.html), avoir configuré un workspace (https://docs.ros.org/en/humble/Tutorials/Beginner-Client-Libraries/Creating-A-Workspace/Creating-A-Workspace.html) et avoir installé le turtlebot3.

# pour installer tous les packages du turtlebot3
# remplacez humble par votre distro ROS2
cd ~/ros2_ws
colcon build
source install/setup.bash
sudo apt-get install ros-humble-turtlebot3*
# n'oubliez pas d'exporter le modèle de Turtlebot3 que vous souhaitez utiliser
export TURTLEBOT3_MODEL=waffle_pi

Nous allons ensuite lancer la simulation du turtlebot3 dans gazebo. Le turtlebot3 va publier les topics que nous allons utiliser dans le tutoriel.

Partie 1: Concepts

rosbridge_suite (https://github.com/RobotWebTools/rosbridge_suite) avec le node rosbridge-server fournit un serveur WebSocket qui donne accès aux fonctionnalités de ROS pour des programmes non-ROS. WebSocket est un protocole de communication qui permet une communication bidirectionnelle entre les clients et les serveurs à travers une connexion unique et durable. Des clients roslib ont été développés dans differents languages de programmation (Python, Rust, Java, Javascript). rosbridge_server permet donc une intégration entre ROS avec un large éventail de technologies, notamment des applications Web, des appareils mobiles, des environnements de simulation. Dans ce tutoriel nous allons apprendre à utiliser roslibjs qui permet d’interagir avec l’ecosystème ROS en utilisant Javascript. Nous allons créer ensemble une interface web simple permettant d’interagir avec un robot simulé sur Gazebo.

Partie 2: Implémentation

Nous allons dans un premier temps créer une page web index.html dans le dossier webpage_ws. Cette page web html execute du javascript pour utiliser ROSlibjs et déclarer notre publisher et notre subscriber:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>ROS2 ROSLIBjs example</title>
    <link rel="stylesheet" type="text/css" href="style.css">
</head>
<body>
    <h1>ROS2 ROSLIBjs example</h1>
    <div class="container">

        <!-- Inputs pour publier le message Twist sur le topic cmd_vel -->
        <div>
            <label for="linearSpeed">Linear Speed:</label>
            <input type="number" id="linearSpeed" step="0.1" value="0">
            <label for="angularSpeed">Angular Speed:</label>
            <input type="number" id="angularSpeed" step="0.1" value="0">
            <!-- Appelle la fonction submitInputsTwist qui va publier un Twist message -->
            <button onclick="submitInputsTwist()">Publish Twist</button>
        </div>

        <!-- Zone de texte pour afficher les messages reçu par le subscriber d'odom -->
        <div>
            <h2>Received Odometry</h2>
            <textarea id="odometryData" readonly></textarea>
        </div>
        
        <!-- Joystick pour controler le robot en publiant sur cmd_vel -->
        <div id="joyDiv" style="width:200px;height:200px;margin-bottom:20px;"></div>
    </div>
    
    
    <!-- Pour importer roslibjs -->
    <script src="https://s3.eu-west-1.amazonaws.com/rosject.io/js/roslib.min.js"></script>

    <!-- La repository github du joystick https://github.com/bobboteck/JoyStick -->
    <script src="https://github.com/bobboteck/JoyStick/releases/download/v2.0.0/joy.min.js"></script>

    <!-- Javascript -->
    <script>

        // On déclare notre client
        var ros = new ROSLIB.Ros();

        var rosbridgeUrl = 'ws://localhost:9090'; // Remplacer localhost:9090 par l'url rosbridge_server URL (et ne pas ajouter:port)

        // Connecte au ROS2 environment
        ros.on('connection', function () {
            console.log('Connected to ROS1 environment.');
        });

        // Gérer les cas de déconnection
        ros.on('error', function (error) {
            console.error('Error connecting to ROS1 environment:', error);
        });

        ros.on('close', function () {
            console.log('Connection to ROS1 environment closed.');
        });

        // Déclare les variable qui permettent d'interagir avec les topics ROS
        var twistTopic = new ROSLIB.Topic({
            ros: ros,
            name: '/cmd_vel',
            messageType: 'geometry_msgs/Twist'
        });

        var odometryTopic = new ROSLIB.Topic({
            ros: ros,
            name: '/odom',
            messageType: 'nav_msgs/Odometry'
        });
        
        // Subscribe au topic odom et définit la fonction callback
        odometryTopic.subscribe(function (message) {
            console.log(message)
            // Change la valeur de la texte area avec le message reçu depuis le topic
            document.getElementById('odometryData').value = JSON.stringify(message, null, 2);
        });

        function publishTwist(linearSpeed, angularSpeed) {
            
            // Declare le Twist message pour pouvoir publier les valeurs en entrée de la fonction
            var twist = new ROSLIB.Message({
                linear: {
                    x: linearSpeed,
                    y: 0,
                    z: 0
                },
                angular: {
                    x: 0,
                    y: 0,
                    z: angularSpeed
                }
            });
            // Publie le Twist message sur le topic cmd_vel
            twistTopic.publish(twist);
        }

        // Connecte au ROS2 environment
        ros.connect(rosbridgeUrl);

        
        // La fonction appellée lorsque Publish Twist est cliqué
        function submitInputsTwist() {

            // Récupère les valeurs des inputs pour linearSpeed et angularSpeed
            var linearSpeed = parseFloat(document.getElementById('linearSpeed').value);
            var angularSpeed = parseFloat(document.getElementById('angularSpeed').value);
            
            publishTwist(linearSpeed, angularSpeed);
        }

        
        
        // Declare le joystick pour publier les données sur cmd_vel
        var Joy1 = new JoyStick('joyDiv', {}, function(stickData) {
            
            // Récupère les valeurs des axes du joysticks
            let angularSpeed = -stickData.x/50;
            let linearSpeed = stickData.y/50;
            
            // Declare le Twist message pour pouvoir le publier
            var twist = new ROSLIB.Message({
                linear: {
                    x: linearSpeed,
                    y: 0,
                    z: 0
                },
                angular: {
                    x: 0,
                    y: 0,
                    z: angularSpeed
                }
            });
            
            // Publie le Twist message sur le topic cmd_vel
            twistTopic.publish(twist);
        });
        
    </script>
</body>
</html>

Pour résumer le code ci-dessus:

  • On écrit notre page HTML qui va servir d’interface utilisateur.
  • Dans notre Javascript, on crée le client websocket ROSLib et on crée les fonctions qui seront appelées pour differents évenements de la websocket (connection, error, close).
  • On déclare ensuite les variables qui vont nous permettre d’interagir avec les topics.
  • On subscribe au topic /odom et on modifie la valeur du textarea odometryData dans le callback.
  • On crée la fonction publishTwist qui est appelée lorsque le bouton Publish Twist est appelé, elle permet de publier les valeurs.
  • On déclare le joystick et on appelle la fonction publishTwist pour publier sur le topic cmd_vel les valeurs des axes du joysticks.

Vous pouvez également ajouter le fichier CSS style.css:

body {
    font-family: Arial, sans-serif;
    margin: 0;
    padding: 0;
    background-color: #f5f5f5;
    color: #333;
}

h1 {
    text-align: center;
    margin-top: 20px;
}

.container {
    max-width: 600px;
    display: flex;
    flex-direction: column;
    margin: 20px auto;
    background-color: #fff;
    border-radius: 10px;
    padding: 20px;
    box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
    
    text-align: center;
}

label {
    display: inline-block;
    width: 120px;
    margin-bottom: 10px;
}

input[type="number"] {
    width: 80px;
    padding: 5px;
    border-radius: 5px;
    border: 1px solid #ccc;
    margin-right: 10px;
}

button {
    padding: 8px 16px;
    background-color: #4CAF50;
    color: white;
    border: none;
    border-radius: 5px;
    cursor: pointer;
}

button:hover {
    background-color: #45a049;
}

textarea {
    width: 100%;
    height: 150px;
    padding: 10px;
    border-radius: 5px;
    border: 1px solid #ccc;
    resize: none;
} 

Voici le visuel de la page web:

Nous allons voir dans la partie suivante comment l’ouvrir en utilisant notre environnement de développement.

Partie 3: Tester le système

Pour tester l’interface exemple du tutoriel, vous devez dans un premier temps lancer la simulation du turtlebot3 avec la commande suivante dans un premier terminal:

export TURTLEBOT3_MODEL=waffle_pi
ros2 launch turtlebot3_gazebo turtlebot3_house.launch.py

Vous devez ensuite lancer rosbridge_server dans un second terminal:

ros2 launch rosbridge_server rosbridge_websocket_launch.xml

Les prochaines étapes sont seulement pour faire fonctionner l’exemple dans un rosject de theConstuct. Dans un nouveau terminal, vous devez lancer un server python pour hoster la page web via l’installation de theConstruct:

python3 -mhttp.server 7000

Ouvrez un terminal et lancez les commandes suivantes:

# pour obtenir l'url de la page web html
webpage_address
# pour obtenir l'adresse de la websocket fournit par l'installation theConstruct
rosbridge_address

Vous devrez utiliser l’adresse websocket rosbridge_address dans la variable rosbridgeUrl du code.

Si vous effectuez le tutoriel sur votre machine locale, vous pouvez ouvrir directement votre page html avec votre navigateur et l’adresse de la websocket ws://0.0.0.0:9090 (port par defaut utilisé par le node rosbridge_server).

Vous pouvez maintenant ouvrir l’interface créée precedemment en ouvrant le ficher index.html dans votre navigateur. Vous devriez obtenir le résultat suivant:

Dans la textarea, vous pouvez voir l’odometry du robot mis à jour à chaque message reçu. Vous devriez pouvoir également pouvoir déplacer le turtlebot3 en utilisant les textes inputs ou le joystick pour publier sur le cmd_vel.

Feedback

Cet article vous a plu ? Avez-vous des questions sur ce qui est expliqué ? Quoi qu’il en soit, n’hésitez pas à laisser un commentaire dans la section des commentaires ci-dessous, afin que nous puissions interagir et apprendre les uns des autres.

Si vous souhaitez en savoir plus sur d’autres sujets liés à ROS, faites-le nous savoir dans l’espace commentaires et nous ferons une vidéo ou un article à ce sujet.
Topics: ROS Q&A | ros2

 

Video Tutorial

Como usar en ROS2 un paquete de ROS1 generado por SolidWorks to URDF – Spanish ROS Tutorial

Como usar en ROS2 un paquete de ROS1 generado por SolidWorks to URDF – Spanish ROS Tutorial

This tutorial is created by Rosbotics Ambassador 025 Miguel

Rosbotics Ambassador Program https://www.theconstruct.ai/rosbotics-ambassador/)

Que vamos a aprender:

  1. Como crear un paquete en ROS 2
  2. Como modificar el URDF para hacerlo compatible con Rviz 2
  3. Como modificar el launch file
  4. Como modificar el package.xml para encontrar los modelos

Lista de recursos usados en este post

  1. Usa este rosject: https://app.theconstructsim.com/l/5fea4bb1/
  2. The construct: https://app.theconstructsim.com
  3. Cursos de ROS 2:
    1. URDF para el modelado de robots en ROS2: https://app.theconstructsim.com/courses/83
    2. Conceptos básicos de ROS2 en 5 días (Python): https://app.theconstructsim.com/courses/132

Descripción

En este tutorial, aprenderás el proceso de portar un paquete de ROS 1, creado originalmente en SolidWorks, a un formato URDF compatible con ROS 2. Exploraremos los pasos esenciales para migrar tu diseño robótico al nuevo entorno, asegurando la compatibilidad y funcionalidad en la última versión de ROS. Sigue la guía detallada para una transición sin complicaciones y mantén tus proyectos robóticos al día con las últimas tecnologías.

Abriendo el rosject

Para poder seguir al pie de la letra este tutorial, necesitamos tener ROS 2 Humble instalado en nuestro sistema, e idealmente un workspace para crear los paquetes en él. Para facilitarnos el proceso, ya hemos preparado un rosject para esto: https://app.theconstructsim.com/l/5e643001/

Solo copiando el rosject (Abriendo el enlace anterior), tendremos un entorno previamente configurado.

Después de que el rosject se haya copiado correctamente en tu entorno, debemos presionar el botón Ejecuta para ejecutar e inicializar el entorno del rosject.

[Inserta imagen del Rosject]

Crear un paquete de ROS 2 con ament_python

Para poder crear nuestro paquete de ROS 2, necesitamos situarnos en el workspace, y para eso, necesitamos la terminal.

Abramos una terminal oprimiendo el botón de abrir una nueva terminal:

[Inserte imagen de la terminal]

Una vez dentro de la terminal vamos a movernos al ros2_ws/src y creamos nuestro paquete:
cd ~/ros2_ws/src
ros2 pkg create lidar3d --build-type ament_python --dependencies rclpy

Una vez creado nuestro paquete ingresamos a él y copiamos el contenido de nuestro paquete generado por Solidworks:
cd lidar3d
cp -r ../lidar3d/* .

Ahora vamos a abrir el editor de código para modificar nuestros archivos. Para abrir el editor de código oprimimos el botón de editor de código:

 

[Inserte imagen de vscode]

Nos situamos en ros2_ws/src/lidar3d/urdf y abrimos el archivo de urdf:

[Inserte imagen del URDF]

Primero vamos a añadir un nuevo objeto vacío de base_link con un joint al base_link generado por Solidworks ya que rviz 2 no soporta base_link con inercia y le cambiamos el nombre al base_link de Solidworks:

[Inserte imagen de vscode con urdf modificado]

Ahora debido a que modificamos el nombre del paquete, vamos a usar la función de sustituir palabra integrada con Vscode:

[inserte imagen de sustitución]

El siguiente paso es ir a ros2_ws/src/lidar3d/launch para crear un launch de Python compatible con ROS 2, para eso damos click derecho y Nuevo archivo y le ponemos de nombre display.launch.py

[inserte imagen del launch file]

Por ultimo antes de compilar, debemos decirle a nuestro paquete donde se encuentran los solidos URDF los meshes y los launch files, para eso nos vamos a ros2_ws/src/lidar3d y añadimos las respectivas instrucciones install para que encuentre nuestras carpetas:

[Inserte imagen del package modificado]

Ya que tenemos nuestro paquete configurado podemos compilar y ejecutar nuestro launch file para poder generar las configuraciones por defecto de rviz2

chmod +x ~/ros2_ws/src/lidar3d/launch/*.py
cd ~/ros2_ws
colcon build --packages-select lidar3d
source install/setup.bash
ros2 launch lidar3d display.launch.py

[Inserte imagen de rviz y terminal]

Para poder activar las configuraciones requeridas de rviz 2 vamos a modificar nuesto Fixed Frame y cambiamos map por base_link, ahora le damos a añadir y para poder depurar mejor nuestro objeto añadimos el arbol de TF con la opcion TF, y por último vamos a añadir el modelo de nuestro robot añadiendo RobotModel:

[Inserte imagen de rviz]

Como podemos observar, aun no se ve nuestro robot, para eso debemos en la sub-opción de Description Topic seleccionar el topico de robot_description

[Inserte imagen de rviz con el modelo]

Video Tutorial

 

How to dynamically spawn objects in Gazebo Simulation using Python – English ROS Tutorial

How to dynamically spawn objects in Gazebo Simulation using Python – English ROS Tutorial

What are we going to Learn?

  1. How to create ROS2 Package
  2. How to compile ROS2 workspace
  3. How to create node in Python to spawn new object in Gazebo Simulation


Overview:

ROS (Robot Operating System) is a de facto standard for Robotics. In order to program Robots, simulation of Real world systems is very important to test and debug the systems. For simulations of Robotics systems, Gazebo is used commonly in ROS. In this post we will learn how to add new objects in simulation scene without terminating the simulation entirely.

In general, if we want to add new object in simulation scene, we have to terminate all running nodes in simulation, edit the World file (description file for simulation in Gazebo). In order to add new objects, without terminating nodes, we can use Gazebo API in Python to spawn new objects in simulation dynamically.

If you want to learn ROS 2 Python in a practical, hands-on way, check out the course ROS 2 Basics in 5 Days: https://app.theconstruct.ai/courses/132

In this course, you’ll cover the foundational concepts needed to start working with ROS 2, as well as more advanced topics, all while engaging in hands-on practice.

 

Opening the ROSJect:

To follow along the post, we need to have ROS2 installed in our system. To make things easier, we have created ROSJect to follow along: https://app.theconstructsim.com/rosjects/741580

Just open the ROSJect in your browser

Click on “FORK”

Next, Click on “RUN”

Open the new Web Shell

 

Go to the ROS2 Workspace

cd ros2_ws

Then, source the workspace

source install/setup.bash

In one web shell, run Gazebo

gazebo –verbose -s libgazebo_ros_factory.so

In another web shell, run the ROS2 Node

ros2 run robot_spawner_pkg spawn_turtlebot the_robot_name robot_namespace 0.0 0.0 0.1

Congratulations. You have now learned how to spawn objects in Gazebo Simulation using Python.

To learn more about ROS 2, have a look at the course below:

We hope this tutorial was really helpful to you.

This tutorial is created by Robotics Ambassador Muhammad.

Video Tutorial

Pin It on Pinterest