极客工坊

 找回密码
 注册

QQ登录

只需一步,快速开始

查看: 15889|回复: 7

yawpitchroll角度问题

[复制链接]
发表于 2012-12-28 17:48:09 | 显示全部楼层 |阅读模式
本帖最后由 戊辰寒 于 2012-12-28 20:47 编辑

  设定了陀螺仪跟加速度计的精度,设定了数字高低通滤波器。

  测试结果是只有FIFO数据溢出复位以后的第一行数据可信,其他的都乱跳……
  

  如红框所示,分别对应Yaw(Z轴) Pitch(Y轴) Roll(X轴)


图片引自wikipedia.org

请教各位大神如何只提取第一行的数据?


下面是我的程序:

  1. // I2C device class (I2Cdev) demonstration Arduino sketch for MPU6050 class
  2. // 10/7/2011 by Jeff Rowberg <[url=mailto:[email protected]][email protected][/url]>
  3. // Updates should (hopefully) always be available at [url=https://github.com/jrowberg/i2cdevlib]https://github.com/jrowberg/i2cdevlib[/url]
  4. //
  5. // Changelog:
  6. //     2011-10-07 - initial release

  7. /* ============================================
  8. I2Cdev device library code is placed under the MIT license
  9. Copyright (c) 2011 Jeff Rowberg

  10. Permission is hereby granted, free of charge, to any person obtaining a copy
  11. of this software and associated documentation files (the "Software"), to deal
  12. in the Software without restriction, including without limitation the rights
  13. to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  14. copies of the Software, and to permit persons to whom the Software is
  15. furnished to do so, subject to the following conditions:

  16. The above copyright notice and this permission notice shall be included in
  17. all copies or substantial portions of the Software.

  18. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  19. IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  20. FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  21. AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  22. LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  23. OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  24. THE SOFTWARE.
  25. ===============================================
  26. */

  27. // Arduino Wire library is required if I2Cdev I2CDEV_ARDUINO_WIRE implementation
  28. // is used in I2Cdev.h
  29. #include "Wire.h"

  30. // I2Cdev and MPU6050 must be installed as libraries, or else the .cpp/.h files
  31. // for both classes must be in the include path of your project
  32. #include "I2Cdev.h"
  33. #include "MPU6050_6Axis_MotionApps20.h"
  34. // class default I2C address is 0x68
  35. // specific I2C addresses may be passed as a parameter here
  36. // AD0 low = 0x68 (default for InvenSense evaluation board)
  37. // AD0 high = 0x69
  38. MPU6050 mpu;


  39. #define LED_PIN 13
  40. bool blinkState = false;

  41. bool dmpReady = false; // set true if DMP init was successful
  42. uint8_t mpuIntStatus; // holds actual interrupt status byte from MPU
  43. uint8_t devStatus; // return status after each device operation (0 = success, !0 = error)
  44. uint16_t packetSize; // expected DMP packet size (default is 42 bytes)
  45. uint16_t fifoCount; // count of all bytes currently in FIFO
  46. uint8_t fifoBuffer[64]; // FIFO storage buffer
  47. int16_t ax, ay, az;
  48. int16_t gx, gy, gz;
  49. int8_t offset_x, offset_y, offset_z;


  50. // orientation/motion vars
  51. Quaternion q; // [w, x, y, z] quaternion container
  52. VectorInt16 aa; // [x, y, z] accel sensor measurements
  53. VectorInt16 aaReal; // [x, y, z] gravity-free accel sensor measurements
  54. VectorInt16 aaWorld; // [x, y, z] world-frame accel sensor measurements
  55. VectorFloat gravity; // [x, y, z] gravity vector
  56. float euler[3]; // [psi, theta, phi] Euler angle container
  57. float ypr[3]; // [yaw, pitch, roll] yaw/pitch/roll container and gravity vector

  58. // ================================================================
  59. // === INTERRUPT DETECTION ROUTINE ===
  60. // ================================================================

  61. volatile bool mpuInterrupt = false; // indicates whether MPU interrupt pin has gone high
  62. void dmpDataReady() {
  63.     mpuInterrupt = true;
  64. }



  65. // ================================================================
  66. // === INITIAL SETUP ===
  67. // ================================================================

  68. void setup() {
  69.     // join I2C bus (I2Cdev library doesn't do this automatically)
  70.     Wire.begin();

  71.     // initialize serial communication
  72.     // (38400 chosen because it works as well at 8MHz as it does at 16MHz, but
  73.     // it's really up to you depending on your project)
  74.     Serial.begin(9600);
  75.     while (!Serial); // wait for Leonardo enumeration, others continue immediately

  76.     // NOTE: 8MHz or slower host processors, like the Teensy @ 3.3v or Ardunio
  77.     // Pro Mini running at 3.3v, cannot handle this baud rate reliably due to
  78.     // the baud timing being too misaligned with processor ticks. You must use
  79.     // 38400 or slower in these cases, or use some kind of external separate
  80.     // crystal solution for the UART timer.
  81.     // initialize device
  82.     Serial.println("Initializing I2C devices...");
  83.     mpu.initialize();

  84.     // verify connection
  85.     Serial.println("Testing device connections...");
  86.     Serial.println(mpu.testConnection() ? "MPU6050 connection successful" : "MPU6050 connection failed");


  87.     //mpu.setXGyroOffset(6);mpu.setYGyroOffset(-2);
  88.     //mpu.setZGyroOffset(0);
  89.    
  90.     /*Serial.print("Offset:\t");
  91.     Serial.print(mpu.getXAccelOffset()); Serial.print("\t");
  92.     Serial.print(mpu.getYAccelOffset()); Serial.print("\t");
  93.     Serial.print(mpu.getZAccelOffset()); Serial.print("\t");
  94.     Serial.print(mpu.getXGyroOffset()); Serial.print("\t");
  95.     Serial.print(mpu.getYGyroOffset()); Serial.print("\t");
  96.     Serial.println(mpu.getZGyroOffset());
  97.     Serial.print("Gain:\t");
  98.     Serial.print(mpu.getXFineGain()); Serial.print("\t");
  99.     Serial.print(mpu.getYFineGain()); Serial.print("\t");
  100.     Serial.println(mpu.getZFineGain());// Serial.print("\t");
  101.     */   


  102.     mpu.setFullScaleGyroRange(3);
  103.     mpu.setFullScaleAccelRange(3);
  104.    
  105.     mpu.setDLPFMode(6);
  106.     mpu.setDHPFMode(1);
  107.         
  108.     // load and configure the DMP
  109.     Serial.println("Initializing DMP...");
  110.     devStatus = mpu.dmpInitialize();
  111.    
  112.     // make sure it worked (returns 0 if so)
  113.     if (devStatus == 0) {
  114.         // turn on the DMP, now that it's ready
  115.         Serial.println("Enabling DMP...");
  116.         mpu.setDMPEnabled(true);

  117.         // enable Arduino interrupt detection
  118.         Serial.println("Enabling interrupt detection (Arduino external interrupt 0)...");
  119.         attachInterrupt(0, dmpDataReady, RISING);
  120.         mpuIntStatus = mpu.getIntStatus();

  121.         // set our DMP Ready flag so the main loop() function knows it's okay to use it
  122.         Serial.println("DMP ready! Waiting for first interrupt...");
  123.         dmpReady = true;

  124.         // get expected DMP packet size for later comparison
  125.         packetSize = mpu.dmpGetFIFOPacketSize();
  126.     } else {
  127.         // ERROR!
  128.         // 1 = initial memory load failed
  129.         // 2 = DMP configuration updates failed
  130.         // (if it's going to break, usually the code will be 1)
  131.         Serial.print("DMP Initialization failed (code ");
  132.         Serial.print(devStatus);
  133.         Serial.println(")");
  134.     }

  135.         
  136.     // configure Arduino LED for
  137.     pinMode(LED_PIN, OUTPUT);
  138. }

  139. void loop() {
  140.   
  141.     // if programming failed, don't try to do anything
  142.     if (!dmpReady) return;

  143.     // wait for MPU interrupt or extra packet(s) available
  144.     if (!mpuInterrupt && fifoCount < packetSize) return;

  145.     // reset interrupt flag and get INT_STATUS byte
  146.     mpuInterrupt = false;
  147.     mpuIntStatus = mpu.getIntStatus();

  148.     // get current FIFO count
  149.     fifoCount = mpu.getFIFOCount();

  150.     // check for overflow (this should never happen unless our code is too inefficient)
  151.     if ((mpuIntStatus & 0x10) || fifoCount == 1024) {
  152.         // reset so we can continue cleanly
  153.         mpu.resetFIFO();
  154.         Serial.println(F("FIFO overflow!"));

  155.     // otherwise, check for DMP data ready interrupt (this should happen frequently)
  156.     } else if (mpuIntStatus & 0x02) {
  157.         // wait for correct available data length, should be a VERY short wait
  158.         while (fifoCount < packetSize) fifoCount = mpu.getFIFOCount();

  159.         // read a packet from FIFO
  160.         mpu.getFIFOBytes(fifoBuffer, packetSize);
  161.         
  162.         // track FIFO count here in case there is > 1 packet available
  163.         // (this lets us immediately read more without waiting for an interrupt)
  164.         fifoCount -= packetSize;
  165.    
  166.             /*display Euler angles in degrees
  167.             通过欧拉角度显示偏航*/
  168.             mpu.dmpGetQuaternion(&q, fifoBuffer);
  169.             mpu.dmpGetGravity(&gravity, &q);
  170.             mpu.dmpGetYawPitchRoll(ypr, &q, &gravity);
  171.             Serial.print("ypr\t");
  172.             Serial.print(ypr[0] * 180/M_PI);
  173.             Serial.print("\t");
  174.             Serial.print(ypr[1] * 180/M_PI);
  175.             Serial.print("\t");
  176.             Serial.println(ypr[2] * 180/M_PI);


  177.     // read raw accel/gyro measurements from device
  178.     //mpu.getMotion6(&ax, &ay, &az, &gx, &gy, &gz);

  179.     // these methods (and a few others) are also available
  180.     //accelgyro.getAcceleration(&ax, &ay, &az);
  181.     //accelgyro.getRotation(&gx, &gy, &gz);
  182.       
  183.     // display tab-separated accel/gyro x/y/z values
  184.     //Serial.print("a/g:\t");
  185.     /*Serial.print(ax); Serial.print(",");
  186.     Serial.print(ay); Serial.print(",");
  187.     Serial.print(az); Serial.print(",");
  188.     Serial.print(gx); Serial.print(",");
  189.     Serial.print(gy); Serial.print(",");
  190.     Serial.println(gz);*/

  191.     // blink LED to indicate activity
  192.     blinkState = !blinkState;
  193.     digitalWrite(LED_PIN, blinkState);
  194.    }
  195. }
复制代码

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
回复

使用道具 举报

发表于 2013-4-3 16:07:18 | 显示全部楼层
解决了吗?我也遇到同样的问题
回复 支持 反对

使用道具 举报

发表于 2013-5-4 17:24:10 | 显示全部楼层
遇到同样的问题了  有人解决了么?
回复 支持 反对

使用道具 举报

发表于 2013-5-8 23:32:10 | 显示全部楼层
同样的问题,如果添加delay,300ms就可以,但是不理解。这样速率太慢了。
回复 支持 反对

使用道具 举报

发表于 2013-5-9 15:36:42 | 显示全部楼层
采集回来,自己编程
回复 支持 反对

使用道具 举报

发表于 2013-5-11 21:33:21 | 显示全部楼层
我的6050工作一会就停止发送数据了,楼主你碰到这个情况了吗
回复 支持 反对

使用道具 举报

发表于 2014-10-23 10:58:59 | 显示全部楼层
电机运行了吗?可能是电机产生的干扰造成的
回复 支持 反对

使用道具 举报

发表于 2014-10-23 11:00:27 | 显示全部楼层
mebelove 发表于 2013-5-8 23:32
同样的问题,如果添加delay,300ms就可以,但是不理解。这样速率太慢了。

请问,你的delay(300)加在什么地方就好了?
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

Archiver|联系我们|极客工坊

GMT+8, 2026-6-15 09:49 , Processed in 0.053353 second(s), 25 queries .

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表