赞
踩
目录
本示例介绍如何在 MATLAB® 中设置 ROS,并获取有关 ROS 网络和 ROS 消息的信息。
机器人操作系统(ROS)是一种通信接口,可使机器人系统的不同部分相互发现,并在它们之间发送和接收数据。MATLAB® 通过一个函数库支持 ROS,使您能够与支持 ROS 的物理机器人或机器人模拟器(如 Gazebo®)交换数据。
更多信息,请参阅机器人操作系统(ROS)和 ROS 网站上的 "概念 "部分。
使用 rosinit 初始化 ROS。默认情况下,rosinit 会在 MATLAB 中创建一个 ROS 主节点,并启动一个与主节点相连的全局节点。其他 ROS 功能会自动使用全局节点。
rosinit
- Launching ROS Core...
- .....Done in 5.7786 seconds.
- Initializing ROS master on http://172.21.16.85:51063.
- Initializing global node /matlab_global_node_13423 with NodeURI http://ah-avijayar:52604/ and MasterURI http://localhost:51063.
使用 rosnode list 查看 ROS 网络中的所有节点。请注意,唯一可用的节点是由 rosinit 创建的全局节点。
rosnode list
/matlab_global_node_13423
使用 exampleHelperROSCreateSampleNetwork 为 ROS 网络添加三个节点以及样本发布者和订阅者。
exampleHelperROSCreateSampleNetwork
再次使用 rosnode list 查看三个新节点(node_1、node_2 和 node_3)。
rosnode list
- /matlab_global_node_13423
- /node_1
- /node_2
- /node_3
图中显示了 ROS 网络的当前状态。MATLAB 全局节点是断开的,因为它目前没有任何发布者、订阅者或服务。
使用 rostopic 列表查看 ROS 网络中的可用主题。目前有四个活动主题: /pose、/rosout、/scan 和 /tf。默认主题:rosout 和 tf 始终存在于 ROS 网络中。其他两个主题是作为样本网络的一部分创建的。
rostopic list
- /pose
- /rosout
- /scan
- /tf
使用 rostopic info <topicname> 获取特定主题的具体信息。下面的命令显示 /node_1 发布(向 /pose 主题发送消息),而 /node_2 订阅(接收来自该主题的消息)。更多信息请参阅 "与 ROS 发布者和订阅者交换数据"。
rostopic info /pose
- Type: geometry_msgs/Twist
-
- Publishers:
- * /node_1 (http://ah-avijayar:52609/)
-
- Subscribers:
- * /node_2 (http://ah-avijayar:52614/)
使用 rosnode info <nodename> 获取特定节点的信息。下面的命令显示,node_1 向 /pose、/rosout 和 /tf 主题发布信息,订阅 /scan 主题并提供服务: /node_1/get_loggers 和 /node_1/set_logger_level。ROS 网络中创建的所有节点都提供默认日志服务:get_loggers 和 set_logger_level。
rosnode info /node_1
- Node: [/node_1]
- URI: [http://ah-avijayar:52609/]
-
- Publications (3 Active Topics):
- * /pose
- * /rosout
- * /tf
-
- Subscriptions (1 Active Topics):
- * /scan
-
- Services (2 Active):
- * /node_1/get_loggers
- * /node_1/set_logger_level
ROS 服务为跨 ROS 网络的程序调用提供了一种机制。服务客户端向服务服务器发送请求信息,服务服务器会处理请求中的信息并返回响应信息(请参阅 "调用和提供 ROS 服务")。
使用 rosservice list 查看 ROS 网络中所有可用的服务服务器。下面的命令显示,有两个服务(/add 和 /reply)以及所有节点的默认日志记录器服务可用。
rosservice list
- /add
- /matlab_global_node_13423/get_loggers
- /matlab_global_node_13423/set_logger_level
- /node_1/get_loggers
- /node_1/set_logger_level
- /node_2/get_loggers
- /node_2/set_logger_level
- /node_3/get_loggers
- /node_3/set_logger_level
- /reply
使用 rosservice info <servicename> 获取特定服务的信息。
rosservice info /add
- Node: /node_3
- URI: rosrpc://ah-avijayar:52618
- Type: roscpp_tutorials/TwoInts
- Args: MessageType A B
发布者、订阅者和服务使用 ROS 消息来交换信息。每个 ROS 消息都有一个相关的消息类型,它定义了消息中的数据类型和信息布局(请参阅 "使用基本 ROS 消息")。
使用 rostopic type <topicname> 查看主题使用的消息类型。下面的命令显示,/pose 主题使用的消息类型为 geometry_msgs/Twist。
rostopic type /pose
geometry_msgs/Twist
使用 rosmsg show <messagetype> 查看消息类型的属性。(geometry_msgs/Twist)消息类型有两个属性:线性(Linear)和角度(Angular)。每个属性都是几何_msgs/Vector3 类型的消息,而几何_msgs/Vector3 又有三个 double 类型的属性。
rosmsg show geometry_msgs/Twist
- % This expresses velocity in free space broken into its Linear and Angular parts.
- Vector3 Linear
- Vector3 Angular
rosmsg show geometry_msgs/Vector3
- % This represents a vector in free space.
- % It is only meant to represent a direction. Therefore, it does not
- % make sense to apply a translation to it (e.g., when applying a
- % generic rigid transformation to a Vector3, tf2 will only apply the
- % rotation). If you want your data to be translatable too, use the
- % geometry_msgs/Point message instead.
-
- double X
- double Y
- double Z
使用 rosmsg list 查看 MATLAB 中可用消息类型的完整列表。
1.6 关闭 ROS 网络
使用 exampleHelperROSShutDownSampleNetwork 从 ROS 网络中删除样本节点、发布者和订阅者。只有在先前使用 exampleHelperROSStartSampleNetwork 创建了示例网络时,才需要使用此命令。
exampleHelperROSShutDownSampleNetwork
使用 rosshutdown 关闭 MATLAB 中的 ROS 网络。这将关闭由 rosinit 启动的 ROS 主节点,并删除全局节点。建议在完成 ROS 网络工作后使用 rosshutdown。
rosshutdown
- Shutting down global node /matlab_global_node_13423 with NodeURI http://ah-avijayar:52604/ and MasterURI http://localhost:51063.
- Shutting down ROS master on http://172.21.16.85:51063.
ROS 网络由一个 ROS 主站和多个 ROS 节点组成。ROS 主节点通过跟踪所有活跃的 ROS 实体,促进 ROS 网络中的通信。每个节点都需要向 ROS 主站注册,才能与网络中的其他节点通信。MATLAB® 可以启动 ROS 主站,也可以在 MATLAB 外部(例如在另一台计算机上)启动主站。
使用 ROS 时,通常需要遵循以下步骤:
本例向您展示了如何
先决条件: 开始使用 ROS
要在 MATLAB 中创建 ROS 主站,请调用 rosinit(不带任何参数)。该函数还创建了全局节点,MATLAB 使用它与 ROS 网络中的其他节点通信。
rosinit
- Launching ROS Core...
- Done in 0.36647 seconds.
- Initializing ROS master on http://172.29.196.158:56952.
- Initializing global node /matlab_global_node_23704 with NodeURI http://dcc427349glnxa64:33843/ and MasterURI http://localhost:56952.
MATLAB 外部的 ROS 节点现在可以加入 ROS 网络。它们可以使用 MATLAB 主机的主机名或 IP 地址连接到 MATLAB 中的 ROS 主节点。
您可以通过调用 rosshutdown 关闭 ROS 主节点和全局节点。
rosshutdown
- Shutting down global node /matlab_global_node_23704 with NodeURI http://dcc427349glnxa64:33843/ and MasterURI http://localhost:56952.
- Shutting down ROS master on http://172.29.196.158:56952.
你也可以使用 rosinit 命令连接外部 ROS 主站(例如运行在机器人或虚拟机上的 ROS 主站)。你可以通过两种方式指定主站的地址:IP 地址或主控程序运行计算机的主机名。
每次调用 rosinit 后,必须先调用 rosshutdown,然后再以不同语法调用 rosinit。为简洁起见,这些示例中省略了对 rosshutdown 的调用。
master_host "是主机名示例,"192.168.1.1 "是外部 ROS 主站的 IP 地址示例。请根据外部主站在网络中的位置调整这些地址。如果在指定地址找不到主控程序,这些命令将失效。
rosinit('192.168.1.1')
rosinit('master_host')
对 rosinit 的两次调用都假定主站接受 11311 端口的网络连接,这是标准的 ROS 主控端口。如果主控程序运行在其他端口上,可以将其指定为第二个参数。要连接到主机名为 master_host、端口为 12000 的 ROS 主站,请使用以下命令:
rosinit('master_host',12000)
如果知道主站的整个统一资源标识符(URI),则可以使用以下语法创建全局节点并连接到主控程序:
rosinit('http://192.168.1.1:12000')
在某些情况下,您的计算机可能连接到多个网络并拥有多个 IP 地址。本图就是一个例子。
左下角的计算机运行 MATLAB,并连接到两个不同的网络。在一个子网中,它的 IP 地址是 73.195.120.50,而在另一个子网中,它的 IP 地址是 192.168.1.100。这台电脑希望连接到 TurtleBot® 电脑上 IP 地址为 192.168.1.1 的 ROS 主站。作为向主节点注册的一部分,MATLAB 全局节点必须指定其他 ROS 节点可以连接到它的 IP 地址或主机名。TurtleBot 上的所有节点都将使用该地址向 MATLAB 全局节点发送数据。
当使用主节点的 IP 地址调用 rosinit 时,它会尝试检测用于联系主节点的网络接口,并将其作为全局节点的 IP 地址。如果自动检测失败,可以在 rosinit 调用中使用 NodeHost 名-值对明确指定 IP 地址或主机名。NodeHost 名-值对可与已显示的任何其他语法一起使用。
这些命令向 ROS 网络公布的计算机 IP 地址为 192.168.1.100。
rosinit('192.168.1.1','NodeHost','192.168.1.100')
rosinit('http://192.168.1.1:11311','NodeHost','192.168.1.100')
rosinit('master_host','NodeHost','192.168.1.100')
一旦某个节点在 ROS 网络中注册,就可以使用命令 rosnode info <nodename> 查看它发布的地址。调用 rosnode list 可以查看所有已注册节点的名称。
在高级使用情况下,您可能希望通过标准 ROS 环境变量来指定 ROS 主节点的地址和您发布的节点地址。前面几节所解释的语法应该足以满足大多数使用情况。
如果没有为 rosinit 提供参数,函数还会检查标准 ROS 环境变量的值。这些变量是 ROS_MASTER_URI、ROS_HOSTNAME 和 ROS_IP。你可以使用 getenv 命令查看它们的当前值:
- getenv('ROS_MASTER_URI')
- getenv('ROS_HOSTNAME')
- getenv('ROS_IP')
你可以使用 setenv 命令设置这些变量。设置完环境变量后,调用不带参数的 rosinit。ROS 主节点的地址由 ROS_MASTER_URI 指定,全局节点的广告地址由 ROS_IP 或 ROS_HOSTNAME 指定。如果为 rosinit 指定了其他参数,它们将覆盖环境变量中的值。
- setenv('ROS_MASTER_URI','http://192.168.1.1:11311')
- setenv('ROS_IP','192.168.1.100')
- rosinit
不必同时设置 ROS_HOSTNAME 和 ROS_IP。如果同时设置,则 ROS_HOSTNAME 优先。
要使 ROS 连接正常工作,必须确保所有节点都能与主节点和节点间进行通信。各个节点必须与主节点通信,以注册订阅者、发布者和服务。它们还必须能够相互通信,以发送和接收数据。如果 ROS 网络设置不当,就有可能出现能发送数据却无法接收数据的情况(反之亦然)。
该图显示了一个 ROS 网络,其中有一个 ROS 主节点和两个向主节点注册的不同节点。每个节点都会联系主节点,查找 ROS 网络中另一个节点的广告地址。一旦每个节点都知道了对方的地址,就可以在没有主节点参与的情况下建立数据交换。
本例展示了如何在 ROS 网络中发布和订阅主题。
ROS 节点交换数据的主要机制是发送和接收消息。消息在主题上传输,每个主题在 ROS 网络中都有一个唯一的名称。如果一个节点想共享信息,它就会使用发布器向话题发送数据。想要接收消息的节点则使用同一主题的订阅者。除了唯一的名称外,每个话题还有一个消息类型,它决定了在该话题下可以传输的消息类型。
这种发布者和订阅者之间的通信具有以下特点:
话题、发布者和订阅者的概念如图所示:
除了如何在 ROS 网络中发布和订阅主题外,本示例还展示了如何
先决条件 开始使用 ROS,连接到 ROS 网络
使用 rosinit 命令在 MATLAB® 中启动 ROS 主程序。
rosinit
- Launching ROS Core...
- .....Done in 5.4209 seconds.
- Initializing ROS master on http://172.21.16.85:56764.
- Initializing global node /matlab_global_node_69902 with NodeURI http://ah-avijayar:62300/ and MasterURI http://localhost:56764.
使用提供的辅助函数 exampleHelperROSCreateSampleNetwork,创建一个包含多个发布者和订阅者的 ROS 示例网络。
exampleHelperROSCreateSampleNetwork
使用 rostopic 列表查看有哪些话题。
rostopic list
- /pose
- /rosout
- /scan
- /tf
使用 rostopic info 查看是否有节点正在向 /scan 话题发布信息。下面的命令显示 node_3 正在发布该主题。
rostopic info /scan
- Type: sensor_msgs/LaserScan
-
- Publishers:
- * /node_3 (http://ah-avijayar:62315/)
-
- Subscribers:
- * /node_1 (http://ah-avijayar:62305/)
- * /node_2 (http://ah-avijayar:62310/)
使用 rossubscriber 订阅 /scan 话题。如果 ROS 网络中已经存在该话题(如此处),rossubscriber 会自动检测其消息类型,因此无需指定。使用 struct 格式的消息可以提高效率。
- laser = rossubscriber("/scan","DataFormat","struct");
- pause(2)
使用 receive 等待新消息(第二个参数是以秒为单位的超时时间)。(第二个参数是以秒为单位的超时时间。)输出 scandata 包含接收到的消息数据。
scandata = receive(laser,10)
- scandata = struct with fields:
- MessageType: 'sensor_msgs/LaserScan'
- Header: [1×1 struct]
- AngleMin: -0.5467
- AngleMax: 0.5467
- AngleIncrement: 0.0017
- TimeIncrement: 0
- ScanTime: 0.0330
- RangeMin: 0.4500
- RangeMax: 10
- Ranges: [640×1 single]
- Intensities: []
某些消息类型会关联可视化器。对于 LaserScan 消息,rosPlot 会绘制扫描数据。MaximumRange 名 - 值对指定了最大绘图范围。
- figure
- rosPlot(scandata,"MaximumRange",7)
您可以指定在收到新消息时调用的函数,而不是使用 receive 来获取数据。这样就可以在订阅者等待新消息时执行其他 MATLAB 代码。如果要使用多个订阅者,回调是必不可少的。
使用回调函数 exampleHelperROSPoseCallback 订阅 /pose 话题。
robotpose = rossubscriber("/pose",@exampleHelperROSPoseCallback,"DataFormat","struct")
- robotpose =
- Subscriber with properties:
-
- TopicName: '/pose'
- LatestMessage: []
- MessageType: 'geometry_msgs/Twist'
- BufferSize: 1
- NewMessageFcn: @exampleHelperROSPoseCallback
- DataFormat: 'struct'
在主工作区和回调函数之间共享数据的一种方法是使用全局变量。定义两个全局变量 pos 和 orient。
- global pos
- global orient
当 /pose 话题收到新消息数据时,全局变量 pos 和 orient 将在 exampleHelperROSPoseCallback 函数中分配。
等待几秒钟以确保订阅者可以接收消息。最新的位置和方向数据将始终存储在 pos 和 orient 变量中。
- pause(2)
- pos
- pos = 1×3
-
- -0.0292 -0.0199 -0.0029
orient
- orient = 1×3
-
- -0.0270 0.0344 -0.0305
如果在命令行中多次输入 pos 和 orient,就能看到数值在不断更新。
通过清除订阅者变量来停止姿势订阅者
clear robotpose
注:除使用全局外,还有其他方法从回调函数中提取信息。例如,可以将句柄对象作为附加参数传递给回调函数。有关定义回调函数的更多信息,请参阅为图形对象创建回调函数文档。
创建一个向 /chatter 话题发送 ROS 字符串消息的发布器(请参阅 "使用基本 ROS 消息")。
chatterpub = rospublisher("/chatter","std_msgs/String","DataFormat","struct")
- chatterpub =
- Publisher with properties:
-
- TopicName: '/chatter'
- NumSubscribers: 0
- IsLatching: 1
- MessageType: 'std_msgs/String'
- DataFormat: 'struct'
pause(2) % Wait to ensure publisher is registered
创建并填充 ROS 消息,发送到 /chatter 话题。
- chattermsg = rosmessage(chatterpub);
- chattermsg.Data = 'hello world'
- chattermsg = struct with fields:
- MessageType: 'std_msgs/String'
- Data: 'hello world'
使用 rostopic list 验证 /chatter 话题在 ROS 网络中是否可用。
rostopic list
- /chatter
- /pose
- /rosout
- /scan
- /tf
为 /chatter 话题定义一个订阅者。exampleHelperROSChatterCallback 在收到新消息时被调用,并显示消息中的字符串内容。
chattersub = rossubscriber("/chatter",@exampleHelperROSChatterCallback,"DataFormat","struct")
- chattersub =
- Subscriber with properties:
-
- TopicName: '/chatter'
- LatestMessage: []
- MessageType: 'std_msgs/String'
- BufferSize: 1
- NewMessageFcn: @exampleHelperROSChatterCallback
- DataFormat: 'struct'
向 /chatter 话题发布消息。订阅者回调将显示该字符串。
- send(chatterpub,chattermsg)
- pause(2)
- ans =
- 'hello world'
一旦您发布了字符串消息,exampleHelperROSChatterCallback 函数就会被调用。
从 ROS 网络中删除样本节点、发布者和订阅者。清除全局变量 pos 和 orient。
- exampleHelperROSShutDownSampleNetwork
- clear global pos orient
关闭 ROS 主节点并删除全局节点。
rosshutdown
- Shutting down global node /matlab_global_node_69902 with NodeURI http://ah-avijayar:62300/ and MasterURI http://localhost:56764.
- Shutting down ROS master on http://172.21.16.85:56764.
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。