ROS2组件component自定义实现

ROS2系列文章目录

ROS2中nav_msgs/msg/Path 数据含义及使用

ROS2中std_msgs/msg/Header 数据含义及使用

ROS中TF变换详解

ROS2中launch编写及参数含义(launch.xml、python)


提示:阅读并实践本文档后,将掌握并理解ros1中nodelet用法,掌握并理解ros2中component用法

文章目录

  • ROS2系列文章目录
  • ROS中nodelet与component的作用
  • 一、创建功能包并添加依赖
  • 二、新建组件函数文件及修改CMakeLists.txt
    • 1.新建component实现函数
    • 2.修改CMakeLists.txt添加组件信息
      • 2.1 使用cmake添加依赖生成库文件
      • 2.2 构建组件实现
    • 3. 使用指令查看是否加载成功自定义组件
      • 3.1查询插件是否生成
      • 3.2 加载运行自定义插件
  • 总结


ROS中nodelet与component的作用

Nodelet/component旨在提供一种方法,在一台机器上、在一个进程中运行多个算法,在进程内传递消息时不会产生拷贝成本。ros1与ros2中的节点发布与订阅话题数据,本质是将数据打包后通过TCP或者UDP将数据发送、接收、解包后进行数据处理。当存在大量数据如点云、图像等会导致消息传送滞后,因此在同一台机器中,使用nodelet/component会很好的避免数据传输问题,使用该方法只需要发送一个指向该数据的指针,而不是通过TCP/UDP发送数据本身,消息传输会更快。

ROS2中Component官方资料:http://docs.ros.org/en/humble/Tutorials/Intermediate/Writing-a-Composable-Node.html


提示:以下是本篇文章正文内容,下面案例可供参考

本教程的主要目标为:生成一个自定义的组件信息test_component::Test1,功能包为test_component,该组件的主要功能为发布话题“/talker”,发送的数据类型为std_msg/msg/string。

一、创建功能包并添加依赖

创建test_component功能包,添加依赖rclcpp、std_msgs、rcl_components等,实现如下:

ros2 pkg create test_component --build-type ament_cmake --dependencies  rclcpp std_msgs rclcpp_components

在这里插入图片描述

二、新建组件函数文件及修改CMakeLists.txt

1.新建component实现函数

test_component/src目录下新建C++实现源文件,文件名为:my_component.cpp
在这里插入图片描述

2.修改CMakeLists.txt添加组件信息

2.1 使用cmake添加依赖生成库文件

在cmake中包含实现功能必要的头文件:

include_directories(${rclcpp_INCLUDE_DIRS} ${std_msgs_INCLUDE_DIRS} ${rclcpp_components_INCLUDE_DIRS})

使用add_library添加要生成的库,具体使用方法如下:

 add_library(<name> [STATIC | SHARED | MODULE][EXCLUDE_FROM_ALL][<source>...])

将src/my_component.cpp文件添加生产Test1库

add_library(Test1 src/my_component.cpp )

给Test1库链接ros2相关的lib

ament_target_dependencies(Test1 rclcpp std_msgs rcl_components)

添加声明新构建的组件: test_component::Test1

rclcpp_components_register_node(Test1 "test_component::Test1")

声明添加一个新的的组件test_component::Test1到ros2系统中去

rclcpp_components_register_nodes(Test1 "test_component::Test1")

最后,将生成的库安装在指定的目录

install(TARGETS Test1ARCHIVE DESTINATION libLIBRARY DESTINATION libRUNTIME DESTINATION bin
)

上述操作对应的CMakeLists.txt文件如下:

cmake_minimum_required(VERSION 3.8)
project(test_component)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(std_msgs REQUIRED)
find_package(rclcpp_components 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 filesset(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 filesset(ament_cmake_cpplint_FOUND TRUE)ament_lint_auto_find_test_dependencies()
endif()
include_directories(${rclcpp_INCLUDE_DIRS} ${std_msgs_INCLUDE_DIRS} ${rclcpp_components_INCLUDE_DIRS})
add_library(Test1 SHARED src/my_component.cpp )
ament_target_dependencies(Test1 rclcpp std_msgs rclcpp_components)
rclcpp_components_register_nodes(Test1 "test_component::Test1")
install(TARGETS Test1ARCHIVE DESTINATION libLIBRARY DESTINATION libRUNTIME DESTINATION bin
)
ament_package()

2.2 构建组件实现

初始化节点, 从Node继承的类开始,并定义了Test1构造函数,确保类的构造函数采用NodeOptions参数。

  explicit Test1(const rclcpp::NodeOptions & options):Node("test_node",options){// 创建话题发布者pub_ptr = this->create_publisher<std_msgs::msg::String>("/talker",10);// 创建定时器,定时1s后进入回调函数time_ptr = this->create_wall_timer(std::chrono::seconds(1),std::bind(&Test1::time_callback,this));}

使用RSO2中的pluginlib类似的宏调用声明

#include <rclcpp_components/register_node_macro.hpp>
// 给ROS系统调用提供宏定义接口
RCLCPP_COMPONENTS_REGISTER_NODE(test_component::Test1);

生成一个自定义的组件信息test_component::Test1的实现文件test_component.cpp如下:

#include <rclcpp/rclcpp.hpp>
#include <std_msgs/msg/string.hpp>
#include <chrono>
#include <string>
#include <rclcpp_components/register_node_macro.hpp>namespace test_component{//继承rclcpp中的node节点,注意构建组件的构造函数有区别class Test1:public rclcpp::Node{public:// 构造函数中加入rclcpp::NodeOptions,并初始化explicit Test1(const rclcpp::NodeOptions & options):Node("test_node",options){// 创建话题发布者pub_ptr = this->create_publisher<std_msgs::msg::String>("/talker",10);// 创建定时器,定时1s后进入回调函数time_ptr = this->create_wall_timer(std::chrono::seconds(1),std::bind(&Test1::time_callback,this));}private:// 定时器指针rclcpp::TimerBase::ConstSharedPtr time_ptr;// 发布者话题指针rclcpp::Publisher<std_msgs::msg::String>::SharedPtr pub_ptr;// 话题发布数据std_msgs::msg::String data;// 定时器回调函数void time_callback(){static unsigned int i = 0;i++;data.data = std::to_string(i);pub_ptr->publish(data);RCLCPP_INFO(this->get_logger(),"进入定时器回调:%d",i);}};
};
// 给ROS系统调用提供宏定义接口
RCLCPP_COMPONENTS_REGISTER_NODE(test_component::Test1);

3. 使用指令查看是否加载成功自定义组件

3.1查询插件是否生成

使用ROS2推荐的colcon编译工具编译上述功能包后,执行一下指令:

source install/setup.bash
ros2 component types 

执行后输出结果中可以查看到是否已经加载自定义的组件信息
在这里插入图片描述

3.2 加载运行自定义插件

执行组件容器运行指令

ros2 run rclcpp_components component_container

执行完成后,可以通过查询ROS2中的节点指令确认是否启动成功

在这里插入图片描述

使用指令加载命令对生产的自定义插件加载

#ros2 component load /组件管理器名称  功能包  注册的组件名称
ros2 component load /ComponentManager test_component test_component::Test1 

执行上述指令后,在组件管理终端即可看到打印输出的日志信息

在这里插入图片描述使用节点管理工具以及话题打印工具查看是否正常显示节点以及话题内容

请添加图片描述


总结

本教程主要实现一个自定义的组件信息test_component::Test1,功能包为test_component,组件管理器启动加载该组件后,能够正常发布话题“/talker”,据类型为std_msg/msg/string。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/744407.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

新版Android Studio火烈鸟 在新建项目工程时 无法选java的语言模板解决方法

前言 最近下载最新版androidstudio时 发现不能勾选java语言模板了 如果快速点击下一步 新建项目 默认是kotlin语言模板 这可能和google主推kt语言有关 勾选1 如图所示 如果勾选 No Activity 这个模板 是可以选java语言模板的 但是里面没有默认的Activity 勾选2 和以前的用法…

阿里云价格战的背后,难以言说附送阿里云服务器优惠价格明细表

2024阿里云服务器优惠活动政策整理&#xff0c;阿里云99计划ECS云服务器2核2G3M带宽99元一年、2核4G5M优惠价格199元一年&#xff0c;轻量应用服务器2核2G3M服务器61元一年、2核4G4M带宽165元1年&#xff0c;云服务器4核16G10M带宽26元1个月、149元半年&#xff0c;云服务器8核…

运放的基础知识

运算放大器&#xff08;Operational Amplifier&#xff0c;简称运放&#xff09;是一种直流耦合、差模&#xff08;差动模式&#xff09;输入的高增益电压放大器&#xff0c;通常具有单端输出。它能产生一个相对于输入端电势差大数十万倍的输出电势&#xff08;对地而言&#x…

IP地址被泄露了有什么安全隐患吗

在数字时代&#xff0c;IP地址是我们在线身份的关键&#xff0c;它不仅仅是网络中的一个地址标识&#xff0c;更是我们数字安全的门户。黑客对IP地址的兴趣不止于其代表的数字串——它们是进入个人和企业数据宝库的钥匙。那么&#xff0c;当黑客得知我们的IP地址时&#xff0c;…

无需编程技能:Python爬虫与数据可视化毕业论文代写服务

引言 作为一名在软件技术领域深耕多年的专业人士&#xff0c;我不仅在软件开发和项目部署方面积累了丰富的实践经验&#xff0c;更以卓越的技术实力获得了&#x1f3c5;30项软件著作权证书的殊荣。这些成就不仅是对我的技术专长的肯定&#xff0c;也是对我的创新精神和专业承诺…

四川古力未来科技抖音小店:行业标杆的崛起与未来展望

在当下这个数字化、网络化的时代&#xff0c;电商行业正以前所未有的速度迅猛发展。四川古力未来科技有限公司&#xff0c;凭借其敏锐的市场洞察力和创新精神&#xff0c;成功在抖音小店平台上崭露头角&#xff0c;成为行业内的佼佼者。今天&#xff0c;我们就来一起探讨四川古…

Navicat16安装时报错记录

1.安装过程中一定要断网 2.安装好后&#xff0c;先不要直接打开客户端&#xff0c;应该先打开激活破解软件&#xff0c;如下&#xff1a; 选择HOSTS--》再Patch-->是&#xff0c;然后生成注册码&#xff0c;打开客户端正常执行即可

从“断亲”到“自我养育”,看年轻一代消费变迁丨小红书热点

一、不爱走亲戚&#xff0c;年轻人“断亲潮”来袭 今年春节期间&#xff0c;关于“农村出现以家庭为单位的断亲”的话题登上热搜。小红书等社交媒体平台上&#xff0c;也涌现出许多“回怼亲戚”的短视频&#xff0c;娱乐性调侃亦或是“阴阳怪气”地攻击&#xff0c;内容背后是当…

IIS上部署.netcore WebApi项目及swagger

.netcore项目一般是直接双击exe文件&#xff0c;运行服务&#xff0c;今天有个需求&#xff0c;需要把.netcore项目运行在IIS上&#xff0c;遇到了一个小坑&#xff0c;在这里记录一下。 安装IIS&#xff0c;怎么部署站点&#xff0c;这些过于简单就不细说了&#xff0c;不知道…

C++:继承与派生

为什么会有继承这样的语法呢&#xff1f;&#xff1f;试想这样一个场景&#xff1a;假设我们这个App需要去获取不同类型用户的数据&#xff0c;并进行分类&#xff0c;那么就需要我们去写对应不同的类&#xff0c;比如说学生、老师、军人、公司职工…………每个类都需要有名字、…

品牌方如何借热点做话题?媒介盒子分享

每时每刻都有热点&#xff0c;品牌方总想着借热点来做话题营销&#xff0c;然而有些热点能让品牌有效曝光&#xff0c;有些热点稍不注意就会让品牌产生负面舆论&#xff0c;今天媒介盒子就来和大家好好聊聊&#xff1a;品牌方如何借热点做话题。 一、 热点选择 品牌方可以通过…

域内令牌窃取

前言 有这样一种场景&#xff0c;拿到了一台主机权限&#xff0c;是本地管理员&#xff0c;同时在这台主机上登录的是域管成员&#xff0c;这时我们可以通过dump lsass或通过 Kerberos TGT &#xff0c;但是这是非常容易被edr命中的。 本文就通过令牌窃取进行研究&#xff0c…

pgsql常用索引简写

文章来源&#xff1a;互联网博客文章&#xff0c;后续有时间再来细化整理。 在数据库查询中&#xff0c;合理的使用索引&#xff0c;可以极大提升数据库查询效率&#xff0c;充分利用系统资源。这个随着数据量的增加得到提升&#xff0c;越大越明显&#xff0c;也和业务线有关…

《鸟哥的Linux私房菜》第6章——总结与习题参考答案

目录 一、 简介 二、一些新了解的指令 1.touch- 修改文件时间或创建新文件 2.umask-新建文件/目录的默认权限 3.文件隐藏属性 4.文件特殊权限 5.file-观察文件类型 三、简答题部分 一、 简介 本章介绍了一些常用的文件与目录指令&#xff0c;包括新建/删除/复制/移动/查…

2024HVV行动-进军蓝中研判(log4j2、fastjson、Struts2、Shiro)

1、log4j2 特征&#xff1a; 恶意请求中包含 JNDI 协议地址&#xff0c;如"ldap://"、"rmi://"等&#xff0c;被 log4j2 解析为 JNDI 查找。 原理&#xff1a; 在日志输出中&#xff0c;未对字符进行严格的过滤&#xff0c;执行了 JNDI 协议加载的远程恶…

教师如何搭建学生查询考试分数的平台?

随着信息技术的快速发展&#xff0c;搭建一个学生查询考试分数的平台已经成为现代教育管理的重要组成部分。这样的平台不仅可以提高成绩管理的效率&#xff0c;还能为学生提供便捷、及时的成绩查询服务。那么&#xff0c;作为教师&#xff0c;我们应该如何搭建这样一个平台呢&a…

【海贼王的数据航海】栈和队列

目录 1 -> 栈 1.1 -> 栈的概念及结构 1.2 -> 栈的实现 1.2.1 -> Stack.h 1.2.2 -> Stack.c 1.2.3 -> Test.c 2 -> 队列 2.1 -> 队列的概念及结构 2.2 -> 队列的实现 2.2.1 -> Queue.h 2.2.2 -> Queue.c 1 -> 栈 1.1 -> 栈的…

如何缩小你和大厂UI设计师之间的差距?重点关注你的作品集!

据说金三银四&#xff0c;在新一轮招聘旺季到来之前&#xff0c;你做过UI作品集吗&#xff1f;一个好的作品集可以为你的面试增加很多分数&#xff01;在开始之前&#xff0c;分享五个适合交互设计作品集的软件&#xff1a; 一、即时设计 这是一款专门为UI设计而设计的在线矢…

多线程(volatile)

volatile的功能 保证内存可见性禁止指令重排序 内存可见性 简单的理解 两(多)个线程同时针对一个变量进行操作, 一个线程读, 一个线程修改, 此时读到的值不一定是修改过后的值 即读线程没有感知到变量的变化 (其实是 编译器/JVM 对于代码在多线程情况下的优化进行了误判) 从 J…

Linux:设置别名命令alias

相关阅读 Linuxhttps://blog.csdn.net/weixin_45791458/category_12234591.html?spm1001.2014.3001.5482 在Linux中alias命令用于为一串字符&#xff08;常代表命令&#xff09;设置一个别名&#xff0c;该别名在Bash读取并解析一行命令时会被展开。 下面是该命令的语法。 用…