Ubuntu24.04 + ROS2(jazzy)图片的发布及订阅节点

1 环境配置

复制代码
sudo apt install -y ros-jazzy-sensor-msgs ros-jazzy-cv-bridge

如果没有安装opencv,需要先安装 :

复制代码
sudo apt update
sudo apt install libopencv-dev python3-opencv

2 创建空间

复制代码
mkdir ~/image_ws
cd image_ws
mkdir src

3 创建源文件

源文件需要放置在src文件夹中

image_publisher.cpp

图片换成自己的图片

复制代码
#include <rclcpp/rclcpp.hpp>
#include <sensor_msgs/msg/image.hpp>
#include <cv_bridge/cv_bridge.hpp>
#include <opencv2/opencv.hpp>

class ImagePublisher : public rclcpp::Node {
public:
    ImagePublisher() : Node("image_publisher") {
        publisher_ = this->create_publisher<sensor_msgs::msg::Image>("image_topic", 10);
        timer_ = this->create_wall_timer(
            std::chrono::milliseconds(1000),
            [this]() { publish_image(); }
        );
    }

private:
    void publish_image() {
        cv::Mat image = cv::imread("/home/hl/图片/1.jpeg");
        if (image.empty()) {
            RCLCPP_ERROR(this->get_logger(), "Could not read image file.");
            return;
        }

        sensor_msgs::msg::Image::SharedPtr msg =
            cv_bridge::CvImage(std_msgs::msg::Header(), "bgr8", image).toImageMsg();
        publisher_->publish(*msg);
    }

    rclcpp::Publisher<sensor_msgs::msg::Image>::SharedPtr publisher_;
    rclcpp::TimerBase::SharedPtr timer_;
};

int main(int argc, char * argv[])
{
    // 初始化ROS2客户端库
    rclcpp::init(argc, argv);
    
    // 创建ImagePublisher节点并开始处理回调
    auto node = std::make_shared<ImagePublisher>();
    
    // 运行节点直到收到关闭信号
    rclcpp::spin(node);
    
    // 清理资源并关闭ROS2客户端库
    rclcpp::shutdown();
    return 0;
}

image_subscriber.cpp

复制代码
#include <rclcpp/rclcpp.hpp>
#include <sensor_msgs/msg/image.hpp>
#include <cv_bridge/cv_bridge.hpp>
#include <opencv2/opencv.hpp>

class ImageSubscriber : public rclcpp::Node {
public:
    ImageSubscriber() : Node("image_subscriber") {
        subscription_ = this->create_subscription<sensor_msgs::msg::Image>(
            "image_topic", 10,
            [this](const sensor_msgs::msg::Image::SharedPtr msg) { display_image(msg); });
    }

private:
    void display_image(const sensor_msgs::msg::Image::SharedPtr msg) {
        try {
            cv::Mat image = cv_bridge::toCvShare(msg, "bgr8")->image;
            cv::imshow("Received Image", image);
            cv::waitKey(1);
        } catch (const cv_bridge::Exception& e) {
            RCLCPP_ERROR(this->get_logger(), "Could not convert image: %s", e.what());
        }
    }

    rclcpp::Subscription<sensor_msgs::msg::Image>::SharedPtr subscription_;
};

int main(int argc, char * argv[])
{
    // 初始化ROS2客户端库
    rclcpp::init(argc, argv);
    
    // 创建ImagePublisher节点并开始处理回调
    auto node = std::make_shared<ImageSubscriber >();
    
    // 运行节点直到收到关闭信号
    rclcpp::spin(node);
    
    // 清理资源并关闭ROS2客户端库
    rclcpp::shutdown();
    return 0;
}

4 修改cmakelists.txt

复制代码
cmake_minimum_required(VERSION 3.8)
project(image_pkg)

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)
# uncomment the following section in order to fill in
# further dependencies manually.
# find_package(<dependency> REQUIRED)
find_package(rclcpp REQUIRED)
find_package(sensor_msgs REQUIRED)
find_package(cv_bridge REQUIRED)
find_package(OpenCV REQUIRED)

if(BUILD_TESTING)
  find_package(ament_lint_auto REQUIRED)
  # the following line skips the linter which checks for copyrights
  # comment the line when a copyright and license is added to all source files
  set(ament_cmake_copyright_FOUND TRUE)
  # the following line skips cpplint (only works in a git repo)
  # comment the line when this package is in a git repo and when
  # a copyright and license is added to all source files
  set(ament_cmake_cpplint_FOUND TRUE)
  ament_lint_auto_find_test_dependencies()
endif()


add_executable(image_publisher src/image_publisher.cpp)
ament_target_dependencies(image_publisher rclcpp sensor_msgs cv_bridge)

add_executable(image_subscriber src/image_subscriber.cpp)
ament_target_dependencies(image_subscriber rclcpp sensor_msgs cv_bridge)

# 显式链接 OpenCV 库
target_link_libraries(image_publisher ${OpenCV_LIBS})
target_link_libraries(image_subscriber ${OpenCV_LIBS})


install(TARGETS
  image_publisher
  image_subscriber
  DESTINATION lib/${PROJECT_NAME}
)

ament_package()

5 修改package.xml

添加依赖库

复制代码
<?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>image_pkg</name>
  <version>0.0.0</version>
  <description>simple publish/subscrible image</description>
  <maintainer email="hl@todo.todo">hl</maintainer>
  <license>Apache license 2.0</license>

  <buildtool_depend>ament_cmake</buildtool_depend>

  <depend>rclcpp</depend>
  <depend>sensor_msgs</depend>
  <depend>cv_bridge</depend>

  <test_depend>ament_lint_auto</test_depend>
  <test_depend>ament_lint_common</test_depend>

  <export>
    <build_type>ament_cmake</build_type>
  </export>
</package>

6 编译

进入image_ws目录

复制代码
colcon build --packages-select image_pkg

7 运行节点

打开两个终端,分别输入:

复制代码
source install/setup.bash
ros2 run image_pkg image_publiser

source install/setup.bash
ros2 run image_pkg image_subscriber

8 运行结果

9 避坑指南

a.#include <cv_bridge/cv_bridge.hpp> // 而不是 cv_bridge.h

b.不要把opencv库放入ament_target_dependencies,因为它是系统库,而不是ros的,应该显式链接 OpenCV 库target_link_libraries(image_publisher ${OpenCV_LIBS})

相关推荐
如若1238 小时前
Windows SSH + Headscale/Tailscale 组网及免密登录完整配置教程
运维·windows·ubuntu·ssh·内网穿透
菌菌的快乐生活16 小时前
Rufus + Ubuntu 24.04 Server(中山大学镜像)通用安装教程
ubuntu
垆边人似月.17 小时前
Ubuntu 配置 Samba 共享文件夹并映射到 Windows 完整指南
linux·windows·ubuntu
用户8351414049492 天前
把日志和寄存器值喂给AI做故障定位,我的实际问法
linux·ubuntu
进击的荆棘2 天前
MySQL——在ubuntu环境下安装MySQL
数据库·mysql·ubuntu
易点云徐源2 天前
HP 暗影精灵 PRO 16 安装双系统后,开机直接进入 Windows,按 F9 才能进入 Ubuntu:GRUB 菜单不显示的处理方法
linux·运维·ubuntu
Sayai3 天前
Ubuntu 开发环境搭建避坑(一):网卡 EEE 致 60% 周期性丢包,Realtek RTL8125 网络黑洞排查与修复
linux·运维·网络·ubuntu·性能优化
牢姐与蒯3 天前
WSL2 迁移教程:把Ubuntu+WSL2从C盘挪到别的盘
linux·运维·服务器·网络·ubuntu·1024程序员节
小菜要扣篮3 天前
Ubuntu 下使用 vscode 打开 C++ 项目后,无法通过 F12 定位到定义问题解决
c++·vscode·ubuntu
hhhjhl4 天前
Undici 跨端三方库仓颉适配全流程
java·开发语言·ubuntu