初识 ROS
ROS 介绍
- ros 的设计目标:提高机器人研发中的软件复用率
- ros 集成了大量的工具,库,协议,提供了类似操作系统的功能,把原本松散的零部件耦合在了一起
解耦:分成模块
- ros 是一个机器人软件平台
- 在这个环境上,机器人的感知,决策,控制算法可以更好的组织和运行
通信机制
ros 提供了松耦合的分布式的通信方法 ros 的通信机制
开发工具
配置 启动 自检 调试 可视化 登录 测试 终止
应用功能
聚焦于移动性,操作性和感知性,ros 提供了实现机器人功能的广泛的库
生态系统
ros 的支持和发展依托着一个强大的社区
- 发行版
- 软件源
- ros wiki
- 邮件列表
- ros answer
- 博客
ROS 的起源与发展
ROS 的特点
点对点设计
ros 通过点对点设计以及服务和节点管理器等机制可以分散由于计算机视觉和语音识别等功能带来的实时计算压力,这种设计能适应服务机器人遇到的挑战
不依赖编程语言
为了支持多语言编程,ros 采用了一种语言中立的接口定义语言 (IDL) 来实现各模块之间的消息传送
精简与集成
- ros 建立的系统具有模块化的特点,各模块中的代码可以单独编译 , 而且编译使用的 cmake 工具使它很容易的就实现精简的理念
- ros 基本将复杂的代码封装在库里 , 只是创建了一些小的应用程序为 ros 显示库的功能,这就允许了对简单的代码超越原型进行移植和重新使用
- ros 不修改用户的主函数 , 所以代码可以被其他的机器人软件使用,其优点是 ros 很容易和其他的机器人软件平台集成,例如,在计算机视觉方面,ros 已经与 opencv 实现集成
便于测试
- 精心设计的 ros 系统框架将底层硬件控制模块和顶层数据处理与决策模块分离,从而可以使用模拟器替代底层硬件模块,独立测试顶层部分,提高测试效率
- ros 另外提供了一种简单的方法可以在调试过程中记录传感器数据及其他类型的消息数据,并在试验后按时间戳回访 (rosbag), 通过这种方式,每次运行机器人可以获得更多的测试机会,例如,可以记录传感器的数据,并通过多次回放测试不同的数据处理算法
组件化工具包丰富
为了管理复杂的 ros 软件框架,ros 利用了大量的小工具 * 去编译和运行多种多样的 ros 组件,从而设计成了内核,而不是构建一个庞大的开发和运行环境,*(组件化的方式), 例如 3d 可视化工具 rviz, rqt 工具箱,gazebo 仿真等等
免费且开源
遵从 BSD 协议
存在的缺点
- 通信实时性能有限
- 系统稳定性尚不满足工业级要求
- 安全性上没有防护措施
- 目前仅支持 linux (Ubuntu)
ros 系统架构及概念_ros 文件系统
ros 的架构
ros 架构的三个层次
- os 层: linux (ubuntu)
- 中间层:
- tcpros/udpros 通信
- 向上提供 client library
- 应用层:
- master 负责整个系统正常运行
- 功能包中模块以节点为单位
- 只需了解接口,提高开发效率
ros 系统的架构设计
ros 系统的架构主要被设计和划分成了三个部分,每一个部分是一个层级:
- 文件系统级:程序是如何运行的
- 计算图级:程序文件是如何组织和构建的
- 开源社区级:程序的分布式管理
ros 的文件系统
理解 ros 文件系统
ros 程序的不同组件要被放在不同的文件夹下
catkin 编译系统
- gcc/g++
- make: 编译工具
- cmake: makefile 生成器
- catkin: ros 对 cmake 的拓展
catkin 编译的工作流程:
- 首先在工作空间
catkin_ws/src/
下递归地查找其中每一个 ros 的 package- package 中会有
package.xml
和CmakeLists.txt
文件,catkin (cmake) 编译系统依据CMakeLists.txt
文件,从而生成 makefiles (放在catkin_ws/build/
)- 然后 make 刚刚生成的 makefiles 等文件,编译链接生成可执行文件 (放在
catkin_ws/devel/
)
catkin 工作空间
catkin_make
, 编译 src 中所有的软件包
创建 package:
- 进入 src 文件夹
catkin_create_pkg package depends
, package 是包名,depends 是依赖的包名,可以依赖多个软件包catkin_create_pkg
帮你完成了软件包的初始化,填充好了 CMakeLists.txt 和 package.xml, 并且将依赖项填进了这两个文件夹中
package 的文件结构:
- CMakeLists.txt #packag 的编译规则 (必须)
- package.xml #package 的描述信息 (必须)
- src/ #源代码文件
- include/ #C++ 头文件
- scripts/ #可执行脚本
- msg/ #自定义消息
- srv/ #自定义服务
- models/ #3D 模型文件
- urdf/ #urdf 文件
- launch/ #launch 文件
软件包相关命令
- rosdep
rosdep 命令 | 作用 |
---|---|
rosdep check [package] | 检查 package 的依赖是否满足 |
rosdep install [package] | 安装 package 的依赖 |
rosdep db | 生成和显示依赖数据库 |
rosdep init | 初始化 /etc/ros/rosdep 中的源 |
rosdep keys | 检查 package 的依赖是否满足 |
rosdep update | 更新本地的 rosdep 数据库 |
- rosls
rosls [package]
列出某 package
- roscd
roscd [package]
进入到某 package 的目录
- roscp
roscp [package] filename dest_path
直接从某个 package 中复制某个文件到指定目录下
- rospack
rospack 命令 | 作用 |
---|---|
rospack help | 显示 rospack 的用法 |
rospack list | 列出本机所有 package |
rospack depends [package] | 显示 package 的依赖包 |
rospack find [package] | 定位某个 package |
rospack profile | 刷新所有 package 的位置记录 |
其他常见文件类型
- launch 文件
- launch 文件一般以.launch 或.xml 结尾,它对 ROS 需要运行程序进行了打包,通过一句命令来启动
- msg/srv/action 文件
- ROS 程序中自定义的消息 / 服务 / 动作文件
- urdf/xacro 文件
- urdf/xacro 文件是机器人模型的描述文件,以 urdf 或.xacro 结尾
- yaml 文件
- yaml 文件一般存储了 ROS 需要加载的参数信息,一些属性的配置,通常我们会把 yaml 文件存放在 param / 路径下
- dae/stl 文件
- dae 或 stl 文件是 3D 模型问津,机器人的 urdf 或仿真环境通常会引用这类文件,它们描述了机器人的三维模型,相比 urdf 简单定义的性状,dae/stl 文件可以定义复杂的模型,可以直接从 solidworks 或其他建模软件导出机器人装配模型,从而显示出更加精确的外形
- rviz 文件
- rviz 文件本质上是固定格式的文本文件,其中存储了 rviz 窗口的配置 (显示哪些控件,视角,参数), 通常 rviz 文件不需要我们去手动修改,而是直接在 rviz 工具里保存,下次运行时直接读取
ROS 系统架构及概念_ROS 计算图
ROS 计算图
ROS 计算图内容
- ROS 会创建一个连接到所有进程的网络,在系统中的任何节点都可以访问此网络,并通过该网络与其他节点交互,获取其他节点发布的信息,并将自身数据发布到网络上
- 在这一层中最基本的概念包括:节点,节点管理器,参数服务器,消息,服务,话题和消息记录包
节点
- 节点是主要的计算执行进程 (可执行文件运行时的进程)
- 如果你想要有一个可以与其他节点进行交互的进程,那么你需要创建一个节点,并将此节点连接到 ROS 网络;通常情况下,系统包含能够实现不同功能的多个节点;你最好让每个节点都具有特定的单一的功能,而不是在系统中创建一个包罗万象的大节点;
节点需要使用如 roscpp 或 rospy 的 ros 客户端库进行编写
节点管理器 (master)
节点管理器用于节点的名称注册和查找等;它也设置节点间的通信;如果在你的整个 ROS 系统中没有节点管理器,就不会有节点,服务,消息之间的通信;需要注意的是,由于 ROS 本身就是一个分布式网络系统,你可以在某一台计算机上运行节点管理器,在该管理器上或其他计算机上运行节点
注意:
- 如果 master 没有运行起来,其他节点不会运行
- 两个 roscore (master) 不能在两个终端中同时运行
rosout 节点:
因为这个节点用于收集和记录节点调试输出信息,所以它总是在运行
rosnode 命令
消息 (message)
- 节点之间可以通过传送消息进行通讯
- 每一个消息都是一个严格的数据结构
- 原来标准的数据类型 (整型,浮点型,布尔型等等) 都是支持的,同时也支持原始数组类型;消息可以包含任意的嵌套结构和数组 (很类似于 C 语言的结构 structs)
msg 文件夹中存放消息
话题 (topic)
- 两个节点需要通信,需要先定义一个共同话题
- 一个节点可以发布多个话题,一个节点可以订阅多个话题
- topic 的名称必须是独一无二的
- topic 保证了消息的发布者与订阅者的相互解耦,彼此不需要知晓对方的存在
话题的缺点:
- 同步性不高
- 单向通信
案例与应用
rosrun turtlesim turtle_teleop_key
, 键盘控制- rqt_graph 能够创建一个显示当前系统运行情况的动态图形;rqt_graph 是 rqt 程序包中的一部分
rosrun rqt_graph rqt_graph
, 查看节点及话题rostopic list
, 查看所有话题rostopic echo /turtle/cmd_vel
, 输出话题信息rosrun rqt_graph rqt_graph
, 再打开 rqt_graphrostopic type
与rosmsg show
一起使用rostopic pub [topic] [msg_type] [args]
, 使用命令发布话题rostopic pub -1 /turtle1/cmd_vel geometry_msgs/Twist -- '[2.0, 0.0, 0.0]' '[0.0, 0.0, 1.8]'
,-1
, 表示运行一次rostopic pub /turtle1/cmd_vel geometry_msgs/Twist -r 1 -- '[2.0, 0.0, 0.0]' '[0.0, 0.0, 1.8]'
, 表示频率为 1, 每一秒一次- 再次运行 rqt_graph 查看
rostopic hz /turtle1/pose
, 查看频率rostopic type /turtle/cmd_vel | rosmsg show
, 查看话题的参数- rqt_plot 命令可以实时显示一个发布到某个话题上的数据变化图形;这里我们将使用 rqt_plot 命令来绘制正在发布到 /turtle1/pose 话题上的数据变化图形
rosrun rqt_plot rqt_plot
服务 (service)
- 服务是节点之间通讯的另一种方式;服务允许节点发送请求,并获得一个响应
- 请求 / 回复交互方式经常被用于分布式系统中;请求服务通过 sevice 来进行,service 被定义为一对消息结构:一个用于请求,一个用于回复
服务 (service) 与话题 (topic) 的对比:
名称 | topic | service |
---|---|---|
通信方式 | 异步通信 | 同步通信 |
实现原理 | TCP/IP | TCP/IP |
通信模型 | Publish-Subscribe | Request-Reply |
映射关系 | 多对多 | 多对一 |
特点 | 接受者收到的数据会回调 (Callback) | 远程过程调用 (RPC) 服务器端的服务 |
应用场景 | 连续,高频的数据发布 | 偶尔使用的功能 / 具体的任务 |
举例 | 激光雷达,里程计发布数据 | 开关传感器,拍照,逆解计算 |
rosservice 用法:
命令 | 说明 |
---|---|
rosservice args | 打印服务的参数 |
rosservice call | 以命令行的形式调用服务,可以指定具体参数 |
rosservice find | 根据服务类型查找当前服务 |
rosservice info | 打印服务信息 |
rosservice list | 列出当前服务类型 |
rosservice type | 打印服务类型 |
rosservice uri | 打印服务的 ROSRPC uri |
rossrv 用法 (该命令针对的是静态的服务文件 *.srv):
命令 | 说明 |
---|---|
rossrv show |
显示服务类型的所有信息 |
rossrv list | 显示所有服务类型信息 |
rossrv md5 |
显示服务类型的 md5sum 信息 (校验) |
rossrv package |
列出一个程序包中的所有服务类型 |
rossrv packages |
列出包含服务的所有程序包 |
案例与应用
rosservice list
, 显示提供的服务rosservice type [service]
rosservice info [service]
rossrv show [service]
rosservice call [service] [args]
rosservice call clear
, 清空线rosservice call /turtle1/set_pen 255 0 0 3 0
, 红线rosservice type spawn | rossrv show
, 查看 spawn 再生服务的信息rosservice call spawn 2 2 0.2 "turtle2"
- (
x y 角度 名字
), 参数rosservice call kill "name: 'turtle2'"
- (或 `rosservice call kill “turtle2”``)
参数服务器
参数服务器维护一个存储着各种参数的字典,字典就是为了方便读写一些不常改变的参数,给它们加上索引,这个索引是唯一的
通过使用参数,就能够在运行时配置节点或改变节点的工作任务
字典:键值对
Key | /rosdistro | /rosversion | /use_sim_time | … |
---|---|---|---|---|
Value | ‘kinetic’ | ‘1.12.7’ | true | … |
rosservice call clear
, 清空参数,设置生效
rospara 命令:
命令 | 功能 |
---|---|
rosparam set | 设置参数 |
rosparam get | 获取参数 |
rosparam load | 从文件读取参数 |
rosparam dump | 向文件中写入参数 |
rosparam delete | 删除参数 |
rosparam list | 列出参数名 |
消息记录包
- 消息记录包是一种用于保存和回放 ROS 消息数据的文件格式
- 消息记录包是一种用于存储数据的重要机制,它能够获取并记录各种收集的传感器数据
通过消息记录包可以反复获取实验数据,进行必要的开发计算法测试
rosbag 命令:
命令 | 作用 |
---|---|
check | 确定一个包是否可以在当前系统中进行,或者是否可以迁移 |
decompress | 压缩一个或多个包文件 |
filter | 解压一个或多个包文件 |
fix | 在包文件中修复消息,以便在当前系统中播放 |
help | 获取相关命令指示帮助信息 |
info | 总结一个或多个包文件的内容 |
play | 以一种时间同步的方式回放一个或多个包文件的内容 |
record | 用指定主题的内容记录一个包文件 |
reindex | 重新索引一个或多个包文件 |
rosbag 受制于其本身的性能无法完全复制录制时的系统运行行为,rosplay 也一样
用户不应该期望能够完美的模仿系统行为