前置安装:VMware虚拟机,ubuntu版本:20.04,ROS版本:noetic
前置软件:VScode、Terminator等
编程语言:Python
一、创建机器人模型
ROS官方教程中的通过直接编写urdf文件的方式过于繁琐,且其推荐的xacro语言也同样无法解决需要人为计算的弊病。
1、个人推荐较为直观的从三维建模软件(此处为SOLIDWORKS)建模软件直接导出urdf文件。相关的教程可在CSDN找到,此处不再赘述。
需要作如下几点说明:
1)导出的urdf文件可通过宿主机与虚拟机建立共享文件夹传输,简单快捷
https://jingyan.baidu.com/article/f79b7cb38e5391d144023ead.html
2)sw建模时尽量将命名作规范
3)注意各坐标系的相对位置关系,尽可能按一定规律如将Z轴作为旋转轴等,这里以ROS官方教程中的机器人为例:
2、得到机器人模型文件后在ubuntu VScode中打开(按教程修改package.xml等)
其中urdf文件夹下的为导出的urdf文件
meshes文件夹下的为stl格式的三维模型,可以在扩展中扩展stl viewer之类的插件查看三维模型
launch文件夹中包含了两个launch文件,分别是在rviz中显示和在gazebo中显示
1)display.launch
<launch>
<arg
name="model" />
<!-- 加载机器人模型 -->
<param
name="robot_description"
textfile="$(find slam_car_urdf)/urdf/slam_car_urdf.urdf" />
<!-- 启动机器人状态发布节点(缺少会在rviz中报错:no transform from ....) -->
<node
name="joint_state_publisher_gui"
pkg="joint_state_publisher_gui"
type="joint_state_publisher_gui" />
<node
name="robot_state_publisher"
pkg="robot_state_publisher"
type="robot_state_publisher" />
<!-- 启动rviz -->
<node
name="rviz"
pkg="rviz"
type="rviz"
args="-d $(find slam_car_urdf)/urdf.rviz" />
</launch>
2)gazebo.launch
<launch>
<!-- 启动gazebo创建新空间 -->
<include
file="$(find gazebo_ros)/launch/empty_world.launch" />
<!-- 某种坐标转换发布节点 -->
<node
name="tf_footprint_base"
pkg="tf"
type="static_transform_publisher"
args="0 0 0 0 0 0 base_link base_footprint 40" />
<!-- 加载urdf机器人模型信息 -->
<node
name="spawn_model"
pkg="gazebo_ros"
type="spawn_model"
args="-file $(find slam_car_urdf)/urdf/slam_car_urdf.urdf -urdf -model slam_car_urdf"
output="screen" />
<!-- 不知道干嘛用的校准节点 -->
<node
name="fake_joint_calibration"
pkg="rostopic"
type="rostopic"
args="pub /calibrated std_msgs/Bool true" />
</launch>
3)
<?xml version="1.0" encoding="utf-8"?>
<!-- This URDF was automatically created by SolidWorks to URDF Exporter! Originally created by Stephen Brawner (brawner@gmail.com)
Commit Version: 1.6.0-4-g7f85cfe Build Version: 1.6.7995.38578
For more information, please see http://wiki.ros.org/sw_urdf_exporter -->
<robot
name="slam_car_urdf">
<link
name="base_link">
<inertial>
<origin
xyz="-1.79451050096713E-17 0 0.0225"
rpy="0 0 0" />
<mass
value="2.51327412287183" />
<inertia
ixx="0.00762359817271123"
ixy="1.07186196898297E-50"
ixz="-2.72707632382106E-18"
iyy="0.00762359817271123"
iyz="-1.94272883206886E-35"
izz="0.0125663706143592" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/base_link.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/base_link.STL" />
</geometry>
</collision>
</link>
<link
name="right">
<inertial>
<origin
xyz="-3.60878140608269E-19 6.93889390390723E-18 -0.00749999999999999"
rpy="0 0 0" />
<mass
value="0.0577267650097125" />
<inertia
ixx="1.87611986281566E-05"
ixy="-4.27201574096171E-38"
ixz="-1.80534032376123E-23"
iyy="1.87611986281566E-05"
iyz="6.67041240997494E-22"
izz="3.53576435684489E-05" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/right.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/right.STL" />
</geometry>
</collision>
</link>
<joint
name="r"
type="continuous">
<origin
xyz="0 -0.115 0"
rpy="1.5707963267949 0 0" />
<parent
link="base_link" />
<child
link="right" />
<axis
xyz="0 0 1" />
</joint>
<link
name="left">
<inertial>
<origin
xyz="-2.67972330793522E-19 3.46944695195361E-18 0.00750000000000001"
rpy="0 0 0" />
<mass
value="0.0577267650097125" />
<inertia
ixx="1.87611986281566E-05"
ixy="-1.74700545371199E-21"
ixz="8.10839387363186E-24"
iyy="1.87611986281565E-05"
iyz="6.36832889208227E-22"
izz="3.53576435684489E-05" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/left.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/left.STL" />
</geometry>
</collision>
</link>
<joint
name="left_driven"
type="continuous">
<origin
xyz="0 0.115 0"
rpy="1.5708 0 0" />
<parent
link="base_link" />
<child
link="left" />
<axis
xyz="0 0 1" />
</joint>
<link
name="front">
<inertial>
<origin
xyz="0 -2.3404423700906E-19 0"
rpy="0 0 0" />
<mass
value="0.00176714586764426" />
<inertia
ixx="3.97607820219958E-08"
ixy="2.86886809144189E-24"
ixz="-3.22897170824252E-24"
iyy="3.97607820219958E-08"
iyz="-4.24929064425396E-24"
izz="3.97607820219958E-08" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/front.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/front.STL" />
</geometry>
</collision>
</link>
<joint
name="f_driven"
type="continuous">
<origin
xyz="0.07 0 -0.025"
rpy="0 0 0" />
<parent
link="base_link" />
<child
link="front" />
<axis
xyz="1 0 0" />
</joint>
<link
name="back">
<inertial>
<origin
xyz="0 1.1702211850453E-19 8.67361737988404E-19"
rpy="0 0 0" />
<mass
value="0.00176714586764426" />
<inertia
ixx="3.97607820219958E-08"
ixy="2.04657953337569E-24"
ixz="-4.90432414504321E-24"
iyy="3.97607820219958E-08"
iyz="-3.46956680478304E-24"
izz="3.97607820219958E-08" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/back.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/back.STL" />
</geometry>
</collision>
</link>
<joint
name="back_driven"
type="continuous">
<origin
xyz="-0.07 0 -0.025"
rpy="0 0 0" />
<parent
link="base_link" />
<child
link="back" />
<axis
xyz="1 0 0" />
</joint>
<link
name="camera">
<inertial>
<origin
xyz="0 -4.12335585688332E-18 0.0125"
rpy="0 0 0" />
<mass
value="0.00625" />
<inertia
ixx="6.51041666666667E-07"
ixy="-5.95728924546422E-24"
ixz="1.64948095499974E-22"
iyy="3.77604166666667E-07"
iyz="4.99809992886639E-23"
izz="3.77604166666667E-07" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/camera.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/camera.STL" />
</geometry>
</collision>
</link>
<joint
name="camera_fixed"
type="fixed">
<origin
xyz="0.08 0 0.0625"
rpy="0 0 0" />
<parent
link="base_link" />
<child
link="camera" />
<axis
xyz="0 0 0" />
</joint>
<link
name="laser_support">
<inertial>
<origin
xyz="-4.1413007865299E-17 -5.2907515930031E-19 0.075"
rpy="0 0 0" />
<mass
value="0.0471238898038469" />
<inertia
ixx="8.9535390627309E-05"
ixy="4.96308367531817E-23"
ixz="4.80993864318015E-20"
iyy="8.9535390627309E-05"
iyz="2.8535407990337E-37"
izz="2.35619449019235E-06" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/laser_support.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/laser_support.STL" />
</geometry>
</collision>
</link>
<joint
name="laser_sup_fixed"
type="continuous">
<origin
xyz="0 0 0.0625"
rpy="0 0 0" />
<parent
link="base_link" />
<child
link="laser_support" />
<axis
xyz="0 0 1" />
</joint>
<link
name="laser">
<inertial>
<origin
xyz="-1.34362177014971E-17 -2.03864780368065E-18 0.025"
rpy="0 0 0" />
<mass
value="0.141371669411541" />
<inertia
ixx="6.12610567450009E-05"
ixy="2.76303274868706E-36"
ixz="-2.38538838926736E-21"
iyy="6.12610567450009E-05"
iyz="-5.37308287535703E-22"
izz="6.36172512351933E-05" />
</inertial>
<visual>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/laser.STL" />
</geometry>
<material
name="">
<color
rgba="1 1 1 1" />
</material>
</visual>
<collision>
<origin
xyz="0 0 0"
rpy="0 0 0" />
<geometry>
<mesh
filename="package://slam_car_urdf/meshes/laser.STL" />
</geometry>
</collision>
</link>
<joint
name="laser_fixed"
type="continuous">
<origin
xyz="0 0 0.15"
rpy="0 0 0" />
<parent
link="laser_support" />
<child
link="laser" />
<axis
xyz="0 0 1" />
</joint>
</robot>
可以看到插件帮我们导出了模型的必要信息,节点的信息如质量mass、提供碰撞检测的依据collision 、刚体部分的惯性矩阵intertial等,关节信息如装配的相对位置关系origin、导出时配置的坐标系axis、关节类型type等等。
二、在机器人模型的基础上配置雷达并在rviz和gazebo中仿真
1、配置雷达文件
官方文档:
<robot name="my_sensors" xmlns:xacro="http://wiki.ros.org/xacro">
<!-- 此处reference与laser link名相同 -->
<gazebo reference="laser">
<!-- 以下为雷达参数配置-->
<sensor type="ray" name="rplidar">
<pose>0 0 0 0 0 0</pose>
<visualize>true</visualize>
<update_rate>5.5</update_rate>
<ray>
<scan>
<horizontal>
<samples>360</samples>
<resolution>1</resolution>
<min_angle>-3</min_angle>
<max_angle>3</max_angle>
</horizontal>
</scan>
<range>
<min>0.10</min>
<max>30.0</max>
<resolution>0.01</resolution>
</range>
<noise>
<type>gaussian</type>
<mean>0.0</mean>
<stddev>0.01</stddev>
</noise>
</ray>
<plugin name="gazebo_rplidar" filename="libgazebo_ros_laser.so">
<topicName>/scan</topicName>
<frameName>laser</frameName>
</plugin>
</sensor>
</gazebo>
</robot>
2、在gazebo中显示机器人模型并在rviz读取雷达数据
1)新建.xacro文件,将urdf文件内容复制粘贴进,在开头的robot标签中加入xmlns语句,在末尾</robot>标签前添加即可:
<xacro:include filename="camera_config.xacro">
2)编写launch文件
<launch>
<!-- 加载机器人模型参数到参数服务器 -->
<param name="robot_description" command="$(find xacro)/xacro $(find slam_car_urdf)/urdf/slam_car.xacro"/>
<!-- 启动gazebo -->
<include file="$(find gazebo_ros)/launch/empty_world.launch"/>
<!-- 在gazebo中显示机器人模型 -->
<node pkg="gazebo_ros" type="spawn_model" name="model" args="-urdf -model mycar -param robot_description"/>
<!-- 在rviz中导入机器人参数 -->
<node name="joint_state_publisher_gui" pkg="joint_state_publisher_gui" type="joint_state_pulisher_gui"/>
<node name="robot_state_publisher" pkg="robot_state_publisher" type="robot_state_publisher"/>
<node="rviz" pkg="rviz" type="rviz" args="-d $(find slam_car_urdf)/urdf.rviz"/>
</launch>
3)命令行roslaunch运行此launch文件(之前没编译过记得catkin_make)
在gazebo中添加障碍物并配置rviz