目标:定义自定义接口文件( .msg
和 .srv
)并将它们与 Python 和 C++节点一起使用。
教程级别:初学者
时间:20 分钟
目录
背景
先决条件
任务
1. 创建一个新包
2. 创建自定义定义
3
CMakeLists.txt
4
package.xml
5. 构建
tutorial_interfaces
包6 确认消息和服务创建
7. 测试新界面
摘要
下一步
背景
在之前的教程中,您利用消息和服务接口来学习关于主题、服务以及简单的发布者/订阅者(C++/Python)和服务/客户端(C++/Python)节点。在那些情况下,您使用的接口是预先定义的。
虽然使用预定义的接口定义是一种好习惯,但有时您可能也需要定义自己的消息和服务。本教程将向您介绍创建自定义接口定义的最简单方法。
先决条件
您应该有一个 ROS 2 工作空间。
本教程还使用了在发布者/订阅者(C++ 和 Python)和服务/客户端(C++ 和 Python)教程中创建的包来尝试新的自定义消息。
任务
1. 创建一个新包
在本教程中,您将在各自的包中创建自定义的 .msg
和 .srv
文件,然后在另一个包中使用它们。两个包应该在同一个工作空间中。
由于我们将使用在早期教程中创建的 pub/sub 和 service/client 包,请确保您位于这些包的同一工作空间( ros2_ws/src
),然后运行以下命令来创建一个新包:
ros2 pkg create --build-type ament_cmake --license Apache-2.0 tutorial_interfaces
cxy@ubuntu2404-cxy:~/ros2_ws/src$ ros2 pkg create --build-type ament_cmake --license Apache-2.0 tutorial_interfaces
going to create a new package
package name: tutorial_interfaces
destination directory: /home/cxy/ros2_ws/src
package format: 3
version: 0.0.0
description: TODO: Package description
maintainer: ['cxy <cxy@todo.todo>']
licenses: ['Apache-2.0']
build type: ament_cmake
dependencies: []
creating folder ./tutorial_interfaces
creating ./tutorial_interfaces/package.xml
creating source and include folder
creating folder ./tutorial_interfaces/src
creating folder ./tutorial_interfaces/include/tutorial_interfaces
creating ./tutorial_interfaces/CMakeLists.txt
tutorial_interfaces
是新包的名称。请注意,它是且只能是一个 CMake 包,但这并不限制您可以在哪种类型的包中使用您的消息和服务。您可以在 CMake 包中创建自己的自定义接口,然后在 C++或 Python 节点中使用它,这将在最后一节中介绍。
.msg
和 .srv
文件需要分别放置在名为 msg
和 srv
的目录中。在 ros2_ws/src/tutorial_interfaces
中创建目录:
cxy@ubuntu2404-cxy:~/ros2_ws/src/tutorial_interfaces$
mkdir msg srv
2. 创建自定义定义
2.1 消息定义
在您刚刚创建的 tutorial_interfaces/msg
目录中,新建一个名为 Num.msg
的文件,其中包含一行代码声明其数据结构:
int64 num
这是一个自定义消息,用于传输一个名为 num
的 64 位整数。
在您刚刚创建的 tutorial_interfaces/msg
目录中,还要新建一个名为 Sphere.msg
的文件,内容如下:
geometry_msgs/Point center
float64 radius
此自定义消息使用了另一个消息包中的消息(在这种情况下为 geometry_msgs/Point
)。
2.2 srv 定义
在您刚刚创建的 tutorial_interfaces/srv
目录中,创建一个名为 AddThreeInts.srv
的新文件,包含以下请求和响应结构:
int64 a
int64 b
int64 c
---
int64 sum
这是您的自定义服务,它请求三个整数,分别命名为 a
、 b
和 c
,并返回一个名为 sum
的整数。
3 CMakeLists.txt
要将您定义的接口转换为特定语言的代码(如 C++和 Python),以便它们可以在这些语言中使用,请将以下行添加到 CMakeLists.txt
:
find_package(geometry_msgs REQUIRED)
find_package(rosidl_default_generators REQUIRED)
rosidl_generate_interfaces(${PROJECT_NAME}
"msg/Num.msg"
"msg/Sphere.msg"
"srv/AddThreeInts.srv"
DEPENDENCIES geometry_msgs # Add packages that above messages depend on, in this case geometry_msgs for Sphere.msg
)
便条
在 rosidl_generate_interfaces 中的第一个参数(库名称)必须与${PROJECT_NAME}相匹配(见 https://github.com/ros2/rosidl/issues/441#issuecomment-591025515)。
cmake_minimum_required(VERSION 3.8)
# 设置CMake的最低版本要求为3.8
project(tutorial_interfaces)
# 定义项目名称为'tutorial_interfaces'
if(CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang")
add_compile_options(-Wall -Wextra -Wpedantic)
endif()
# 如果使用GNU C++编译器或Clang编译器,则添加编译选项-Wall -Wextra -Wpedantic
# find dependencies
# 查找依赖项
find_package(ament_cmake REQUIRED)
# 查找ament_cmake包,标记为必需
# uncomment the following section in order to fill in
# further dependencies manually.
# find_package(<dependency> REQUIRED)
# 取消注释以下部分以手动添加更多依赖项
# find_package(<dependency> REQUIRED)
find_package(geometry_msgs REQUIRED)
# 查找geometry_msgs包,标记为必需
find_package(rosidl_default_generators REQUIRED)
# 查找rosidl_default_generators包,标记为必需
rosidl_generate_interfaces(${PROJECT_NAME}
"msg/Num.msg"
"msg/Sphere.msg"
"srv/AddThreeInts.srv"
DEPENDENCIES geometry_msgs # Add packages that above messages depend on, in this