900字范文,内容丰富有趣,生活中的好帮手!
900字范文 > LIS3DH 加速度值 读取处理

LIS3DH 加速度值 读取处理

时间:2021-05-09 02:03:35

相关推荐

LIS3DH 加速度值 读取处理

折腾加速度芯片的过程中的一些记录,

相关数据和依据来源于以下两个官方文档:

AD输出位数:

加速度的值经过AD转换后以数字形式输出,这里首先要搞清楚,AD转换后的数据是多少位的,官方英文版的手册给出的说明是:

不同的工作模式、有效数据位数不同。

低功耗是8位、高分辨是12、普通10位。这个由两个寄存器的位来控制。上表总最后一列中说明不同位(工作模式)时,在满量程为 ± 2g的时候,最小一个数值代表多少mg,也就是一个单位表示重力加速度的值的千分之几。一般情况下用到的加速度测量都不大,为了更高的分辨率都选±2g量程。

中文版给了一个例子,其中的BLE是寄存器【CTRL_REG4 (23h)】中一位,但是只有在高分辨模式下才能设置。否则只能是默认值 == 0;

并且给了相应的说明

通过上面的解释可以得知:这个例子是 高分辨模式、12bitAD、。

如果不修改BLE保持默认,那么是小端模式。我们一般读寄存器的时候都是连续读的,所以RAW[0]中是OUT_X_L 也就是0x28的值。因为是12位,就需要两个8位拼接成一个16位。小端模式 ,得到的16位数值应该是 RAW[1]<<8 | RAW[0] == 0x15E0

由于左对齐,12位有效,最后4位无用,右移4位

B 0001 0101 1110 0000 右移4位 0000 0001 0101 1110

转换为十六进制 0x 01 5E 转为 10进制 == 350

那么怎么表示 -350呢,

用补码表示,首先将350二进制的最高位变为1,剩下的位都取反、然后再加一;

这个是12位的,变成16位需要左移4位,后面补4个0.

最后将这个转为十六进制就是 0xEA20

28h == 20h 29h ==EA

其实说了这么多,就是要理解下面这个 0xF000,为什么最高4位全是1。

int16_t pdata[3] = {0, 0, 0};uint8_t regValue[6] = {0, 0, 0, 0, 0, 0};IIC_read_len(m_device_address,(LIS3DH_REG_OUT_X_L | 0x80),regValue,6);/* Format the data. */for(uint8_t i=0;i<3;i++){if(regValue[2*i+1] & 0x80) symbol[i] = 0xF000;else symbol[i] = 0x0000;}pdata[0] =symbol[0] | ((( ( ( int16_t )regValue[1] ) << 8 ) + ( int16_t )regValue[0] ) >> 4);pdata[1] =symbol[1] | ((( ( ( int16_t )regValue[3] ) << 8 ) + ( int16_t )regValue[2] ) >> 4);pdata[2] =symbol[2] | ((( ( ( int16_t )regValue[5] ) << 8 ) + ( int16_t )regValue[4] ) >> 4);NRF_LOG_INFO("\t\tX:%d\t\t Y:%d\t\t Z:%d\t\t\n\r",pdata[0],pdata[1],pdata[2]);

原始整数,12位,右对齐,高位4个0;

转为负值,高位4个1;

AD数值,左对齐,先要右移4位,然后将高位全部置为1

int16 有符号数,直接赋值,OK!

补码、大小端、AD位数、数据对齐;

这些对于我们这些非计算机专业的来说,还是有点难的。

纯属个人兴趣;若文中有错误的地方欢迎留言指正,不胜感激。

参考以下文章,感谢原作者:

《lis3dh调试心得,读取正确的加速度值》

文末评论:

你好,三轴加速度的数据在寄存器中好像是以原码的形式存在的,而并非是补码的形式,所以你的LIS3DH_Get_AccRaw()计算是有问题的,而且你在结果上或上0xf000,导致最高四位全为1,这样的话拿到的结果肯定是会偏大的。请知悉

是不对的,数值确实是补码方式存储的,高4位全是1,这个没关系,因为是补码。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。