Pages: [1] 2 3 ... 10   Go Down
Author Topic: Aumentar la frecuencia de muestreo (Solucionado)  (Read 19686 times)
0 Members and 1 Guest are viewing this topic.
Argentina
Offline Offline
Full Member
***
Karma: 1
Posts: 104
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Hola, soy muy nuevo en el manejo de esta increíble herramienta soy docente, he armado una barrera óptica con un viejo mouse para ser usada en un trabajo práctico de física, que consiste en calcular la velocidad de una flecha lanzada con una ballesta, lo he logrado a medias http://anajesusa.wordpress.com/2011/07/16/midiendo-la-velocidad-de-una-flecha-con-un-mouse-viejo-y-el-arduino/
Quisiera que algún experimentado me oriente para que la velocidad de muestreo sea mayor, he logrado medir hasta 2 milisegundos lo que me parece mucho, en caso de querer usar el mismo dispositivo para medir la velocidad de un balín de rifle de aire comprimido por ejemplo.
El código que usé es este:
Seguramente para Uds esto será muy rústico y con errores sepan por favor disimular
/*
Barrera de luz
*/
// to the pins used:
const int analogInPin = A0; // acá entra el cable que viene del fototransistor
int sensorValue = 0; //
//int outputValue = 0; //
unsigned long time;
void setup() {
Serial.begin(115200);
}
void loop() {
// read the analog in value:
sensorValue = analogRead(analogInPin);
// print the results to the serial monitor:
//Serial.print(“Time: “);
time = millis();
Serial.print(time);
Serial.print(” “);
Serial.println(sensorValue);
}
Saludos
César
« Last Edit: August 18, 2011, 05:14:50 pm by CesarCarlos » Logged


0
Offline Offline
Newbie
*
Karma: 0
Posts: 36
Arduino rocks
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Yo usaria una interrupcion: se activa cuando sucede algo.

En mi blog (en mi firma) tienes un ejemplo de algo similar, pues busco detectar un paso por meta.
Logged

La electrónica y el slot (o esos cochecitos)
http://www.juanjofrancia.es/arduslot

Donostia
Offline Offline
God Member
*****
Karma: 0
Posts: 740
elektronikadonbosco
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Yo el problema que veo es que menos que 2 milisegundos me resulta difícil teniendo en cuenta que la ejecución de las instrucciones necesita su tiempo. En el arduino no se cuanto tiempo necesita en ejecutar cada instrucción (tal vez salga en el datasheet), pero si es 1 milisegundo piensa que en tu bucle hay 5 instrucciones, asi que ejecutarlas te está comiendo el tiempo.
Logged

0
Offline Offline
Edison Member
*
Karma: 16
Posts: 1579
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Hola,

Para algo tan concreto, lo mejor es que te mires cómo esta programada la función analogRead() de Arduino (Wiring). La conversión creo que dura unos 13 ciclos (25 si es la primera vez), por lo que tienes que mirar a cuanto han configurado el prescaler del módulo ADC. Lo mejor es tirar del datasheet del micro + ojear la función. Si bajas la resolución del ADC, puedes aumentar bastante la velocidad.

Puedes ojear http://interface.khm.de/index.php/lab/experiments/arduino-realtime-audio-processing/, que estan haciendo tratamiento de sonido a tiempo real. Muestrean a 15 kHz.

Por otro lado, usando sensores de barrera (salida digital) e interrupciones, para el tipo de aplicación que quieres, creo que será  mucho mejor que algo analógico.


Saludos


Igor R.
« Last Edit: August 09, 2011, 04:15:54 am by Igor R » Logged


Ciudad Real
Offline Offline
God Member
*****
Karma: 1
Posts: 747
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

yo lo haría con interrupciones, y que la función de interrupción sea que almacene la variable millis() en un array o variable, estamos hablando de que el reloj va a 16 Mhz o 20 mhz, 2 mseg a esta velocidad me parece muchísimo, si lo haces como te digo la función de la interrupción no gastara mucho tiempo ( en ensamblador seria un MOV de un registro a otro )

yo utilizaría entradas digitales, las analógicas tardan mucho en hacer la conversión , además como ya he comentado en otros post las entradas analógicas están multiplexadas, solo hay un conversor analógico, cuantas mas entradas analógicas se utilicen menor será la frecuencia que puedas utilizar. además al no ser el mismo tiempo de conversión de una vez que otra ( depende del nivel de la señal) tampoco puede calcular con exactitud la diferencia de tiempos entre una señal y otra.

yo utilizaria 2 interrupciones
1º que almacene el valor de millis() en variablesensor1
2ª que almacene el valor de millis() en variablesensor2

y por display o serie o como quieras que muestre el calculo de (espacio entre sensores)/(variablesensor2-variablesensor1)

quizás se me escape algo ...

Un saludo ¡



Logged

0
Offline Offline
Edison Member
*
Karma: 17
Posts: 1407
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

lo que dice Igor y SrDonGato pero utilizando micros en lugar de millis

http://www.arduino.cc/en/Reference/Micros
Logged

* Si preguntas, pon el código de tu programa, hace mucho mas fácil ayudarte. Y me ahorro un mensaje pidiendo que lo hagas.
* Si consigues solucionar tu problema, dedica unos minutos a explicar en tu post como lo conseguiste para beneficio de todos.
* Cambia el 'Subject' de tu hilo y añade 'SOLUCIONADO' cuando hayas llegado a una solución al problema que planteaste.
* Utiliza un 'Subject' para tu hilo que explique de que va el hilo.
Si estas empezando:
* Comienza a usar Arduino
* Guías de iniciación a Arduino
* Ejemplos
* Referencia del Lenguaje
* Conceptos básicos
Guia de usuario de arduino
Tutoriales en Ingles
Si necesitas que alguien te escriba el código: http://www.freelancer.com/  o esta  http://www.guru.com/

Ciudad Real
Offline Offline
God Member
*****
Karma: 1
Posts: 747
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

desconocía la función esa smiley-grin pero claro está que cuanto mayor sea la resolucion de tiempo más precision en la medida tendrá smiley
Logged

0
Offline Offline
Edison Member
*
Karma: 16
Posts: 1579
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

El principal problema es cómo instalarlo. Si lo haces digital, la manera más sencilla sería construirte un cubo o similar, que tengas varias barreras ópticas a la entrada y a la salida, para asegurarte que cubres el area para captar la flecha y disparar a través de dicho cubo.

Luego medirlo en Arduino, se puede usar un timer del micro directamente (en vez de millis() o micros()) para tener la máxima precisión posible. Al final, la parte soft de Arduino, yo creo que es la más sencilla (analógica o digital). Ya habeis visto en link que hacen tratamiendo de sonido a tiempo real con el micro....

Cada manera tienes sus pros y contras, de manera analógica, posiblemente requiere menos instalación hardware (aunque requerirá etapa de adaptación de la señal, por ejemplo con Schmitt trigger o etapa amplificadora). Se me ocurre que con sensores de presión, micrófonos ó midiendo de manera inductiva (magnetizando la punta de la flecha), también se podría hacer.

¿Alguien sabe cómo miden los comerciales? Tipo a :
« Last Edit: August 09, 2011, 09:08:46 am by Igor R » Logged


Argentina
Offline Offline
Full Member
***
Karma: 1
Posts: 104
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Hola y muchas gracias por las respuestas!! con Micros() he probado tal como esta pero no mejora, el cuello de botella esta por otro lado, yo soy muy novato y de programación casi nulo, he hecho todo en forma intuitiva. Esog voy a incursionar por tu web a ver si rescato algo de lo que me comentas, también veré el enlace de Igor R, yo hice tambié con el mismo código una interesante prueba calculando la frecuencia de resonancia de las cuerdas de una guitarra esta en mi blog http://anajesusa.wordpress.com/ pero claro estamos hablando de pocos Hz, 15Khz es palabra mayor.
Por favor tengan paciencia conmigo, estoy medio viejo y me cuesta un poco la parte de programación.
César
Logged


0
Offline Offline
Edison Member
*
Karma: 16
Posts: 1579
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Prueba a configurar el prescaler del ADC (registro ADCSRA, bits 2:0). Al aumentar la frecuencia del módulo ADC disminuye la precisión. Atmel recomienda para 10 bits, que el reloj del ADC debe estar entre 50 kHz-200 kHz. Con un prescaler de 64, estarías un poco por encima  pero cercano a lo recomendado para 10 bits (250 kHz). Si no me equivoco en las cuentas, la conversion cuesta 13 ciclos y el cristal es de 16Mhz, por lo que (16000/64)/13=19230 Hz, por lo que nuestro amigo Nyquist dice que podrías adquirir señales de hasta 8 kHz con esta configuración.

A parte, existe una modalidad del ADC, que te inicia la conversión cuando hay overflow, por ejemplo, del timer 0 ó 1 (se configura en el registro ADCSRB). Yo creo que te interesa ésto, para adquirir de forma periódica.

Otra cosa que puedes usar es sólo 8 bits, y de esta manera,sólo tienes que leer un registro (para aumentar velocidad al no tener que hacer operaciones al recoger el valor del conversor y por otro lado podrías aumentar más la frec del ADC).

Todo ésto lo tienes en el datasheet del micro, ya que el lenguaje Arduino no lo tiene implementado. Pero claro, estamos hablando de una cosa muy específica y que necesitas profundizar.


 smiley-wink
« Last Edit: August 09, 2011, 11:22:12 am by Igor R » Logged


Argentina
Offline Offline
Full Member
***
Karma: 1
Posts: 104
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Igor, discupla mi ignorancia como ingreso al prescaler, (estoy super verde  smiley-red)
Para DonGato, hay un solo sensor, lo que mide es la sombra de la flecha, la distancia es el largo del proyectil
He probado esto:
unsigned long tsombra;  //declaro una variable, se usara como contador de bucles.

void setup() {    //hay que ponerlo siempre, aqui se configura el asunto
    pinMode(2, INPUT);     // set the digital pin as input:
    Serial.begin(115200);   //lento pero llega, No se si es necesario definir los baudios
    }

void loop(){  //hay que ponerlo siempre, este es le bucle de la chicha
digitalWrite(13, HIGH);
    tsombra=0;   //reseteamos contador

    while (digitalRead(2)==1) {}  //mientras el pin esta a 1 queda en bucle esperando sombra
    while (digitalRead(2)==0) {tsombra++;} //mientras esta en oscuro incrementa "tsombra".

    Serial.print("T. sombra= "); //envia resultado
    Serial.println(tsombra);   
    }
pero hechas las pruebas no me convence, tal vez haya algo mal.
Igor vi en tu web la maqueta de control PID, me llamó la atención que usaran un resistor NTC para sensor de calor siendo los diodos 1n4148 tan lineales en esta función, mi primer trabajo con arduino fue adaptar una sonda hecha con este diodo para usarlo como termostato electrónico en una estufa para microbiología. http://anajesusa.wordpress.com/2011/07/06/la-placa-arduino/
Logged


0
Offline Offline
Edison Member
*
Karma: 16
Posts: 1579
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Hola Cesar,

El principal motivo fue usar un sensor no lineal, y usar una tabla en memoria flash para linealizarlo y porque el precio de un termistor es casi similar al del diodo (hablando de comprar 1 unidad). Por añadir más cosillas didácticas, puedes ver que precisamente ésto, es uno de los objetivos del proyecto. Pero podría ser una modificación perfecta, si sólo se quiere focalizar en el PID.

Para cambiar el prescaler, tan sólo tienes que cambiar los bits del registro ADCSRA. Por ejemplo, puedes hacer:
ADCSRA|= (1<<ADPS2)|(1<<ADPS1)|(0<<ADPS0)
Si no entiendes que hace ésto, puedes mirarte los compound y bitwise operators de la página de Arduino.

Otra forma, es usar los macros predefenidos cbi y sbi (clear bit and set bit):
sbi(ADCSRA, ADPS2);
sbi(ADCSRA, ADPS1);
cbi(ADCSRA, ADPS0);

Aunque yo también me haría una nueva función analogReadFast(), optimizandola un poco (como sólo vas a mirar una entrada analógica, puedes quitar la parte que configura el multiplexador). Puedes mirar las "tripas" de Arduino (arduino\hardware\arduino\cores\arduino\).En el archivo wiring_analog.c tienes cómo está creada la función analogRead().
También me haría un función de configuración del modulo ADC, en el cual configuraría el prescaler, sólo 8 bits (si quieres mayor velocidad), etc


Saludos


Igor R.
« Last Edit: August 09, 2011, 01:04:43 pm by Igor R » Logged


Argentina
Offline Offline
Full Member
***
Karma: 1
Posts: 104
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Ya veo, me quede pegado en tu blog Igor, lo de tabla guardada en la flash esta muy bueno, ya se me ocurrió algo con eso, tengo un medidor de vacío hecho con una PT100 (resistencia de platino) que no sigue ninguna función ya había solucionado eso con un arcaico código que por verguenza no pongo (aunque funciona  smiley) veré de hacer algo semejante a lo de tu proyecto.
Cuando llegue a casa pruebo colocar la linea para cambiar el prescaler, con ese valor queda en 256, el valor defecto es de 1024?  con ese valor queda 4 veces mas rápido el reloj?
Si luego de hacer esto cargo otro código y no modifico el timer este queda configurado en ese valor o vuelve a 1024.
Logged


0
Offline Offline
Edison Member
*
Karma: 16
Posts: 1579
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Descárgate el datasheet del microcontrolador que trae el Arduino, y contesta tu mismo a la pregunta del prescaler?  smiley-wink
La respuesta viene el mismo, en forma de una tabla.
Si al leerlo tienes alguna duda, entonces seguimos hablando....je,je,je

Cuando cargues otro código, se te configurará con el valor por defecto de Arduino.

 smiley-razz
« Last Edit: August 09, 2011, 05:35:04 pm by Igor R » Logged


Argentina
Offline Offline
Full Member
***
Karma: 1
Posts: 104
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Ademas de docente soy bioquímico, asi que soy medio durazno para las hojas de datos, pero estudiaré  smiley-lol, gracias Igor
Logged


Pages: [1] 2 3 ... 10   Go Up
Jump to: