4. SDF模型进阶:从URDF到SDF的进化之路

各位同学,今天我们来聊聊SDF模型。说实话,我刚接触Gazebo那会儿,第一反应也是「URDF不是挺好的吗?干嘛还要学SDF?」。后来踩了不少坑才明白——URDF和SDF,各有各的战场。

4.1 URDF vs SDF:到底差在哪?

先给个直观对比。URDF是ROS的亲儿子,专门为机器人描述而生。SDF呢?它是Gazebo的亲儿子,从仿真角度设计的。

特性 URDF SDF
设计目标 机器人运动学描述 完整仿真场景描述
支持多机器人 单个文件只能描述一个机器人 一个文件可包含多个模型
物理属性 仅支持简单碰撞和惯性 支持摩擦、阻尼、刚度等
环境描述 不支持 支持灯光、地形、粒子等
插件系统 有限 丰富的传感器和执行器插件

我个人习惯是:做纯机器人运动学分析时用URDF,一旦涉及复杂仿真场景,立刻切到SDF。你想想看,URDF连个地面摩擦系数都定义不了,怎么模拟真实环境?

4.2 模型物理属性配置

物理属性这块,我踩过的坑最多。记得有一次仿真里机器人老是打滑,查了半天才发现是摩擦系数没设对。

4.2.1 惯性参数

惯性矩阵是物理仿真的基础。SDF里这样写:

<inertial>
  <mass>1.5</mass>
  <inertia>
    <ixx>0.0125</ixx>
    <ixy>0.0</ixy>
    <ixz>0.0</ixz>
    <iyy>0.0125</iyy>
    <iyz>0.0</iyz>
    <izz>0.0125</izz>
  </inertia>
</inertial>
注意:惯性矩阵必须正定!我曾经犯过错误,ixx、iyy、izz设成0,结果仿真直接崩了。每个值都要大于0。

4.2.2 碰撞与摩擦

摩擦系数怎么设?看这个例子:

<surface>
  <friction>
    <ode>
      <mu>0.8</mu>
      <mu2>0.6</mu2>
    </ode>
  </friction>
  <bounce>
    <restitution_coefficient>0.2</restitution_coefficient>
  </bounce>
</surface>

mu是滑动摩擦系数,mu2是扭转摩擦系数。嗯,这里要注意:mu2不设的话默认等于mu。但实际场景中,轮子滚动和滑动的摩擦是不一样的。

4.3 材质与颜色设置

颜色设置看似简单,但很多人搞混。SDF里用<material>标签,支持RGBA和纹理两种方式。

4.3.1 纯色材质

<material>
  <ambient>0.2 0.2 0.2 1.0</ambient>
  <diffuse>0.8 0.2 0.2 1.0</diffuse>
  <specular>0.5 0.5 0.5 1.0</specular>
  <emissive>0.0 0.0 0.0 1.0</emissive>
</material>

四个通道分别控制环境光、漫反射、镜面反射和自发光。我建议新手先调diffuse,其他保持默认就好。

4.3.2 纹理贴图

<material>
  <script>
    <uri>model://my_robot/materials/textures</uri>
    <name>metal_plate</name>
  </script>
</material>
小技巧:纹理路径用model://开头,Gazebo会自动解析。别用路径,否则换台电脑就找不到了。

4.4 模型导入导出

这部分我最有发言权。当年做项目时,客户给的是SolidWorks模型,要转成SDF。折腾了好几天才摸清门道。

4.4.1 从URDF转SDF

ROS自带转换工具:

# 单个URDF转SDF
gz sdf -p robot.urdf > robot.sdf

# 批量转换
rosrun gazebo_ros spawn_model -file robot.urdf -sdf -model robot

但要注意,转换不是万能的。URDF里没有的物理属性,转换后也不会自动生成。我建议转完后手动检查一遍。

4.4.2 从CAD模型导入

CAD模型转SDF,标准流程是:

  1. CAD软件导出STL或Collada格式
  2. 用Blender或MeshLab简化网格
  3. 手动编写SDF文件引用网格
  4. 添加物理属性和碰撞体
<link name="chassis">
  <visual>
    <geometry>
      <mesh>
        <uri>model://my_robot/meshes/chassis.stl</uri>
        <scale>1 1 1</scale>
      </mesh>
    </geometry>
  </visual>
  <collision>
    <geometry>
      <box>
        <size>0.8 0.5 0.3</size>
      </box>
    </geometry>
  </collision>
</link>
避坑指南:我曾经直接用高精度STL做碰撞体,结果仿真卡成PPT。记住:碰撞体尽量用简单几何体,视觉体用精细网格。两者可以不一样!

4.4.3 导出SDF模型

导出相对简单。Gazebo里右键模型,选择「Save As」就能导出SDF。但导出的文件可能包含路径,需要手动修正。

我一般用这个脚本批量处理:

#!/bin/bash
# 批量替换路径为model://
sed -i 's|/home/.*/models/|model://|g' *.sdf

4.5 知识体系总览

说了这么多,咱们用一张图来总结本章的核心内容:

SDF模型进阶 URDF vs SDF 物理属性配置 材质与颜色 模型导入导出 设计目标不同 多模型支持 物理属性差异 惯性参数 碰撞摩擦 阻尼刚度 纯色材质 纹理贴图 RGBA通道 URDF转SDF CAD模型导入 SDF导出 SDF模型进阶知识体系

这张图把本章的核心内容串起来了。你看,URDF对比是基础,物理属性和材质颜色是核心技能,导入导出是实战工具。四者缺一不可。

核心要点回顾:

  • SDF比URDF更适合复杂仿真场景
  • 物理属性要特别注意惯性矩阵的正定性
  • 视觉体和碰撞体可以分开设置,碰撞体尽量用简单几何
  • 模型导入后一定要手动检查物理参数

好了,这一章的内容就到这儿。记住我的一句话:SDF不是URDF的替代品,而是互补品。什么时候用哪个,取决于你的场景需求。下节课我们开始动手搭建第一个完整的SDF模型,到时候你们会发现,其实没那么难。

可可精品资料库