简介:esp-12f_mpu6050_demo.rar 是一份面向物联网与嵌入式开发者的实战示例工程,聚焦 ESP-12F(ESP8266 Wi-Fi 模块)通过 I²C 总线驱动 MPU6050 六轴惯性测量单元的完整实现。资源解决的是从传感器初始化、寄存器读写到加速度与角速度数据解析的入门与调试问题,适合已具备基础 C 语言与单片机知识、希望快速上手运动追踪或姿态检测的开发者。压缩包共 605 个文件,约 11.02MB,以 233 个 h 头文件、163 个 c 源文件为主体,辅以 makefile 构建脚本、bin 固件、a 静态库、ld 链接脚本及少量 md 说明文档,覆盖驱动、编译与烧录全流程。内容预览可见 libc.a、libmbedtls.a、liblwip.a 等底层库,说明工程依赖链完整。已有 483 人学习下载,读者可从中获得 I²C 引脚连接(SCL 接 GPIO14、地址线拉高至 3.3V 对应 0x68)的参考配置、传感器数据读取与滤波处理思路,以及可直接编译运行的工程骨架,便于二次开发与项目移植。1. 从一块吃灰的 ESP-12F 说起:这个 Demo 到底能跑出什么手里攒了几块 ESP-12F 模块,一直没想好拿来做什么,直到翻出一颗 MPU6050 六轴传感器。这个esp-12f_mpu6050_demo.rar就是干这件事的:让 ESP-12F 通过 IIC 总线读取 MPU6050 的加速度和角速度数据,串口打印出来。听起来简单,但真上手你会发现,ESP-12F 的 GPIO 和 Arduino 的引脚编号对不上,MPU6050 的 IIC 地址和寄存器配置也有坑。这个 Demo 把初始化、读写、数据转换的完整链路都跑通了,适合刚接触 ESP8266 和 IIC 传感器的开发者,也适合想拿它当数据采集节点做二次开发的人。下面从工程结构开始拆。2. 工程结构与 IIC 通信链路:从引脚定义到数据读取2.1 目录里有什么拿到压缩包解压后,常见的目录结构是这样的(不同 IDE 可能略有差异,但核心文件一致):esp-12f_mpu6050_demo/ ├── esp-12f_mpu6050_demo.ino # 主程序入口 ├── MPU6050.cpp # 传感器驱动实现 ├── MPU6050.h # 驱动头文件,寄存器地址和类定义 ├── Wire.h / Wire.cpp # IIC 底层封装(部分工程自带) └── README.md # 接线说明和编译注意事项主程序负责初始化串口、IIC 和传感器,然后循环读取数据。驱动文件把 MPU6050 的寄存器操作封装成函数,比如readAccel()、readGyro()。这种分层方式的好处是,换一个 IIC 传感器只需要改驱动层,主程序逻辑不动。2.2 ESP-12F 的 IIC 引脚怎么接ESP-12F 的 GPIO 编号和 Arduino 的 D1、D2 不是一回事。常见做法是:ESP-12F 引脚功能接 MPU6050GPIO4SDASDAGPIO5SCLSCL3.3V电源VCCGND地GND注意 MPU6050 模块有的带稳压,有的不带。如果模块上标了 5V 输入,那 VCC 接 5V 也能用;如果只标 3.3V,就老老实实接 3.3V,否则 IIC 电平不匹配,读出来全是 0 或者直接卡死。2.3 初始化代码逐段拆先看主程序里的初始化部分:#include <Wire.h> #include "MPU6050.h" MPU6050 mpu; void setup() { Serial.begin(115200); // 串口波特率,和后面打印一致 Wire.begin(4, 5); // SDA=GPIO4, SCL=GPIO5 mpu.initialize(); // 写配置寄存器,唤醒传感器 if (!mpu.testConnection()) { // 读 WHO_AM_I 寄存器验证 Serial.println("MPU6050 连接失败"); while (1) delay(10); // 卡住,避免后面读脏数据 } Serial.println("MPU6050 就绪"); }Wire.begin(4, 5)里的两个参数就是 SDA 和 SCL 的 GPIO 编号,不是物理引脚序号。initialize()内部会往PWR_MGMT_1寄存器写 0,把传感器从睡眠模式唤醒。testConnection()读的是WHO_AM_I寄存器,默认返回 0x68,如果读回来不是这个值,说明接线或地址有问题。2.4 读加速度和角速度循环里读数据的代码:void loop() { int16_t ax, ay, az, gx, gy, gz; mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz); // 加速度换算成 g,灵敏度默认 ±2g 对应 16384 LSB/g float accelX = ax / 16384.0; float accelY = ay / 16384.0; float accelZ = az / 16384.0; // 角速度换算成 °/s,默认 ±250°/s 对应 131 LSB/(°/s) float gyroX = gx / 131.0; float gyroY = gy / 131.0; float gyroZ = gz / 131.0; Serial.printf("Accel: %.2f %.2f %.2f Gyro: %.2f %.2f %.2f\n", accelX, accelY, accelZ, gyroX, gyroY, gyroZ); delay(100); }getMotion6()一次性读 14 个字节,从ACCEL_XOUT_H开始连续读,包含加速度、温度和角速度。这里没有单独读温度,如果需要可以加一个getTemperature()。换算系数 16384 和 131 是默认量程下的值,如果初始化时改了ACCEL_CONFIG或GYRO_CONFIG,这两个数要跟着变。比如加速度改成 ±4g,系数就是 8192。2.5 驱动层的关键寄存器MPU6050.cpp里最核心的是这两个函数:void MPU6050::writeByte(uint8_t reg, uint8_t data) { Wire.beginTransmission(devAddr); // devAddr 默认 0x68 Wire.write(reg); Wire.write(data); Wire.endTransmission(); } uint8_t MPU6050::readByte(uint8_t reg) { Wire.beginTransmission(devAddr); Wire.write(reg); Wire.endTransmission(false); // 重复起始,不释放总线 Wire.requestFrom(devAddr, (uint8_t)1); return Wire.read(); }endTransmission(false)里的false很关键,它发送重复起始条件,而不是停止条件。如果写成true,读操作会变成两次独立传输,某些 ESP8266 核心库下会读不到数据。这个细节在 Arduino UNO 上可能不明显,但在 ESP-12F 上很容易翻车。3. 编译烧录与串口验证:让数据真正出来3.1 开发环境选择这个 Demo 可以用 Arduino IDE 或 PlatformIO 编译。Arduino IDE 需要先装 ESP8266 开发板支持,然后在板子列表里选 “Generic ESP8266 Module”。几个关键配置:配置项值说明Flash Size4M (1M SPIFFS)常见 ESP-12F 模块Upload Speed115200再高可能不稳定CPU Frequency80 MHz默认即可Debug portDisabled不占用串口PlatformIO 的话,platformio.ini里写:[env:esp12e] platform = espressif8266 board = esp12e framework = arduino monitor_speed = 1152003.2 烧录接线ESP-12F 没有 USB 接口,需要 USB-TTL 模块。接线:TX 接 RX,RX 接 TX(交叉)GPIO0 拉低进下载模式,烧录完断开再复位CH_PD 接 3.3V电源一定要用 3.3V,5V 会烧烧录时如果报 “Failed to connect”,先检查 GPIO0 是不是在下载模式,再检查 TX/RX 有没有接反。ESP-12F 对电源比较敏感,USB-TTL 的 3.3V 输出电流不够时,可以外接一个 3.3V 稳压模块。3.3 串口看到什么算成功烧录完成后,打开串口监视器,波特率 115200。正常输出:MPU6050 就绪 Accel: 0.02 -0.01 1.00 Gyro: 0.15 -0.08 0.03 Accel: 0.02 -0.01 1.00 Gyro: 0.12 -0.10 0.02静止时 Z 轴加速度接近 1.00g,X、Y 接近 0。角速度三个轴都接近 0。如果 Z 轴是 -1.00,说明传感器装反了,不影响使用,换算时取反就行。如果所有值都是 0 或者 65535,先查接线,再查WHO_AM_I读出来是不是 0x68。3.4 数据抖动怎么处理原始数据有噪声是正常的,MPU6050 的角速度零偏尤其明显。常见做法是加一个简单的一阶低通滤波:float filteredGyroX = 0.9 * filteredGyroX + 0.1 * gyroX;系数 0.9 和 0.1 可以根据实际抖动调整,0.9 越大越平滑但延迟也越大。如果要做姿态解算,这个 Demo 只提供了原始数据,还需要加互补滤波或卡尔曼滤波,那是另一个话题了。4. 避坑与常见问题:接线、地址、时序的坑4.1 串口一直打印“连接失败”现象:testConnection()返回 false,串口反复打印失败信息。原因:IIC 地址不对,或者 SDA/SCL 接反。MPU6050 的 AD0 引脚决定地址,AD0 接地是 0x68,接 VCC 是 0x69。很多模块默认 AD0 接地,但如果你买的是带 AD0 引脚的板子,要确认一下。解决:先用 IIC 扫描程序扫一遍总线,看能不能扫到 0x68。扫不到就查接线,扫到了但地址不是 0x68,就改驱动里的devAddr。4.2 读出来的数据全是 0现象:getMotion6()返回的六个值都是 0。原因:传感器还在睡眠模式,或者PWR_MGMT_1寄存器没写成功。ESP-12F 的 IIC 时序在某些核心库版本下会有问题,写寄存器后没有足够延时。解决:在initialize()里写PWR_MGMT_1之后加delay(50),再读一次PWR_MGMT_1确认值变成了 0。如果还是不行,把 IIC 时钟降到 100kHz,Wire.setClock(100000)。4.3 数据偶尔跳变或卡死现象:串口输出正常几秒后突然卡住,或者数据出现极大值。原因:IIC 总线被拉死,通常是接线过长或者没有上拉电阻。ESP-12F 内部有弱上拉,但 MPU6050 模块如果没带上拉,长导线会导致信号边沿变缓。解决:在 SDA 和 SCL 上各加一个 4.7kΩ 上拉到 3.3V。导线尽量短,不要超过 20cm。如果还不行,在Wire.begin()之后加Wire.setClock(50000)进一步降速。4.4 烧录后程序不跑现象:烧录成功,但串口没有任何输出。原因:ESP-12F 的 GPIO15 需要接地才能正常启动,有些模块没有下拉电阻。另外 GPIO0 烧录后如果还接地,会一直停在下载模式。解决:确认 GPIO15 接 GND,GPIO0 烧录完断开或接 VCC,然后按一下复位键。如果用的是带自动复位的 USB-TTL,检查 DTR 和 RTS 有没有接对。5. 二次开发:从串口打印到无线传输和姿态解算这个 Demo 的定位是“能跑通”,但真拿来做项目,通常要改两个方向:一是把数据传出去,二是把原始数据变成姿态角。先说无线传输。ESP-12F 自带 WiFi,最直接的做法是加一个 UDP 或 TCP 客户端,把getMotion6()读到的数据打包发到上位机。改的时候注意不要在loop()里做阻塞式发送,否则采样率会掉。常见做法是每读 10 次发一次,或者用millis()做时间片。下面是一个 UDP 发送的骨架:#include <WiFiUdp.h> WiFiUDP udp; char packet[64]; void loop() { int16_t ax, ay, az, gx, gy, gz; mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz); sprintf(packet, "%d,%d,%d,%d,%d,%d", ax, ay, az, gx, gy, gz); udp.beginPacket("192.168.1.100", 8888); udp.write(packet); udp.endPacket(); delay(20); // 50Hz 采样 }这里delay(20)是简单做法,更稳的方式是用millis()判断时间差,避免 WiFi 发送耗时导致采样间隔不均匀。再说姿态解算。MPU6050 的原始数据不能直接当角度用,需要做融合。最简单的互补滤波:float angleX = 0; float alpha = 0.98; void updateAngle(float accelX, float accelY, float accelZ, float gyroX, float dt) { float accelAngleX = atan2(accelY, accelZ) * 180 / PI; angleX = alpha * (angleX + gyroX * dt) + (1 - alpha) * accelAngleX; }alpha取 0.98 表示信任陀螺仪多一点,因为加速度计对振动敏感。dt是两次采样的时间差,单位秒。这个滤波在静态下效果不错,动态下会有延迟,要求高的话换卡尔曼。最后说一个我踩过的坑:ESP-12F 的 ADC 和 WiFi 共用资源,如果同时用analogRead()和 WiFi 发送,读数会飘。解决办法是读 ADC 时关掉 WiFi,或者换外部 ADC。这个 Demo 没涉及 ADC,但如果你要加电池电压检测,记得避开这个坑。从那以后我每次改 IIC 传感器的代码,都先把WHO_AM_I读出来确认地址,再动其他逻辑。这个习惯帮我省了很多来回查接线的时间。希望帮到你。本文还有配套的精品资源,点击获取
简介:esp-12f_mpu6050_demo.rar 是一份面向物联网与嵌入式开发者的实战示例工程,聚焦 ESP-12F(ESP8266 Wi-Fi 模块)通过 I²C 总线驱动 MPU6050 六轴惯性测量单元的完整实现。资源解决的是从传感器初始化、寄存器读写到加速度与角速度数据解析的入门与调试问题,适合已具备基础 C 语言与单片机知识、希望快速上手运动追踪或姿态检测的开发者。压缩包共 605 个文件,约 11.02MB,以 233 个 h 头文件、163 个 c 源文件为主体,辅以 makefile 构建脚本、bin 固件、a 静态库、ld 链接脚本及少量 md 说明文档,覆盖驱动、编译与烧录全流程。内容预览可见 libc.a、libmbedtls.a、liblwip.a 等底层库,说明工程依赖链完整。已有 483 人学习下载,读者可从中获得 I²C 引脚连接(SCL 接 GPIO14、地址线拉高至 3.3V 对应 0x68)的参考配置、传感器数据读取与滤波处理思路,以及可直接编译运行的工程骨架,便于二次开发与项目移植。1. 从一块吃灰的 ESP-12F 说起:这个 Demo 到底能跑出什么手里攒了几块 ESP-12F 模块,一直没想好拿来做什么,直到翻出一颗 MPU6050 六轴传感器。这个esp-12f_mpu6050_demo.rar就是干这件事的:让 ESP-12F 通过 IIC 总线读取 MPU6050 的加速度和角速度数据,串口打印出来。听起来简单,但真上手你会发现,ESP-12F 的 GPIO 和 Arduino 的引脚编号对不上,MPU6050 的 IIC 地址和寄存器配置也有坑。这个 Demo 把初始化、读写、数据转换的完整链路都跑通了,适合刚接触 ESP8266 和 IIC 传感器的开发者,也适合想拿它当数据采集节点做二次开发的人。下面从工程结构开始拆。2. 工程结构与 IIC 通信链路:从引脚定义到数据读取2.1 目录里有什么拿到压缩包解压后,常见的目录结构是这样的(不同 IDE 可能略有差异,但核心文件一致):esp-12f_mpu6050_demo/ ├── esp-12f_mpu6050_demo.ino # 主程序入口 ├── MPU6050.cpp # 传感器驱动实现 ├── MPU6050.h # 驱动头文件,寄存器地址和类定义 ├── Wire.h / Wire.cpp # IIC 底层封装(部分工程自带) └── README.md # 接线说明和编译注意事项主程序负责初始化串口、IIC 和传感器,然后循环读取数据。驱动文件把 MPU6050 的寄存器操作封装成函数,比如readAccel()、readGyro()。这种分层方式的好处是,换一个 IIC 传感器只需要改驱动层,主程序逻辑不动。2.2 ESP-12F 的 IIC 引脚怎么接ESP-12F 的 GPIO 编号和 Arduino 的 D1、D2 不是一回事。常见做法是:ESP-12F 引脚功能接 MPU6050GPIO4SDASDAGPIO5SCLSCL3.3V电源VCCGND地GND注意 MPU6050 模块有的带稳压,有的不带。如果模块上标了 5V 输入,那 VCC 接 5V 也能用;如果只标 3.3V,就老老实实接 3.3V,否则 IIC 电平不匹配,读出来全是 0 或者直接卡死。2.3 初始化代码逐段拆先看主程序里的初始化部分:#include <Wire.h> #include "MPU6050.h" MPU6050 mpu; void setup() { Serial.begin(115200); // 串口波特率,和后面打印一致 Wire.begin(4, 5); // SDA=GPIO4, SCL=GPIO5 mpu.initialize(); // 写配置寄存器,唤醒传感器 if (!mpu.testConnection()) { // 读 WHO_AM_I 寄存器验证 Serial.println("MPU6050 连接失败"); while (1) delay(10); // 卡住,避免后面读脏数据 } Serial.println("MPU6050 就绪"); }Wire.begin(4, 5)里的两个参数就是 SDA 和 SCL 的 GPIO 编号,不是物理引脚序号。initialize()内部会往PWR_MGMT_1寄存器写 0,把传感器从睡眠模式唤醒。testConnection()读的是WHO_AM_I寄存器,默认返回 0x68,如果读回来不是这个值,说明接线或地址有问题。2.4 读加速度和角速度循环里读数据的代码:void loop() { int16_t ax, ay, az, gx, gy, gz; mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz); // 加速度换算成 g,灵敏度默认 ±2g 对应 16384 LSB/g float accelX = ax / 16384.0; float accelY = ay / 16384.0; float accelZ = az / 16384.0; // 角速度换算成 °/s,默认 ±250°/s 对应 131 LSB/(°/s) float gyroX = gx / 131.0; float gyroY = gy / 131.0; float gyroZ = gz / 131.0; Serial.printf("Accel: %.2f %.2f %.2f Gyro: %.2f %.2f %.2f\n", accelX, accelY, accelZ, gyroX, gyroY, gyroZ); delay(100); }getMotion6()一次性读 14 个字节,从ACCEL_XOUT_H开始连续读,包含加速度、温度和角速度。这里没有单独读温度,如果需要可以加一个getTemperature()。换算系数 16384 和 131 是默认量程下的值,如果初始化时改了ACCEL_CONFIG或GYRO_CONFIG,这两个数要跟着变。比如加速度改成 ±4g,系数就是 8192。2.5 驱动层的关键寄存器MPU6050.cpp里最核心的是这两个函数:void MPU6050::writeByte(uint8_t reg, uint8_t data) { Wire.beginTransmission(devAddr); // devAddr 默认 0x68 Wire.write(reg); Wire.write(data); Wire.endTransmission(); } uint8_t MPU6050::readByte(uint8_t reg) { Wire.beginTransmission(devAddr); Wire.write(reg); Wire.endTransmission(false); // 重复起始,不释放总线 Wire.requestFrom(devAddr, (uint8_t)1); return Wire.read(); }endTransmission(false)里的false很关键,它发送重复起始条件,而不是停止条件。如果写成true,读操作会变成两次独立传输,某些 ESP8266 核心库下会读不到数据。这个细节在 Arduino UNO 上可能不明显,但在 ESP-12F 上很容易翻车。3. 编译烧录与串口验证:让数据真正出来3.1 开发环境选择这个 Demo 可以用 Arduino IDE 或 PlatformIO 编译。Arduino IDE 需要先装 ESP8266 开发板支持,然后在板子列表里选 “Generic ESP8266 Module”。几个关键配置:配置项值说明Flash Size4M (1M SPIFFS)常见 ESP-12F 模块Upload Speed115200再高可能不稳定CPU Frequency80 MHz默认即可Debug portDisabled不占用串口PlatformIO 的话,platformio.ini里写:[env:esp12e] platform = espressif8266 board = esp12e framework = arduino monitor_speed = 1152003.2 烧录接线ESP-12F 没有 USB 接口,需要 USB-TTL 模块。接线:TX 接 RX,RX 接 TX(交叉)GPIO0 拉低进下载模式,烧录完断开再复位CH_PD 接 3.3V电源一定要用 3.3V,5V 会烧烧录时如果报 “Failed to connect”,先检查 GPIO0 是不是在下载模式,再检查 TX/RX 有没有接反。ESP-12F 对电源比较敏感,USB-TTL 的 3.3V 输出电流不够时,可以外接一个 3.3V 稳压模块。3.3 串口看到什么算成功烧录完成后,打开串口监视器,波特率 115200。正常输出:MPU6050 就绪 Accel: 0.02 -0.01 1.00 Gyro: 0.15 -0.08 0.03 Accel: 0.02 -0.01 1.00 Gyro: 0.12 -0.10 0.02静止时 Z 轴加速度接近 1.00g,X、Y 接近 0。角速度三个轴都接近 0。如果 Z 轴是 -1.00,说明传感器装反了,不影响使用,换算时取反就行。如果所有值都是 0 或者 65535,先查接线,再查WHO_AM_I读出来是不是 0x68。3.4 数据抖动怎么处理原始数据有噪声是正常的,MPU6050 的角速度零偏尤其明显。常见做法是加一个简单的一阶低通滤波:float filteredGyroX = 0.9 * filteredGyroX + 0.1 * gyroX;系数 0.9 和 0.1 可以根据实际抖动调整,0.9 越大越平滑但延迟也越大。如果要做姿态解算,这个 Demo 只提供了原始数据,还需要加互补滤波或卡尔曼滤波,那是另一个话题了。4. 避坑与常见问题:接线、地址、时序的坑4.1 串口一直打印“连接失败”现象:testConnection()返回 false,串口反复打印失败信息。原因:IIC 地址不对,或者 SDA/SCL 接反。MPU6050 的 AD0 引脚决定地址,AD0 接地是 0x68,接 VCC 是 0x69。很多模块默认 AD0 接地,但如果你买的是带 AD0 引脚的板子,要确认一下。解决:先用 IIC 扫描程序扫一遍总线,看能不能扫到 0x68。扫不到就查接线,扫到了但地址不是 0x68,就改驱动里的devAddr。4.2 读出来的数据全是 0现象:getMotion6()返回的六个值都是 0。原因:传感器还在睡眠模式,或者PWR_MGMT_1寄存器没写成功。ESP-12F 的 IIC 时序在某些核心库版本下会有问题,写寄存器后没有足够延时。解决:在initialize()里写PWR_MGMT_1之后加delay(50),再读一次PWR_MGMT_1确认值变成了 0。如果还是不行,把 IIC 时钟降到 100kHz,Wire.setClock(100000)。4.3 数据偶尔跳变或卡死现象:串口输出正常几秒后突然卡住,或者数据出现极大值。原因:IIC 总线被拉死,通常是接线过长或者没有上拉电阻。ESP-12F 内部有弱上拉,但 MPU6050 模块如果没带上拉,长导线会导致信号边沿变缓。解决:在 SDA 和 SCL 上各加一个 4.7kΩ 上拉到 3.3V。导线尽量短,不要超过 20cm。如果还不行,在Wire.begin()之后加Wire.setClock(50000)进一步降速。4.4 烧录后程序不跑现象:烧录成功,但串口没有任何输出。原因:ESP-12F 的 GPIO15 需要接地才能正常启动,有些模块没有下拉电阻。另外 GPIO0 烧录后如果还接地,会一直停在下载模式。解决:确认 GPIO15 接 GND,GPIO0 烧录完断开或接 VCC,然后按一下复位键。如果用的是带自动复位的 USB-TTL,检查 DTR 和 RTS 有没有接对。5. 二次开发:从串口打印到无线传输和姿态解算这个 Demo 的定位是“能跑通”,但真拿来做项目,通常要改两个方向:一是把数据传出去,二是把原始数据变成姿态角。先说无线传输。ESP-12F 自带 WiFi,最直接的做法是加一个 UDP 或 TCP 客户端,把getMotion6()读到的数据打包发到上位机。改的时候注意不要在loop()里做阻塞式发送,否则采样率会掉。常见做法是每读 10 次发一次,或者用millis()做时间片。下面是一个 UDP 发送的骨架:#include <WiFiUdp.h> WiFiUDP udp; char packet[64]; void loop() { int16_t ax, ay, az, gx, gy, gz; mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz); sprintf(packet, "%d,%d,%d,%d,%d,%d", ax, ay, az, gx, gy, gz); udp.beginPacket("192.168.1.100", 8888); udp.write(packet); udp.endPacket(); delay(20); // 50Hz 采样 }这里delay(20)是简单做法,更稳的方式是用millis()判断时间差,避免 WiFi 发送耗时导致采样间隔不均匀。再说姿态解算。MPU6050 的原始数据不能直接当角度用,需要做融合。最简单的互补滤波:float angleX = 0; float alpha = 0.98; void updateAngle(float accelX, float accelY, float accelZ, float gyroX, float dt) { float accelAngleX = atan2(accelY, accelZ) * 180 / PI; angleX = alpha * (angleX + gyroX * dt) + (1 - alpha) * accelAngleX; }alpha取 0.98 表示信任陀螺仪多一点,因为加速度计对振动敏感。dt是两次采样的时间差,单位秒。这个滤波在静态下效果不错,动态下会有延迟,要求高的话换卡尔曼。最后说一个我踩过的坑:ESP-12F 的 ADC 和 WiFi 共用资源,如果同时用analogRead()和 WiFi 发送,读数会飘。解决办法是读 ADC 时关掉 WiFi,或者换外部 ADC。这个 Demo 没涉及 ADC,但如果你要加电池电压检测,记得避开这个坑。从那以后我每次改 IIC 传感器的代码,都先把WHO_AM_I读出来确认地址,再动其他逻辑。这个习惯帮我省了很多来回查接线的时间。希望帮到你。本文还有配套的精品资源,点击获取