外观
陀螺仪(IMU)使用指南(IMU Guide)
1. 什么是 IMU?
IMU(Inertial Measurement Unit,惯性测量单元)是一种能够测量物体运动状态的传感器。在 FTC 比赛中,IMU 通常指的是内置在控制中心(Control Hub 或 Expansion Hub)内部的陀螺仪传感器。IMU 能够测量机器人的旋转角度、旋转速度以及加速度等数据。
简单来说,IMU 就像人类的"平衡感",让机器人能够知道自己的朝向、倾斜状态和运动情况。
注意:自 2022 年 9 月起,REV Robotics 开始在 Control Hub 中使用新型 IMU 芯片 BHI260AP,替代原来的 BNO055 芯片。本指南适用于两种芯片,但使用新 IMU 需要确保 SDK 版本在 8.1 或以上,且 Control Hub 操作系统在 1.1.3 或以上。
2. 为什么需要使用 IMU?
在 FTC 比赛中,IMU 有以下几个重要应用:
- 精确转向:帮助机器人进行精确角度的转弯(例如旋转恰好 90 度)
- 直线行驶:即使在不平坦的地面上也能保持直线行驶
- 机器人状态监测:检测机器人是否处于预期的角度或判断是否翻倒
- 高级自动导航:实现更复杂的自动化移动路径
- 连接自动阶段和遥控阶段:保存机器人在自动阶段结束时的朝向,在遥控阶段继续使用
3. 机器人坐标系统
在使用 IMU 前,需要理解机器人的坐标系统。FTC 使用的是机器人中心坐标系统,包含三个互相垂直的轴:
- Z 轴:垂直向上指向天花板
- Y 轴:指向机器人的前方(由团队自行定义哪个方向是"前")
- X 轴:指向机器人的右侧

小贴士:在机器人上贴一个"前进方向"的标签,可以避免团队成员对方向的混淆。
4. 三种关键旋转角度
IMU 可以测量机器人围绕三个轴的旋转角度:
偏航角(Yaw):机器人围绕 Z 轴的旋转角度,也称为航向角(Heading)
- 测量机器人左右转动的角度
- 逆时针旋转为正值,顺时针旋转为负值
- 范围:-180 度到+180 度
俯仰角(Pitch):机器人围绕 X 轴的旋转角度
- 测量机器人前后倾斜的角度
- 前端抬起为正值,后端抬起为负值
- 范围:-180 度到+180 度
横滚角(Roll):机器人围绕 Y 轴的旋转角度
- 测量机器人左右倾斜的角度
- 左侧抬起为正值,右侧抬起为负值
- 范围:-180 度到+180 度

右手定则:用右手拇指指向轴的正方向,其余四指弯曲的方向就是该轴的正旋转方向。
5. IMU 的基本使用步骤
5.1 硬件配置
- 在 FTC Robot Controller 应用中,进入"Configure Robot"(配置机器人)
- 添加一个名为"imu"的 IMU 设备
- 保存配置
5.2 初始化 IMU
在操作模式(OpMode)代码中,需要先初始化 IMU:
java
// 从硬件图获取IMU对象
IMU imu = hardwareMap.get(IMU.class, "imu");
// 设置IMU方向(告诉IMU控制中心在机器人上的安装方向)
RevHubOrientationOnRobot.LogoFacingDirection logoDirection = RevHubOrientationOnRobot.LogoFacingDirection.UP;
RevHubOrientationOnRobot.UsbFacingDirection usbDirection = RevHubOrientationOnRobot.UsbFacingDirection.FORWARD;
RevHubOrientationOnRobot orientation = new RevHubOrientationOnRobot(logoDirection, usbDirection);
// 用这个方向初始化IMU
imu.initialize(new IMU.Parameters(orientation));1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
注意:上面的代码假设控制中心水平放置,LOGO 朝上,USB 接口朝前。如果你的安装方式不同,需要调整这两个方向参数。
5.3 读取 IMU 角度数据
初始化后,可以读取 IMU 的角度数据:
java
// 获取机器人的偏航-俯仰-横滚角
YawPitchRollAngles robotOrientation = imu.getRobotYawPitchRollAngles();
// 读取各个角度值(以度为单位)
double yaw = robotOrientation.getYaw(AngleUnit.DEGREES); // 偏航角/航向角
double pitch = robotOrientation.getPitch(AngleUnit.DEGREES); // 俯仰角
double roll = robotOrientation.getRoll(AngleUnit.DEGREES); // 横滚角
// 显示在驾驶站上
telemetry.addData("偏航角", "%.1f度", yaw);
telemetry.addData("俯仰角", "%.1f度", pitch);
telemetry.addData("横滚角", "%.1f度", roll);
telemetry.update();1
2
3
4
5
6
7
8
9
10
11
12
13
2
3
4
5
6
7
8
9
10
11
12
13
5.4 重置航向角
有时候需要将当前朝向设为 0 度作为参考点:
java
imu.resetYaw(); // 将当前偏航角重置为0度1
5.5 获取角速度数据
除了角度,IMU 还可以测量角速度(旋转速度):
java
// 获取角速度数据(以度/秒为单位)
AngularVelocity angularVelocity = imu.getRobotAngularVelocity(AngleUnit.DEGREES);
// 读取各轴的角速度
double yawVelocity = angularVelocity.zRotationRate; // Z轴角速度
double pitchVelocity = angularVelocity.xRotationRate; // X轴角速度
double rollVelocity = angularVelocity.yRotationRate; // Y轴角速度
// 显示在驾驶站上
telemetry.addData("偏航角速度", "%.1f度/秒", yawVelocity);
telemetry.addData("俯仰角速度", "%.1f度/秒", pitchVelocity);
telemetry.addData("横滚角速度", "%.1f度/秒", rollVelocity);
telemetry.update();1
2
3
4
5
6
7
8
9
10
11
12
13
2
3
4
5
6
7
8
9
10
11
12
13
6. IMU 的实际应用示例
6.1 精确转弯
java
// 定义目标角度(向右转90度)
double targetAngle = 90.0;
double currentAngle = 0;
double allowedError = 2.0; // 允许2度的误差
// 重置航向角
imu.resetYaw();
// 开始转动
leftDrive.setPower(0.4); // 左电机正转
rightDrive.setPower(-0.4); // 右电机反转
// 持续检查角度直到转到目标角度
while (opModeIsActive() && Math.abs(currentAngle - targetAngle) > allowedError) {
// 获取当前角度
currentAngle = imu.getRobotYawPitchRollAngles().getYaw(AngleUnit.DEGREES);
// 显示当前角度
telemetry.addData("当前角度", "%.1f度", currentAngle);
telemetry.addData("目标角度", "%.1f度", targetAngle);
telemetry.addData("还差", "%.1f度", targetAngle - currentAngle);
telemetry.update();
}
// 停止转动
leftDrive.setPower(0);
rightDrive.setPower(0);1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
6.2 保持直线行驶
java
// 先重置航向角作为参考
imu.resetYaw();
// 设置基础速度
double basePower = 0.5;
double maxCorrection = 0.2; // 最大校正幅度
// 直线行驶
while (opModeIsActive()) {
// 获取当前航向角
double currentAngle = imu.getRobotYawPitchRollAngles().getYaw(AngleUnit.DEGREES);
// 计算转向校正(偏离0度时进行调整)
// 系数0.03表示每偏离1度,调整0.03的功率
double correction = currentAngle * 0.03;
// 限制校正的最大幅度
correction = Math.max(-maxCorrection, Math.min(correction, maxCorrection));
// 应用到电机上
leftDrive.setPower(basePower - correction);
rightDrive.setPower(basePower + correction);
// 显示数据
telemetry.addData("航向角", "%.1f度", currentAngle);
telemetry.addData("校正值", "%.3f", correction);
telemetry.update();
}1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
6.3 检测机器人是否翻倒
java
// 持续监测机器人姿态
while (opModeIsActive()) {
// 获取俯仰角和横滚角
YawPitchRollAngles orientation = imu.getRobotYawPitchRollAngles();
double pitch = orientation.getPitch(AngleUnit.DEGREES);
double roll = orientation.getRoll(AngleUnit.DEGREES);
// 检查是否翻倒(俯仰角或横滚角超过45度)
boolean isTippedOver = (Math.abs(pitch) > 45 || Math.abs(roll) > 45);
if (isTippedOver) {
// 机器人已翻倒,执行应急操作
telemetry.addData("警告", "机器人已翻倒!");
// 停止所有电机
leftDrive.setPower(0);
rightDrive.setPower(0);
} else {
// 正常操作
telemetry.addData("状态", "正常");
}
telemetry.addData("俯仰角", "%.1f度", pitch);
telemetry.addData("横滚角", "%.1f度", roll);
telemetry.update();
}1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
7. 高级主题
7.1 处理角度跨越 ±180 度边界
当机器人旋转超过 180 度时,角度会从+180 突变到-180(或反之)。这在编程中需要特殊处理:
java
// 计算从当前角度到目标角度的最短路径
double calculateShortestRotation(double currentAngle, double targetAngle) {
double error = targetAngle - currentAngle;
// 处理角度跨越±180度边界的情况
if (error > 180) {
error -= 360;
} else if (error < -180) {
error += 360;
}
return error;
}1
2
3
4
5
6
7
8
9
10
11
12
13
2
3
4
5
6
7
8
9
10
11
12
13
7.2 补偿偏航角漂移
偏航角(航向角)会随时间缓慢漂移,这是 IMU 的固有特性。对于需要长时间运行的程序,可以通过以下方法减轻影响:
- 定期重置:在关键点重置偏航角
- 使用外部参考:结合其他传感器(如编码器、视觉识别)提供额外参考
- 漂移补偿:测量漂移率并在代码中补偿
7.3 非正交安装方向配置
如果控制中心不是水平、垂直或 90 度角安装,可以使用更复杂的方向配置:
java
// 使用三个旋转角度定义Hub方向
double xRotation = 15; // 绕X轴旋转15度
double yRotation = 0; // 绕Y轴旋转0度
double zRotation = 5; // 绕Z轴旋转5度
// 创建方向对象
Orientation hubRotation = xyzOrientation(xRotation, yRotation, zRotation);
RevHubOrientationOnRobot orientationOnRobot = new RevHubOrientationOnRobot(hubRotation);
// 初始化IMU
imu.initialize(new IMU.Parameters(orientationOnRobot));1
2
3
4
5
6
7
8
9
10
11
2
3
4
5
6
7
8
9
10
11
8. 常见问题与解决方案
8.1 如何判断 IMU 方向设置是否正确?
正确设置 IMU 方向后,机器人的动作应该与角度读数一致:
- 向上抬起前部:俯仰角(Pitch)应该增加
- 向上抬起左侧:横滚角(Roll)应该增加
- 逆时针旋转:偏航角(Yaw)应该增加
如果角度变化与预期相反,需要调整 IMU 的方向设置。
8.2 IMU 数据不稳定或不准确
可能原因和解决方法:
- 初始化不完整:确保在使用 IMU 前给它足够的初始化时间
- 方向设置错误:检查
LogoFacingDirection和UsbFacingDirection参数 - 振动干扰:改善 IMU 的安装位置,减少振动
- 电磁干扰:远离电机和其他电子设备
8.3 如何在自动和遥控阶段之间保持航向?
航向角在操作模式之间会保持,除非机器人或应用重启。利用这一特性:
- 在自动阶段结束时,保存最终的航向角
- 在遥控阶段开始时,使用这个角度作为参考
9. 小贴士与最佳实践
- 标记前进方向:在机器人上贴一个"前进方向"的标签
- 稳定初始化:让机器人在初始化 IMU 时保持静止
- 校准检查:使用 ConceptExploringIMUOrientation 样例程序检查 IMU 配置
- 适当的转弯速度:精确转弯时使用较低的电机功率
- 定期重置:长时间运行时定期重置偏航角
- 备份机制:为 IMU 故障准备备用导航方法
- 充分测试:测试不同场景下 IMU 的表现
10. 参考资料
本指南希望能帮助你理解并有效使用 FTC 机器人中的 IMU。随着你的实践经验增加,你将能够开发出更先进的 IMU 应用,提高机器人的性能和可靠性。
