坐标系与刚体运动基础

各位同学,今天我们来聊聊飞控里最基础、也最容易搞混的一块内容——坐标系与刚体运动。

说实话,我刚入行那会儿,觉得坐标系不就是个参考系嘛,有啥好学的?结果第一次调四旋翼,飞机在天上乱转,我盯着日志看了三天,才发现是欧拉角顺序搞反了。嗯,从那以后,我再也不敢小看这部分内容了。

世界坐标系与机体坐标系

先说说世界坐标系。你可以把它想象成一个“绝对参考系”。

我习惯用东北天坐标系(ENU)作为世界坐标系:

  • X轴:指向东
  • Y轴:指向北
  • Z轴:指向天(向上)

为什么用这个?因为GPS给的数据就是基于这个系的,省得来回转换。

机体坐标系就简单了——它跟着飞机走。原点在飞机质心:

  • X轴:指向机头
  • Y轴:指向右翼
  • Z轴:指向机腹(向下)

你想想看,IMU测出来的加速度、角速度,都是相对于机体坐标系的。但你要控制飞机往东飞,就得把机体坐标系下的数据转换到世界坐标系下。怎么转?这就引出了欧拉角。

欧拉角:直观但暗藏陷阱

欧拉角说白了就是三个旋转角度:

  • 偏航角(Yaw,ψ):绕Z轴旋转
  • 俯仰角(Pitch,θ):绕Y轴旋转
  • 横滚角(Roll,φ):绕X轴旋转

这里有个坑——旋转顺序。我见过太多新手在这里翻车了。

⚠️ 注意: 欧拉角的旋转顺序不是任意的!飞控里最常用的是 Z-Y-X 顺序(先偏航,再俯仰,最后横滚)。如果你用了别的顺序,姿态解算结果会完全不一样。

我曾经在项目里遇到过,一个同事用了Z-X-Y顺序,结果飞机在悬停时莫名其妙地往一边漂。查了两天,才发现是旋转顺序的问题。从那以后,我每次写代码都会在注释里明确标注旋转顺序。

欧拉角还有一个致命问题——万向锁。当俯仰角接近±90°时,偏航和横滚会耦合在一起,丢失一个自由度。所以,实际飞控里很少直接用欧拉角做姿态控制。

四元数:飞控的“真香”选择

四元数是什么?说白了就是一个四维复数:

q = w + xi + yj + zk

其中 w 是实部,x、y、z 是虚部。它满足:

i² = j² = k² = ijk = -1

为什么飞控都用四元数?三个原因:

  1. 无万向锁——随便你怎么转,不会丢自由度
  2. 计算量小——只有4个参数,比旋转矩阵的9个参数省多了
  3. 插值平滑——做姿态平滑时,四元数的球面线性插值(SLERP)非常自然

我个人的习惯是:IMU数据进来后,直接用四元数做姿态解算。只有在给地面站显示姿态时,才转成欧拉角给人看。

💡 小技巧: 四元数归一化很重要!每次更新完四元数,记得做一次归一化,否则数值误差会累积,导致姿态漂移。

旋转矩阵:从理论到代码

旋转矩阵是一个3×3的正交矩阵,行列式为1。它可以把一个向量从一个坐标系旋转到另一个坐标系。

从四元数到旋转矩阵的转换公式:

R = [
  [1-2(y²+z²), 2(xy-wz), 2(xz+wy)],
  [2(xy+wz), 1-2(x²+z²), 2(yz-wx)],
  [2(xz-wy), 2(yz+wx), 1-2(x²+y²)]
]

看着复杂?其实在代码里就是几行矩阵运算的事。我建议你把这个公式存成工具函数,别每次都手算——我当年手算错过一次符号,飞机直接翻了180°。

齐次变换矩阵:把旋转和平移打包

齐次变换矩阵是个4×4的矩阵,它把旋转和平移合在一起:

T = [R  t]
    [0  1]

其中 R 是3×3旋转矩阵,t 是3×1平移向量。

为什么要用齐次?因为你可以把多个变换连乘在一起:

T_world_to_camera = T_world_to_body × T_body_to_gimbal × T_gimbal_to_camera

这样,一个矩阵就包含了从世界坐标系到相机坐标系的所有变换。我在做视觉SLAM时,天天跟这个打交道。

知识体系总览

下面这张图,是我自己总结的坐标系与刚体运动的知识结构:

坐标系与刚体运动知识体系 世界坐标系 东北天(ENU) 绝对参考系 机体坐标系 前右下(FRD) 随体参考系 坐标变换 欧拉角 偏航、俯仰、横滚 直观但万向锁 Z-Y-X顺序 四元数 w + xi + yj + zk 无万向锁 需归一化 旋转矩阵 3×3正交矩阵 9个参数 计算量大 齐次变换矩阵 4×4矩阵:旋转 + 平移 可连乘多个变换 应用:姿态解算、视觉SLAM、路径规划

实际项目中的选择建议

说了这么多,到底该用哪个?我根据经验给你个参考:

场景 推荐表示 原因
IMU姿态解算 四元数 无万向锁,计算快
地面站显示 欧拉角 人眼直观,容易理解
视觉SLAM 齐次变换矩阵 方便连乘,统一旋转和平移
路径规划 四元数 + 旋转矩阵 插值平滑,转换灵活

核心要点:

  • 世界坐标系用ENU,机体坐标系用FRD
  • 欧拉角只用于显示,别用于控制
  • 四元数是飞控的“标配”,记得归一化
  • 齐次变换矩阵是“瑞士军刀”,一个矩阵搞定所有变换

好了,这一章的内容就到这儿。坐标系这东西,你刚开始觉得简单,但真正用起来处处是坑。我建议你动手写几行代码,把四元数转旋转矩阵、旋转矩阵转欧拉角这些函数自己实现一遍。相信我,踩过坑之后,你才会真正理解它们。

专注资料整理