机器人仿真——URDF建模

机器人仿真——URDF建模

URDF定义

URDF全称为Unified Robot Description Format,中文可以翻译为“统一机器人描述格式”。与计算机文件中的.txt文本格式、.jpg图像格式等类似,URDF是一种基于XML规范、用于描述机器人结构的格式。根据该格式的设计者所言,设计这一格式的目的在于提供一种尽可能通用的机器人描述规范。
从机构学角度讲,机器人通常被建模为由连杆和关节组成的结构。连杆是带有质量属性的刚体,而关节是连接、限制两个刚体相对运动的结构。关节也被成为运动副。通过关节将连杆依次连接起来,就构成了一个个运动链(也就是这里所定义的机器人模型)。一个URDF文档即描述了这样的一系列关节与连杆的相对关系、惯性属性、几何特点和碰撞模型。具体来说,包括
机器人模型的运动学与动力学描述
机器人的几何表示
机器人的碰撞模型

一、浅识URDF

1、什么是URDF

1、 Unified Robot Description Format,统一机器人描述格式;
2、ROS中一个非常重要的机器人描述格式;
3、可以解析URDF文件中使用XML格式描述的机器人模型;
4、ROS同时也提供URDF文件的C++解析器

2、URDF标签说明

<link>

  • 用于描述机器人某个刚体部分的外观和物理属性;
  • (比如尺寸(size)、颜色(color)、形状(shape)、惯性矩阵(inertial matrix)、碰撞属性(collision properties)等)
    XML格式
<link name="<link name>">
<!-- 描述机器人link部分的外观参数 -->
	<inertial>......</inertial>
	<!-- 描述link的惯性参数 -->
	<visual>......</visual>
	<!-- 描述link的碰撞属性 -->
	<collision>......</collision>
</link>

<joint>

关节类型 描述
continuous 旋转关节,可以围绕单轴无限旋转
revolute 旋转关节,类似于continuous,但是有旋转的角度限制
prismatic 滑动关节,沿某一轴线移动的关节,带有位置极限
planar 平面关节,允许在平面正交方向上平移或者旋转
floating 浮动关节,允许进行平移、旋转运动
fixed 固定关节,不允许运动的特殊关节

XML格式

<joint name="<name of the joint>" type="<joint type>">
	<parent link="parent_link"/>
	<child link="child_link"/>
	<!--关节的参考位置,用来校准关节的绝对位置-->
	<calibration ....../>
	<!--描述关节的物理属性,例如阻尼值、物理静摩擦力等;经常在动力仿真中用到-->
	<dynamics damping ....../>
	<!--描述运动的一些极限值,包括关节运动的上下限位置,速度限制,力矩限制等-->
	<limit effort ....../>
	<!--描述该关节与已有关节的关系-->
	<mimic....../>
	<!--描述安全控制器系数-->
	<safety_controller....../>
	......
</joint>

<robot>

  • 完整机器人模型的最顶层标签;
  • < link > 和 < joint >标签必须包含在 < robot > 标签内。

XML格式

<robot name="name of the robot">
	<link>......</link>
	<link>......</link>
	<joint>......</joint>
	<joint>......</joint>
</robot>

3、创建功能包

创建一个机器人模型的功能包

#进入工作空间
cd ./catkin_ws/src/
#创建功能包
catkin_create_pkg mbot_description urdf xacro
cd ./catkin_ws/src/mbot_description
mkdir urdf
mkdir meshes
mkdir launch
mkdir config

机器人仿真——URDF建模

红色方框中的报错是因为我已经创建了该文件夹。

查看文件夹并注释
机器人仿真——URDF建模

文件夹名称 作用
urdf 存放机器人模型的URDF或xacro文件
meshes 放置URDF中引用的模型渲染文件,机器人外观纹理,让外观和实际更相似
launch 保存相关启动文件
config 保存rviz的配置文件、功能包的配置文件

二、建模的实现

编辑launch启动文件

cd ./catkin_ws/src/mbot_description/launch
sudo gedit display_mbot_base_urdf.launch

机器人仿真——URDF建模
display_mbot_base_urdf.launch文件内容

<launch>
   <!-- 加载的参数名字叫robot_description,具体内容是urdf相关模型的路径 -->
	<param name="robot_description" textfile="$(find mbot_description)/urdf/mbot_base.urdf" />
	<!-- 设置GUI参数,显示关节控制插件 -->
	<param name="use_gui" value="true"/>
	<!-- 运行joint_state_publisher节点,发布机器人的关节状态  -->
	<node name="joint_state_publisher" pkg="joint_state_publisher" type="joint_state_publisher" />
	<!-- 运行robot_state_publisher节点,发布tf  -->
	<node name="robot_state_publisher" pkg="robot_state_publisher" type="state_publisher" />
	<!-- 运行rviz可视化界面,保存每次打开之后的相关插件,保存到config文件夹下面 -->
	<node name="rviz" pkg="rviz" type="rviz" args="-d $(find mbot_description)/config/mbot_urdf.rviz" required="true" />
</launch>

复制上面代码粘贴到文件中

使用圆柱体创建一个车体模型

cd ./catkin_ws/src/mbot_description/urdf
sudo gedit mbot_base.urdf

机器人仿真——URDF建模

<?xml version="1.0" ?>
<robot name="mbot">
    <link name="base_link">
        <visual>
            <origin xyz=" 0 0 0" rpy="0 0 0" />
            <!-- link坐标位置,放在最* ,xyz单位是米,rpy单位是弧度-->
            <geometry>
                <cylinder length="0.16" radius="0.20"/>
            </geometry>
            <!-- 机器人的外观效果,使用圆柱体,高0.16,半径0.20 -->
            <material name="yellow">
                <color rgba="1 0.4 0 1"/>
            </material>
             <!--  通过rgba来描述颜色,颜色命名为yellow,a为1是不透明-->
        </visual>
        <!--visual指的是一些物理属性的标签 -->
    </link>



</robot>

查看效果

roslaunch mbot_description display_mbot_base_urdf.launch

出现报错
机器人仿真——URDF建模
按照错误的提示,逐步去解决问题,解决一个编译一次
问题一:
Could not find the GUI, install the ‘joint_state_publisher_gui’ package

sudo apt-get install ros-melodic-joint-state-publisher-gui

机器人仿真——URDF建模
问题二
[joint_state_publisher-1] process has died [pid 12201, exit code 1, cmd /opt/

urdf文件第一行前面到空格全部去掉,一般格式正确后都会有颜色的,写urdf一定要注意格式,并且将其中的注释给去掉,后面再添加相应代码的时候注意去掉注释内容

问题三:
RVIZ启动但不显示模型
①将Fixed Frame改为base_link
②点击下方的Add按钮添加RobotModel
机器人仿真——URDF建模
效果演示

鼠标放置模型上,可以对模型进行放缩。

机器人仿真——URDF建模
创建左侧车轮

sudo gedit display_mbot_base_urdf.launch

将代码贴到上个文件的空白处

    <joint name="left_wheel_joint" type="continuous">
    <!--   joint名字为left_wheel_joint,属性为continuous,即无限旋转-->
        <origin xyz="0 0.19 -0.05" rpy="0 0 0"/>
        <!--  坐标位置,在base_link基础上,Y偏移0.19,z偏移-0.05-->
        <parent link="base_link"/>
        <child link="left_wheel_link"/>
        <!--  主关节:base_link,上面的圆柱形车体-->
        <!--  子关节:left_wheel_link,左轮-->
        <!--  主关节最后是一个,本代码是base_link-->
        <axis xyz="0 1 0"/>
        <!--left_wheel_link绕某一个轴做旋转,指定为Y轴  -->
    </joint>
     <!--joint用来连接两个link-->
    <link name="left_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>
  <!--左轮信息-->

查看效果

roslaunch mbot_description display_mbot_base_urdf.launch

机器人仿真——URDF建模
添加TF坐标,将左面robotmodel选项取消
机器人仿真——URDF建模
创建右侧车轮

    <joint name="right_wheel_joint" type="continuous">
        <origin xyz="0 -0.19 -0.05" rpy="0 0 0"/>
        <!--  坐标位置,在base_link基础上,Y偏移-0.19,z偏移-0.05,与左轮正好相反-->
        <parent link="base_link"/>
        <child link="right_wheel_link"/>
        <axis xyz="0 1 0"/>
    </joint>
    <link name="right_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

查看效果

roslaunch mbot_description display_mbot_base_urdf.launch

机器人仿真——URDF建模
创建前后支撑轮

    <joint name="front_caster_joint" type="continuous">
        <origin xyz="0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="front_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="front_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
                  <!--用圆形*代替  -->
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="back_caster_joint" type="continuous">
        <origin xyz="-0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="back_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="back_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

查看效果

roslaunch mbot_description display_mbot_base_urdf.launch

机器人仿真——URDF建模

三、添加摄像头(camera)

执行下列指令

cd ./catkin_ws/src/mbot_description/urdf
sudo gedit mbot_with_camera.urdf 
cd ./catkin_ws/src/mbot_description/launch
sudo gedit display_mbot_with_camera_urdf.launch  

机器人仿真——URDF建模
添加如下内容

<?xml version="1.0" ?>
<robot name="mbot">

    <link name="base_link">
        <visual>
            <origin xyz=" 0 0 0" rpy="0 0 0" />
            <geometry>
                <cylinder length="0.16" radius="0.20"/>
            </geometry>
            <material name="yellow">
                <color rgba="1 0.4 0 1"/>
            </material>
        </visual>
    </link>

    <joint name="left_wheel_joint" type="continuous">
        <origin xyz="0 0.19 -0.05" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="left_wheel_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="left_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

    <joint name="right_wheel_joint" type="continuous">
        <origin xyz="0 -0.19 -0.05" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="right_wheel_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="right_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

    <joint name="front_caster_joint" type="continuous">
        <origin xyz="0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="front_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="front_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="back_caster_joint" type="continuous">
        <origin xyz="-0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="back_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="back_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>
	<!--摄像头相关内容-->
    <link name="camera_link">
        <visual>
            <origin xyz=" 0 0 0 " rpy="0 0 0" />
            <geometry>
            
                <box size="0.03 0.04 0.04" />
                   <!--外观是个盒子模拟成摄像头,长宽高分别是0.03 0.04 0.04-->
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="camera_joint" type="fixed">
        <origin xyz="0.17 0 0.10" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="camera_link"/>
    </joint>
</robot>

指令

cd ./catkin_ws/src/mbot_description/launch
sudo gedit display_mbot_with_camera_urdf.launch 

机器人仿真——URDF建模
添加如下内容

<launch>
   <!-- 加载的参数名字叫robot_description,具体内容是urdf相关模型的路径 -->
	<param name="robot_description" textfile="$(find mbot_description)/urdf/mbot_with_camera.urdf " />
	<!-- 设置GUI参数,显示关节控制插件 -->
	<param name="use_gui" value="true"/>
	<!-- 运行joint_state_publisher节点,发布机器人的关节状态  -->
	<node name="joint_state_publisher" pkg="joint_state_publisher" type="joint_state_publisher" />
	<!-- 运行robot_state_publisher节点,发布tf  -->
	<node name="robot_state_publisher" pkg="robot_state_publisher" type="state_publisher" />
	<!-- 运行rviz可视化界面,保存每次打开之后的相关插件,保存到config文件夹下面 -->
	<node name="rviz" pkg="rviz" type="rviz" args="-d $(find mbot_description)/config/mbot_urdf.rviz" required="true" />
</launch>

效果演示

roslaunch mbot_description display_mbot_with_camera_urdf.launch  

机器人仿真——URDF建模

四、添加激光雷达(Lidar)

执行指令

cd ./catkin_ws/src/mbot_description/urdf
sudo gedit mbot_with_laser.urdf

机器人仿真——URDF建模
添加如下内容

<?xml version="1.0" ?>
<robot name="mbot">

    <link name="laser_link">
		<visual>
			<origin xyz=" 0 0 0 " rpy="0 0 0" />
			<geometry>
				<cylinder length="0.05" radius="0.05"/>
			</geometry>
			<material name="black"/>
		</visual>
    </link>
    <joint name="laser_joint" type="fixed">
        <origin xyz="0 0 0.105" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="laser_link"/>
    </joint>


    <link name="left_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

    <joint name="right_wheel_joint" type="continuous">
        <origin xyz="0 -0.19 -0.05" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="right_wheel_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="right_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

    <joint name="front_caster_joint" type="continuous">
        <origin xyz="0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="front_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="front_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="back_caster_joint" type="continuous">
        <origin xyz="-0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="back_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="back_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>
	<!--摄像头相关内容-->
    <link name="camera_link">
        <visual>
            <origin xyz=" 0 0 0 " rpy="0 0 0" />
            <geometry>
            
                <box size="0.03 0.04 0.04" />
                   <!--外观是个盒子模拟成摄像头,长宽高分别是0.03 0.04 0.04-->
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="camera_joint" type="fixed">
        <origin xyz="0.17 0 0.10" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="camera_link"/>
    </joint>
</robot>

指令

cd ./catkin_ws/src/mbot_description/launch
sudo gedit display_mbot_with_laser_urdf.launch

机器人仿真——URDF建模
添加如下内容

<launch>
   <param name="robot_description" textfile="$(find mbot_description)/urdf/mbot_with_laser.urdf " />
	<param name="use_gui" value="true"/>
	
	<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 mbot_description)/config/mbot_urdf.rviz" required="true" />
</launch>

效果演示

roslaunch mbot_description display_mbot_with_laser_urdf.launch

机器人仿真——URDF建模

五、添加Kinect

指令

cd ./catkin_ws/src/mbot_description/urdf
sudo gedit mbot_with_kinect.urdf

机器人仿真——URDF建模
添加如下内容

<?xml version="1.0" ?>
<robot name="mbot">

   <link name="kinect_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 1.5708"/>
            <geometry>
                <mesh filename="package://mbot_description/meshes/kinect.dae" />
                
            </geometry>
        </visual>
    </link>
    <joint name="laser_joint" type="fixed">
        <origin xyz="0.15 0 0.11" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="kinect_link"/>
    </joint>

    <link name="left_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

    <joint name="right_wheel_joint" type="continuous">
        <origin xyz="0 -0.19 -0.05" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="right_wheel_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="right_wheel_link">
        <visual>
            <origin xyz="0 0 0" rpy="1.5707 0 0" />
            <geometry>
                <cylinder radius="0.06" length = "0.025"/>
            </geometry>
            <material name="white">
                <color rgba="1 1 1 0.9"/>
            </material>
        </visual>
    </link>

    <joint name="front_caster_joint" type="continuous">
        <origin xyz="0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="front_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="front_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="back_caster_joint" type="continuous">
        <origin xyz="-0.18 0 -0.095" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="back_caster_link"/>
        <axis xyz="0 1 0"/>
    </joint>

    <link name="back_caster_link">
        <visual>
            <origin xyz="0 0 0" rpy="0 0 0"/>
            <geometry>
                <sphere radius="0.015" />
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>
	<!--摄像头相关内容-->
    <link name="camera_link">
        <visual>
            <origin xyz=" 0 0 0 " rpy="0 0 0" />
            <geometry>
            
                <box size="0.03 0.04 0.04" />
                   <!--外观是个盒子模拟成摄像头,长宽高分别是0.03 0.04 0.04-->
            </geometry>
            <material name="black">
                <color rgba="0 0 0 0.95"/>
            </material>
        </visual>
    </link>

    <joint name="camera_joint" type="fixed">
        <origin xyz="0.17 0 0.10" rpy="0 0 0"/>
        <parent link="base_link"/>
        <child link="camera_link"/>
    </joint>
</robot>

指令

cd ./catkin_ws/src/mbot_description/launch
sudo gedit display_mbot_with_kinect_urdf.launch

机器人仿真——URDF建模
添加如下内容

<launch>
        <param name="robot_description" textfile="$(find mbot_description)/urdf/mbot_with_kinect.urdf " />
	<param name="use_gui" value="true"/>
	
	<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 mbot_description)/config/mbot_urdf.rviz" required="true" />
</launch>

在meshes文件中创建纹理描述信息。 新建文件名称: kinect.dae

由于无法获得相关信息文件,无法进行效果演示。

指令

roslaunch mbot_description display_mbot_with_kinect_urdf.launch

六、检查URDF模型整体结构

urdf文件夹下执行 urdf_to_graphiz+要检查的urdf文件

urdf_to_graphiz mbot_with_camera.urdf

打开生成的pdf文件查看
机器人仿真——URDF建模
URDF建模存在的问题:

  • 模型冗长,重复内容过多;
  • 参数修改麻烦,不便于二次开发;
  • 没有参数计算功能

七、总结与参考资料

1、总结

整篇文章主要讲的ROS的建模,其实整体内容还是比较简单的,但是重复的步骤太多了。这也是URDF建模的缺点。事物都有两面性,我们需要客观看待,有缺点我们不能对其进行全面的否定。但是我们可以改进它,将它进行优化。

2、参考资料

ROS学习笔记------ROS机器人系统设计.
Could not find the GUI, install the ‘joint_state_publisher_gui’ package.RVIZ成功启动不显示圆柱模型.
ROS: [xxx.launch] is neither a launch file in package.
ROS学习笔记(2)6轴机器臂 [xxx.launch] is neither a launch file in package.

上一篇:Solidworks生成URDF文件并在Rviz显示时模型分离


下一篇:TinyOS节点间通信相关接口和组件介绍