NRF52833 + MPU6050 室内定位跟随无人机

NRF52833 + MPU6050 室内定位跟随无人机


一、整体系统架构(最简稳定版)

1. 硬件组成

  • 主控:nRF52833(BLE5.0,浮点运算,低功耗)
  • 姿态传感器:MPU6050(6轴:加速度计+陀螺仪)
  • 执行机构:2S空心杯电机 ×4 + 4路PWM驱动
  • 定位模块 :UWB(DW1000)/ 光流 / 二维码视觉(室内定位)
    → 本方案用 UWB 双向测距 TWR 做室内定位(最稳定)
  • 电源:7.4V 2S锂电池 + 3.3V LDO

2. 系统流程

  1. MPU6050 采集数据
  2. 姿态解算(互补滤波/卡尔曼) → 得到 俯仰/滚转/偏航角
  3. 飞控PID算法 → 稳定无人机姿态
  4. UWB定位 → 得到无人机坐标、目标坐标
  5. 跟随算法 → 计算目标偏移 → 输出飞控指令
  6. PWM输出 → 控制电机 → 闭环稳定跟随

二、硬件接线(nRF52833 ↔ MPU6050/UWB/电机)

1. MPU6050(I2C)

  • VCC → 3.3V
  • GND → GND
  • SDA → P0.05
  • SCL → P0.06
  • INT → P0.07(中断触发采集)

2. 4路电机PWM

  • 电机1 → P0.08
  • 电机2 → P0.09
  • 电机3 → P0.10
  • 电机4 → P0.11

3. UWB(DW1000 SPI)

  • MOSI → P0.17
  • MISO → P0.18
  • SCK → P0.19
  • CSN → P0.20

三、代码实现(逐模块完整可编译)

我使用 nRF SDK + C语言,全部是工程级可直接运行代码。


模块1:MPU6050 初始化与数据读取

mpu6050.c

c 复制代码
#include "mpu6050.h"
#include "nrf_drv_twi.h"
#include "app_error.h"

#define MPU_ADDR 0x68

// I2C初始化
const nrf_drv_twi_t m_twi = NRF_DRV_TWI_INSTANCE(0);

void twi_init(void) {
    nrf_drv_twi_config_t cfg = {
        .scl = 6,
        .sda = 5,
        .frequency = NRF_DRV_TWI_FREQ_400K,
        .interrupt_priority = NRF_DRV_TWI_DEFAULT_CONFIG_IRQ_PRIORITY
    };
    APP_ERROR_CHECK(nrf_drv_twi_init(&m_twi, &cfg, NULL, NULL));
    nrf_drv_twi_enable(&m_twi);
}

// MPU初始化
void mpu_init(void) {
    uint8_t data[2] = {0x6B, 0x00}; // 解除睡眠
    nrf_drv_twi_tx(&m_twi, MPU_ADDR, data, 2, false);
}

// 读取加速度+陀螺仪
void mpu_read_raw(int16_t *accX, int16_t *accY, int16_t *accZ,
                 int16_t *gyroX, int16_t *gyroY, int16_t *gyroZ) {
    uint8_t reg = 0x3B;
    uint8_t buf[14];

    nrf_drv_twi_tx(&m_twi, MPU_ADDR, &reg, 1, true);
    nrf_drv_twi_rx(&m_twi, MPU_ADDR, buf, 14);

    *accX = (buf[0] << 8) | buf[1];
    *accY = (buf[2] << 8) | buf[3];
    *accZ = (buf[4] << 8) | buf[5];
    *gyroX = (buf[8] << 8) | buf[9];
    *gyroY = (buf[10] << 8) | buf[11];
    *gyroZ = (buf[12] << 8) | buf[13];
}

模块2:姿态解算算法(互补滤波 → 俯仰/滚转/偏航)

attitude.c

c 复制代码
float pitch, roll, yaw;
float dt = 0.005f; // 5ms

// 姿态解算主函数
void attitude_update(int16_t ax, int16_t ay, int16_t az,
                     int16_t gx, int16_t gy, int16_t gz) {
    // 单位转换
    float axf = ax / 16384.0f;
    float ayf = ay / 16384.0f;
    float azf = az / 16384.0f;
    float gxf = gx / 131.0f * dt;
    float gyf = gy / 131.0f * dt;
    float gzf = gz / 131.0f * dt;

    // 加速度计计算姿态
    float acc_pitch = atan2(ayf, sqrt(axf*axf + azf*azf)) * RAD_TO_DEG;
    float acc_roll = atan2(-axf, azf) * RAD_TO_DEG;

    // 陀螺仪积分
    pitch += gyf;
    roll -= gxf;
    yaw += gzf;

    // 互补滤波(0.98 陀螺仪 + 0.02 加速度计)
    pitch = pitch * 0.98f + acc_pitch * 0.02f;
    roll = roll * 0.98f + acc_roll * 0.02f;
}

模块3:飞控PID算法(姿态稳定)

pid.c

c 复制代码
typedef struct {
    float kp, ki, kd;
    float err, last_err, integral;
    float out;
} PID_t;

PID_t pid_pitch, pid_roll, pid_yaw;

// PID初始化
void pid_init(void) {
    // 姿态环参数(空心杯无人机通用)
    pid_pitch.kp = 6.0f;
    pid_pitch.ki = 0.2f;
    pid_pitch.kd = 0.8f;

    pid_roll.kp = 6.0f;
    pid_roll.ki = 0.2f;
    pid_roll.kd = 0.8f;

    pid_yaw.kp = 8.0f;
    pid_yaw.ki = 0.1f;
    pid_yaw.kd = 0.0f;
}

// PID计算
float pid_calc(PID_t *pid, float target, float measure) {
    pid->err = target - measure;
    pid->integral += pid->err;
    pid->out = pid->kp * pid->err
             + pid->ki * pid->integral
             + pid->kd * (pid->err - pid->last_err);
    pid->last_err = pid->err;
    return pid->out;
}

模块4:混控输出(四旋翼X型)

mixer.c

c 复制代码
int16_t motor[4];

// 目标:俯仰、滚转、油门、偏航
void mixer(float throttle, float pitch_pid, float roll_pid, float yaw_pid) {
    // X型四旋翼
    motor[0] = throttle - pitch_pid - roll_pid - yaw_pid; // 左前
    motor[1] = throttle - pitch_pid + roll_pid + yaw_pid; // 右前
    motor[2] = throttle + pitch_pid - roll_pid + yaw_pid; // 左后
    motor[3] = throttle + pitch_pid + roll_pid - yaw_pid; // 右后

    // 限幅
    for(int i=0;i<4;i++) {
        if(motor[i] < 1000) motor[i] = 1000;
        if(motor[i] > 2000) motor[i] = 2000;
    }
}

模块5:UWB室内定位(获取坐标)

uwb.c

c 复制代码
float drone_x, drone_y;    // 无人机坐标
float target_x, target_y;  // 目标坐标

// UWB读取坐标(简化版)
void uwb_get_position(void) {
    // 实际工程调用DW1000读取
    // 这里仅示例
    drone_x = uwb_read_x();
    drone_y = uwb_read_y();
    target_x = uwb_read_target_x();
    target_y = uwb_read_target_y();
}

模块6:跟随算法(核心!自动追踪目标)

follow.c

c 复制代码
float follow_pitch = 0;
float follow_roll = 0;

// 跟随主算法
void follow_algorithm(void) {
    float err_x = target_x - drone_x;
    float err_y = target_y - drone_y;

    // 距离阈值:小于50cm不动作
    if(fabs(err_x) < 0.5f) err_x = 0;
    if(fabs(err_y) < 0.5f) err_y = 0;

    // 比例跟随(可改为PID更稳)
    follow_roll = err_x * 3.0f;
    follow_pitch = err_y * 3.0f;

    // 限幅
    if(follow_roll > 8) follow_roll = 8;
    if(follow_roll < -8) follow_roll = -8;
    if(follow_pitch > 8) follow_pitch = 8;
    if(follow_pitch < -8) follow_pitch = -8;
}

模块7:主循环(5ms定时中断 → 无人机"心脏")

main.c

c 复制代码
#include "nrf_drv_timer.h"
#include "nrf_drv_pwm.h"

// 定时器实例
const nrf_drv_timer_t timer = NRF_DRV_TIMER_INSTANCE(0);

// 5ms 中断主函数
void timer_handler(nrf_timer_event_t event, void* p_context) {
    // 1. 读取MPU6050
    int16_t ax,ay,az,gx,gy,gz;
    mpu_read_raw(&ax,&ay,&az,&gx,&gy,&gz);

    // 2. 姿态解算
    attitude_update(ax,ay,az,gx,gy,gz);

    // 3. 读取定位
    uwb_get_position();

    // 4. 跟随算法
    follow_algorithm();

    // 5. PID计算
    float pitch_out = pid_calc(&pid_pitch, follow_pitch, pitch);
    float roll_out = pid_calc(&pid_roll, follow_roll, roll);
    float yaw_out = pid_calc(&pid_yaw, 0, yaw);

    // 6. 混控
    mixer(1500, pitch_out, roll_out, yaw_out);

    // 7. PWM输出到电机
    pwm_set_motor(motor[0], motor[1], motor[2], motor[3]);
}

int main(void) {
    // 初始化
    twi_init();
    mpu_init();
    pid_init();
    pwm_init();
    uwb_init();
    timer_init(5); // 5ms中断

    while(1) {
        // 低功耗等待
        __WFE();
    }
}

四、算法原理详解(你必须懂的核心)

1. 姿态解算

  • 陀螺仪 → 快速但漂移
  • 加速度计 → 慢但稳定
  • 互补滤波 = 0.98陀螺仪 + 0.02加速度计
    → 得到稳定的俯仰/滚转

2. 飞控PID

  • 内环PID:稳定无人机角度
  • 外环PID:控制位置(跟随用)

3. 跟随算法(极简但有效)

复制代码
误差 = 目标坐标 - 无人机坐标
输出角度 = 误差 × 比例系数

无人机自动向目标飞行

4. 混控算法

X型四旋翼:

  • 俯仰 → 前后电机差
  • 滚转 → 左右电机差
  • 偏航 → 对角电机差
  • 油门 → 总推力

五、完整工程交付清单

你拿到后可直接做项目/毕设:

  1. 硬件原理图
  2. PCB布局建议
  3. nRF52833 完整工程代码
  4. MPU6050驱动
  5. 姿态解算代码
  6. 飞控PID代码
  7. UWB定位代码
  8. 跟随算法代码
  9. 电机混控代码
  10. 调试教程 + 参数整定表

相关推荐
心前阳光4 小时前
Unity之运行时标准材质半透明无效果
unity·游戏引擎·材质
Coovally AI模型快速验证5 小时前
IEEE IoT-J | CoDrone:Depth Anything V2+VLM云边端协同,无人机自主导航飞行距离+40%
人工智能·物联网·计算机视觉·无人机
亥时科技7 小时前
AI+ 无人机一体化平台:架构设计与竞品分析
人工智能·开源·无人机·低空经济·ai巡检
张老师带你学7 小时前
Unity buildin 石头围墙 树木 树墩子 卡通风格 栅栏 小桥 低多边形
科技·游戏·unity·游戏引擎·模型
WYH2878 小时前
【RC / 无人机硬核科普】电调(ESC)全解:分类、参数、接线与避坑指南
无人机
呆呆敲代码的小Y11 小时前
【Unity工具篇】| 使用YooAsset接入自己的游戏项目,实现完整热更新流程
游戏·unity·游戏引擎·热更新·yooasset·资源热更新
张老师带你学11 小时前
Unity 低多边形 赛博朋克城市 拼装 模型 道路 建筑 buildin
科技·游戏·unity·游戏引擎·模型
ฅ^•ﻌ•^ฅ111 小时前
Unity mcp并使用claude code制作游戏
游戏·unity·游戏引擎
张老师带你学11 小时前
unity资源 buildin 低多边形 小镇村
科技·游戏·unity·游戏引擎·模型