参考书籍为:ROS Robotics By Example (Second Edition) —— Carol Fairchild Dr.Thomas L.Harman,微信读书可免费阅读。
首先,在catkin_ws
工作空间下,使用catking_create_pkg
建立package目录ros_robotics
programmer@ubuntu:~/catkin_ws/src$ catkin_create_pkg ros_robotics
Created file ros_robotics/package.xml
Created file ros_robotics/CMakeLists.txt
Successfully created files in /home/programmer/catkin_ws/src/ros_robotics. Please adjust the values in package.xml.
然后,使用catkin_make
进行编译
programmer@ubuntu:~/catkin_ws/src$ cd ~/catkin_ws
programmer@ubuntu:~$ catkin_make
再建立urdf目录,用来存放描述机器人的文件
programmer@ubuntu:~/catkin_ws/src/ros_robotics$ cd ~/catkin_ws/src/ros_robotics
programmer@ubuntu:~/catkin_ws/src/ros_robotics$ mkdir urdf
programmer@ubuntu:~/catkin_ws/src/ros_robotics$ cd urdf
本节的代码文件都可以直接从github下载,不想阅读源码可通过该链接下载 ROS-Robotics-By-Example-2nd-Edition/Chapter2_code/ros_robotics/urdf/,,如果不想下载全部,只下载指定的文件内容,看这篇文章《如何从 GitHub 上下载指定项目的单个文件或文件夹》。
并在urdf目录下,建立一份dd_robot.urdf
文件,但记得拷贝进去时,内容里不要有中文,经实践,中文不在其支持的字符范围内,解析会出错,内容为:
<robot name="dd_robot">
<link name="base_link">
<visual>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
visual>
link>
robot>
然后前往ros_robotics目录下,建立一个子目录launch,并在此目录下建立一份ddrobot_rviz.launch
文件
programmer@ubuntu:~/catkin_ws/src/ros_robotics/urdf$ cd ..
programmer@ubuntu:~/catkin_ws/src/ros_robotics$ mkdir launch
programmer@ubuntu:~/catkin_ws/src/ros_robotics$ vim ddrobot_rviz.launch
<launch>
<arg name="model" />
<arg name="gui" default="False" />
<param name="robot_description"
textfile="$(find ros_robotics)/urdf/$(arg model)"
/>
<param name="use_gui" value="$(arg gui)"/>
<node name="joint_state_publisher"
pkg="joint_state_publisher"
type="joint_state_publisher" />
<node name="robot_state_publisher"
pkg="robot_state_publisher"
type="state_publisher" />
<node name="rviz" pkg="rviz" type="rviz"
args="-d $(find ros_robotics)/urdf.rviz"
required="true" />
launch>
然后在终端执行以下命令,就会弹出一个rviz窗口
$ roslaunch ros_robotics ddrobot_rviz.launch model:=dd_robot.urdf
点击Displays工具栏右下角的Add,添加组件,并编辑Fixed Frame为base_link
然后添加轮子,仿照dd_robot.urdf
,在相同目录下建立第二份文件dd_robot2.urdf
,在dd_robot.urdf
文件的基础上,加了两个轮子,具体内容为:
<robot name="dd_robot">
<link name="base_link">
<visual>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
visual>
link>
<link name="right_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
visual>
link>
<joint name="joint_right_wheel" type="continuous">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
<link name="left_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
visual>
link>
<joint name="joint_left_wheel" type="continuous">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
robot>
保存好后,关闭上一个rviz窗口,执行
$ roslaunch ros_robotics ddrobot_rviz.launch model:=dd_robot2.urdf
就会看到,红色轴是X轴,绿色轴是Y轴,蓝色轴是Z轴。TF - ROS Wiki
再建一份dd_robot3.urdf
文件,在底部添加一个万向轮
<robot name="dd_robot">
<link name="base_link">
<visual>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
visual>
<visual name="caster">
<origin xyz="0.2 0 -0.125" rpy="0 0 0" />
<geometry>
<sphere radius="0.05" />
geometry>
visual>
link>
<link name="right_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
visual>
link>
<joint name="joint_right_wheel" type="continuous">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
<link name="left_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
visual>
link>
<joint name="joint_left_wheel" type="continuous">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
robot>
新建一份dd_robot4.urdf
,修改各模块颜色,可以看到left wheel只简单引用了一个rgba
属性值里的a代表alpha
,表示透明度,1不透明,0透明。
<robot name="dd_robot">
<link name="base_link">
<visual>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
<material name="blue">
<color rgba="0 0.5 1 1"/>
material>
visual>
<visual name="caster">
<origin xyz="0.2 0 -0.125" rpy="0 0 0" />
<geometry>
<sphere radius="0.05" />
geometry>
visual>
link>
<link name="right_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
<material name="black">
<color rgba="0.05 0.05 0.05 1"/>
material>
visual>
link>
<joint name="joint_right_wheel" type="continuous">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
<link name="left_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
<material name="black"/>
visual>
link>
<joint name="joint_left_wheel" type="continuous">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
robot>
给各个link添加
<robot name="dd_robot">
<link name="base_link">
<visual>
<collision>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
collision>
<material name="blue">
<color rgba="0 0.5 1 1"/>
material>
visual>
<visual name="caster">
<collision>
<origin xyz="0.2 0 -0.125" rpy="0 0 0" />
<geometry>
<sphere radius="0.05" />
geometry>
collision>
visual>
link>
<link name="right_wheel">
<visual>
<collision>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
collision>
<material name="black">
<color rgba="0.05 0.05 0.05 1"/>
material>
visual>
link>
<joint name="joint_right_wheel" type="continuous">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
<link name="left_wheel">
<visual>
<collision>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
collision>
<material name="black"/>
visual>
link>
<joint name="joint_left_wheel" type="continuous">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
robot>
提前安装gui相关ros包
sudo apt update
#sudo apt install ros--joint-state-publisher-gui,我的ros_version是kinetic,根据版本决定
sudo apt install ros-kinetic-joint-state-publisher-gui
然后执行
roslaunch ros_robotics ddrobot_rviz.launch model:=dd_robot5.urdf gui:=True
效果如图,random随机赋予旋转角度,center是位置归零按键
给物体添加了inertia惯性属性
<robot name="dd_robot">
<link name="base_link">
<visual>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
<material name="blue">
<color rgba="0 0.5 1 1"/>
material>
visual>
<collision>
<origin xyz="0 0 0" rpy="0 0 0" />
<geometry>
<box size="0.5 0.5 0.25"/>
geometry>
collision>
<inertial>
<mass value="5"/>
<inertia ixx="0.13" ixy="0.0" ixz="0.0" iyy="0.21" iyz="0.0" izz="0.13"/>
inertial>
<visual name="caster">
<origin xyz="0.2 0 -0.125" rpy="0 0 0" />
<geometry>
<sphere radius="0.05" />
geometry>
visual>
<collision>
<origin xyz="0.2 0 -0.125" rpy="0 0 0" />
<geometry>
<sphere radius="0.05" />
geometry>
collision>
<inertial>
<mass value="0.5"/>
<inertia ixx="0.0001" ixy="0.0" ixz="0.0" iyy="0.0001" iyz="0.0" izz="0.0001"/>
inertial>
link>
<link name="right_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
<material name="darkgray">
<color rgba=".2 .2 .2 1"/>
material>
visual>
<collision>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
collision>
<inertial>
<mass value="0.5"/>
<inertia ixx="0.01" ixy="0.0" ixz="0.0" iyy="0.005" iyz="0.0" izz="0.005"/>
inertial>
link>
<joint name="joint_right_wheel" type="continuous">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
<link name="left_wheel">
<visual>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
<material name="darkgray">
<color rgba=".2 .2 .2 1"/>
material>
visual>
<collision>
<origin xyz="0 0 0" rpy="1.570795 0 0" />
<geometry>
<cylinder length="0.1" radius="0.2" />
geometry>
collision>
<inertial>
<mass value="0.5"/>
<inertia ixx="0.01" ixy="0.0" ixz="0.0" iyy="0.005" iyz="0.0" izz="0.005"/>
inertial>
link>
<joint name="joint_left_wheel" type="continuous">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<axis xyz="0 1 0" />
joint>
robot>
在使用下面的命令运行gazebo时,我遇到了一个错误,可能你也会遇到,一个什么都没有的empty_world也还是需要阳光和大地,就像我的世界初始化一样。
$ roslaunch gazebo_ros empty_world.launch
Error [parser.cc:581] Unable to find uri[model://sun]
Error [parser.cc:581] Unable to find uri[model://ground_plane]
解决方案:Unable to find uri[model://sun]、uri[model://ground_plane] 错误解决,只要下载好对应的model包并放到指定位置即可,这里有两个下载源:gazebo_models - gitee和gazebo_models - github,使用DownGit工具,从github上下载指定内容会比全部下载更快些,我这里暂时只需要下载这两个。另外,如果遇到Gazebo闪退,请看控制台打印的信息,是否与该文章说明内容相同:《VMware: vmw_ioctl_command error Invalid argument解决办法》,若不同请找其它解决方案,记得source文件起效。
文件后缀从.urdf
变成了.gazebo
,文件内容不贴了,以免文章过于冗长,请从github上下载,下载地址请往上翻阅,有些属性被替换成了gazebo中特有的。
书本上使用以下命令,判断是否能从urdf格式转换成sdf格式
$ gzsdf –p dd_robot.gazebo
但我的机器上出现了以下错误,查看专栏《ROS采坑记录》下的文章,原因是 gzsdf 在 gazebo3后的版本取消了,啊,妸荷甘与神农同学于老龙吉。
gzsdf: command not found
用以下命令替代,执行后会打印出很长的一段内容,没报错就先不管它。
gz sdf -p dd_robot.gazebo
在launch目录下建立一份ddrobot_gazebo.launch
文件,内容为
<launch>
<include file="$(find
gazebo_ros)/launch/empty_world.launch">
<arg name="world_name"
value="$(find ros_robotics)/worlds/ddrobot.world"/>
<arg name="paused" default="false"/>
<arg name="use_sim_time" default="true"/>
<arg name="gui" default="true"/>
<arg name="headless" default="false"/>
<arg name="debug" default="false"/>
include>
<node name="spawn_urdf" pkg="gazebo_ros"
type="spawn_model" output="screen"
args="-file
$(find ros_robotics)/urdf/dd_robot.gazebo
-urdf -model ddrobot" />
launch>
在launch的同级目录下,建立一个worlds
目录,不清楚具体目录和文件结构,可以看书本发布在github上的源码。并在worlds
目录下,建立一份ddrobot.world
文件,内容为
<sdf version="1.4">
<world name="default">
<include>
<uri>model://ground_planeuri>
include>
<include>
<uri>model://sunuri>
include>
<include>
<uri>model://construction_coneuri>
<name>construction_conename>
<pose>-3.0 0 0 0 0 0pose>
include>
<include>
<uri>model://construction_coneuri>
<name>construction_conename>
<pose>3.0 0 0 0 0 0pose>
include>
world>
sdf>
然后执行以下命令,效果如下。有model少的话,按之前的方法去下载。
$ roslaunch ros_robotics ddrobot_gazebo.launch
除了Gazebo,Matlab Simulink通过 Robotics System Toolbox的加持,也支持对ROS进行仿真,见 Robot Operating System (ROS) Support from ROS Toolbox,Matlab也提供了例子,见 Get Started with ROS - MathWorks
Stage是一个针对移动机器人与传感器的开源2D仿真器,见 The Player Project - Free Software tools for robot and sensor applications
虚拟机器人实验平台,商用,由Coppelia Robotics公司开发,V-REP官网。
在上面的例子中,只用到了一种Continous的连接关节,但这不是所有,还有其它5种,将以代码+动图形式,分别展示效果。
【ROS URDF模型中的6种joint类型】
配图,配上关节的动图
找到之前的dd_robot5.urdf
文件,并复制一份命名为dd_robot5_revolute.urdf
,并做出如下修改
...
<joint name="joint_right_wheel" type="revolute">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<!--New content-->
<limit effort="30" velocity="1.0" lower="-1.00" upper="1.00" />
<axis xyz="0 1 0" />
</joint>
...
<joint name="joint_left_wheel" type="revolute">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<!--New content-->
<limit effort="30" velocity="1.0" lower="-1.00" upper="1.00" />
<axis xyz="0 1 0" />
</joint>
...
然后执行
roslaunch ros_robotics ddrobot_rviz.launch model:=dd_robot5_revolute.urdf gui:=True
也称平移关节,找到之前的dd_robot5.urdf
文件,并复制一份命名为dd_robot5_prismatic.urdf
,并做出如下修改,看上去和revolute关节一样,但它们的lower和upper的单位一个是角度,一个是距离。
...
<joint name="joint_right_wheel" type="revolute">
<parent link="base_link"/>
<child link="right_wheel"/>
<origin xyz="0 -0.30 0" rpy="0 0 0" />
<!--New content-->
<limit effort="30" velocity="1.0" lower="-3" upper="3" />
<axis xyz="0 1 0" />
</joint>
...
<joint name="joint_left_wheel" type="revolute">
<parent link="base_link"/>
<child link="left_wheel"/>
<origin xyz="0 0.30 0" rpy="0 0 0" />
<!--New content-->
<limit effort="30" velocity="1.0" lower="-3" upper="3" />
<axis xyz="0 1 0" />
</joint>
...
然后执行
roslaunch ros_robotics ddrobot_rviz.launch model:=dd_robot5_prismatic.urdf gui:=True
效果如下,看上去有些不伦不类,但只是效果演示,但你要真说它是不伦不类还有点牵强,谁规定汽车轮子不能横移的呢?
//@TODO
//@TODO
名称 | 说明 |
---|---|
固定关节(Fixed) | //@TODO |
有限旋转关节(Revolute) | //@TODO |
无限旋转关节(Continous) | //@TODO |
滑动关节(Prismatic) | //@TODO |
浮动关节(Float) | //@TODO |
平面关节(Planar) | //@TODO |