ROS中编写Publisher和Subscriber的方法(Python版) 您所在的位置:网站首页 publish是什么文件 ROS中编写Publisher和Subscriber的方法(Python版)

ROS中编写Publisher和Subscriber的方法(Python版)

2023-10-03 13:15| 来源: 网络整理| 查看: 265

参考:http://wiki.ros.org/ROS/Tutorials/WritingPublisherSubscriber(python)

1 编写Publisher节点

节点是连接到ROS网络的可执行文件的ROS术语。在这里,我们创建一个不断广播消息的发布者(“talker”)节点。创建一个ros包,也可以用现有的ros包,比如:

roscd beginner_tutorials

 创建包的方法参考之前的文章《ROS中编写服务器和客户端的方法(C++版)》

1.1 代码

首先创建一个‘script’的路径来保存python代码

mkdir scripts cd scripts

然后,新建一个文件,命名为talker.py,复制以下代码进去:

#!/usr/bin/env python # license removed for brevity import rospy from std_msgs.msg import String def talker(): pub = rospy.Publisher('chatter', String, queue_size=10) rospy.init_node('talker', anonymous=True) rate = rospy.Rate(10) # 10hz while not rospy.is_shutdown(): hello_str = "hello world %s" % rospy.get_time() rospy.loginfo(hello_str) pub.publish(hello_str) rate.sleep() if __name__ == '__main__': try: talker() except rospy.ROSInterruptException: pass 1.2 代码解释

让我们来一行一行地看代码意义

#!/usr/bin/env python

每个python版本的ROS节点在开头都有这样一个声明,表示这个文件是python类型

import rospy from std_msgs.msg import String

如果要写ROS节点,需要导入rospy。std_msgs.msg的目的是可以使用std_msgs/String消息类型来发布

pub = rospy.Publisher('chatter', String, queue_size=10) rospy.init_node('talker', anonymous=True)

这部分代码定义了talker与其它ROS节点的通讯。

pub = rospy.Publisher("chatter", String, queue_size=10) 表示你正在使用String类型的消息来发布你的节点到chatter。String就是std_msgs.msg.String类。如果任何订阅者都没有足够快地接收到消息,queue_size将会限制队列消息的数量。在旧的ROS版本中,忽略掉了这一点。

下一行是非常重要的,因为它告诉rospy你的ros节点名字,直到rospy有了这个信息,它才能够和ROS Master开始通讯。在这个例子中,你的节点名字是talker

anoymous=True 通过在你名字的后边添加一个随机数,来保证你的节点独一无二。

rate = rospy.Rate(10) # 10hz

这一行创建速率对象rate.在其方法sleep()的帮助下,它提供了一个以一定速率循环的方便的方法。参数10表示我们期望以每秒循环10次(只要我们的处理时间不超过1/10秒)

while not rospy.is_shutdown(): hello_str = "hello world %s" % rospy.get_time() rospy.loginfo(hello_str) pub.publish(hello_str) rate.sleep()

这个循环是一个相当标准的rospy结构:检查rospy.is_shutdown标志位然后开始工作(‘work’)。你必须检查is_shutdown()来确定你的成熟是否应该退出(例如有Ctrl-C操作或其它)。在这个例子中,‘work’是调用pub.publish(hello_str)来发布一个字符串到chatter话题。循环调用rate.sleep(),睡眠足够的时间,以便通过循环来保持所需的速率。

(你可以运行rospy.sleep()和time.sleep()来达到相同的定时效果)

循环中海油rospy.loginfo(str),这条执行三重任务:消息打印到屏幕上,写入到节点的日志文件中,并且被写入rosout。rosout可以方便的进行调试:你可以使用rqt_console来提取消息,而不必使用节点的输出找到控制台窗口。

std_msgs.msg.String是一个非常简单的消息类型,所以你可能会想知道发布更复杂的类型是什么样子。一般的经验是构造函数args与.msg文件中的顺序相同。你也可以传递任何参数,也可以直接初始化字段。

msg = String() msg.data = str

或者可以初始化一些值,剩余的采用默认值:

String(data=str)

你可能会好奇剩余的几行代码:

try: talker() except rospy.ROSInterruptException: pass

除了标准的Python_main_检查之外,他会捕获一个rospy.ROSInterruptException异常,当Ctrl-C被按下或者Node被关闭时,它将以rospy.sleep()和rospy.Rate.sleep()的方法抛出。引发这个异常的原因是因为在sleep()之后不会再继续执行代码。

现在,让我们来写一个节点来接收这条消息。

2.写一个Subscriber节点 2.1 代码

还是在上一节文件夹中,建立一个listener.py的文件,复制以下代码:

#!/usr/bin/env python import rospy from std_msgs.msg import String def callback(data): rospy.loginfo(rospy.get_caller_id() + "I heard %s", data.data) def listener(): # In ROS, nodes are uniquely named. If two nodes with the same # node are launched, the previous one is kicked off. The # anonymous=True flag means that rospy will choose a unique # name for our 'listener' node so that multiple listeners can # run simultaneously. rospy.init_node('listener', anonymous=True) rospy.Subscriber("chatter", String, callback) # spin() simply keeps python from exiting until this node is stopped rospy.spin() if __name__ == '__main__': listener() 2.2 代码解释

listener.py与talker.py文件类似,在listener中会引入一种新的基于回调机制callback来订阅消息。

rospy.init_node('listener', anonymous=True) rospy.Subscriber("chatter", String, callback) # spin() simply keeps python from exiting until this node is stopped rospy.spin()

这个声明表示你的节点订阅消息类型为std_msgs.msgs.String的chatter主题。当接收到新的消息时,回调callback将作为第一个参数被调用。

我们也改变了对rospy.init_node()的调用,我们添加了anonymous=True关键字参数。ROS要求每个节点都有唯一的名称,如果有相同名称的节点出现,则会突破前一个节点。这样就可以很容易地从网络上启动故障的节点。anonymous=True标志高速rospy为节点生成唯一的名称,以便可以轻松地运行多个listener.py节点。

最后添加rospy.spin()只是为了让你的节点退出,直到节点已经关闭。与roscpp不同,rospy.spin()不影响用户回调函数,因为它们有自己的线程。

3 构建自己的节点

我们使用CMake作为我们的构建系统,是的,即使对于python节点也必须使用它。这是为了确保自动生成的消息和服务的python代码被创建。

运行到catkin工作空间,然后运行catkin_make:

cd ~/catkin_ws catkin_make

然后分别在三个不同的终端运行下边的指令

roscore rosrun beginner_tutorials talker.py rosrun beginner_tutorials listener.py

运行结果如下



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有