这个urdf文件,URDF(Unified Robot Description Format), 是一种特殊的xml文件格式, 作为机器人的一种描述文件, 在ROS里面大量使用. 在仿真中用的很多,用于创建机器人的仿真模型
1.URDF文件描述
1.1link与joint
在URDF文件中, 第一个出现的就是下图, 很形象的将URDF要定义的主要内容给展现了出来. 一般, 机器人都是由link和joint进行描述. 都会呈现为树状(想象数据结构里面的树), 如图1, 由一个根link(link1)向上, 分别出现了两个分支–link2和link3, 分别由joint连接link. link4就可以类似的理解.
了解机器人的一般描述方式之后, 我们来看一下下图中这个形状的机器人该怎么来描述它.
<robot name="test_robot"> //命名
<link name="link1" />
<link name="link2" />
<link name="link3" />
<link name="link4" />
<joint name="joint1" type="continuous">
<parent link="link1"/> //父节点
<child link="link2"/> //子节点
</joint> //关节
<joint name="joint2" type="continuous">
<parent link="link1"/>
<child link="link3"/>
</joint>
<joint name="joint3" type="continuous">
<parent link="link3"/>
<child link="link4"/>
</joint>
</robot>
而现在,你们肯定想要问,link是怎么放得呢,还有他的形状是什么样的呢?请往下看。
1.2 位置
为了能够确定位置,我们可以使用origin子标签进行定义link所应该在的位置. 但是有一点应该注意到, link和link之间是使用joint进行连接, 那么link的位置, 就由连接他的joint确定. 所以, 该子标签是定义在joint内.
而且link不是个质点,而是个刚体所以光有描述点的x,y,z是不够用的, 还需要使用rpy. rpy角是描述船舶在海中航行时姿态的一种方法. 将船的行驶方向取为z轴, 绕z轴旋转称为滚动(Roll), 绕y轴旋转称为俯仰(Pitch), 绕x轴旋转称为偏转(Yaw). 这种描述方式大量运用于各个领域.(z是指机器人的上方,y是指机器人的左侧,x是指右侧,rpy中第一个参数是绕x轴转的角度,第二个为y,第三个是z,注意这里的角度是弧度值)
下面为代码块
<robot name="test_robot">
<link name="link1" />
<link name="link2" />
<link name="link3" />
<link name="link4" />
<joint name="joint1" type="continuous">
<parent link="link1"/>
<child link="link2"/>
<origin xyz=".5 .3 0.7"
rpy="0 0 0" />
</joint>
<joint name="joint2" type="continuous">
<parent link="link1"/>
<child link="link3"/>
<origin xyz="-.2 .5 -0.3" rpy="0 0 1.57" />
</joint>
<joint name="joint3" type="continuous">
<parent link="link3"/>
<child link="link4"/>
<origin xyz=".5 0 0.2" rpy="0 0 -1.57" />
</joint>
</robot>
下面为我写的代码块的具体实现
1.3形状
在解决了每个link的相对位置之后, 还有一个很关键的问题, 就是每个link长什么样子呢? 圆的? 扁的? 还是奇形怪状的? 下面示例了一些常用的形状, 其中box表示长方体,cylinder是圆柱,sphere球
但可以导入stl格式的文件, 还可以导入dae格式.下述示例中导入了一个小刀.
<?xml version="1.0"?>
<robot name="test_robot">
<link name="link1">
<visual>
<geometry>
<cylinder length="0.6" radius="0.2" />
</geometry>
</visual>
</link>
<link name="link2">
<visual>
<geometry>
<box size="0.6 0.2 .1" />
</geometry>
</visual>
</link>
<link name="link3" >
<visual>
<geometry>
<sphere radius="0.2"/>
</geometry>
</visual>
</link>
<link name="link4" >
<visual>
origin rpy="0 -1.57 0" xyz="0 0 0"/>
<geometry>
<mesh filename="package://urdf_csdn/urdf/mesh/knife.stl"/>
</geometry>
</visual>
</link>
<joint name="joint1" type="fixed">
<parent link="link1"/>
<child link="link2"/>
<origin xyz="0.22 0 0.6" rpy="0 1.57 0" />
</joint>
<joint name="joint2" type="continuous">
<parent link="link1"/>
<child link="link3"/>
<origin xyz="-0.1 0.5 0" />
</joint> <joint name="joint3" type="fixed">
<parent link="link3"/>
<child link="link4"/>
<origin xyz=".5 0 0" rpy="0 0 -1.57" />
</joint>
</robot>
1.4 Collision 和 joint限制
当然, 每个link一般是不会产生重合的, 在运动规划的时候, 也会去避免碰撞到自己, 所以针对于每一个link, 还有一个collision标签, 和visual标签内容完全一样.
前面内容可以看到, 每个link可以看作是一个刚体, 刚体和刚体之间是通过joint进行连接, 那么, 问题就来了. 这个joint是固定的? 还是可以任意的动? 如果可以动, 那么, 问题又来了, 极限位置是多少? 等等等等…
比如, 我们限定joint2只能沿着y轴旋转, 则需要添加<axis xyz="0 1 0"/>, 类似的, 可以指定其他关节的转动轴, 例如<axis xyz="-0.2 0.1 1"/>.
比如, 我们要限定joint2的移动范围, 则需要添加<limit lower="-3.14" upper="3.14" effort="150.0" velocity="3.15"/>, 从标签中可以看到, 上下限以及速度, 力矩等都是可以指定的.
下附一篇注释比较详细的代码
<?xml version="1.0"?>
<robot name="two_rod"> <!-- 为当前设计的机器人结构起名,之后会成为生成这个结构pdf的文件名 -->
<material name="blue"> <!-- “材料”定义一个颜色变量名blue,可为下面的结构设置颜色 -->
<color rgba="0 0 .8 1"/> <!-- 定义这个颜色的rgb值 a值代表透明度-->
</material>
<link name="base_link"> <!-- 定义第一个“结构”的名字。一般规则:以某一个结构作为基准坐标系时,起名为base_link -->
<visual> <!-- 以“视觉”关键字包围起来的部分,为在rviz中的可见部分 -->
<geometry> <!-- 以“几何”关键字包围起来的部分,为这个结构的形状。存在cylinder、box、sphere等形状,还有一种为mesh,为从其他文件载入。eg:mesh filename="package://pr2_description/meshes/gripper_v0/l_finger_tip.dae" -->
<cylinder length="0.2" radius="0.03"/> <!-- 这个“圆筒”形状的默认颜色为红色,这里定义了它的长度和半径 -->
</geometry>
</visual>
</link>
<link name="rod"> <!-- 这里定义了第二个“结构” -->
<visual>
<geometry>
<cylinder length="0.2" radius="0.03"/>
</geometry>
<origin rpy="0 1.57075 0 " xyz="0.1 0 0"/> <!-- “原点”定义在自己坐标系中的姿态和位置 -->
<material name="blue"/> <!-- 这里使用了上面定义的blue颜色 -->
</visual>
<collision> <!-- “碰撞”体积定义在仿真时,对应结构的物理体积,一般使它和geometry中的参数设置一致。其他情况:需要更快计算碰撞检测时可将复杂结构的碰撞体积定义为比较简单的几何形状,或者为了限制行为接近敏感设备时将碰撞体积设置较大来增加安全区域 -->
<geometry>
<cylinder length="0.2" radius="0.03"/> <!-- 同上的圆筒参数一致 -->
</geometry>
<origin rpy="0 1.57075 0 " xyz="0.1 0 0"/> <!-- 原点参数也一致 -->
</collision>
<inertial> <!-- “惯量” -->
<mass value="0.05"/> <!-- “质量”单位Kg -->
<inertia ixx="1.0" ixy="0.0" ixz="0.0" iyy="1.0" iyz="0.0" izz="1.0"/> <!-- 为转动惯量矩阵,需要刚体动力学基础,可用一些三维制图软件计算 -->
</inertial>
</link>
<joint name="connect" type="prismatic"> <!-- “关节”用来定义结构之间的关系,这里设置的为“棱形”,存在fixed、continuous、revolute等连接方式 -->
<axis xyz="1 0 0" /> <!-- 用来设置这个关节的移动方向,默认为x轴,若为0 0 1则为沿z轴移动,也可以复合设置 -->
<parent link="base_link"/> <!-- 指定这个关节所连接的“父”结构 -->
<child link="rod"/> <!-- 指定这个关节所连接的“子”结构 -->
<limit effort="1000.0" lower="-0.38" upper="0" velocity="0.5"/> <!-- “极限”用来约束:“力量”、“最大值”、“最小值”、“速度”的上限,默认为无穷大 -->
<origin rpy="0 0 0" xyz="0.19 0 .2"/> <!-- “原点”定义在父结构坐标系中,子结构坐标系的姿态和位置 -->
</joint>
</robot>