Skip to main content

ROS 2 Introduction

You will learn basic information about ROS 2 and what concepts are at the heart of each ROS 2 application. You will also become familiar with the ROSbot platform, which will be used for learning ROS 2. After setting up the environment, the first task will be to start and visualize the camera frames. The tutorial can be carried out both on the real platform and in the simulation.

Prerequisites

This tutorial series is dedicated for ROSbot XL equipped with LiDAR and camera. However, don't worry if your configuration is different or if you are using a different ROSbot. Most of the information and commands provided are compatible with ROSbot 2R/2 PRO, and thanks to Docker images, the necessary changes are simple and come down to launching the appropriate container, depending on your hardware configuration. It is also possible to solve the tutorial using the Gazebo simulation.

info

If you don't already own a ROSbot, you can get one from the Husarion store.

The tutorials are designed to flow sequentially and are best followed in order. If you're looking to quickly assess the content of a specific tutorial, refer to the ROS 2 Tutorials repository, which contains the completed outcomes.

What is ROS 2?

"The Robot Operating System (ROS) is a set of software libraries and tools for building robot applications. From drivers and state-of-the-art algorithms to powerful developer tools, ROS has the open source tools you need for your next robotics project.

Since ROS was started in 2007, a lot has changed in the robotics and ROS community. The goal of the ROS 2 project is to adapt to these changes, leveraging what is great about ROS 1 and improving what isn’t." ROS 2 webpage.


ros_logo


We have prepared a set of tutorials to help you start building advanced robots. These tutorials are designed to be performed on Husarion ROSbot XL, but they are also a valuable portion of knowledge for anybody interested in ROS 2.

System structure

ROS is a software suite that allows for quick and easy building of autonomous robotic systems. ROS should be considered as a set of tools for creating new solutions or adjusting already existing ones. A major advantage of this system is a great set of drivers and implemented algorithms widely used in robotics.

Nodes

The base unit in ROS is called a node. Nodes are in charge of handling devices or computing algorithms - each node for a separate task. Nodes can communicate with each other using topics or services. ROS software is distributed in packages. A single package is usually developed for performing one type of task and can contain one or multiple nodes.

Topics

In ROS, topic is a data stream used to exchange information between nodes. Topics are used to send frequent messages of one type, such as sensor readouts or information on motor goal speed. Each topic is registered under a unique name and with a defined message type. Nodes can connect to the topic to either publish messages or subscribe to them. For a given topic, one node can not publish and subscribe to it at the same time, but there are no restrictions on the number of different nodes publishing or subscribing.

Services

Communication through services resembles a client-server model. In this mode, one node (the server) registers a service in the system. Then, any other node can ask that service and get a response. In contrast to topics, services allow for two-way communication, as a request can also contain some data.

Visualization of this structure is taken from the official ROS 2 Documentation

ROSbot XL platform

This tutorial is created for ROSbot XL, an open-source robot platform, equipped with a camera and lidar. You can read more about it here: ROSbot XL.

Tutorials are prepared for a platform equipped with:

  • 1 x Raspberry Pi 4
  • 1 x LIDAR (e.g. RPLIDAR S2)
  • 1 x RGBD camera (e.g. Intel D435)

In the basic configuration, ROSbot XL is equipped with:

  • 1 x Digital Board based on STM32F407 microcontroller
  • 1 x Power Board
  • 4 x DC motor
  • 1 x IMU sensor
  • 1 x Li-Ion Batteries
  • 1 x Antenna connected directly to a Wi-Fi module
  • 1 x Speaker

And this is how it looks like:

image

image

You can also go through ROS 2 Tutorials using the Ignition Gazebo simulator environment instead of the physical robot. You can find the installation method in the next paragraph environment setup. If you want to use the simulation, you should have native ROS Humble installation that requires Ubuntu 22.04 operating system. Full guide can be found here.

We also created a package with all the nodes and launch files from our ROS 2 Tutorials. You can download ready to use pkg from GitHub page.

image

Environment setup

To get started with ROS, the simplest way is to connect via ssh to your ROSbot. It is also possible to test the functionality of ROS on your local computer by using the Gazebo simulator.

ROSbot

Before you start working with ROS 2 on the ROSbot platform, you need to connect to your device first. You can establish the connection in two ways: using ssh or via a remote desktop. Instructions on how to connect to ROSbot:

Hello World - first steps in ROS 2

The first example of functionality will be running a basic talker node from the demo_nodes_cpp package. The sole purpose of this node is to display and send messages at a frequency of 1 Hz. The content of the message is of course Hello World with a number specifying the number of messages sent. The message is also sent and can be received by other nodes or by tools. You'll get to know more about that in a moment. Now you'll learn two ways of running the code, using ros2 run and ros2 launch commands.

Execute node - ros2 run

Let's run your first node!

husarion@husarion:~$
ros2 run demo_nodes_cpp talker

After running the command above, you should see something like this:

[INFO] [1681987653.420573969] [talker]: Publishing: 'Hello World: 1'
[INFO] [1681987654.420811998] [talker]: Publishing: 'Hello World: 2'
[INFO] [1681987655.420825802] [talker]: Publishing: 'Hello World: 3'
...

As we mentioned, the message is not only printed, but also sent and can be received by any other node. So let's launch another node from the demo_nodes_cpp package named listener. Launch a new terminal and type.

husarion@husarion:~$
ros2 run demo_nodes_cpp listener

You should see the currently received message as the output

[INFO] [1681987653.420573969] [listener]: I heard: [Hello World: 11]
[INFO] [1681987654.420811998] [listener]: I heard: [Hello World: 12]
[INFO] [1681987655.420825802] [listener]: I heard: [Hello World: 13]
...
Details about ros2 run

Running nodes

Command ros2 run allows you to run an executable in an arbitrary package from anywhere without having to give its full path. ros2 run executes only one file. To start a new node, type ros2 run and two more arguments: package_name and node_type, as shown below.

ros2 run package_name node_type [--ros-args options]

package_name and node_type are the names of package and node that you want to run. When using the ros2 run command, the node is executed in the terminal, and text logs are displayed on the screen.

Parameters

ROS nodes take set of arguments that allow various properties to be reconfigured. Examples include configuring the name/namespace of the node, names of topic/service used, and parameters on the node. All ROS-specific arguments have to be specified after a --ros-args flag.

Possible options could be:

  • Remapping topic name - change the name of the topic subscribed or published by a node.

    -r old_topic_name:=new_topic_name
  • Setting parameter

    -p param_name:=param_value
  • Defining node - bind specific identifier to a node.

    -r  __node:=new_node_name
note

There are two underscores before the name. If you want to learn more about naming convention used by ROS 2 see ROS 2 documentation.

Execute nodes - ros2 launch

ros2 launch is a tool that simplifies the running of multiple nodes at the same time. This tool uses launch files which contain the configuration of all nodes to be run. Usage of ros2 launch is simple and similar to the ros2 run command. One key difference is that ros2 launch can automatically start many nodes.

To execute the launch file type:

ros2 launch package launch_file [arguments]

or

ros2 launch launch_file [arguments]

The first one is for the case when you use the launch file provided with the package (you can run it from any folder). The second option is when you use a standalone launch file (you must run it in the folder where the launch file is located or point the path to it).

Structure of the launch file

ROS 2 supports three different languages ​​for writing the launch file. These can be Python, XML, or YAML. Below are examples that implement the same functionality as described in ros2 run. In addition to starting the talker and listener nodes, we will also add a parameter that will allow us to decide when the listener node will start. You can compare all the languages ​​discussed below.

Let's create your first launch files!

Python

First, we need to create a new file called example.launch.py. To do this we will use the text editor nano. Create a new file with the following command:

husarion@husarion:~$
nano example.launch.py

and paste the code visible below.

example.launch.py
from launch import LaunchDescription
from launch_ros.actions import Node
from launch.actions import DeclareLaunchArgument
from launch.conditions import LaunchConfigurationEquals


def generate_launch_description():
run_listener_arg = DeclareLaunchArgument("run_listener", default_value="true")

talker_node = Node(
package="demo_nodes_cpp", executable="talker", name="talker_node"
)
listener_node = Node(
package="demo_nodes_cpp",
executable="listener",
name="listener_node",
condition=LaunchConfigurationEquals("run_listener", "true"),
)

return LaunchDescription([run_listener_arg, talker_node, listener_node])

Press <ctrl + o> and then <ctrl + x> to save and quit.

Details about Python launch

The code explained

  1. These import statements pull in some Python launch modules.

    from launch import LaunchDescription
    from launch_ros.actions import Node
    from launch.actions import DeclareLaunchArgument
    from launch.conditions import LaunchConfigurationEquals
  2. Next, we create function which must return LaunchDescription:

    def generate_launch_description():
    .
    .
    .
    return LaunchDescription([...])
  3. Then we create an argument that will decide whether to start the listener.

      run_listener_arg = DeclareLaunchArgument('run_listener', default_value='true')
  4. We set the nodes to run.

        talker_node = Node(
    package="demo_nodes_cpp", executable="talker", name="talker_node"
    )
    listener_node = Node(
    package="demo_nodes_cpp",
    executable="listener",
    name="listener_node",
    condition=LaunchConfigurationEquals("run_listener", "true"),
    )
  5. The final action launches the mimic node with the remaps:

      return LaunchDescription([run_listener_arg, talker_node, listener_node])

Configure nodes

  • For remapping the topic names add remapping argument inside the Node constructor:

    Node(..., remappings=[("/old_name", "/new_name")])
  • For setting parameter add parameters argument inside the Node constructor:

    Node(..., parameters=[{"parameter_name": parameter_value}])
It's only basics

There are many more possibilities that can be useful in more advanced systems. For more information, please visit the documentation, especially Launch file different formats

Execute launch file

As a reminder, to execute the launch file simply type ros2 launch with a path to your launch file. If your launch files are in the same directory you can type.

Python
husarion@husarion:~$
ros2 launch example.launch.py

Setup run_listener parameters to false.

husarion@husarion:~$
ros2 launch example.launch.py run_listener:=false

You should get output similar to this:

image

Basic tools

ROS 2 has a lot of tools that allow you to quickly analyze running processes. Now you'll learn how to check available nodes and topics. For this we use two simple commands: ros2 node and ros2 topic.

Examining nodes - ros2 node

When you have talker and listener running, you can check all nodes that are running in the system. To do this, type in a in new terminal:

husarion@husarion:~$
ros2 node list

As the output you should get:

husarion@husarion:~$ ros2 node list
/listener_node
/talker_node

This means, that you have now two nodes running: /talker_node and /listener_node. This command can be useful to check if all nodes are working. To check detailed information about a particular node, you can use the following command:

husarion@husarion:~$
ros2 node info /talker_node

And as the output you should get:

husarion@husarion:~$ ros2 node info /talker_node
/talker_node
Subscribers:
/parameter_events: rcl_interfaces/msg/ParameterEvent
Publishers:
/chatter: std_msgs/msg/String
/parameter_events: rcl_interfaces/msg/ParameterEvent
/rosout: rcl_interfaces/msg/Log
Service Servers:
/talker_node/describe_parameters: rcl_interfaces/srv/DescribeParameters
/talker_node/get_parameter_types: rcl_interfaces/srv/GetParameterTypes
/talker_node/get_parameters: rcl_interfaces/srv/GetParameters
/talker_node/list_parameters: rcl_interfaces/srv/ListParameters
/talker_node/set_parameters: rcl_interfaces/srv/SetParameters
/talker_node/set_parameters_atomically: rcl_interfaces/srv/SetParametersAtomically
Service Clients:

Action Servers:

Action Clients:

The most important thing for you should be that the talker_node actually publishes a message with the subject /chatter and the type of that message is /std_msgs/msg/String. In addition to the mentioned publisher, you can find many other interfaces that are typical for each node and are necessary for proper operation. An example may be services that allow reading or writing parameters (/talker_node/get_parameters, rcl_interfaces/srv/SetParameters).

Details about ros2 node

ros2 node is a command line application for examining which nodes are registered in the system and also checking their statuses.

Using the application looks as follows:

ros2 node command [node_name]

command could be:

  • list - display list of running nodes
  • info - display info regarding selected node

For more information check ROS 2 documentation.

Examining topics - ros2 topic

Now we will check what topics are registered in the system and receive some info about them. In the new console type in:

husarion@husarion:~$
ros2 topic list

You should get in the output:

husarion@husarion:~$ ros2 topic list
/chatter
/parameter_events
/rosout

This means that you have three topics registered in the system. Let’s get some info about the first of them:

husarion@husarion:~$
ros2 topic info /chatter

As the output you should get:

husarion@husarion:~$ ros2 topic info /chatter
Type: std_msgs/msg/String
Publisher count: 1
Subscription count: 1

From that you can read, that via topic /chatter only messages of type std_msgs/msg/String can be transmitted. There is only one publisher (talker_node) and one subscriber (listener_node) to it.

Details about ros2 topic

ros2 topic is a command line application for examining which topics are already being published and subscribed, checking details of the selected topic or reading messages being sent in it.

Using the application looks as follows:

ros2 topic command [topic_name]

The most useful command could be:

  • list - display list of topics
  • echo - display messages published in the topic
  • info - display info regarding selected topic
  • hz - displays the frequency of sending messages

For more information check ROS 2 documentation.

Examining system - rqt_graph

rqt_graph is a graphical tool for the visualization of data flow across different nodes in the system. Thanks to this application, you can quickly visualize information about relationships between nodes - what topics are sent between them - and also receive the most important information about the topics such as: message type, message name and publication frequency.

Using the application looks as follows:

rqt_graph

There will be no response in the terminal, but a new window will appear. You will see:

rqt_graph

Interpretation of the graph is as follows:

  • ovals represent nodes,
  • arrows represent topics
  • rectangles containing other elements represent the namespace. For example, a stereo camera may have two nodes - one for each camera: /camera/imageLeft and /camera/imageRight. In this case, all nodes containing the same shared part of the name will be inside the rectangle.

Question 1

Which command will you use to run 3 nodes at once?
a) ros2 run [node1][node2] [node3]
b) ros2 launch
c) ros2 node
d) there is no possibility - each node should be run separately

Answer
b)

Task 1

Try renaming the topic name from /chatter to /message in any launch file. Check your solution using ros2 topic list and ros2 topic echo commands.

Starting camera

In this section, we will set up a ROS system that is equipped with an Orbbec Astra camera and show an image from the camera on display. Use remote desktop to connect to your ROSbot. You can also follow the tutorial in simulation mode using Gazebo and Husarion VM mentioned before.

Starting ROSbot camera

Running the camera on ROSbot is very simple thanks to the use of docker images. All you need to do is run the specified container.

docker compose up -d microros <rosbot_service> <camera_service>

Depending on your ROSbot model and specific configuration you should use an appropriate name for your <rosbot_service> and <camera_service>. Check Husarion Docker to find suitable image.

For ROSbot XL with Astra camera, this command should look like this:

husarion@husarion:~$
docker compose up -d microros rosbot-xl astra

Task 2

Use ros2 node and ros2 topic tools to check if new nodes or topics appeared in the system. Next, find some info regarding new nodes and topics.

Hint
Go to examining nodes and examining topics and see prepared examples.

View the camera image

Now using ros2 node list we can see that the camera has started. To get a camera image preview, we can run another node called rqt_image_view located in the package with the same name.

Below there is a command to run rqt_image_view node.

husarion@husarion:~$
ros2 run rqt_image_view rqt_image_view

After that command new window should appear. Select appropriate topic to visualize. As the output, you should see the items in front of your camera.

astra_image_view

for remote desktop

In case of an error, make sure to export the DISPLAY variable.

husarion@husarion:~$
export DISPLAY=:0

It is recommended to put this line in .bashrc so that it will be executed automatically every time you run the terminal.

husarion@husarion:~$
echo 'export DISPLAY=:0' >> ~/.bashrc

The frame rate can be slow because the whole image is transferred through the network. You will learn how to compress and speed up your system in one of the next tutorials.

Summary

After completing this tutorial you should know what are the basic components and tools of ROS 2. You should know how to start nodes in two ways: using ros2 run and ros2 launch command, and how to set parameters and remap topic names in both scenarios. You should also be able to check what nodes are running in the system and what topics are available, using the ros2 node and ros2 topic tools. You are also familiar with rqt_graph tool, and you know how to read information from it about the relationship between individual nodes.


by Rafał Górecki, Husarion

Do you need any support with completing this tutorial or have any difficulties with software or hardware? Feel free to describe your thoughts on our community forum: https://community.husarion.com/ or to contact our support: support@husarion.com