ROS用python编写订阅者和发布者(使用存放在其他package的自定义msg文件)
本文记录一下用python编写使用自定义消息的ros订阅者和发布者时存在的一些问题。
声明一下,本文的代码是从自己项目工程截取的,不适合直接使用,只适合作为参照模板
1、首先是如何创建msg文件和编译
文件结构如图:
catkin_ws
├── build
├── devel
└── src
├── robot_msgs
│ ├── CMakeLists.txt
│ ├── msg
│ │ └── Controldata.msg
│ └── package.xml
└── tcp_ros
└── script
└── test.py
catkin_ws工作空间里有两个package,一个只用来存放消息(可自行添加更多消息),一个用于存放代码。
Controldata.msg消息文件如下:
uint32 cmd
float32 param1
float32 param2
在robot_msgs包里的CMakerList.txt:
cmake_minimum_required(VERSION 2.8.3)
project(robot_msgs)
#这里添加依赖message_generation 用于生成消息
find_package(catkin REQUIRED COMPONENTS
message_generation
std_msgs
geometry_msgs
)
#这里添加消息文件Controldata.msg
add_message_files(
DIRECTORY msg
FILES
Controldata.msg
)
generate_messages(DEPENDENCIES std_msgs geometry_msgs)
#这里增加消息生成包message_runtime
catkin_package(CATKIN_DEPENDS message_runtime std_msgs geometry_msgs)
在robot_msgs包里的package.xml添加如下:
<build_depend>message_generation</build_depend>
<run_depend>message_runtime</run_depend>
在tcp_ros包里的CMakerList:
find_package(catkin REQUIRED COMPONENTS #查找robot_msgs包
roscpp
rospy
std_msgs
robot_msgs
)
catkin_package( #包含robot_msgs包
INCLUDE_DIRS include
LIBRARIES tjurobot
CATKIN_DEPENDS roscpp rospy std_msgs robot_msgs message_runtime
DEPENDS system_lib
)
2、python编写的发布者节点
-
发布者程序: 关键是如何在python节点里导入存在其他package的msg文件!!
#!/usr/bin/env python # license removed for brevity import rospy from robot_msgs.msg import Controldata #翻译为:从robot_msgs包里的msg文件夹内导入名为Controldata的msg文件! def talker(): pub = rospy.Publisher('chatter', Controldata, queue_size=10) #设置发布话题名为“chatter”,消息类型为Controldata.msg,消息队列最大容量为10帧的对象pub rospy.init_node('talker', anonymous=True) #初始化名为“talker”的节点 rate = rospy.Rate(10) # 10hz while not rospy.is_shutdown(): send_msg = Controldata() #初始化一个消息结构体:直接以该msg文件名作为函数 send_msg.cmd =0X15 #给send_msg结构体内参数赋值(也就是该msg文件内参数) send_msg.param1 = 123 send_msg.param2 = 0 pub.publish(send_msg) #调用pub对象的publish函数发布话题 rate.sleep() #在循环中可以用刚刚好的睡眠时间维持期望的速率,适用于需要不停发布的话题 if __name__ == '__main__': try: talker() except rospy.ROSInterruptException: pass
3、python编写的订阅者节点
-
订阅者程序:关键是如何在回调函数里运用话题数据
#!/usr/bin/env python import rospy from robot_msgs.msg import Controldata def callback_fuc(data): #该data则相当于发布者的send_msg结构体 rospy.loginfo("I heard %d,%d,%d", data.cmd,data.param1,data.param2) def listener(): rospy.init_node('listener', anonymous=True) #初始化名为“listener”的订阅者节点:anonymous=True会为节点生成唯一的名称避免节点重名 rospy.Subscriber("chatter", Controldata, callback_fuc) #设置订阅者属性:订阅的话题名“chatter”,话题对应的msg消息文件名,回调函数名 rospy.spin() #必须要有,否则无法接收,但会相当于死循环程序会卡在这里 if __name__ == '__main__': listener()
关于如何解决rospy.spin()后程序卡死无法执行的问题可参照该博客:
(94条消息) 解决rospy.spin()一直循环,无法执行剩余程序_DLUT_小叮当的博客-CSDN博客_rospy.spin
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· winform 绘制太阳,地球,月球 运作规律
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人