ROS2高效学习第五章 -- ros2 service 编程之自定义服务

ros2 service 编程之自定义服务

  • 1 前言和资料
  • 2 正文
    • 2.1 两种自定义服务的讨论
    • 2.2 自定义服务独立成包
      • 2.2.1 自定义服务(diy_interface)
      • 2.2.2 service_cpp使用自定义服务
      • 2.2.3 service_py使用自定义服务
    • 2.3 自定义服务放在模块包里(service_mix )
  • 3 总结

1 前言和资料

在ROS2高效学习第二章 – ros2常用命令和相关概念学习,熟练玩起来小乌龟样例这篇博客里,我们讲解了 ros2 service 的基本概念和调试命令,本文我们讲解 ros2 service 编程。内容编排上,我们将复用ROS2高效学习第四章 – ros2 topic 编程之自定义 msg的结构和内容,也使用两种方式实现自定义服务:一是自定义服务独立成包(复用 diy_interface 包);二是自定义服务与终端包放在一起,并实现 cpp 和 python 混合编程。
本文参考资料如下:
(1)ROS2高效学习第二章 – ros2常用命令和相关概念学习,熟练玩起来小乌龟样例 第2.5节
(2)ROS2高效学习第四章 – ros2 topic 编程之自定义 msg
(3)Writing-A-Simple-Cpp-Service-And-Client
(4)Writing-A-Simple-Py-Service-And-Client
(5)Custom-ROS2-Interfaces

2 正文

2.1 两种自定义服务的讨论

在ROS2高效学习第四章 – ros2 topic 编程之自定义 msg的2.1节,我们对自定义 msg 有详细的讨论,连带讲解了 ros2 cpp 和 python混合编程的实现方式。而自定义服务与自定义 msg 具有非常强的雷同性,同样的讨论对自定义服务完全适用,这里不再赘述,请读者移步另一篇博客阅读。

2.2 自定义服务独立成包

2.2.1 自定义服务(diy_interface)

(1)在 diy_interface 中,创建自定义服务文件

cd ~/colcon_ws/src/diy_interface
mkdir srv
touch srv/QuestionAndAnswer.srv

(2)编写QuestionAndAnswer.srv,内容就是一问一答。

string question
---
string answer

(3)添加 CMakeLists.txt

rosidl_generate_interfaces(${PROJECT_NAME}"msg/Student.msg""msg/Sphere.msg""srv/QuestionAndAnswer.srv"DEPENDENCIES geometry_msgs # Add packages that above messages depend on, in this case geometry_msgs for Sphere.msg
)

(4)编译并测试

~/colcon_ws
colcon build --packages-select diy_interface
source install/local_setup.bash
ros2 interface show diy_interface/srv/QuestionAndAnswer

在这里插入图片描述

2.2.2 service_cpp使用自定义服务

(1)创建 service_cpp 包和相关文件

cd ~/colcon_ws/src
ros2 pkg create --build-type ament_cmake --license Apache-2.0 service_cpp  --dependencies rclcpp
cd service_cpp
mkdir launch
touch launch/service_diy_launch.py
touch src/client_diy.cpp src/server_diy.cpp

(2)编写client_diy.cpp

#include <memory>
#include <chrono>#include "rclcpp/rclcpp.hpp"
#include "diy_interface/srv/question_and_answer.hpp"class ServiceClient : public rclcpp::Node 
{
public:ServiceClient() : Node("service_client") {client_ = this->create_client<diy_interface::srv::QuestionAndAnswer>("question_and_answer");}int init() {while (!client_->wait_for_service(std::chrono::seconds(1))) {if (!rclcpp::ok()) {RCLCPP_ERROR(this->get_logger(), "Interrupted while waiting for the service. Exiting.");return 0;}RCLCPP_INFO(this->get_logger(), "service not available, waiting again...");}return 0;}void run(const std::string &str) {auto request = std::make_shared<diy_interface::srv::QuestionAndAnswer::Request>();request->question = str;auto result = client_->async_send_request(request);if (rclcpp::spin_until_future_complete(this->get_node_base_interface(), result) == rclcpp::FutureReturnCode::SUCCESS) {RCLCPP_INFO(this->get_logger(), "[cpp client] send: %s, receive: %s", request->question.c_str(), result.get()->answer.c_str()); } else {RCLCPP_ERROR(this->get_logger(), "Failed to call service add_two_ints");} }private:rclcpp::Client<diy_interface::srv::QuestionAndAnswer>::SharedPtr client_;
};int main(int argc, char * argv[]) {rclcpp::init(argc, argv);auto node = std::make_shared<ServiceClient>();node->init();while (rclcpp::ok()) {std::string str = "how are you?";node->run(str);std::this_thread::sleep_for(std::chrono::seconds(1));}rclcpp::shutdown();return 0;
}

(3)编写server_diy.cpp

#include <memory>#include "rclcpp/rclcpp.hpp"
#include "diy_interface/srv/question_and_answer.hpp"class ServiceServer : public rclcpp::Node 
{
public:ServiceServer() : Node("service_server") {server_ = this->create_service<diy_interface::srv::QuestionAndAnswer>("question_and_answer", std::bind(&ServiceServer::answer_callback, this, std::placeholders::_1, std::placeholders::_2));}
private:void answer_callback(const std::shared_ptr<diy_interface::srv::QuestionAndAnswer::Request> request,std::shared_ptr<diy_interface::srv::QuestionAndAnswer::Response> response) {response->answer = "I'm fine, thank you.";RCLCPP_INFO(this->get_logger(), "[cpp server] receive: %s, return: %s", request->question.c_str(), response->answer.c_str());}private:rclcpp::Service<diy_interface::srv::QuestionAndAnswer>::SharedPtr server_;
};int main(int argc, char * argv[]) {rclcpp::init(argc, argv);rclcpp::spin(std::make_shared<ServiceServer>());rclcpp::shutdown();return 0;
}

(4)编写CMakeLists.txt

cmake_minimum_required(VERSION 3.8)
project(service_cpp)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(diy_interface REQUIRED)add_executable(server_diy src/server_diy.cpp)
ament_target_dependencies(server_diy rclcpp diy_interface)add_executable(client_diy src/client_diy.cpp)
ament_target_dependencies(client_diy rclcpp diy_interface)install(TARGETSserver_diyclient_diyDESTINATION lib/${PROJECT_NAME})install(DIRECTORYlaunchDESTINATION share/${PROJECT_NAME}
)
ament_package()

(5)添加 package.xml

  <depend>rclcpp</depend><depend>diy_interface</depend>  

(6)编写 service_diy_launch.py

from launch import LaunchDescription
from launch_ros.actions import Nodedef generate_launch_description():return LaunchDescription([Node(package='service_cpp',namespace='cpp',executable='server_diy',name='server_diy'),Node(package='service_cpp',namespace='cpp',executable='client_diy',name='client_diy')])

(7)编译并运行

~/colcon_ws
colcon build --packages-select diy_interface service_cpp
source install/local_setup.bash
ros2 launch service_cpp service_diy_launch.py

在这里插入图片描述

2.2.3 service_py使用自定义服务

(1)service_py 是 service_cpp 的 python 版实现,功能完全一样,这里不再详述创建步骤,具体请参考源码:service_py,源码说明一切!
(2)编译并运行

~/colcon_ws
colcon build --packages-select diy_interface service_py
source install/local_setup.bash
ros2 launch service_py service_diy_launch.py

在这里插入图片描述

2.3 自定义服务放在模块包里(service_mix )

(1)service_mix 使用 cpp 和 python 混合编程, server 端使用 cpp 实现,client 端使用 python 实现。在 service_mix 包里,添加了自定义服务:给圆半径,求圆面积。关于创建步骤,service_mix 与 ROS2高效学习第四章 – ros2 topic 编程之自定义 msg 第2.3节的 pubsub_mix 基本相同,这里不再赘述,具体请参考源码:service_mix,源码说明一切!
(2)编译并运行

~/colcon_ws
colcon build --packages-select service_mix
source install/local_setup.bash
ros2 launch service_mix service_mix_launch.py

在这里插入图片描述

3 总结

本文的代码托管在本人的github上:diy_interface,service_cpp,service_py,service_mix

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

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

python3.x的在线与离线安装纯净版

由于计划搭建一套使用python自动分析日志的流程&#xff0c;发现我们的测试环境CentOS 7仍然没有安装python3&#xff0c;无法使用这些新的库。Python 3在设计上着重提升了语言的一致性和易用性&#xff0c;它引入了许多关键改进&#xff0c;此外&#xff0c;Python 3环境拥有丰…

2024环境工程、能源系统与化学材料国际会议(ICEEESCM 2024)

2024环境工程、能源系统与化学材料国际会议&#xff08;ICEEESCM 2024) 一、【会议简介】 2024环境工程、能源系统与化学材料国际会议&#xff08;ICEEESCM 2024)将于2024年在西安举行。会议将围绕环境工程、能源系统与化学材料等议题展开讨论&#xff0c;旨在为从事环境工程…

【golang】25、图片操作

用 “github.com/fogleman/gg” 可以画线, 框 用 “github.com/disintegration/imaging” 可以变换颜色 一、渲染 1.1 框和字 import "github.com/fogleman/gg"func DrawRectangles(inPath string, cRects []ColorTextRect, fnImgNameChange FnImgNameChange) (st…

雨云:为你拨开云雾见青天

一、雨云品牌概览 雨云&#xff0c;这名字一听就让人联想到蓝天白云&#xff0c;清爽自然。那么&#xff0c;这个品牌是否真的如其名&#xff0c;能为我们这些在数字世界中漂泊的旅人提供一片宁静、稳定的“云”呢&#xff1f;接下来&#xff0c;让我们深入了解雨云的资质、能…

js 面试运行机制和存储(从以下几方面理解),栈和堆的理解

1 工作原理 每个浏览器都有自己的引擎&#xff0c;通过引擎把代码解析运行起来。 2 生命周期 3-1 内存分配 3-2 内存使用 3-3 内存回收 3 栈和堆的理解 timer也是个函数--所以也是引用类型。 4 如何运行 以下可忽略 首先声明变量&#xff0c;放在左侧栈中执行&#xff0c;在执行…

AI大预言模型——ChatGPT在地学、GIS、气象、农业、生态、环境应用

原文链接&#xff1a;AI大预言模型——ChatGPT在地学、GIS、气象、农业、生态、环境应用 一开启大模型 1 开启大模型 1)大模型的发展历程与最新功能 2)大模型的强大功能与应用场景 3)国内外经典大模型&#xff08;ChatGPT、LLaMA、Gemini、DALLE、Midjourney、Stable Diff…

C++设计模式之——组合模式

文章目录 组合模式的基本概念&#xff1a;**C代码案例简述&#xff1a; 组合模式&#xff08;Composite Pattern&#xff09;是一种结构型设计模式&#xff0c;它允许你将对象组织成树形结构&#xff0c;并且能够像处理单个对象一样处理整个组合结构。在组合模式中&#xff0c;…

嵌入式中回调函数的实现方法

一、什么是回调函数 1.1、回调函数的定义和基本概念 回调函数是一种特殊的函数&#xff0c;它作为参数传递给另一个函数&#xff0c;并在被调用函数执行完毕后被调用。回调函数通常用于事件处理、异步编程和处理各种操作系统和框架的API。 基本概念&#xff1a; 回调&#xf…

MATLAB环境下基于高斯滤波器-广义拉普拉斯算子的细胞核自动检测

作为病理图像分析的基础&#xff0c;细胞核检测可为细胞形态、纹理等多种相关分析提供支持&#xff0c;对于临床诊断具有重要意义。但是细胞核的人工识别过程十分费时费力&#xff0c;并且不同医生之间存在主观标注差异。因此&#xff0c;利用计算机技术进行自动检测能够更为客…

cuttag

1、官方流程&#xff0c;太空了&#xff0c;还是得结合文章分析 CUT&Tag Data Processing and Analysis Tutorial 2、paper流程参考 【Metabolic reprogramming by histone deacetylase inhibition preferentially targets NRF2-activated tumors】 【TASOR is a pseudo…

新版本的AndroidStudio生产签名文件打包失败

最近在创建新项目的时候&#xff0c;使用AS生产新的签名并打包时&#xff0c;打包失败&#xff0c;一开始报签名格式问题&#xff0c;查了一下&#xff0c;有的说要迁移到行业标准格式PKCS12,但是试了一下还是报错&#xff0c;再次查资料发现是JDK版本问题&#xff0c;不过还有…

基于centos的linux上docker安装,及mysql、redis等应用在docker容器中的安装

Docker环境安装 安装yum-utils&#xff1a; yum install ‐y yum‐utils device‐mapper‐persistent‐data lvm2为yum源添加docker仓库位置&#xff1a; yum‐config‐manager ‐‐add‐repo https://download.docker.com/linux/centos/docker‐ce.repo如果上面执行命令后…

黑马JavaWeb课程中安装vue脚手架出现的问题

1 安装node.js 要想前端工程化&#xff0c;必须安装node.js&#xff0c;前端工程化的环境。 在成功安装node.js后&#xff0c; 修改全局包安装路径为Node.js安装目录&#xff0c; 修改npm镜像源为淘宝镜像源&#xff0c;这里出现第一个问题&#xff0c;视频中给的淘宝镜像为&…

【Pytorch】成功解决AttributeError: ‘tuple’ object has no attribute ‘dim’

【Pytorch】成功解决AttributeError: ‘tuple’ object has no attribute ‘dim’ &#x1f308; 个人主页&#xff1a;高斯小哥 &#x1f525; 高质量专栏&#xff1a;Matplotlib之旅&#xff1a;零基础精通数据可视化、Python基础【高质量合集】、PyTorch零基础入门教程&…

大势智慧黄先锋:现实世界数字重建 拥抱AI 擘画自主可控的三维画卷

来源&#xff1a;中国地理信息产业协会 实景三维涉及到大面积、高精度的地理空间信息数据&#xff0c;然而早期国内99%以上的实景三维数据制作测绘单位都基于国外软件进行三维重建&#xff0c;如此重要的工作大量使用国外软件&#xff0c;如何确保国家地理空间信息的安全&#…

零拷贝技术深入分析

一、零拷贝 在前面的文章“深浅拷贝、COW及零拷贝”中对零拷贝进行过分析&#xff0c;但没有举例子&#xff0c;也没有深入进行展开分析。本文将结合实际的例程对零拷贝进行更深入的分析和说明。 在传统的IO操作中&#xff0c;以文件通过网络传输为例 &#xff0c;一般会经历以…

神经网络系列---卷积

文章目录 卷积神经网络卷积转置卷积 卷积核和反卷积的三种实现方式卷积的次数计算 卷积神经网络 在神经网络的卷积层中&#xff0c;向下取整&#xff08;Floor&#xff09;是一种常用的策略&#xff0c;特别是在处理输出尺寸不是整数的情况时。当你计算出卷积层输出的尺寸&…

Tomcat概念、安装及相关文件介绍

目录 一、web技术 1、C/S架构与B/S架构 1.1 http协议与C/S架构 1.2 http协议与B/S架构 2、前端三大核心技术 2.1 HTML&#xff08;Hypertext Markup Language&#xff09; 2.2 css&#xff08;Cascading Style Sheets&#xff09; 2.3 JavaScript 3、同步和异步 4、…

KakaoTalk数据库和加密文件密钥生成方法

KakaoTalk数据库密钥 KakaoTalk的数据库为sqlite3数据库&#xff0c;经过加密处理&#xff0c;不同类别的数据库采用不同的密钥加密。聊天记录的数据库由一个称为PRAGMA KEY的密钥进行加密&#xff0c;这里简称为PK。 PK的生成 PK的格式如下: ODSnnkkwyAHsXwgCEIQLCpAxdSZh…

【数学建模获奖经验】2023第八届数维杯数学建模:华中科技大学本科组创新奖获奖分享

2024年第九届数维杯大学生数学建模挑战赛将于&#xff1a;2024年5月10日08:00-5月13日09:00举行&#xff0c;近期同学们都开始陆续进入了备赛阶段&#xff0c;今天我们就一起来看看上一届优秀的创新奖选手都有什么获奖感言吧~希望能帮到更多热爱数学建模的同学。据说点赞的大佬…