stm32|STM32中iic驱动mpu6050例程

一、mpu6050寄存器相关知识
1.本机地址
可在寄存器使用手册查找
stm32|STM32中iic驱动mpu6050例程
文章图片

mpu6050在iic中是七位地址,Bit6~Bit1是他的前六位地址,默认是110100,末位由AD0引脚的值确定,并不是该寄存器的Bit0位。
若AD0引脚置0,则mpu6050的本机地址是1101000,十六进制为0x68。
2.复位mpu6050
需要配置的是0x6B寄存器的Bit7位。
stm32|STM32中iic驱动mpu6050例程
文章图片

设置为1时,该位??会将所有内部寄存器重置为其默认值。复位完成后,该位自动清除为0。需要延时100ms。
3.时钟源配置
需要配置的是0x6B寄存器的Bit2~Bit0位。
stm32|STM32中iic驱动mpu6050例程
文章图片

stm32|STM32中iic驱动mpu6050例程
文章图片

上电时,时钟源默认为内部振荡器。手册中建议将设备配置为使用陀螺仪之一(或外部时钟)作为时钟参考,可以提高稳定性。也就是1~5任选。
4.设置MPU6050工作模式
需要配置的是0x6B寄存器的Bit6位。
stm32|STM32中iic驱动mpu6050例程
文章图片

SLEEP设置为1为睡眠模式,设置为0为工作模式。
5.设置输出三轴陀螺仪和三轴加速度数据
需要配置的是0x6C寄存器的Bit6~Bit0位。
stm32|STM32中iic驱动mpu6050例程
文章图片

设置为1时,加速度计和陀螺仪置于待机模式。置0时,加速度计和陀螺仪置于开启状态。
6.禁止中断
需要配置的是0x38寄存器的Bit0位。
stm32|STM32中iic驱动mpu6050例程
文章图片

置1开启中断模式,置0关闭中断模式。
7.设置采样频率
需要配置的是0x38寄存器。
stm32|STM32中iic驱动mpu6050例程
文章图片

采样率=陀螺仪输出率/(1 + SMPLRT_DIV)
【stm32|STM32中iic驱动mpu6050例程】9.关闭辅助IIC模块
需要配置的是0x6A寄存器的Bit5位。
stm32|STM32中iic驱动mpu6050例程
文章图片

当I2C_MST_EN设置为1时,将启用IIC主模式;当该位清除时为0时,辅助IIC总线线路(AUX_DA和AUX_CL)由主IIC总线逻辑驱动(SDA和SCL)。
10.启动旁路多路复用器
需要配置的是0x37寄存器的Bit1位。
stm32|STM32中iic驱动mpu6050例程
文章图片

当I2C_BYPASS_EN等于1并且I2C_MST_EN(0x6A寄存器)等于0时,主机应用处理器将能够直接访问MPU-60X0的辅助I2C总线。 当该位等于0时,不管I2C_MST_EN的状态如何,主机应用处理器将无法直接访问MPU-60X0的辅助I2C总线。
11.配置陀螺仪的满量程范围
需要配置的是0x1B寄存器的Bit4~Bit3位。
stm32|STM32中iic驱动mpu6050例程
文章图片

stm32|STM32中iic驱动mpu6050例程
文章图片

有四个量程可供选择。
12.配置加速度计的满量程范围
需要配置的是0x1C寄存器的Bit4~Bit3位。
stm32|STM32中iic驱动mpu6050例程
文章图片

stm32|STM32中iic驱动mpu6050例程
文章图片

有四个量程可供选择。
8.加速度计数据寄存器
stm32|STM32中iic驱动mpu6050例程
文章图片

这里需要注意的是他的数据格式
stm32|STM32中iic驱动mpu6050例程
文章图片

翻译过来就是:存储格式是16位二进制的补码值,小于32768的数都是正数,大于32768的数都是负数,假设十进制读数为40000,则他的读出的数是40000-65536=(-25536)。也就是读数的范围为[-32768,32767)。
接下来,MPU6050并不会以 g 单位输出,我们需要在读完后进行转换。先来看看各个量程对应的灵敏度。
stm32|STM32中iic驱动mpu6050例程
文章图片

不同的量程范围对应着不同的灵敏度。以量程为±2g为例,假设补码转换后的数据是1000,从上表中得知在±2g下的灵敏度为16384LSB/g,得出的加速度值应该为1000÷16384=0.061g。
9.陀螺仪数据寄存器
数据存储格式和加速度计一样,都是16位2的补码值,也有对应的灵敏度转换。
stm32|STM32中iic驱动mpu6050例程
文章图片

stm32|STM32中iic驱动mpu6050例程
文章图片

stm32|STM32中iic驱动mpu6050例程
文章图片

二、代码实现;
mpu6050.c代码

#include "mpu6050.h"uint8_t buffer[14]; void MPU6050_setClockSource(uint8_t source){ MPU_IICwriteBits(0x68, 0x6B, 2, 3, source); }void MPU6050_setFullScaleGyroRange(uint8_t range) { MPU_IICwriteBits(0x68, 0x1B, 4, 2, range); }void MPU6050_setFullScaleAccelRange(uint8_t range) { MPU_IICwriteBits(0x68, 0x1C, 4, 2, range); }void MPU6050_resetEnabled(uint8_t enabled) { MPU_IICwriteBit(0x68, 0x6B, 7, enabled); Delay_ms(100); }void MPU6050_set_Gyro_Accel_outRange(uint8_t range) { MPU_IICwriteBits(0x68, 0x6C, 5, 6, range); }void MPU6050_set_SMPRT_DIV(uint8_t range) { MPU_IICwriteByte(0x68,0x19,range); }void MPU6050_set_Gyro_DLPF_outRange(uint8_t range) { MPU_IICwriteBits(0x68, 0x1A, 2, 3, range); }void MPU6050_INT_Disabled(uint8_t enabled) { MPU_IICwriteBit(0x68, 0x38, 0, enabled); }void MPU6050_setSleepEnabled(uint8_t enabled) { MPU_IICwriteBit(0x68, 0x6B, 6, enabled); }void MPU6050_testConnection(void) { while(buffer[0] != 0x68){ MPU_IICreadBytes(0x68, 0x75, 1, buffer); }; }void MPU6050_setI2CMasterModeEnabled(uint8_t enabled) { MPU_IICwriteBit(0x68, 0x6A, 5, enabled); }void MPU6050_setI2CBypassEnabled(uint8_t enabled) { MPU_IICwriteBit(0x68, 0x37, 1, enabled); }void MPU6050_initialize(void) { MPU_IIC_Init(); //IIC初始化 MPU6050_testConnection(); //检测MPU6050 是否已经连接 MPU6050_resetEnabled(1); //复位mpu6050需延时100ms MPU6050_setClockSource(2); //设置时钟 MPU6050_set_Gyro_Accel_outRange(0); // 设置输出三轴陀螺仪和三轴加速度数据 MPU6050_INT_Disabled(0); //禁止中断 MPU6050_set_SMPRT_DIV(0); //采样分频 MPU6050_setFullScaleGyroRange(3); //陀螺仪最大量程 +-1000度每秒 MPU6050_setFullScaleAccelRange(0); //加速度度最大量程 +-2G MPU6050_set_Gyro_DLPF_outRange(2); //设置陀螺仪和加速度计的低通滤波器 MPU6050_setSleepEnabled(0); //进入工作状态 MPU6050_setI2CMasterModeEnabled(0); //不让MPU6050 控制AUXI2C MPU6050_setI2CBypassEnabled(1); //主控制器的I2C与 MPU6050的AUXI2C 直通。控制器可以直接访问HMC5883L }

测试代码
float Accel_Y,Gyro_Y; Gyro_Y=(MPU_I2C_ReadOneByte(0x68,0x45)<<8)+MPU_I2C_ReadOneByte(0x68,0x46); if(Gyro_Y>32767)Gyro_Y-=65536; Gyro_Y=Gyro_Y/16.4; Accel_Y=(MPU_I2C_ReadOneByte(0x68,0x3D)<<8)+MPU_I2C_ReadOneByte(0x68,0x3E); if(Accel_Y>32767) Accel_Y-=65536; Accel_Y=Accel_Y/16384; printf("Gyro_Y : %fAccel_Y: %f \n",Gyro_Y, Accel_Y);

运行效果
stm32|STM32中iic驱动mpu6050例程
文章图片

    推荐阅读