Tengo una placa 9DOF en la que e cargado el software AHRS y quiero transmitir esos datos al arduino uno por el puerto serie pero no consigo escribir correctamente el programa. Alguien me puede ayudar?
Hola sergimk.
Tal vez te sirva la información de mi blog si lo que tienes es la 9DOF Razor de Sparkfun de lo que no tengo total seguridad ya que no concretas.
Hay varias entradas, léelas todas pero imagino que te servirán los códigos publicados en la Parte 2.
Increíble de verdad muchísimas gracias!!!! me es de gran ayuda de verdad, no se como no encontré tu blog antes.
Me gustaria felicitarte por el trabajo que estas haciendo me parece genial!!!
He intentado probar el código que sugieres en el parte 3 del 9DOF razor pero cuando lo intento verificar el interprete de arduino me da error me dice que 'Read_Gyro' was not declared in this scope
Gracias, me alegro de que te guste y sea de ayuda mi blog.
El error lo estás teniendo porque sólo estás abriendo en el IDE el archivo "Razor_AHRS_v2_0.ino". Al hacer la descarga desde mi blog te descarga un archivo zip. Al descomprimirlo tienes una carpeta con varios archivos. Tienes que ejecutar el archivo "Razor_AHRS_v2_0.ino" desde esa carpeta y sin quitar ninguno de los archivos restantes. Así al abrirlo en el IDE verás todos los archivos cargados en solapas y te compilará bien.
Ya, ya me di cuenta pero al abrir la carpeta segia sin funcionar, no lo podía solucionar así que tuve que reinstalar el programa de ardino y ya esta se soluciono no se que pasaría
De todas maneras muchas gracias, y el programa va genial
Ahora lo que me gustaría hacer es que el arduino mueva un servo en función del valor de uno de los ejes del razor, algo parecido a esto: Servo que gira según un ángulo de Tait-Bryan - YouTube
Si lo preguntas así sin más eso suena a que ni lo has intentado o es que ni sabes por dónde empezar.
Si es lo primero te sugiero que pruebes tú mismo y luego preguntes lo que te falla.
Si es lo segundo te sugiero que practiques y estudies con los ejemplos del IDE, sigas con búsquedas en Google y termines intentándolo para volver aquí a preguntar dónde tropiezas o qué es lo que no te sale.
No era ninguna pregunta simplemente comentaba cual seria mi siguiente paso pero efectivamente no tengo ni idea de como hacerlo así que ya iré investigando
Es sencillo. Mapeas los datos para establecer el ángulo de giro del servo según la lectura del ángulo del IMU.
De acuerdo entonces si por ejemplo quiero mover el servo respecto a la lectura del yaw tengo que mapear los datos después de la lectura del yaw, que seria aquí no?
#include <Servo.h>
Servo servo;
unsigned long TiempoControl1 = 0;
unsigned long TiempoControl2 = 0;byte Trama[17];
boolean Error9DOF = false;
boolean Signoroll = true;
boolean Signopitch = true;
boolean Signoyaw = true;
int roll = 0;
int pitch = 0;
int yaw = 0;
boolean SignoAccelX = true;
boolean SignoAccelY = true;
boolean SignoAccelZ = true;
int AccelX = 0;
int AccelY = 0;
int AccelZ = 0;void setup() {
servo.attach(9);
}
void loop() {
if (Serial.available() > 16) {
while (Serial.available() > 16) {
Trama[0] = Serial.read();if (Trama[0] = '!' && Serial.available() > 15) {
for (int i=1; i < 17; i++) {
Trama = Serial.read();
}*
if (Trama[15] == '\r' && Trama[16] == '\n') {*
Error9DOF = false;*
}*
else {*
Error9DOF = true;*
}*
}*
}if (Error9DOF == false)*
if (Trama[1] == 111 || Trama[1] == 101 || Trama[1] == 11 || Trama[1] == 1 ) {*
Signoyaw = true;*
}*
else {*
Signoyaw =false;*
}*
if (Signoyaw == true) {*
yaw = word(Trama[6],Trama[7]);*
}*
else {*
yaw = - word(Trama[6],Trama[7]);*
}*
AQUI [/quote]
Lo que no se entre que valores estan los datos que da el gyro ni que escribir pare indicar la lectura del yaw
Sí, ahí sería.
Este código no envía los datos del gyro. Envía los ángulos roll, pitch y yaw y los valores del acelerómetro.
Sobre los valores de roll, pitch y yaw si lees todo el código verás que aunque poco voy escribiendo alguna explicación. En algún sitio indico que los valores los envío en centésimas de grado. Es decir, si un ángulo real es 124,56 grados, la correspondiente variable te estará dando el valor 12456. Así optimizo el tiempo de envío por puerto serie.
pues nada sigo atascado en el mismo punto, algún consejo??
¿En qué punto exactamente estás atascado?
¿Has intentado hacer algo de lo que te indiqué? ¿Cuál es el código que te quedó y que no hace lo que tú quieres? Si no hace lo que tú quieres, ¿qué es lo que te hace?
Pues el problema lo tengo con el programa que no consigo ni que sea correcto y se me carge en el arduino
No tengo muy claro como e de mapear
El codigo que me queda es el mismo de antes solo que intento añadirle lo de mapear los datos y no me funciona
-
¿Qué códido es el que intentas cargar y no lo hace? ¿Qué errores te da al intentarlo?
-
¿Cómo estás haciendo el mapeo y cómo sabes que no te funciona si ni siquiera has conseguido cargarlo?
Haber es que no tengo ni idea de como hacerlo y e estado buscando mucho y no hay manera...
El codigo que tengo es:
#include <Servo.h>
Servo servo;
unsigned long TiempoControl1 = 0;
unsigned long TiempoControl2 = 0;byte Trama[17];
boolean Error9DOF = false;
boolean Signoroll = true;
boolean Signopitch = true;
boolean Signoyaw = true;
int roll = 0;
int pitch = 0;
int yaw = 0;
boolean SignoAccelX = true;
boolean SignoAccelY = true;
boolean SignoAccelZ = true;
int AccelX = 0;
int AccelY = 0;
int AccelZ = 0;void setup() {
servo.attach(9);
}
void loop() {
if (Serial.available() > 16) {
while (Serial.available() > 16) {
Trama[0] = Serial.read();if (Trama[0] = '!' && Serial.available() > 15) {
for (int i=1; i < 17; i++) {
Trama = Serial.read();
}if (Trama[15] == '\r' && Trama[16] == '\n') {
Error9DOF = false;
}
else {
Error9DOF = true;
}}
}
if (Error9DOF == false)
if (Trama[1] == 111 || Trama[1] == 101 || Trama[1] == 11 || Trama[1] == 1 ) {
Signoyaw = true;
}
else {
Signoyaw =false;
}if (Signoyaw == true) {
yaw = word(Trama[6],Trama[7]);
}
else {
yaw = - word(Trama[6],Trama[7]);
}
Entonces para mapear la lectura del sensor tengo que indicar cual es el valor que quiero utilizar, no?
Eso es una de las cosas que no se como hacer ya para empezar
Procedimiento: pegar ese código en una ventana del IDE, click sobre el botón verificar (el del símbolo "tick") y comprobar los errores de compilación que informa en la parte inferior de la ventana. Ir leyendo uno a uno los errores, entenderlos e intentar solucionarlos.
Errores que marca:
- En la línea 40: incompatible types of "int" to "byte [17]"
Efectivamente, es la línea
Trama = Serial.read();
Estás asignando una variable "Trama" que por defecto es int para leer del puerto serie que lo que entran son bytes. La variable creada como byte es un array por lo que te has dejado de poner la posición dentro del array. En el código original que te dije de descargar sí está, cambiarías cosas y lo borrarías. Resumiendo la instrucción a poner es:
Trama [i] = Serial.read();
- Dos errores iguales en la línea 74: expected "}" at end of input.
Es decir, que faltan dos símbolos "}" de poner al final. Efectivamente, no has cerrado las llaves correspondientes a las aperturas de "void loop() {" y "if (Serial.available() > 16) {"
Aunque no marca error también veo que te has dejado de activar el puerto serie. En void setup() hay que poner Serial.begin(57600); ya que al menos en mi código original en el Razor la velocidad que puse en el código era 57600 bps.
Con estas pocas cosas el código queda:
#include <Servo.h>
Servo servo;
unsigned long TiempoControl1 = 0;
unsigned long TiempoControl2 = 0;
byte Trama[17];
boolean Error9DOF = false;
boolean Signoroll = true;
boolean Signopitch = true;
boolean Signoyaw = true;
int roll = 0;
int pitch = 0;
int yaw = 0;
boolean SignoAccelX = true;
boolean SignoAccelY = true;
boolean SignoAccelZ = true;
int AccelX = 0;
int AccelY = 0;
int AccelZ = 0;
void setup() {
Serial.begin(57600);
servo.attach(9);
}
void loop() {
if (Serial.available() > 16) {
while (Serial.available() > 16) {
Trama[0] = Serial.read();
if (Trama[0] = '!' && Serial.available() > 15) {
for (int i=1; i < 17; i++) {
Trama [i] = Serial.read();
}
if (Trama[15] == '\r' && Trama[16] == '\n') {
Error9DOF = false;
}
else {
Error9DOF = true;
}
}
}
if (Error9DOF == false)
if (Trama[1] == 111 || Trama[1] == 101 || Trama[1] == 11 || Trama[1] == 1 ) {
Signoyaw = true;
}
else {
Signoyaw =false;
}
if (Signoyaw == true) {
yaw = word(Trama[6],Trama[7]);
}
else {
yaw = - word(Trama[6],Trama[7]);
}
}
}
Compila bien, ahora hay que comprobarlo imprimiendo en la consola la variable yaw y comprobando que los valores son acordes a lo que mueves el Razor.
A continuación tienes tu valor yaw y lo mapeas para el rango que quieres mover el servo.
Bueno primero de todo quiero darte las gracias por toda la ayuda que me estas dando y por coregirme los errores.
He intentado seguir con el programa que lo que quedaría sería coger el valor del yaw, leerlo, mapearlo, y escribir este nuevo valor en el servo.
Lo que yo creo que sería esto:
int yaw val = Serial.read;
val = map (val,0,17999,0,179);
servo.write(val);
delay(15);
y el código quedaría :
#include <Servo.h>
Servo servo;
unsigned long TiempoControl1 = 0;
unsigned long TiempoControl2 = 0;byte Trama[17];
boolean Error9DOF = false;
boolean Signoroll = true;
boolean Signopitch = true;
boolean Signoyaw = true;
int roll = 0;
int pitch = 0;
int yaw = 0;
boolean SignoAccelX = true;
boolean SignoAccelY = true;
boolean SignoAccelZ = true;
int AccelX = 0;
int AccelY = 0;
int AccelZ = 0;void setup() {
Serial.begin(57600);
servo.attach(9);}
void loop() {
if (Serial.available() > 16)
{while (Serial.available() > 16)
{Trama[0] = Serial.read();if (Trama[0] = '!' && Serial.available() > 15)
{for (int i=1; i < 17; i++)
{Trama = Serial.read(); }
if (Trama[15] == '\r' && Trama[16] == '\n')*
{*
Error9DOF = false;*
}*
else {*
Error9DOF = true;*
}*
}*
}if (Error9DOF == false)*
if (Trama[1] == 111 || Trama[1] == 101 || Trama[1] == 11 || Trama[1] == 1 ) {*
Signoyaw = true;*
}*
else {*
Signoyaw =false;*
}*
if (Signoyaw == true) {*
yaw = word(Trama[6],Trama[7]);*
}*
else {*
yaw = - word(Trama[6],Trama[7]);*
}*
}*
int yaw val = Serial.read;
val = map (val,0,17999,0,179);
servo.write(val);
delay(15);
} [/quote]
y no funciona me vuelve a dar error, creo que el error esta a la hora de declarar el valor del yaw
Has vuelto a poner
Trama = Serial.read();
cuando es
Trama [i]= Serial.read();
No entiendo :~ si te lo puse todo en el código. Además si lo verificas te vuelve a dar el mismo error tal y como te lo expliqué en la anterior respuesta :~
Después estás haciendo
int yaw val = Serial.read;
que tal y como te está marcando el error el pobre programa no tiene ni idea de lo que significa. La verdad que yo, aparte de estar mal, tampoco sé lo que querías hacer.
Lo que tienes que hacer es declarar por ejemplo la variable val donde se declaran todas las variables, al principio junto al resto de declaraciones.
int val = 0;
y al final, una vez que ya tienes leído desde el puerto serie el valor de yaw justamente en la variable yaw, la mapeas sobre val y la escribes en el servo.
val = map (yaw, -18000, 18000, 0, 180);
servo.write (val);
delay (15);
Además en este caso no haría falta el delay puesto que los valores nuevos de yaw se reciben cada 20 ms (si no lo has modificado en el código del Razor, que si interesa se puede modificar). Por tanto no se le mandarán posiciones distintas al servo como mínimo cada 20 ms independientemente del delay (15).
Vale supongo que quedaria así :
#include <Servo.h>
Servo servo;
unsigned long TiempoControl1 = 0;
unsigned long TiempoControl2 = 0;byte Trama[17];
boolean Error9DOF = false;
boolean Signoroll = true;
boolean Signopitch = true;
boolean Signoyaw = true;
int roll = 0;
int pitch = 0;
int yaw = 0;
boolean SignoAccelX = true;
boolean SignoAccelY = true;
boolean SignoAccelZ = true;
int AccelX = 0;
int AccelY = 0;
int AccelZ = 0;int val = 0;
void setup() {
Serial.begin(57600);
servo.attach(9);}
void loop() {
if (Serial.available() > 16) {
while (Serial.available() > 16) {
Trama[0] = Serial.read();if (Trama[0] = '!' && Serial.available() > 15) {
for (int i=1; i < 17; i++) {
Trama = Serial.read();
}*
if (Trama[15] == '\r' && Trama[16] == '\n') {*
Error9DOF = false;*
}*
else {*
Error9DOF = true;*
}*
}*
}if (Error9DOF == false)*
if (Trama[1] == 111 || Trama[1] == 101 || Trama[1] == 11 || Trama[1] == 1 ) {*
Signoyaw = true;*
}*
else {*
Signoyaw =false;*
}*
if (Signoyaw == true) {*
yaw = word(Trama[6],Trama[7]);*
}*
else {*
yaw = - word(Trama[6],Trama[7]);*
}*
}*
val = map (yaw, 0, 18000, 0, 180);
servo.write (val);
delay (15);
}[/quote]
lo único que e creído que tenia que cambiar a sido el mapeo de los datos del sensor que tu me as puesto de -18000 a 18000 y yo solo quiero que vaya de 0 a 180º
*Bueno el código ahora me lo da por bueno pero lo único que hace el servo es vibrar no modifica su posición y no entiendo porque ... *
Pues no entiendo cómo te lo puede cargar porque por enésima vez en el código que has puesto sigue sin estar corregido el Trama = Serial.read ();
Después de eso si no te funciona tendrás que ir testeando las variables imprimiéndolas en el monitor comprobando si son coherentes hasta averiguar dónde está el fallo.
Por cierto, si sólo mapeas entre 0 y 18000 tendrás que tener cuidado de no colocar el Razor en posición de un ángulo yaw negativo porque entonces le llegará a la instrucción servo un valor negativo y lógicamente no lo admite. Comprueba no te esté pasando ya.