Gazebo 仿真环境系列教程(二):在 Gazebo 中构建自己的机器人
文章目录
- 一、基础知识介绍
- 二、构建机器人
- 2.1 创建世界文件
- 2.2 构建机器人模型
- 2.2.1 定义模型
- 2.2.2 定义底盘
- 2.2.3 添加左轮
- 2.2.4 添加右轮
- 2.2.5 添加万向轮
- 2.2.6 连接各个部件(关节)
- 四、完整代码
- 五、启动运行机器人世界
- 参考文献
本文将详细指导您如何在 Gazebo 仿真环境中使用 SDFormat 构建一个简单的两轮机器人。通过本文我们将逐步构建出自己的机器人模型。
一、基础知识介绍
- SDFormat(Simulation Description Format):是一种用于描述机器人模拟器、可视化和控制中的对象和环境的 XML 格式。它提供了丰富的标签和属性,用于定义机器人的结构、物理属性和行为。
- Gazebo:是一个开源的三维机器人仿真器,广泛应用于机器人算法的开发与测试。
二、构建机器人
2.1 创建世界文件
- 创建一个新的文件
building_robot.sdf
,并复制以下代码:
<?xml version="1.0" ?>
<sdf version="1.10"><world name="car_world"><physics name="1ms" type="ignored"><max_step_size>0.001</max_step_size><real_time_factor>1.0</real_time_factor></physics><pluginfilename="gz-sim-physics-system"name="gz::sim::systems::Physics"></plugin><pluginfilename="gz-sim-user-commands-system"name="gz::sim::systems::UserCommands"></plugin><pluginfilename="gz-sim-scene-broadcaster-system"name="gz::sim::systems::SceneBroadcaster"></plugin><light type="directional" name="sun"><cast_shadows>true</cast_shadows><pose>0 0 10 0 0 0</pose><diffuse>0.8 0.8 0.8 1</diffuse><specular>0.2 0.2 0.2 1</specular><attenuation><range>1000</range><constant>0.9</constant><linear>0.01</linear><quadratic>0.001</quadratic></attenuation><direction>-0.5 0.1 -0.9</direction></light><model name="ground_plane"><static>true</static><link name="link"><collision name="collision"><geometry><plane><normal>0 0 1</normal></plane></geometry></collision><visual name="visual"><geometry><plane><normal>0 0 1</normal><size>100 100</size></plane></geometry><material><ambient>0.8 0.8 0.8 1</ambient><diffuse>0.8 0.8 0.8 1</diffuse><specular>0.8 0.8 0.8 1</specular></material></visual></link></model></world>
</sdf>
该代码创建了一个空的世界,其中包含一个地面平面和一盏太阳光。
2.2 构建机器人模型
2.2.1 定义模型
在 </model>
标签前添加以下代码,定义机器人的名称和初始位置:
<model name='vehicle_blue' canonical_link='chassis'><pose relative_to='world'>0 0 0 0 0 0</pose>
name
是机器人的唯一标识符。canonical_link
是机器人的中心链接,表示机器人的默认参考点。<pose>
标签定义了模型的位置和方向,relative_to
属性指定了参考框架。
2.2.2 定义底盘
在模型标签内添加以下代码,定义机器人的底盘:
<link name='chassis'><pose relative_to='__model__'>0.5 0 0.4 0 0 0</pose><inertial><mass>1.14395</mass><inertia><ixx>0.095329</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.381317</iyy><iyz>0</iyz><izz>0.476646</izz></inertia></inertial><visual name='visual'><geometry><box><size>2.0 1.0 0.5</size></box></geometry><material><ambient>0.0 0.0 1.0 1</ambient><diffuse>0.0 0.0 1.0 1</diffuse><specular>0.0 0.0 1.0 1</specular></material></visual><collision name='collision'><geometry><box><size>2.0 1.0 0.5</size></box></geometry></collision>
</link>
<pose>
定义了底盘相对于模型的偏移位置。<inertial>
定义了底盘的质量和惯性属性。<visual>
定义了底盘的视觉外观,包括形状和颜色。<collision>
定义了底盘的碰撞几何形状。
2.2.3 添加左轮
在底盘标签后添加以下代码,定义机器人的左轮:
<link name='left_wheel'><pose relative_to="chassis">-0.5 0.6 0 -1.5707 0 0</pose><inertial><mass>1</mass><inertia><ixx>0.043333</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.043333</iyy><iyz>0</iyz><izz>0.08</izz></inertia></inertial><visual name='visual'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry><material><ambient>1.0 0.0 0.0 1</ambient><diffuse>1.0 0.0 0.0 1</diffuse><specular>1.0 0.0 0.0 1</specular></material></visual><collision name='collision'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry></collision>
</link>
2.2.4 添加右轮
复制左轮代码,将其修改为右轮:
<link name='right_wheel'><pose relative_to="chassis">-0.5 -0.6 0 -1.5707 0 0</pose><inertial><mass>1</mass><inertia><ixx>0.043333</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.043333</iyy><iyz>0</iyz><izz>0.08</izz></inertia></inertial><visual name='visual'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry><material><ambient>1.0 0.0 0.0 1</ambient><diffuse>1.0 0.0 0.0 1</diffuse><specular>1.0 0.0 0.0 1</specular></material></visual><collision name='collision'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry></collision>
</link>
2.2.5 添加万向轮
添加以下代码,定义机器人的万向轮:
<frame name="caster_frame" attached_to='chassis'><pose>0.8 0 -0.2 0 0 0</pose>
</frame><link name='caster'><pose relative_to='caster_frame'/><inertial><mass>1</mass><inertia><ixx>0.016</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.016</iyy><iyz>0</iyz><izz>0.016</izz></inertia></inertial><visual name='visual'><geometry><sphere><radius>0.2</radius></sphere></geometry><material><ambient>0.0 1 0.0 1</ambient><diffuse>0.0 1 0.0 1</diffuse><specular>0.0 1 0.0 1</specular></material></visual><collision name='collision'><geometry><sphere><radius>0.2</radius></sphere></geometry></collision>
</link>
2.2.6 连接各个部件(关节)
在模型标签内添加以下代码,定义关节连接:
<joint name='left_wheel_joint' type='revolute'><pose relative_to='left_wheel'/><parent>chassis</parent><child>left_wheel</child><axis><xyz expressed_in='__model__'>0 1 0</xyz><limit><lower>-1.79769e+308</lower><upper>1.79769e+308</upper></limit></axis>
</joint><joint name='right_wheel_joint' type='revolute'><pose relative_to='right_wheel'/><parent>chassis</parent><child>right_wheel</child><axis><xyz expressed_in='__model__'>0 1 0</xyz><limit><lower>-1.79769e+308</lower><upper>1.79769e+308</upper></limit></axis>
</joint><joint name='caster_wheel' type='ball'><parent>chassis</parent><child>caster</child>
</joint>
revolute
关节用于连接车轮和底盘,允许旋转运动。ball
关节用于连接万向轮。
四、完整代码
以下是完整的 SDF 文件内容:
<?xml version="1.0" ?>
<sdf version="1.10"><world name="car_world"><physics name="1ms" type="ignored"><max_step_size>0.001</max_step_size><real_time_factor>1.0</real_time_factor></physics><pluginfilename="gz-sim-physics-system"name="gz::sim::systems::Physics"></plugin><pluginfilename="gz-sim-user-commands-system"name="gz::sim::systems::UserCommands"></plugin><pluginfilename="gz-sim-scene-broadcaster-system"name="gz::sim::systems::SceneBroadcaster"></plugin><light type="directional" name="sun"><cast_shadows>true</cast_shadows><pose>0 0 10 0 0 0</pose><diffuse>0.8 0.8 0.8 1</diffuse><specular>0.2 0.2 0.2 1</specular><attenuation><range>1000</range><constant>0.9</constant><linear>0.01</linear><quadratic>0.001</quadratic></attenuation><direction>-0.5 0.1 -0.9</direction></light><model name="ground_plane"><static>true</static><link name="link"><collision name="collision"><geometry><plane><normal>0 0 1</normal></plane></geometry></collision><visual name="visual"><geometry><plane><normal>0 0 1</normal><size>100 100</size></plane></geometry><material><ambient>0.8 0.8 0.8 1</ambient><diffuse>0.8 0.8 0.8 1</diffuse><specular>0.8 0.8 0.8 1</specular></material></visual></link></model><model name='vehicle_blue' canonical_link='chassis'><pose relative_to='world'>0 0 0 0 0 0</pose><link name='chassis'><pose relative_to='__model__'>0.5 0 0.4 0 0 0</pose><inertial><mass>1.14395</mass><inertia><ixx>0.095329</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.381317</iyy><iyz>0</iyz><izz>0.476646</izz></inertia></inertial><visual name='visual'><geometry><box><size>2.0 1.0 0.5</size></box></geometry><material><ambient>0.0 0.0 1.0 1</ambient><diffuse>0.0 0.0 1.0 1</diffuse><specular>0.0 0.0 1.0 1</specular></material></visual><collision name='collision'><geometry><box><size>2.0 1.0 0.5</size></box></geometry></collision></link><link name='left_wheel'><pose relative_to="chassis">-0.5 0.6 0 -1.5707 0 0</pose><inertial><mass>1</mass><inertia><ixx>0.043333</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.043333</iyy><iyz>0</iyz><izz>0.08</izz></inertia></inertial><visual name='visual'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry><material><ambient>1.0 0.0 0.0 1</ambient><diffuse>1.0 0.0 0.0 1</diffuse><specular>1.0 0.0 0.0 1</specular></material></visual><collision name='collision'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry></collision></link><link name='right_wheel'><pose relative_to="chassis">-0.5 -0.6 0 -1.5707 0 0</pose><inertial><mass>1</mass><inertia><ixx>0.043333</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.043333</iyy><iyz>0</iyz><izz>0.08</izz></inertia></inertial><visual name='visual'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry><material><ambient>1.0 0.0 0.0 1</ambient><diffuse>1.0 0.0 0.0 1</diffuse><specular>1.0 0.0 0.0 1</specular></material></visual><collision name='collision'><geometry><cylinder><radius>0.4</radius><length>0.2</length></cylinder></geometry></collision></link><frame name="caster_frame" attached_to='chassis'><pose>0.8 0 -0.2 0 0 0</pose></frame><link name='caster'><pose relative_to='caster_frame'/><inertial><mass>1</mass><inertia><ixx>0.016</ixx><ixy>0</ixy><ixz>0</ixz><iyy>0.016</iyy><iyz>0</iyz><izz>0.016</izz></inertia></inertial><visual name='visual'><geometry><sphere><radius>0.2</radius></sphere></geometry><material><ambient>0.0 1 0.0 1</ambient><diffuse>0.0 1 0.0 1</diffuse><specular>0.0 1 0.0 1</specular></material></visual><collision name='collision'><geometry><sphere><radius>0.2</radius></sphere></geometry></collision></link><joint name='left_wheel_joint' type='revolute'><pose relative_to='left_wheel'/><parent>chassis</parent><child>left_wheel</child><axis><xyz expressed_in='__model__'>0 1 0</xyz><limit><lower>-1.79769e+308</lower><upper>1.79769e+308</upper></limit></axis></joint><joint name='right_wheel_joint' type='revolute'><pose relative_to='right_wheel'/><parent>chassis</parent><child>right_wheel</child><axis><xyz expressed_in='__model__'>0 1 0</xyz><limit><lower>-1.79769e+308</lower><upper>1.79769e+308</upper></limit></axis></joint><joint name='caster_wheel' type='ball'><parent>chassis</parent><child>caster</child></joint></model></world>
</sdf>
五、启动运行机器人世界
- 将上述完整代码保存为
building_robot.sdf
文件。 - 打开终端,导航到文件所在目录。
- 运行以下命令启动 Gazebo 模拟器:
gz sim building_robot.sdf
运行结果如下:
如上图所示,该世界包含一个底盘和两个轮子的机器人模型。可以通过 Gazebo 的界面工具进行进一步的交互和测试。通过以上步骤,我们已成功构建了一个简单的两轮机器人模型。后续可以继续探索如何为机器人添加更多的功能和特性。
参考文献
Gazebo Tutorials