|
【MAX32630FTHR】--IIC之BMI160&OLED
[复制链接]
本帖最后由 df_flying 于 2017-9-26 22:46 编辑
由原理图可以看到MAX32630FTHR板载了一颗BMI160,和MAX14960同时接在了IIC2上,同时将IIC1引脚通过排针接了出来,这里正好可以接一个OLED显示。 根据所给的demo程序,其实IIC2的初始化在MAX14960初始化的时候就已经完成了,有一点不太清楚就是对应的IIC引脚并没有通过GPIO_Config()经行初始化。但为了保险这里OLED对应的IIC1的GPIO做了下简单的初始化。
利用板载的BMI160可以方便的判断下IIC的读程序是否存在问题,也验证下IIC是否连通,代码如下
I2CM_Read(MXC_I2CM2,BMI160_ADD,&add,1,&rec,1);
LOG("BMI160: ID is %d\r\n",rec);
if(rec != 209)
{
return -1;
}
后来通过BMI160的0x7e写命令后,一开始在0x0C位一直读不到数据,单步调试好像也没有发现问题,甚至可以读到160的时间戳,仔细看了下官方提供的I2CM_Write函数后,不知道是理解错了,还是...这里的函数竟然将所要写的地址作为第一个date,接上后面的数据同时写入,才是正确的,如下,不清楚封装中的cmd_data有啥用。
data[0] = 0x7E;//地址
data[1] = 0x11;//CMD
I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
BMI初始化程序如下:
- int bmi160_Init(void)
- {
- uint8_t add = 0x00,cmd= 0x00;
- uint8_t rec;
- uint8_t data[2];
- I2CM_Read(MXC_I2CM2,BMI160_ADD,&add,1,&rec,1);
- LOG("BMI160: ID is %d\r\n",rec);
- if(rec != 209)
- {
- return -1;
- }
- //acc mode
- // cmd = 0x11; //00 suspend 01normal 10 low power
- data[0] = 0x7E;
- data[1] = 0x11;
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- //gyr mode
- data[0] = 0x7E;
- data[1] = 0x15; //00 suspend 01 normal 10reserved 11 fast
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- //0x41 4g
- data[0] = 0x41;
- data[1] = 0x05;
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- //0x40
- data[0] = 0x40;
- data[1] = 0x29;
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- //0x42
- data[0] = 0x42;
- data[1] = 0x29;
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- //0x43
- data[0] = 0x43;
- data[1] = 0x03;
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- //0X7A
- // data[0] = 0x7A;
- // data[1] = 0x15;
- // I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- // HAL_Delay(100);
- // //0X7B
- // data[0] = 0x7B;
- // data[1] = 0x0b;
- // I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- // HAL_Delay(100);
- //0X41
- data[0] = 0x41;
- data[1] = 0x05;
- I2CM_Write(MXC_I2CM2,BMI160_ADD,NULL,0,data,2);
- HAL_Delay(100);
- return 0;
- }
复制代码
BMI测试程序如下:
- void bmi160_Test(void)
- {
- uint8_t add1 = 0x0c;
- uint8_t data[15];
- int16_t accx,accy,accz,gyrx,gyry,gyrz;
-
- I2CM_Read(MXC_I2CM2,BMI160_ADD,&add1,1,data,15);
-
- gyrx = (data[1]<<8) |data[0];// /13120
- gyry = (data[3]<<8) |data[2];
- gyrz = (data[5]<<8) |data[4];
- accx = (data[7]<<8) |data[6]; // /16384*2
- accy = (data[9]<<8) |data[8];
- accz = (data[11]<<8) |data[10];
-
- acc_x = (float) accx / 16384*2;
- acc_y = (float) accy / 16384*2;
- acc_z = (float) accz / 16384*2;
-
- gyr_x = (float) gyrx / 1312*10;
- gyr_y = (float) gyry / 1312*10;
- gyr_z = (float) gyrz / 1312*10;
-
- LOG("BMI160: accx=%.4f accy=%.4f accz=%.4f gyrx=%.4f gyry=%.4f gyrz=%.4f\r\n",acc_x,acc_y,acc_z,gyr_x,gyr_y,gyr_z);
- // LOG("REC = %d",rec);
-
- // uint8_t step[2];
- // add1=0x78;
- // I2CM_Read(MXC_I2CM2,BMI160_ADD,&add1,1,step,2);
- // LOG("step is %d\r\n",(step[0]<<8)|step[1]);
- }
复制代码
代码中含有对BMI160step的使用,试了下好像不是很准,可能是设置的还有些问题。测试结果如下:
OLED模块也带了不少的参考资源,这里主要是自己设置下底层函数,以及IIC1的初始化,模块上已有IIC的上啦电阻了,所以模块的两个NC上拉并不需要再焊接了。
OLED相关底层函数以及初始化
- int oled_I2cWriteCmd(uint8_t cmd)
- {
- uint8_t data[2];
- data[0] = OLED_CMDADD;
- data[1] = cmd;
- if (I2CM_Write(OLED_I2CM,OLED_ADD,NULL,0,data,2) != 2) {
- return E_COMM_ERR;
- }
- return 0;
- }
- /*
- *
- */
- int oled_I2cWriteData(uint8_t data)
- {
- uint8_t wdata[2];
- wdata[0] = OLED_DATAADD;
- wdata[1] = data;
- if (I2CM_Write(OLED_I2CM,OLED_ADD,NULL,0,wdata,2) != 2) {
- return E_COMM_ERR;
- }
- return 0;
- }
复制代码- const sys_cfg_i2cm_t oled_sys_cfg = {
- .clk_scale = CLKMAN_SCALE_DIV_1,
- .io_cfg = IOMAN_I2CM1(IOMAN_MAP_A, 1)
- };
- const gpio_cfg_t oled_iic = {PORT_3,(PIN_4 | PIN_5),GPIO_FUNC_GPIO,GPIO_PAD_OPEN_DRAIN };
- /*
- *
- */
- void oled_Init(void)
- {
- // int err=0;
- GPIO_Config(&oled_iic);
- if((I2CM_Init(OLED_I2CM, &oled_sys_cfg, I2CM_SPEED_400KHZ))!= E_NO_ERROR)
- {
- printf("I2C1 err \r\n");
- }
- HAL_Delay(200);
复制代码
测试结果如图:
直接上代码了,也方便以后自己查找,见附件
|
|