玩四轴的都知道, MWC V2.5 飞控主板,板载陀螺仪传感器就是MPU6050.(不信你可以拿放大镜看). 
而默认的MWC开源程序是自己读取MPU6050的原始数据,经过,自己的一套算法.算出来四轴当前的姿态. 
所以,MWC的源程序里面也就没有使用 MPU6050的 DMP进行计算姿态. 
笔者为了做产品. 研究了很长时间的MWC源程序,始终没看懂. 后来不得已.最终在同事的劝说下.鼓起勇气 
全部自己写.. 
经过一个星期的拆解移植.终于把MWC的开源程序大卸八块成独立可用的程序. 然后又重新组装在一起. 
但是读取MPU6050 陀螺仪姿态的时候发现,读取的是原始数据. 无法使用.而且还需要转换成Yaw Pitch Roll 这种数据格式. 
这套复杂的数据融合算法. 俺表示搞不定.. 
在上网查找资料的时候发现,MPU6050传感器默认就能进行数据融合计算.而且不占CPU资源 
这个天大的好消息.引起了我的兴趣.本来CPU就不够用. 这一定要利用起来.

当我从网上down来源代码, 复制到我的程序的时候,发现. 
DMP输出的数据呈现周期性的数据异常. 数据波动非常大. 这要是用在飞机上一定机毁人亡…. 
期初我以为是干扰,研究了一个礼拜的卡尔曼数据滤波算法. 最后也没搞定. 
我发现凡事数据有异常的附近 一定会出现 FIFO overflow ! 
找到到源代码 DEBUG_PRINTLN(F(“FIFO overflow !”)); 
打印这行代码的条件是

 if ((mpuIntStatus & 0x10) || fifoCount == 1024) {// reset so we can continue cleanlympu.resetFIFO();Serial.println(F("FIFO overflow!"));// otherwise, check for DMP data ready interrupt (this should happen frequently)}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

这个条件的意思是,如果mpuIntStatus 的状态不对,或者读取的数据长度等于 1024 
那么都会报这个错误.

我单纯的注释掉 DEBUG_PRINTLN(F(“FIFO overflow !”)); 是不行的.数据还是会周期性的异常. 
数据不正确,干啥都不行. 
百度了下,网上说,这个问题的根本原因是CPU读取DMP的数据 速度太慢造成了 FIFO 缓冲器溢出. 
经过多方查资料,才知道,MPU6050 要想正确使用DMP必须将传感器的12号引脚连接到CPU的外部中断引脚上, 
使用中断函数立即去读取DMP的数据.就不会溢出了.

但是悲剧的情况是,MWCV2.5 电路板竟然没有将MPU6050的12号针脚引出. 针脚特别小.我的焊工又不行.真想扔了重新买一块. 
那怎么办呢? 
我想反正也能读出来数据, 我抛弃掉异常数据,或者不让异常数据产生就好了. 
我第一个方法是,在每次读完数据以后就reset一下DMP输出的FIFO数据.这样就不会溢出了.缓冲区还是很大的. 
结果是不会溢出了. 但还是会有异常数据. 
于是我将DMP读取的数据长度打印出来, 发现,正常的数据长度都是84或者126, 不正常的就各种长度.

经过我的仔细研究数据读取代码. 竟然发现了,我的数据为啥会异常的根本原因..

原因就是我没用中断去读DMP的数据.而是循环不定时随机读的. 不同步的读取势必会有DMP计算到一部分,我这边CPU去读的情况. 
出现这种情况,CPU读到一部分数据,数据不全. 肯定异常 现在问题明白了. . 
解决方法如下. 
如何才能判断数据是读完的呢?这个地方用了点小技巧. 
只要每次读取数据能读满, 那么这次数据就是正常的.否则.就是不正常的数据..

见下面的代码注释

 //郑桂良发现的超级规则.....
#ifdef DEBUGif (fifoCount  % packetSize != 0   ) //840 是 packetSize * 20 的大小 packetSize是每次读取数据的大小.{//mpu.resetFIFO(); 不用reset也行.//DEBUG_PRINTLN(F("数据读取异常,未按节拍读取,MPU6050 的 DMP 未计算完毕就读取了,只读取了一部分.造成后面的数据计算错误.")); //这种不同步异常造成的原因是MPU6050 的12号针脚 是一个对外发送中断信号的针脚.当DMP计算完毕以后会改变这个针脚的电平.//需要将这个12针脚与单片机的外部中断针脚相连.使用外部中断函数立即去读取DMP的数据. 才不会导致数据越堆越多.//但是悲剧的情况是,我的电路板竟然没有将MPU6050的12号针脚引出....我的程序是循环读.就出现这个异常了.return  ;  //放弃本次读取,下次再读.}
#endif
//郑桂良发现的超级规则.....
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

你只要简单的将代码改一下就可以了.把代码

if ((mpuIntStatus & 0x10) || fifoCount == 1024) {// reset so we can continue cleanlympu.resetFIFO();Serial.println(F("FIFO overflow!"));// otherwise, check for DMP data ready interrupt (this should happen frequently)}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

改成

//郑桂良发现的超级规则.....
//840 是 packetSize * 20 的大小 /本来这里是 == 1024if ( (mpuIntStatus & 0x10) || ( fifoCount  % packetSize != 0 ) ||                 (fifoCount >= 840 )) //换成这个if条件就好了.{// reset so we can continue cleanlympu.resetFIFO(); //DEBUG_PRINTLN(F("FIFO overflow !")); //FIFO overflow 问题的本质就是,读取数据速度不够快导致FIFO溢出。//据说解决的方法就是,不能只用一个dmp_read_fifo(gyro, accel, quat, &sensor_timestamp, &sensors,&more);函数。//我参考了据说“非常成功”的代码,他们使用的库都差不多,或者一样,那么玄机就在如何加快读取?//请各位大神帮帮忙,要不然我就直接读取陀螺仪加速度计原始数据自己做数据融合了,但是我觉得INVsense公司做dmp必定有它的道理吧。//还是想用DMP读取数据return 9; }

使用 MWC V2.5 中的 MPU6050中的DMP进行计算姿态(转载)相关推荐

  1. C#中Winform程序中如何实现多维表头【不通过第三方报表程序】

    问题:C#中Winform程序中如何实现多维表头. 在网上搜了很多方法,大多数方法对于我这种新手,看的都不是很懂.最后在新浪博客看到了一篇比较易懂的文章:[DataGridView二维表头与合并单元格 ...

  2. 关于python缩进的描述中_关于Python程序中与“缩进”有关的说法中,以下选项中正确的是()...

    关于Python程序中与"缩进"有关的说法中,以下选项中正确的是() 答:缩进在程序中长度统一且强制使用 同文学或同音乐主题的民歌,<_______>是其中之一.此曲经 ...

  3. python中json dumps_python中json.loads,dumps,jsonify使用

    search_info = {'id':132,'user_role':3} print type(search_info) #输出 #转为string用dumps print type(json.d ...

  4. VS2010中“工具选项中的VC++目录编辑功能已被否决”解决方法

    http://blog.csdn.net/chaijunkun/article/details/6658923 这是VS2010的改变,不能够在"工具-选项"中看到"VC ...

  5. django-celery中配置celery中的日志

    django-celery中配置celery中的日志 django配置文件中的logging只是针对django中的views.API起作用,对celery不起作用,也就是说celery不能使用dja ...

  6. word录入表单数据 java 导入系统,java导入excel | 怎么把excel中的数据批量导入到word中的表格中...

    用javascript怎么实现把excel中的数据批量导入到数据库表中 这个js不能直接实现吧 我们程序用到 先读取excel内容转换成数组 然后放到页面上 再提交表单 储存 MySql如何批量添加数 ...

  7. php数组重复值销毁,如何从PHP中删除数组中的重复值

    如何从PHP中删除数组中的重复值 如何从PHP中删除数组中的重复值? 21个解决方案 204 votes 使用array_unique(). 例: $array = array(1, 2, 2, 3) ...

  8. oracle urlencode 中文,Python2和Python3中urllib库中urlencode的使用注意事项

    前言 在Python中,我们通常使用urllib中的urlencode方法将字典编码,用于提交数据给url等操作,但是在Python2和Python3中urllib模块中所提供的urlencode的包 ...

  9. R语言计算F1评估指标实战:F1 score、使用R中caret包中的confusionMatrix()函数为给定的logistic回归模型计算F1得分(和其他指标)

    R语言计算F1评估指标实战:F1 score.使用R中caret包中的confusionMatrix()函数为给定的logistic回归模型计算F1得分(和其他指标) 目录

最新文章

  1. 92django_url
  2. jquery选择器 之 获取父级元素、同级元素、子元素
  3. 人脸检测 RetinaFace
  4. python实训项目-实验楼Python项目
  5. boost::statechart模块自定义反应测试相关的测试程序
  6. git安装、使用及常见报错
  7. ios 图片截取功能 图片拼接功能
  8. 「云+未来」上海峰会,报名开启
  9. 使用Docker部署前端项目实战教程,该踩的坑我都帮你踩了!
  10. JS 中样式显示(clientWidth和clientHeight、offsetLeft、scrollHeight )
  11. vs2005无法附加进程
  12. html网页中两侧浮动广告怎么做,网页两侧浮动广告图片js代码
  13. 【AP_EJOR】Robust solutions to multi-objective linear programs with uncertain data(2)
  14. UML结构建模图———复合结构图
  15. 父母尚在苟且,你却在炫耀诗和远方
  16. Java基础篇--异常机制
  17. 算法题:Rod Cutting
  18. 如何重新发明短信息这个古老的轮子
  19. Revit二次开发环境平台的搭建
  20. 利用UE简化JAVA后端的SQL语句编辑

热门文章

  1. 回归Dos操作的快感,进入PowerShell世界 (转)
  2. 使用Java代码在应用层获取Android系统属性
  3. 搜星流程(1)-[Qualcomm][BSP-GPS]
  4. 基于IMX515EVK+WINCE6.0---支持PB6.0通过USB下载镜像文件
  5. Windows配置jdk环境变量JAVA_HOME与path
  6. SpringCloud(8)微服务监控Spring Boot Admin
  7. 抽象类 VS 接口 (3)
  8. linux中rpm命令管理
  9. 使用 Intel HAXM 为 Android 模拟器加速,媲美真机(转)
  10. Entity Framework中IQueryable, IEnumerable, IList的区别(转自网络)