Use ros1 under ros2_ Bridge and ros1 custom message bridge

Posted by mrbaseball34 on Fri, 18 Feb 2022 19:01:00 +0100

Use ros1 under ros2_ Bridge and ros1 custom message bridge

  • Sample environment

    Operating system: ubuntu 20.04 amd64

    ros version: noetic

    ros2 version: foxy

  • ros1 sample code

    1. Create workspace catkin for ros1_ WS, function pack custom_msgs and create an MSG file testnoetic msg

      TestNoetic. The contents of the MSG file are as follows:

      string test_str1
      int32 test_int1
      

      Compile the function package. Since you are familiar with ros1, we will not introduce the details of ros1 compilation here;

    2. Create ros2 workspace colcon_ws, function pack custom_msgs and create an MSG file testfoxy msg

      ros2 create package instruction:

      ros2 pkg create --build-type ament_cmake custom_msgs
      

      TestFoxy. The contents of the MSG file are as follows:

      string test_str2
      int32 test_int2
      

      Note: the naming of the msg file of ros2 has the rule of regular expression. It should start with a capital letter. Each variable in the file content cannot have a capital letter. For more detailed rules, please refer to the official document

    3. Since the file name of the message to be bridged in the example is different from the internal variable name, you need to define the mapping file mapping_rules.yaml

      -
        ros1_package_name: 'custom_msgs'
        ros1_message_name: 'TestNoetic'
        ros2_package_name: 'custom_msgs'
        ros2_message_name: 'TestFoxy'
        fields_1_to_2:
          test_str1: 'test_str2'
          test_int1: 'test_int2'
      

      This mapping file is placed in package XML directory at the same level. This file only needs to be given when the two package names or msg names or variable names are different. If the names are the same, they can be omitted. If this file exists, cmakelists Txt as follows:

      cmake_minimum_required(VERSION 3.5)
      project(custom_msgs)
      
      # Default to C++14
      if(NOT CMAKE_CXX_STANDARD)
        set(CMAKE_CXX_STANDARD 14)
      endif()
      
      if(CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang")
        add_compile_options(-Wall -Wextra -Wpedantic)
      endif()
      
      find_package(ament_cmake REQUIRED)
      find_package(builtin_interfaces REQUIRED)
      find_package(rosidl_default_generators REQUIRED)
      
      rosidl_generate_interfaces(custom_msgs
          msg/TestFoxy.msg
        DEPENDENCIES
          builtin_interfaces
      )
      
      install(FILES mapping_rules.yaml
        DESTINATION share/${PROJECT_NAME}
      )
      
      ament_export_dependencies(rosidl_default_runtime)
      
      ament_package()
      

      package. The XML is as follows:

      <?xml version="1.0"?>
      <?xml-model href="http://download.ros.org/schema/package_format3.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?>
      <package format="3">
        <name>custom_msgs</name>
        <version>0.0.0</version>
        <description>The custom_msgs package</description>
      
        <maintainer email="weibw@todo.todo">weibw</maintainer>
      
        <license>TODO</license>
      
        <depend>rclpy</depend>
        <depend>builtin_interfaces</depend>
        <depend>rosidl_default_generators</depend>
      
        <member_of_group>rosidl_interface_packages</member_of_group>
      
        <export>
          <build_type>ament_cmake</build_type>
          <ros1_bridge mapping_rules="mapping_rules.yaml"/>
        </export>
      </package>
      
    4. Compile custom under ros2_ Msgs Feature Pack

      source /opt/ros/foxy/setup.bash
      cd colcon_ws
      colcon build --packages-select custom_msgs
      
    5. Download ros1_bridge source code, because we want to bridge custom messages, so ros1_bridge must be recompiled

      Download the source code to github and put it in colcon_ In WS workspace

      source /opt/ros/noetic/setup.bash
      source /opt/ros/foxy/setup.bash
      source catkin_ws/devel/setup.bash
      source colcon/install/setup.bash
      cd colcon_ws
      colcon build --packages-select ros1_bridge --cmake-force-configure
      

      After compilation, enter the following command line:

      source colcon/install/setup.bash
      ros2 run ros1_bridge dynamic_bridge --print-pairs | grep custom_msgs
      

      If displayed:

      - 'custom_msgs/msg/TestFoxy' (ROS 2) <=> 'custom_msgs/TestNoetic' (ROS 1)
      

      It means that the bridge data conversion is successful

    6. After compiling, create a ros2 software package bridge for testing_ Test, write a simple subscriber to listen to the topic and verify whether the bridge is successful

      ros2 pkg create --build-type ament_cmake bridge_test --dependencies custom_msgs
      
      • Create test CPP, as follows

        #include <memory>
        
        #include "rclcpp/rclcpp.hpp"
        #include "custom_msgs/msg/test_foxy.hpp"
        using std::placeholders::_1;
        
        class MinimalSubscriber : public rclcpp::Node
        {
          public:
            MinimalSubscriber()
            : Node("minimal_subscriber")
            {
              subscription_ = this->create_subscription<custom_msgs::msg::TestFoxy>(
              "topic", 10, std::bind(&MinimalSubscriber::topic_callback, this, _1));
            }
        
          private:
            void topic_callback(const custom_msgs::msg::TestFoxy::SharedPtr msg) const
            {
              RCLCPP_INFO(this->get_logger(), "I heard custom_msgs::msg::TestFoxy : '%d'", msg->test_int);
            }
            rclcpp::Subscription<custom_msgs::msg::TestFoxy>::SharedPtr subscription_;
        };
        
        int main(int argc, char * argv[])
        {
          rclcpp::init(argc, argv);
          rclcpp::spin(std::make_shared<MinimalSubscriber>());
          rclcpp::shutdown();
          return 0;
        }
        
      • CMakelists.txt as follows

        cmake_minimum_required(VERSION 3.5)
        project(bridge_test)
        
        # Default to C99
        if(NOT CMAKE_C_STANDARD)
          set(CMAKE_C_STANDARD 99)
        endif()
        
        # Default to C++14
        if(NOT CMAKE_CXX_STANDARD)
          set(CMAKE_CXX_STANDARD 14)
        endif()
        
        if(CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang")
          add_compile_options(-Wall -Wextra -Wpedantic)
        endif()
        
        # find dependencies
        find_package(ament_cmake REQUIRED)
        find_package(rclcpp REQUIRED)
        find_package(custom_msgs REQUIRED)
        
        add_executable(subscriber src/test.cpp)
        ament_target_dependencies(subscriber rclcpp custom_msgs)
        
        install(TARGETS
          subscriber
          DESTINATION lib/${PROJECT_NAME})
        
        ament_package()
        
      • package. The XML is as follows

        <?xml version="1.0"?>
        <?xml-model href="http://download.ros.org/schema/package_format3.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?>
        <package format="3">
          <name>bridge_test</name>
          <version>0.0.0</version>
          <description>TODO: Package description</description>
          <maintainer email="weibw@todo.todo">weibw</maintainer>
          <license>TODO: License declaration</license>
        
          <buildtool_depend>ament_cmake</buildtool_depend>
          <depend>rclcpp</depend>
          <depend>custom_msgs</depend>
        
          <test_depend>ament_lint_auto</test_depend>
          <test_depend>ament_lint_common</test_depend>
        
          <export>
            <build_type>ament_cmake</build_type>
          </export>
        </package>
        
      • Compile function pack

        cd colcon_ws
        colcon build --packages-select bridge_test
        
    7. Verify the success of bridging custom messages

      • In the ros1 environment, use the command line tool to broadcast topic data at a fixed frequency

        source /opt/ros/noetic/setup.bash
        source catkin_ws/devel/setup.bash
        roscore&
        rostopic pub topic custom_msgs/TestNoetic "test_str1: 'hello'
        test_int: 234" -r 2
        
      • Running subscription node in ros2 environment

        source /opt/ros/foxy/setup.bash
        source colcon_ws/install/setup.bash
        ros2 run bridge_test subscriber
        
      • Run ros1_bridge

        source /opt/ros/noetic/setup.bash
        source /opt/ros/foxy/setup.bash
        source catkin_ws/devel/setup.bash
        source colcon/install/setup.bash
        ros2 run ros1_bridge dynamic_bridge
        

        At this time, you should see the following print in the subscription node terminal of ros2:

        [INFO] [1645162912.958789169] [minimal_subscriber]: I heard custom_msgs::msg::TestFoxy : '234'
        

        So far, this article ends

Topics: C++ AI Autonomous vehicles ROS2