上篇记录了,利用模拟IIC读取LSM6DS3TR数据,这篇记录利用硬件IIC和LSM6DS3TR官方例程,读取加速计、陀螺仪、温度数据,并利用加速计数据装换成角度。
官网例程写的很好,有兴趣的网友可以下载下来看看,对自己的编程思路也是一个提高,连接放到下面。
(9条消息) LSM6DS3TR-C官网例程-单片机文档类资源-CSDN文库
官网把所用寄存器分别封装成一个结构体,就列一个例子如下:CTRL1_XL寄存器
typedef struct
{
#if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
uint8_t bw0_xl : 1;
uint8_t lpf1_bw_sel : 1;
uint8_t fs_xl : 2;
uint8_t odr_xl : 4;
#elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
uint8_t odr_xl : 4;
uint8_t fs_xl : 2;
uint8_t lpf1_bw_sel : 1;
uint8_t bw0_xl : 1;
#endif /* DRV_BYTE_ORDER */
} lsm6ds3tr_c_ctrl1_xl_t;
(其他寄存器可以下载官网程序自己查看)
官网也把配置寄存器的操作封装成一个函数,也拿对CTRL1_XL寄存器的配置 举例,程序如下
int32_t lsm6ds3tr_c_xl_full_scale_set(stmdev_ctx_t *ctx, lsm6ds3tr_c_fs_xl_t val)
{
lsm6ds3tr_c_ctrl1_xl_t ctrl1_xl;
int32_t ret;
ret = lsm6ds3tr_c_read_reg(ctx, LSM6DS3TR_C_CTRL1_XL,(uint8_t *)&ctrl1_xl, 1);
if (ret == 0)
{
ctrl1_xl.fs_xl = (uint8_t) val;
ret = lsm6ds3tr_c_write_reg(ctx, LSM6DS3TR_C_CTRL1_XL,(uint8_t *)&ctrl1_xl, 1);
}
return ret;
}
我们主要看 紫色 函数,如下:
int32_t lsm6ds3tr_c_read_reg(stmdev_ctx_t *ctx, uint8_t reg,uint8_t *data,uint16_t len)
{
int32_t ret;
ret = ctx->read_reg(ctx->handle, reg, data, len);
return ret;
}
int32_t lsm6ds3tr_c_write_reg(stmdev_ctx_t *ctx, uint8_t reg,uint8_t *data,uint16_t len)
{
int32_t ret;
ret = ctx->write_reg(ctx->handle, reg, data, len);
return ret;
}
看到了,要实现紫色字体标注的函数,就要实现 红色字体标注的函数,所以红色字体的函数就是我们自己要实现的(具体实现函数,一会下面在贴出来)。
红色字体函数是结构体内的函数指针,我们找到这个结构体看看里面的内容,如下
typedef int32_t (*stmdev_write_ptr)(void *, uint8_t, const uint8_t *, uint16_t);
typedef int32_t (*stmdev_read_ptr)(void *, uint8_t, uint8_t *, uint16_t);
typedef struct
{
/** Component mandatory fields **/
stmdev_write_ptr write_reg;
stmdev_read_ptr read_reg;
/** Customizable optional pointer **/
void *handle;
} stmdev_ctx_t;
看到了吗?所以我们要实现这两个函数,只需自己编写两个函数,然后在初始化结构体的时候,让这两个指针指向咱编写的实现函数就可以了
现在咱先编写2个实现函数如下:
static int32_t LSM6D3TR_write(void *handle, uint8_t reg, const uint8_t *bufp,uint16_t len)
{
HAL_I2C_Mem_Write(handle,LSM6DS3TR_C_I2C_ADD_L,reg,I2C_MEMADD_SIZE_8BIT,(uint8_t*)bufp,len,1000);//HAL库实现IIC写
/******如下是模拟IIC实现写***********************/
// LSM6D3S_Start();
// LSM6D3S_SendByte(LSM6DS3_I2C_ADDRESS);
// LSM6D3S_Wait_ACK();
// LSM6D3S_SendByte(reg);
// LSM6D3S_Wait_ACK();
// for(uint8_t i = 0;i < len; i++)
// {
// LSM6D3S_SendByte(*(bufp+i));
// }
// LSM6D3S_Wait_ACK();
// LSM6D3S_Stop();
return 0;
}
int32_t LSM6D3TR_read(void *handle, uint8_t reg, uint8_t *bufp,uint16_t len)
{
HAL_I2C_Mem_Read(handle,LSM6DS3TR_C_I2C_ADD_L, reg,I2C_MEMADD_SIZE_8BIT,(uint8_t *)bufp, len, 1000);//HAL库实现IIC读
/*******以下是模拟IIC实现读********/
// LSM6D3S_Start();
// LSM6D3S_SendByte(LSM6DS3_I2C_ADDRESS);
// LSM6D3S_Wait_ACK();
// LSM6D3S_SendByte(reg);
// LSM6D3S_Wait_ACK();
//
// LSM6D3S_Start();
// LSM6D3S_SendByte(LSM6DS3_I2C_ADDRESS+1);
// LSM6D3S_Wait_ACK();
//
// for(uint8_t i=0;i
// *bufp=LSM6D3S_Read_Byte(1);
// bufp++;
// }
//
// *bufp = LSM6D3S_Read_Byte(0);
//
// LSM6D3S_Stop();
return 0;
}
实现函数编写完成,在看看是怎么将实现函数与官网函数连接在一起的,就用到结构体了,只需在结构体初始化时,指向实现函数就行了,如下:
void lsm6ds3tr_c_read_data_polling(void)
{
/* Initialize mems driver interface */
stmdev_ctx_t dev_ctx;
dev_ctx.write_reg = LSM6D3TR_write;
dev_ctx.read_reg = LSM6D3TR_read;
dev_ctx.handle = &SENSOR_BUS;
/* Init test platform */
// platform_init();
/* Wait sensor boot time */
// platform_delay(BOOT_TIME);
HAL_Delay(20);
/* Check device ID */
whoamI = 0;
lsm6ds3tr_c_device_id_get(&dev_ctx, &whoamI);
if ( whoamI != LSM6DS3TR_C_ID )
while (1); /*manage here device not found */
/* Restore default configuration */
lsm6ds3tr_c_reset_set(&dev_ctx, PROPERTY_ENABLE);
......
.......
}
对于读取出来的数据,怎么装换成角度,自己查找资料,推荐网友分享
(9条消息) 三轴加速度计得到角度值原理_YW_1256的博客-CSDN博客_加速度计角度
工程代码下载如下:
(9条消息) LSM6DS3TR-C姿态传感器的使用(二)---HAL库硬件IIC和官方例程-单片机文档类资源-CSDN文库