3
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

【備忘録】ROSパッケージのROS2移行

Last updated at Posted at 2021-04-22

既存のROSパッケージをROS2で使用するためのコンバーティングに関する備忘録。

ROSパッケージの準備

ROSのチュートリアルのパッケージを利用する。
まずcatkin形式のパッケージを作る。
以下のコマンドを実行する。

cd ~/catkin_ws/src
catkin_create_pkg beginner_tutorials std_msgs rospy roscpp

次にtalkerノードとlistenerノードのソースを格納する。
~/catkin_ws/src/beginner_tutorials/src配下に以下のlistener.cppとtalker.cppのファイルを作成し、以下のものを張り付ける。

listener.cpp
# include "ros/ros.h"
# include "std_msgs/String.h"

void chatterCallback(const std_msgs::String::ConstPtr& msg)
{
  ROS_INFO("I heard: [%s]", msg->data.c_str());
}

int main(int argc, char **argv)
{
  ros::init(argc, argv, "listener");
  ros::NodeHandle n;
  ros::Subscriber sub = n.subscribe("chatter", 1000, chatterCallback);
  ros::spin();

  return 0;
}
talker.cpp
# include <sstream>
# include "ros/ros.h"
# include "std_msgs/String.h"
int main(int argc, char **argv)
{
  ros::init(argc, argv, "talker");
  ros::NodeHandle n;
  ros::Publisher chatter_pub = n.advertise<std_msgs::String>("chatter", 1000);
  ros::Rate loop_rate(10);
  int count = 0;
  std_msgs::String msg;
  while (ros::ok())
  {
    std::stringstream ss;
    ss << "hello world " << count++;
    msg.data = ss.str();
    ROS_INFO("%s", msg.data.c_str());
    chatter_pub.publish(msg);
    ros::spinOnce();
    loop_rate.sleep();
  }
  return 0;
}

次に~/catkin_ws/src/beginner_tutorials/package.xmlを編集する。
以下のものを張り付ける。

package.xml
<package>
  <name>beginner_tutorials</name>
  <version>0.0.0</version>
  <description>talker</description>
  <maintainer email="you@yourdomain.tld">Your Name</maintainer>
  <license>Apache 2.0</license>
  <buildtool_depend>catkin</buildtool_depend>
  <build_depend>roscpp</build_depend>
  <build_depend>std_msgs</build_depend>
  <run_depend>roscpp</run_depend>
  <run_depend>std_msgs</run_depend>
</package>

最後に~/catkin_ws/src/beginner_tutorials/CMakeLists.txtを編集する。
以下のものを張り付ける。

CMakeLists.txt
cmake_minimum_required(VERSION 2.8.3)
project(beginner_tutorials)

## Find catkin and any catkin packages
find_package(catkin REQUIRED COMPONENTS roscpp rospy std_msgs genmsg)

## Declare a catkin package
catkin_package()

## Build talker and listener
include_directories(include ${catkin_INCLUDE_DIRS})

add_executable(talker src/talker.cpp)
target_link_libraries(talker ${catkin_LIBRARIES})

add_executable(listener src/listener.cpp)
target_link_libraries(listener ${catkin_LIBRARIES})

ROSパッケージの動作確認

パッケージが正しく動作するかを確かめる。
以下のコマンドを実行しパッケージをビルドする。

cd ~/catkin_make
catkin_make

次に3つのターミナルを起動してそれぞれ以下のコマンドを実行する。以下が正常に動いているものである.

roscore
roscore
talkerノード
rosrun beginner_tutorials talker
[ INFO] [1618961980.031075257]: hello world 0
[ INFO] [1618961980.131142666]: hello world 1
[ INFO] [1618961980.231113532]: hello world 2
[ INFO] [1618961980.331107085]: hello world 3
[ INFO] [1618961980.431122565]: hello world 4
[ INFO] [1618961980.531117988]: hello world 5
listenerノード
rosrun beginner_tutorials listener
[ INFO] [1618961980.332236166]: I heard: [hello world 0]
[ INFO] [1618961980.432181902]: I heard: [hello world 1]
[ INFO] [1618961980.532188363]: I heard: [hello world 2]
[ INFO] [1618961980.632173786]: I heard: [hello world 3]
[ INFO] [1618961980.732066074]: I heard: [hello world 4]
[ INFO] [1618961980.832214154]: I heard: [hello world 5]

ROS2への移植

ROS2用のワークスペースに先ほど作成したROSパッケージ(beginner_tutorials)をコピーする。

talkerノードの移植作業

修正する点を列挙する。

# ROS ROS2 備考
1 #include "ros/ros.h" #include "rclcpp/rclcpp.hpp" ROS2用C++用クライアントライブラリに変更
2 #include "std_msgs/String.h" #include "std_msgs/msg/string.hpp" std_msgs/String型のメッセージのヘッダをインクルード
3 ros::init(argc, argv, "talker");
ros::NodeHandle n;
rclcpp::init(argc, argv);
auto node = rclcpp::Node::make_shared("talker");
ノードの初期化の書式を変更
4 ros::Publisher chatter_pub = n.advertise<std_msgs::String>("chatter", 1000); auto chatter_pub = node->create_publisher<std_msgs::msg::String>("chatter",rmw_qos_profile_default); パブリッシャの書式を変更
5 ros::Rate loop_rate(10); rclcpp::Rate loop_rate(10); rosからrclcppに変更
6 std_msgs::String msg; auto msg = std::make_shared<std_msgs::msg::String>(); std_msgs/String型でmsgという名前の変数を登録する際の書式を変更
7 while (ros::ok()) while (rclcpp::ok()) rosからrclcppに変更
8 msg.data = ss.str(); msg->data = ss.str(); アローに変更
9 chatter_pub.publish(msg); chatter_pub->publish(msg); アローに変更
10 ROS_INFO("%s", msg.data.c_str()); RCLCPP_INFO(node->get_logger(),"%s", msg->data.c_str()); ROS_INFOをRCLCPP_INFOの書式に変更
11 ros::spinOnce(); rclcpp::spin_some(node); スピンの書式の変更

以下が上記の点を修正したコードである。

talker.cpp
# include <sstream>
# include "rclcpp/rclcpp.hpp"
# include "std_msgs/msg/string.hpp"

int main(int argc, char **argv)
{
  rclcpp::init(argc, argv);
  auto node = rclcpp::Node::make_shared("talker");
  auto chatter_pub = node->create_publisher<std_msgs::msg::String>("chatter", rmw_qos_profile_default);
  rclcpp::Rate loop_rate(10);
  int count = 0;
  auto msg = std::make_shared<std_msgs::msg::String>();
  while (rclcpp::ok())
  {
    std::stringstream ss;
    ss << "hello world " << count++;
    msg->data = ss.str();
    RCLCPP_INFO(node->get_logger(),"%s", msg->data.c_str());
    chatter_pub->publish(msg);
    rclcpp::spin_some(node);
    loop_rate.sleep();
  }
 
  return 0;
}

listenerノードの移植作業

修正する点を列挙する。

# ROS ROS2 備考
1 #include "ros/ros.h" #include "rclcpp/rclcpp.hpp" ROS2用C++用クライアントライブラリに変更
2 #include "std_msgs/String.h" #include "std_msgs/msg/string.hpp" std_msgs/String型のメッセージのヘッダをインクルード
3 記述なし std::shared_ptr<rclcpp::Node> node; nodeをグローバル変数に登録
4 void chatterCallback(const std_msgs::msg::String::ConstPtr msg) void chatterCallback(const std_msgs::msg::String::SharedPtr msg) ConstPtrからSharedPtrに変更
5 ROS_INFO("%s", msg.data.c_str()); RCLCPP_INFO(node->get_logger(),"%s", msg->data.c_str()); ROS_INFOをRCLCPP_INFOの書式に変更
6 ros::init(argc, argv, "listener");
ros::NodeHandle n;
rclcpp::init(argc, argv);
node = std::make_shared<rclcpp::Node>("listener");
ノードの初期化の書式を変更
7 ros::Subscriber sub = n.subscribe("chatter", 1000, chatterCallback); auto chatter_sub = node->create_subscription("chatter", rclcpp::QoS(10),chatterCallback); サブスクライバの書式を変更
8 ros::spin(node); rclcpp::spin(node); rosからrclcppに変更

以下が上記の点を修正したコードである。

listener.cpp
# include "rclcpp/rclcpp.hpp"
# include "std_msgs/msg/string.hpp"

std::shared_ptr<rclcpp::Node> node;

void chatterCallback(const std_msgs::msg::String::SharedPtr msg)
{
  RCLCPP_INFO(node->get_logger(),"%s", msg->data.c_str());
}

int main(int argc, char **argv)
{
  rclcpp::init(argc, argv);
  node = std::make_shared<rclcpp::Node>("listener");
  auto chatter_sub = node->create_subscription<std_msgs::msg::String>(
    "chatter", 
    rclcpp::QoS(10),
    chatterCallback
  );
  rclcpp::spin(node);

  return 0;
}

package.xmlの移植作業

修正する点を列挙する。

# ROS ROS2 備考
1 <package> <package format="2"> マニュフェストのバージョンを2に変更
2 <buildtool_depend>catkin</buildtool_depend> <buildtool_depend>ament_cmake</buildtool_depend> catkinではなくamentを使用
3 <build_depend>roscpp</build_depend> <build_depend>rclcpp</build_depend>
<build_depend>rmw_implementation</build_depend>
ビルドの依存関係を修正
4 <run_depend>roscpp</run_depend>
<run_depend>std_msgs</run_depend>
<exec_depend>rclcpp</exec_depend>
<exec_depend>rmw_implementation</exec_depend>
<exec_depend>std_msgs</exec_depend>
実行の依存関係を修正
5 記述なし <export>
<build_type>ament_cmake</build_type>
</export>
ビルドタイプ宣言を追加

以下が上記の点を修正したコードである。

package.xml
<package format="2">
  <name>beginner_tutorials</name>
  <version>0.0.0</version>
  <description>talker</description>
  <maintainer email="you@yourdomain.tld">Your Name</maintainer>
  <license>Apache 2.0</license>
  <buildtool_depend>ament_cmake</buildtool_depend>
  <build_depend>rclcpp</build_depend>
  <build_depend>rmw_implementation</build_depend>
  <build_depend>std_msgs</build_depend>
  <exec_depend>rclcpp</exec_depend>
  <exec_depend>rmw_implementation</exec_depend>
  <exec_depend>std_msgs</exec_depend>
  <export>
    <build_type>ament_cmake</build_type>
  </export>
</package>

CMakeLists.txtの移植作業

修正する点を列挙する。

# ROS ROS2 備考
1 cmake_minimum_required(VERSION 2.8.3) cmake_minimum_required(VERSION 3.5) Cmakeのバージョンの変更
2 記述なし set(CMAKE_CXX_STANDARD 14) C++14に設定
3 find_package(catkin REQUIRED COMPONENTS roscpp std_msgs) find_package(ament_cmake REQUIRED)
find_package(rclcpp REQUIRED)
find_package(rmw_implementation REQUIRED)
find_package(std_msgs REQUIRED)
ament_cmakeから個別にパッケージを探し出す
4 catkin_package() ament_package() パッケージの登録の宣言をcatkinからamentに変更し、末尾に記述する
5 include_directories(include ${catkin_INCLUDE_DIRS}) include_directories(${rclcpp_INCLUDE_DIRS} 依存パッケージのパスを指定(1)
6 ${rmw_implementation_INCLUDE_DIRS} 依存パッケージのパスを指定(2)
7 ${std_msgs_INCLUDE_DIRS}) 依存パッケージのパスを指定(3)
8 target_link_libraries(talker ${catkin_LIBRARIES}) target_link_libraries(talker パッケージライブラリを追加(1)
9 ${rclcpp_LIBRARIES} パッケージライブラリを追加(2)
10 ${rmw_implementation_LIBRARIES} パッケージライブラリを追加(3)
11 ${std_msgs_LIBRARIES}) パッケージライブラリを追加(4)
12 記述なし install(TARGETS talker DESTINATION lib/${PROJECT_NAME}) 実行ファイルの保存先を追記
13 target_link_libraries(listener ${catkin_LIBRARIES}) target_link_libraries(listener パッケージライブラリを追加(1)
14 ${rclcpp_LIBRARIES} パッケージライブラリを追加(2)
15 ${rmw_implementation_LIBRARIES} パッケージライブラリを追加(3)
16 ${std_msgs_LIBRARIES}) パッケージライブラリを追加(4)
17 記述なし install(TARGETS listener DESTINATION lib/${PROJECT_NAME}) 実行ファイルの保存先を追記

以下が上記の点を修正したコードである。

CMakeLists.txt
cmake_minimum_required(VERSION 3.5)
project(beginner_tutorials)

set(CMAKE_CXX_STANDARD 14)

## Find ament and any ament_package packages
find_package(ament_cmake REQUIRED)
find_package(rclcpp REQUIRED)
find_package(rmw_implementation REQUIRED)
find_package(std_msgs REQUIRED)

## Build talker and listener
include_directories(${rclcpp_INCLUDE_DIRS}
                    ${rmw_implementation_INCLUDE_DIRS}
                    ${std_msgs_INCLUDE_DIRS})

add_executable(talker src/talker.cpp)
target_link_libraries(talker
                      ${rclcpp_LIBRARIES}
                      ${rmw_implementation_LIBRARIES}
                      ${std_msgs_LIBRARIES})
install(TARGETS talker DESTINATION lib/${PROJECT_NAME})        

add_executable(listener src/listener.cpp)
target_link_libraries(listener
                      ${rclcpp_LIBRARIES}
                      ${rmw_implementation_LIBRARIES}
                      ${std_msgs_LIBRARIES})
install(TARGETS listener DESTINATION lib/${PROJECT_NAME})

## Declare a ament package
ament_package()

ROS2パッケージの動作確認

パッケージが正しく動作するかを確かめる。
以下のコマンドを実行しパッケージをビルドする。

cd ~/ros2-dashing
colcon build

次に2つのターミナルを起動してそれぞれ以下のコマンドを実行する。以下が正常に動いているものである.

talkerノード
source ~/ros2-dashing/install/setup.bash
ros2 run beginner_tutorials talker
[INFO] [talker]: hello world 0
[INFO] [talker]: hello world 1
[INFO] [talker]: hello world 2
[INFO] [talker]: hello world 3
[INFO] [talker]: hello world 4
[INFO] [talker]: hello world 5
listenerノード
source ~/ros2-dashing/install/setup.bash
ros2 run beginner_tutorials listener
[INFO] [listener]: hello world 0
[INFO] [listener]: hello world 1
[INFO] [listener]: hello world 2
[INFO] [listener]: hello world 3
[INFO] [listener]: hello world 4
[INFO] [listener]: hello world 5
3
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?