一周搞定9轴MPU9250(无华)(3)--数据采集

来源:互联网 发布:软件算无形资产吗 编辑:程序博客网 时间:2024/06/08 17:56
数据采集主要是调通IIC,MPU9250比较坑的一点是他的地磁计的数据采集,网上很多人也有这个问题。有了上一节所说的stm32cube生成的代码,使用它的库函数很好实现IIC数据的收发 。
主要是调用HAL_I2C_Mem_Write()进行数据写,HAL_I2C_Mem_Read()进行数据读。这时可以对传感器进行读写操作。首先我们调通mpu9250的mpu6500,也即陀螺仪和加速度计。
使用下面一段程序进行模块的初始化。

void MPU_INIT(void)
{
HAL_I2C_Mem_Read( &hi2c1, 0xD0,0x75,1,wrbuf, 1,20);
//读ID,确认IIC能够使用
if(wrbuf[0] != 0x71)
{
return;
}
HAL_Delay(500);
WriteReg(MPU6500_I2C_ADDR,MPU6500_CONFIG,MPU_GYRO_LPS_184HZ);
WriteReg(MPU6500_I2C_ADDR,MPU6500_GYRO_CONFIG,MPU_GYRO_FS_500);
WriteReg(MPU6500_I2C_ADDR,MPU6500_ACCEL_CONFIG,MPU_ACCE_FS_8G);
WriteReg(MPU6500_I2C_ADDR,MPU6500_SMPLRT_DIV,0x07); //125HZ 1000/(1+7)
WriteReg(MPU6500_I2C_ADDR,MPU6500_ACCEL_CONFIG_2,MPU_ACCE_LPS_460HZ);
WriteReg(MPU6500_I2C_ADDR,MPU6500_INT_PIN_CFG,0x02); //turn on Bypass Mode
HAL_I2C_Mem_Read( &hi2c1, AK8963_I2C_ADDR, AK8963_WIA,1, wrbuf, 1,20);
if(wrbuf[0] != 0x48)
{
return;
}
WriteReg(AK8963_I2C_ADDR ,AK8963_CNTL1,0x02); //continuous mode1

}

void WriteReg(u8 addr,u8 reg,uint8_t data)
{
HAL_I2C_Mem_Write(&hi2c1, addr, reg, 1, &data, 1, 20);
}

初始化完成之后,就可以使用IIC循环读数据寄存器了。数据寄存器为
#define MPU6500_GYRO_XOUT_H ((u8)0x43)
#define MPU6500_GYRO_XOUT_L ((u8)0x44)
#define MPU6500_GYRO_YOUT_H ((u8)0x45)
#define MPU6500_GYRO_YOUT_L ((u8)0x46)
#define MPU6500_GYRO_ZOUT_H ((u8)0x47)
#define MPU6500_GYRO_ZOUT_L ((u8)0x48)

#define MPU6500_ACCEL_XOUT_H 0x3B //????????
#define MPU6500_ACCEL_XOUT_L 0x3C
#define MPU6500_ACCEL_YOUT_H 0x3D
#define MPU6500_ACCEL_YOUT_L 0x3E
#define MPU6500_ACCEL_ZOUT_H 0x3F
#define MPU6500_ACCEL_ZOUT_L 0x40

对寄存器进行读即可。这里介绍一下这个库函数HAL_I2C_Mem_Read,它可以指定读数据的长度,并且可以指定读地址的长度,是一个比较好用的库函数。我们直接调用它进行读操作即可,
HAL_I2C_Mem_Read( &hi2c1, 0xD0,GYRO_XOUT_H,1, wrbuf, 6,20);
然后对数据进行以下转换就可以得到数据。
比较坑的是地磁计AK8963的数据读取。我们这里使用bypass模式对地磁传感器进行读操作,它必须对状态寄存器进行读操作,才能得到正确的数值,否则只能读取到第一次的值,以后就不改变。
void READ_MPU9250_MAG(void)
{
memset(wrbuf,0,6);
// WriteReg(MPU6500_I2C_ADDR,MPU6500_INT_PIN_CFG,0x02); //turn on Bypass Mode
HAL_I2C_Mem_Read( &hi2c1, AK8963_I2C_ADDR, AK8963_ST1,1, wrbuf, 1,20);
if( (wrbuf[0]&0x03))
{
HAL_I2C_Mem_Read( &hi2c1, AK8963_I2C_ADDR, AK8963_HXL,1, wrbuf, 6,20);
memcpy(&mpurdata,wrbuf,6);
mag.x = MPU_MAGN_K*(float)mpurdata.x;
mag.y = MPU_MAGN_K*(float)mpurdata.y;
mag.z = MPU_MAGN_K*(float)mpurdata.z;
}
HAL_I2C_Mem_Read( &hi2c1, AK8963_I2C_ADDR, AK8963_ST2,1, wrbuf, 1,20);
// ExchangeBuf(wrbuf);
}

上面是低地磁计的读取函数,可以看到,在连续读模式下,我们必须对其AK8963_ST2这个寄存器进行读操作才能得到正确的数值。
完成程序的编写之后,我们可以得到正确的数值。

对程序和硬件有需要的同学,可以访问 。

9轴模块购买,程序下载戳:https://item.taobao.com/item.htm?spm=686.1000925.0.0.xbxSkp&id=557034187077
有什么疑问或者交流的加我QQ475292178,请注明“交流探讨”