Paso 4: El MPU6050 3 ejes giroscopio y acelerómetro
Lo que necesitamos es una señal proporcional al ángulo de la inclinación - que es el eje Y en el software y este giro cuando está sentado plano. Una vez más no recomiendo saltar justo a la solución final tengo, prueba primero el giro por cuenta propia y ver en el puerto serie cuál es el ángulo que se incline hacia adelante y hacia atrás (con sin motor). por lo que necesitará utilizar el programa desde este enlace de Jeff Rowberg que escribió el software del controlador
https://github.com/jrowberg/i2cdevlib/BLOB/Master/...
También necesitará utilizar su biblioteca (mismo enlace). Si su programa no se compila luego no tienes su biblioteca
i2cdevlib instalado en el Arduino. Lo puede descargar de este indestructible
Cuando se ejecuta el programa de prueba puede muy bien se que cuando el péndulo está en vertical de 90 grados que el ángulo es compensado por decir nada hasta +/-10 grados! Esto varía de dispositivo a dispositivo (soy llevado a creer) y es por qué puse una maceta de adorno en el diseño final.
El cableado del giroscopio MPU6050 es sencillo
Conectar a VCC y Gnd a 3,3 v y tierra de Arduino (no 5V!)
conectar el pin Int (interrupción) al Pin 2 de Arduino
conecta SCL y XDA al mismo el correspondiente rotulado pins en Arduino. Esto es para el bus i2c.
Los otros pines no se usan.
Montara el giro en una pieza pequeña de plástico mediante dos tornillos pequeños (son ya perforado los agujeros en el dispositivo por supuesto). Luego utilicé una pistola de pegamento para pegar el conjunto al chasis de la rueda. Este es el programa de prueba para el giro. No los motores de potencia, sólo lo uso para probar. Usar al serial monitor en Arduino para ver salidas del girocompás.
------------------------------------------------------------------------------------------------------------------
Demostración de clase (I2Cdev) dispositivo I2C Arduino sketch para la clase MPU6050 utilizando DMP (MotionApps v2.0)
21/06/2012 por Jeff Rowberg
Actualizaciones (con suerte) siempre deben estar disponibles en https://github.com/jrowberg/i2cdevlib
Changelog:
2013-05-08 - añadido soporte de Fastwire transparente
-Añadida Nota sobre calibración de girocompás
2012-06-21 - añade Nota sobre Arduino 1.0.1 + error de compatibilidad de Leonardo
2012-06-20 - desbordamiento de FIFO mejor manipulación y simplificado el proceso de leer
2012-06-19 - código de inicialización de DMP totalmente cambiados y la simplificación
2012-06-13 - extraer datos de giro y aceleración del paquete de FIFO en lugar de leer directamente
2012-06-09 - roto FIFO de lectura secuencia de fijar y cambiar interrupción detección a levantamiento
2012-06-05 - añadir salida de aceleración de marco de referencia inicial de compensación de gravedad
-Añadir archivo auxiliar de matemáticas 3D dibujo de ejemplo de DMP6
-Añadir Euler de salida y formatos de salida de desvío/Pitch/Roll
2012-06-04 - eliminar offset accel para mejores resultados (gracias Sungon Lee)
2012-06-01 - sensibilidad de giro fijo a 2000 grados/seg en vez de 250
2012-05-30 - básico trabajo de inicialización de DMP
/* ============================================
Código de la biblioteca de I2Cdev dispositivo se coloca bajo la licencia MIT
Copyright (c) 2012 Jeff Rowberg
Permiso por este medio es concedido, de forma gratuita, a cualquier persona obtener una copia
de este software y archivos de documentación asociados (el "Software"), para tratar
en el Software sin restricción, incluyendo sin limitación los derechos
para utilizar, copiar, modificar, fusionar, publicar, distribuir, sublicenciar, y/o vender
copias del Software y permitir que las personas a las que el Software es
equipado para ello, conforme a las siguientes condiciones:
El aviso de copyright y este aviso de permiso se incluirá en
todas las copias o partes importantes del Software.
EL SOFTWARE SE PROPORCIONA "TAL CUAL", SIN GARANTÍA DE NINGÚN TIPO, EXPRESA O
IMPLÍCITA, INCLUYENDO PERO SIN LIMITARSE A, LAS GARANTÍAS DE COMERCIABILIDAD,
APTITUD PARA UN PROPÓSITO PARTICULAR Y NO INFRACCIÓN. EN NINGÚN CASO, LA
AUTORES O LOS TITULARES DEL COPYRIGHT SERÁN RESPONSABLES DE CUALQUIER RECLAMACIÓN, DAÑOS U OTROS
RESPONSABILIDAD, YA SEA EN UNA ACCIÓN DE RESPONSABILIDAD CONTRACTUAL, EXTRACONTRACTUAL O DE OTRO TIPO, QUE SE PRESENTA,
DE O EN RELACIÓN CON EL SOFTWARE O EL USO U OTRAS OPERACIONES EN
EL SOFTWARE.
===============================================
*
/ I2Cdev y MPU6050 deben instalarse como bibliotecas, o de lo contrario los archivos .cpp/.h
para ambas clases deben estar en el camino de la inclusión de su proyecto
#include "I2Cdev.h"
#include "MPU6050_6Axis_MotionApps20.h"
#include "MPU6050.h" / / no es necesario si utiliza MotionApps incluir archivo
Biblioteca de Arduino alambre es necesario si I2Cdev I2CDEV_ARDUINO_WIRE implementación
se utiliza en I2Cdev.h
#if I2CDEV_IMPLEMENTATION == I2CDEV_ARDUINO_WIRE
#include "Wire.h"
#endif
Dirección I2C de clase por defecto es 0x68
determinadas direcciones I2C pueden ser pasados como parámetro de aquí
AD0 baja = 0x68 (valor predeterminado de breakout de SparkFun y Comité de evaluación de InvenSense)
AD0 alta = 0x69
MPU6050 mpu;
Mpu(0x69) de MPU6050; <-uso de AD0 alta
/* =========================================================================
Nota: además de conexión 3, 3V, GND, SDA y SCL, este sketch
depende en el pin INT de la MPU-6050 conectar el Arduino
pin de interrupción externa 0 #. En el Arduino Uno y Mega 2560, este es
pin de I/O digital 2.
* ========================================================================= *
* =========================================================================
Nota: V1.0.1 Arduino con la Junta de Leonardo genera un error de compilación
Cuando se utiliza el Serial.write (buf, len). La salida de la tetera utiliza este método.
La solución requiere una modificación en el archivo Arduino USBAPI.h, que
es afortunadamente simple pero molesto. Esto se solucionará en el IDE de la siguiente
lanzamiento. Para obtener más información, vea estos enlaces:
http://Arduino.CC/Forum/index.php/Topic, 109987.0.h...
http://code.Google.com/p/Arduino/issues/detail?id=...
* ========================================================================= */
Quite el comentario de "OUTPUT_READABLE_QUATERNION" Si quieres ver el real
formato de componentes en [w, x, y, z] cuaternión (no el mejor para analizar
en un remoto host como el procesamiento o algo aunque)
#define OUTPUT_READABLE_QUATERNION
Quite el comentario de "OUTPUT_READABLE_EULER" Si desea ver los ángulos de Euler
(en grados) calculan a partir de los quaternions de la FIFO.
Tenga en cuenta que los ángulos de Euler sufren de cerradura del cardán (para más información, consulte
http://en.wikipedia.org/wiki/Gimbal_lock)
#define OUTPUT_READABLE_EULER
Quite el comentario de "OUTPUT_READABLE_YAWPITCHROLL" Si usted quiere ver el desvío
/ pitch/roll ángulos (en grados) calculados a partir de los cuaterniones que viene
de la FIFO. Nota que esto también requiere cálculos del vector de gravedad.
También nota que los ángulos de guiñada/pitch/roll de cerradura del cardán (para
más información, ver: http://en.wikipedia.org/wiki/Gimbal_lock)
#define OUTPUT_READABLE_YAWPITCHROLL
Quite el comentario de "OUTPUT_READABLE_REALACCEL" Si usted quiere ver aceleración
eliminar componentes con gravedad. Este marco de referencia de aceleración es
no compensa para la orientación, por lo tanto + X siempre es + X de acuerdo a la
sensor, simplemente sin los efectos de la gravedad. Si quieres aceleración
compensación para la orientación, nos OUTPUT_READABLE_WORLDACCEL en su lugar.
#define OUTPUT_READABLE_REALACCEL
Quite el comentario de "OUTPUT_READABLE_WORLDACCEL" Si usted quiere ver aceleración
componentes con gravedad quitan y ajustado para el marco mundial de
Referencia (desvío está en relación con la orientación inicial, puesto que ningún magnetómetro
está presente en este caso). Podría ser muy útil en algunos casos.
#define OUTPUT_READABLE_WORLDACCEL
Quite el comentario de "OUTPUT_TEAPOT" Si quieres salida que coincide con la
formato utilizado para la demostración de la tetera de InvenSense
#define OUTPUT_TEAPOT
#define LED_PIN 13 / / (Arduino es 13, Teensy es 11, Teensy ++ es 6)
bool blinkState = false;
Vars de control estado MPU
bool dmpReady = false; sistema true si init DMP fue exitosa
mpuIntStatus de uint8_t; contiene el byte de estado de interrupción real de la MPU
devStatus de uint8_t; volver estado después de cada operación de dispositivo (0 = éxito,! 0 = error)
packetSize uint16_t; espera que el tamaño del paquete de DMP (por defecto es de 42 bytes)
fifoCount de uint16_t; cuenta de bytes todos actualmente en FIFO
fifoBuffer de uint8_t [64]; Buffer de almacenamiento FIFO
orientación del movimiento vars
Cuaternión q; [w, x, y, z] contenedor cuaternión
VectorInt16 aa; [x, y, z] medidas de sensor de aceleración
VectorInt16 aaReal; [x, y, z] medidas de sensor de aceleración de gravedad-libre
AaWorld de VectorInt16; [x, y, z] medidas de sensor de accel world-marco
VectorFloat de gravedad; [x, y, z] vector de gravedad
flotador de euler [3]; [psi, theta, phi] contenedor de ángulo de Euler
flotador ypr [3]; [yaw, pitch, roll] vector contenedor y la gravedad del desvío/pitch/roll
estructura de paquetes para demo de InvenSense tetera
teapotPacket de uint8_t [14] = {'$', 0 x 02, 0.0, 0.0, 0.0, 0.0, 0 x 00, 0 x 00, '\r', '\n'};
// ================================================================
=== RUTINA DE DETECCIÓN DE INTERRUPCIÓN DE ===
// ================================================================
volátiles bool mpuInterrupt = false; indica si el pin de interrupción MPU ha ido alta
void dmpDataReady() {}
mpuInterrupt = true;
}
// ================================================================
=== CONFIGURACIÓN INICIAL ===
// ================================================================
void setup() {}
Únete a bus I2C (I2Cdev biblioteca no esta automáticamente)
#if I2CDEV_IMPLEMENTATION == I2CDEV_ARDUINO_WIRE
Wire.Begin();
TWBR = 24; reloj de I2C 400KHz (200kHz si el CPU es de 8MHz)
#elif I2CDEV_IMPLEMENTATION == I2CDEV_BUILTIN_FASTWIRE
Fastwire::Setup (400, true);
#endif
inicializar la comunicación serial
(115200 elegido porque se requiere para la salida de la Demo de tetera, pero tiene
realmente depende de ti dependiendo de tu proyecto)
Serial.Begin(115200);
mientras (!. Serie); esperar para la enumeración de Leonardo, otros siguen inmediatamente
Nota: 8MHz o procesadores del host más lento, como el Teensy a 3.3v o Ardunio
Mini Pro funciona a 3.3v, no puede manejar esta velocidad confiablemente debido a
la sincronización de velocidad siendo demasiado desalineada con garrapatas de procesador. Se debe utilizar
38400 o más lenta en estos casos, o utilizar algún tipo de externo se separa
solución de cristal para el temporizador de la UART.
inicializar el dispositivo
Serial.println (F ("inicializar I2C dispositivos..."));
MPU.Initialize();
verificar conexión
Serial.println (F ("prueba dispositivo conexiones..."));
¿Serial.println(MPU.testconnection()? F("MPU6050 Connection successful"): F ("MPU6050 fallada la conexión"));
Espere listo
Serial.println (F ("\nSend de cualquier carácter para iniciar programación DMP y demo:"));
mientras que (Serial.available() & & Serial.read()); buffer vacío
mientras (!. Serial.Available()); esperar a que los datos
mientras que (Serial.available() & & Serial.read()); búfer vacío otra vez
cargar y configurar la DMP
Serial.println (F ("inicializar DMP..."));
devStatus = mpu.dmpInitialize();
fuente de su propio giro desplaza aquí, escala mínima sensibilidad
mpu.setXGyroOffset(220);
mpu.setYGyroOffset(76);
mpu.setZGyroOffset(-85);
mpu.setZAccelOffset(1788); 1688 de fábrica para mi chip de prueba
Asegúrese de que funcionaba (devuelve 0 si es así)
Si (devStatus == 0) {}
Encienda el DMP, ahora que está listo
Serial.println (F ("habilitar DMP..."));
mpu.setDMPEnabled(true);
habilitar la detección de interrupción de Arduino
Serial.println (F ("habilitar interrupción detección (interrupción externa 0 de Arduino)..."));
attachInterrupt (0, dmpDataReady, RISING);
mpuIntStatus = mpu.getIntStatus();
establecer nuestra bandera DMP listo para que la función loop() principal sepa que está bien usarlo
Serial.println (F ("DMP listo! Esperando primera interrupción..."));
dmpReady = true;
Haz esperado tamaño de paquete DMP para posterior comparación
packetSize = mpu.dmpGetFIFOPacketSize();
} else {}
¡ ERROR!
1 = carga inicial de la memoria no se pudo
2 = actualizaciones de configuración DMP no pudiera
(si se va a romper, generalmente el código será 1)
Serial.Print (F ("error de inicialización de DMP (código"));
Serial.Print(devStatus);
Serial.println(F(")"));
}
configurar el LED de salida
pinMode (LED_PIN, salida);
}
// ================================================================
=== PRINCIPALES PROGRAMA LOOP ===
// ================================================================
void loop() {}
Si no de programación, no intente hacer nada
Si (! dmpReady) volver;
espera interrupción MPU o paquetes adicionales disponibles
mientras (! mpuInterrupt & & fifoCount < packetSize) {}
otras cosas del comportamiento del programa aquí
// .
// .
// .
Si eres muy paranoico con frecuencia puede probar entre otros
cosas para ver si mpuInterrupt es true y si es así, "break;" de la
bucle while() procesar inmediatamente los datos de la MPU
// .
// .
// .
}
Bandera de interrupción de RESET y conseguir byte INT_STATUS
mpuInterrupt = false;
mpuIntStatus = mpu.getIntStatus();
Haz recuento actual de FIFO
fifoCount = mpu.getFIFOCount();
verificación de desbordamiento (esto nunca ocurre a menos que nuestro código es demasiado ineficiente)
Si ((mpuIntStatus & 0x10) || fifoCount == 1024) {}
reiniciar para que podamos seguir limpiamente
mpu.resetFIFO();
Serial.println (F ("desbordamiento de la FIFO!"));
en caso contrario, Compruebe la interrupción listo datos de DMP (esto ocurre con frecuencia)
} else if (mpuIntStatus & 0 x 02) {}
espere para la longitud correcta de los datos disponibles, debe ser muy breve espera
mientras que (fifoCount < packetSize) fifoCount = mpu.getFIFOCount();
leer un paquete de FIFO
mpu.getFIFOBytes (fifoBuffer, packetSize);
pista aquí cuenta de FIFO en caso de que se dispone de > 1 paquete
(esto nos permite más inmediatamente sin esperar una interrupción)
fifoCount = packetSize;
#ifdef OUTPUT_READABLE_QUATERNION
Mostrar los valores cuaternión en forma fácil matriz: w x y z
mpu.dmpGetQuaternion (& q, fifoBuffer);
Serial.Print("quat\t");
Serial.Print(q.w);
Serial.Print("\t");
Serial.Print(q.x);
Serial.Print("\t");
Serial.Print(q.y);
Serial.Print("\t");
Serial.println(q.z);
#endif
#ifdef OUTPUT_READABLE_EULER
Mostrar ángulos de Euler en grados
mpu.dmpGetQuaternion (& q, fifoBuffer);
mpu.dmpGetEuler (euler & q);
Serial.Print("euler\t");
Serial.Print (euler [0] * 180/constantio);
Serial.Print("\t");
Serial.Print (euler [1] * 180/constantio);
Serial.Print("\t");
Serial.println (euler [2] * 180/constantio);
#endif
#ifdef OUTPUT_READABLE_YAWPITCHROLL
Mostrar ángulos de Euler en grados
mpu.dmpGetQuaternion (& q, fifoBuffer);
mpu.dmpGetGravity (gravedad & q);
mpu.dmpGetYawPitchRoll (ypr & q y gravedad);
Serial.Print("ypr\t")
Serial.Print (ypr [0] * 180/constantio);
Serial.Print("\t");
/////////////////////////////////////////////////////////////////////////////////////////
/ Este es el giro Ángulo ypr [1], utilizamos este otro para la cesta de péndulo y convertir a grados en la línea de abajo.
Asegúrese de que obtener cerca de cero cuando el carro es vertical.b n
Serial.Print (ypr [1] * 180/constantio);
Serial.Print("\t");
//////////////////////////////////////////////////////////////////////////////////////////////////////////
Serial.println (ypr [2] * 180/constantio);
#endif
#ifdef OUTPUT_READABLE_REALACCEL
Mostrar la aceleración real, ajustada para quitar gravedad
mpu.dmpGetQuaternion (& q, fifoBuffer);
mpu.dmpGetAccel (& aa, fifoBuffer);
mpu.dmpGetGravity (gravedad & q);
mpu.dmpGetLinearAccel (& aaReal, & aa & gravedad);
Serial.Print("areal\t");
Serial.Print(aaReal.x);
Serial.Print("\t");
Serial.Print(aaReal.y);
Serial.Print("\t");
Serial.println(aaReal.z);
#endif
#ifdef OUTPUT_READABLE_WORLDACCEL
Mostrar la aceleración inicial del mundo marco, ajustada para quitar gravedad
y rotados en base a conocido orientación del cuaternión
mpu.dmpGetQuaternion (& q, fifoBuffer);
mpu.dmpGetAccel (& aa, fifoBuffer);
mpu.dmpGetGravity (gravedad & q);
mpu.dmpGetLinearAccel (& aaReal, & aa & gravedad);
mpu.dmpGetLinearAccelInWorld (& aaWorld & aaReal, & q);
Serial.Print("aworld\t");
Serial.Print(aaWorld.x);
Serial.Print("\t");
Serial.Print(aaWorld.y);
Serial.Print("\t");
Serial.println(aaWorld.z);
#endif
#ifdef OUTPUT_TEAPOT
Mostrar los valores cuaternión en formato demo de InvenSense tetera:
teapotPacket [2] = fifoBuffer [0];
teapotPacket [3] = fifoBuffer [1];
teapotPacket [4] = fifoBuffer [4];
teapotPacket [5] = fifoBuffer [5];
teapotPacket [6] = fifoBuffer [8];
teapotPacket [7] = fifoBuffer [9];
teapotPacket [8] = fifoBuffer [12];
teapotPacket [9] = fifoBuffer [13];
Serial.Write (teapotPacket, 14);
teapotPacket [11] ++; packetCount, bucles en 0xFF a propósito
#endif
parpadear el LED para indicar la actividad
blinkState =! blinkState;
digitalWrite (LED_PIN, blinkState);
}
}