Autor Tema: VELOCIMETRO CON TIMER0  (Leído 5638 veces)

0 Usuarios y 3 Visitantes están viendo este tema.

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
VELOCIMETRO CON TIMER0
« en: 17 de Abril de 2015, 05:11:28 »
Hola, estaria interesado en realizar un velocimetro con el TIMER0, pero no tengo mucha idea de como hacerlo. Si me pudierais ayudar. Utilizo el pic18F4550

Desconectado juaperser1

  • Colaborador
  • DsPIC30
  • *****
  • Mensajes: 2979
Re: VELOCIMETRO CON TIMER0
« Respuesta #1 en: 17 de Abril de 2015, 05:43:29 »
de que quieres medir la velocidad y de que hardware dispones?
Visita mi canal para aprender sobre electrónica y programación:

https://www.youtube.com/channel/UCxOYHcAMLCVEtZEvGgPQ6Vw

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: VELOCIMETRO CON TIMER0
« Respuesta #2 en: 17 de Abril de 2015, 07:10:30 »
tengo el pic18f4550, un cristal de 20MHz, ccs compiler, y lo quiero para medir la velocidad de una motocicleta 49cc mediante un sensor.

Desconectado juaperser1

  • Colaborador
  • DsPIC30
  • *****
  • Mensajes: 2979
Re: VELOCIMETRO CON TIMER0
« Respuesta #3 en: 17 de Abril de 2015, 07:29:19 »
el Sensor ya lo tienes? que tipo es?

puede ser un paso por 0 o un encoder, en caso de que sea encoder que es incremental absoluto?

lo mejor para esta aplicación es un paso por cero optico o de efecto hall, necesitas saber el diametro de la rueda.

de esta manera cuando pase por 0 empiezas a contar y cuando vuelva a pasar por 0 paras de contar, hay tienes el tiempo que ha tardado en dar una vuelta completa, si saber el radio de la rueda ya puedes calcular la velocidad angular y de hay la velocidad lineal, partiendo de que no hay deslizamiento.
Visita mi canal para aprender sobre electrónica y programación:

https://www.youtube.com/channel/UCxOYHcAMLCVEtZEvGgPQ6Vw

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: VELOCIMETRO CON TIMER0
« Respuesta #4 en: 17 de Abril de 2015, 18:13:38 »
tengo un sensor efecto hall, el diametro sera uno cualquiera porque sera para demostrar que funciona en un proyecto.

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: VELOCIMETRO CON TIMER0
« Respuesta #5 en: 17 de Abril de 2015, 21:59:01 »
Quedan 2 opciones..

Una es contar el tiempo entre vueltas (cada ves que el iman pasa sobre el sensor), esto te va a dar una idea de a que velocidad va la moto. tendrias que sacar un promedio de varias lecturas antes de mostrarlas

La otra es contar la cantidad de vuelta que hay en 1 segundo, esto tambien te daria la velocidad, para mi esta seria la indicada. Con un timer y un modulo CCP creo que es totalmente posible, solo tendrias que recoger el dato y mostrarlo.

Desconectado AleSergi

  • PIC16
  • ***
  • Mensajes: 209
Re: VELOCIMETRO CON TIMER0
« Respuesta #6 en: 17 de Abril de 2015, 23:45:07 »
Hola, no comprendo porque pretendés emplear el timer0, si no es un requisito de tu proyecto, dado que es para algo tuyo, como has indicado.
La forma fácil de hacerlo sin liarse es emplear el módulo CCP, con su utilidad CAPTURE (también tiene compare y pwm), aquí se emplea el TIMER1 como base de tiempo/contador, programable, y con el módulo ccp se capturan sus cuentas, todo por hardware, según hallas configurado la circuiteria, pues con unos simples cálculos, obtenés el tiempo en el que la rueda dio una revolución ycon ello calculas la velocidad.

Desconectado juaperser1

  • Colaborador
  • DsPIC30
  • *****
  • Mensajes: 2979
Re: VELOCIMETRO CON TIMER0
« Respuesta #7 en: 18 de Abril de 2015, 04:05:37 »

Te escribo esto:

Citar
lo mejor para esta aplicación es un paso por cero optico o de efecto hall, necesitas saber el diametro de la rueda.

de esta manera cuando pase por 0 empiezas a contar y cuando vuelva a pasar por 0 paras de contar, hay tienes el tiempo que ha tardado en dar una vuelta completa, si saber el radio de la rueda ya puedes calcular la velocidad angular y de hay la velocidad lineal, partiendo de que no hay deslizamiento.

Y me contestas esto:

Citar
tengo un sensor efecto hall, el diametro sera uno cualquiera porque sera para demostrar que funciona en un proyecto

No se porque pero me da la impresión de que lo que quieres es que te hagan el proyecto  :D :D, debes de empezar a hacerlo por ti mismo, y en las dudas que te vayan surgiendo ves preguntando que seguro te las resolverán, pero debes ser mas claro y explicar bien tu problema, para que te puedan ayudar.
Visita mi canal para aprender sobre electrónica y programación:

https://www.youtube.com/channel/UCxOYHcAMLCVEtZEvGgPQ6Vw

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: VELOCIMETRO CON TIMER0
« Respuesta #8 en: 22 de Abril de 2015, 07:16:50 »
Hola a todos, seguramente no me explique bien lo que quería hacer y tampoco pretendía que me hicieseis el programa, lo siento si pareció eso.
Tengo conectado en el pin 6 (RA4/T0CK1) del pic18F4550 el sensor inductivo. Lo que pretendo realizar es lo siguiente. Es mediante una rueda de pequeñas dimensiones de unos 8 cm de diámetro, yo mismo le daré impulso con la mano, para que coja velocidad y poder simular lo que haría en la rueda de una moto a pequeña escala. Estoy probando de hacer el programa, mediante que el TIMER0 cuente pulsos (aplicando la formula de velocidad), pero no consigo hacerlo bien y me estoy liando, si pudierais aconsejarme. Gracias.

Código: [Seleccionar]
#include <18F4550.h>
#fuses NOWDT,XT,NOPROTECT,NOLVP
#use delay(clock=20000000)
#include "C:\Users\xx\Desktop\VELOCIDAD\flex_lcd420.c"

int16 counter;
float Velocidad=0;
#int_TIMER0
void TIMER0_isr(){
counter=get_timer0();    //lee contador TMR0
Velocidad= Counter * 25.13 * 0.036;
 printf(lcd_putc,"%61u vel", Velocidad);
lcd_gotoxy(1,1);
counter=0;
Velocidad=0;
set_timer0(0);                      //Reinicia cuenta

}

void main(){
lcd_init();

   setup_timer_0(rtcc_ext_l_to_h|RTCC_DIV_2);   //Configuración TMR0
   
   set_timer0(0);                               //Borrado contador
   
   enable_interrupts(global);
}

Desconectado juaperser1

  • Colaborador
  • DsPIC30
  • *****
  • Mensajes: 2979
Re: VELOCIMETRO CON TIMER0
« Respuesta #9 en: 22 de Abril de 2015, 08:08:29 »
Bueno ese programa no puede funcionar lo primero que veo que falta es el bucle while principal, si no lo pones tu programa terminara y ya no hará nada, esto no puede faltar nunca. Colocarlo y veras como podrás realizar mas pruebas pero así no podrás hacer nada.

Otra cosa que veo es que no  configuras los pines en ningún lado, no recuerdo bien el ccs, pero debes configurar tu pin como entrada.

 Te recomendaría olvides primero formulas y todo, pon el while configura el primer y revisa si entra en la interrupción, cuando eso funciones entonces sumas la pantalla y las cuentas.

Un saludo.
« Última modificación: 22 de Abril de 2015, 08:15:13 por juaperser1 »
Visita mi canal para aprender sobre electrónica y programación:

https://www.youtube.com/channel/UCxOYHcAMLCVEtZEvGgPQ6Vw

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: VELOCIMETRO CON TIMER0
« Respuesta #10 en: 22 de Abril de 2015, 08:58:31 »
Hay 2 errores mas podria agregar,

El primero es hacer calculos/escribir en el LCD en una interrupcion. Aunque depende de que tan rapido lo haga y si no necesita de otra interrupcion.

El segundo es que tiene un mal concepto de que es una interrupcion en el Timer. al ver que en la interrupcion pregunta por que valor tiene el timer. Si ocurre la interrupcion por el Timer es por que paso de 0xFF a 0x00 ( si es 8 bits ) por lo tanto siempre leerias 0x00.


Empecemos como vas a medir la velocidad de la rueda, si pienso en timers se me ocurren 2 formas.

- Medir entre 2 pulsos del sensor para saber cuando tardo en dar una vuelta.
- Medir en un tiempo conocido cuantas vueltas pulsos dio el sensor ( Si lo hago cada un segundo, lo unico que tendria que hacer al numero que me de es multiplicarlo por 60 y ya tendria las RPM para pasarlo a velocidad deberia saber el radio de la rueda )

Vamos por parte dijo Jack.

El primer caso:

Significa que deberia tener 2 interrupciones, una de una entrada externa (sea por RB0 o por CCP) y otra del timer. Lo ideal un timer de 16bits
Al producirse la primer interrupcion por flanco ascendente pongo a 0 el timer y recien ahi habilito la interrupcion del timer.
La segunda interrupcion por flanco ascendente, tomo el valor del timer y luego lo pongo a 0, salgo aviso con un flag que ya esta listo el dato y que se procese en el main.
Proxima interrupcion por flanco ascendente, nuevamente tomo el valor y lo pongo a 0 nuevamente, aviso con un flag que entro y que se procese en el main.

Posibles problemas:
Que puede pasar que se tarde mucho en cruzar el sensor (se detenga la rueda o vaya muy lento), entonces deberias tener un "seguro" o la capacidad de contar mucho mas.
Con la interrupcion del timer vas a saber si el timer rebalso por completo y si pones un contador vas a saber cuantas veces sucedio, esto si o si tiene que estar.

Para este caso no conviene usar el Timer 0, conviene usar el Timer 1 o 3, que se usa con el modulo CCP. Esto hace que apenas se detecte un flanco ascendente/descendente se guarde automaticamente en otro registro el valor del timer y Se genera una interrupcion, de todas formas deberias de tener en cuenta lo anterior con respecto a los timers. Si es de 16 bits como cuando lo usas con el CCP incluso podes no ponerlo a 0 al timer y luego hacer la diferencia, valor nuevo - valor viejo = tiempo que paso

Segundo caso:

En este caso tambien seria ideal un timer de 16 bits o tal ves con 8 alcance, asi intentar llegar al segundo o tal ves valores como 0.2s,0.1s,etc
Aqui solamente configuras tu Temporizador a un tiempo predeterminado como dije antes y habilitas el modulo CCP para que cuente los flancos ascendentes ( si son muchos podes incluso dividirlo con su preescaler )
Cuando ocurre la interrupcion del Timer, guardas el valor que quedo del CCP, lo pones a 0 y avisas mediante un flag al main que ya esta listo para procesarse la informacion. Tambien recargas tu timer.
En tu main Si fuera de 0.1s el timer deberias multiplicar por 600 el valor almacenado en el CCP para saber cuantas RPM tenes.
« Última modificación: 22 de Abril de 2015, 09:35:06 por KILLERJC »

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: VELOCIMETRO CON TIMER0
« Respuesta #11 en: 24 de Abril de 2015, 08:03:00 »
He seguido vuestros consejos, pero ahora me quedado estancado y nose si voy bien o voy mal, y por donde tirar. He creado la interrupcion, pero cuando me dices que guarde el valor del CCP y luego lo ponga a 0, te refieres dentro del main o en la propia interrupcion?

Código: [Seleccionar]
#include <18F4550.h>
#fuses NOWDT,XT,MCLR
#use delay(clock=20000000)
#include "C:\Users\xx\Desktop\VELOCIDAD\flex_lcd420.c"

int1 pulso=0;
float RPM=0;
int16 TFS=0;

#int_CCP1
void CCP1_irs()         //Interrupcion
{
setup_ccp1(CCP_CAPTURE_RE);    //Configuracion modo Captura
TFS=CCP_1;
if (pulso==0){    //FIn de pulso
pulso=1;
}         //Pulso a medir
}

void main(){

lcd_init();
setup_timer_1(T1_INTERNAL);      //Configuracion TMR1
setup_ccp1(CCP_CAPTURE_RE);      //Configuracion modo Captura en flanco subida
enable_interrupts(int_ccp1);
enable_interrupts(global);

do {
   if (pulso==1){ //¿Pulso nuevo?
    RPM=TFS*60;
   
    printf(lcd_putc," %61u RPM", RPM);
   
    pulso=0;         //Espera pulso
    }
}
while(TRUE);
}

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: VELOCIMETRO CON TIMER0
« Respuesta #12 en: 26 de Abril de 2015, 04:32:40 »
Perdon por la tardanza.

Cuando me referi que lo pongas a 0 es al timer.

El CCP ante un evento copia el valor del timer a su registro. Si no lo borras deberias tener los 2 ultimos valores y realizar la resta de esos 2 valores, complicandose  en el manejo cuando el timer hace un overflow.

EN fin tu rutina de interrupcion seria:

CCP:
Poner a 0 timer 1
Copiar valor del CPP a una variable
Habilitar una flag, poner a 1 una flag, ni siquiera preguntar si estaba en 0.

Timer1:
flag = 0
contador++;


Tu main:

Aca configuracion de todos los modulos

While (1)
{
se activo la flag ?
SI ->
        aca se puede hacer un promediado de varias entradas antes de hacer todos los calculos y mostrar
        valor del timer * tiempo de cada pulso de clock (Tosc si no hay preescaler) + (tiempo de overflow del timer * contador) = Tiempo transcurrido de una vuelta  (esto es algo que te va a quedar a la e-6 )
        3600 / tiempo transcurrido en una vuelta = RPM
        flag = 0
}

Es la primera opcion y bastante complicada la segundo caso se hace mas facil

Interrup:
Timer:
Cargo valor de ser necesario
ContadorT++;
flag=1

CCP:
ContadorPulsos++;


Main:
Conf de todas las cosas
Timer a 0.2s el overflow (Voy a suponer que llega a 0.2s)

while(1)
{
Flag = 1 ?
Si ->
    Contador de pulsos * 5 * 60 = RPM
    Flag = 0
}

El 5 es para que sea de 0.2s a 1s y luego los 60 para que sean 60s , podrias tambien tomar 5 muestras, sumarlas y luego multiplicarlas por 60. O tambien hacer que a la 5ta entrada de la interrupcion del timer ( sigo suponiendo que lo haces a 0.2s) habilite el flag

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: VELOCIMETRO CON TIMER0
« Respuesta #13 en: 04 de Mayo de 2015, 08:04:47 »
Perdon por el retraso, he estado fuera unos dias y no he podido contestar. He hecho lo que me comentaste, tengo conectado el sensor en el pin 18 (C2) para el modo captura. Tengo una duda en relacion donde introducir el printf si dentro del if o fuera. Porque lo he probado tanto dentro del if como fuera y me aparece dígitos que no tienen sentido en el LCD. Otra cosa que he hecho a sido el decir que el C2 sea entrada, pero en el puerto C tambien uso el LCD que he dicho que continue siendo salida. En la carga del timer tengo dudas si he decido la correcta, he puesto que cargue cada 0.5 s

Código: [Seleccionar]
#include "C:\Users\xx\Desktop\VELOCIDAD\vel2.h"
#include "C:\Users\xx\Desktop\flex_lcd420.c"
#FUSES MCLR


int16 contador=0;
int1 flag=0;
int16 pulsos=0;
float RPM=0;
float VEL=0;

#int_TIMER1
void  TIMER1_isr(void)
{
set_timer1(3036);             //Carga del TMR1
Contador++;
flag=1;
}

#int_CCP1
void  CCP1_isr(void)
{
Pulsos++;
}



void main()
{
   
   Set_tris_C(0x04); //C2 ENTRADA
   
   
   lcd_init();
   
   
   printf(lcd_putc, "VELOCIMETRO");
   lcd_gotoxy(1,2);
   printf(lcd_putc,"VELOCIDAD KM/H");

   
   setup_timer_1(T1_INTERNAL|T1_DIV_BY_8);
   setup_ccp1(CCP_CAPTURE_RE);
   enable_interrupts(INT_TIMER1);
   enable_interrupts(INT_CCP1);
   enable_interrupts(GLOBAL);
   
    while(1)
   {
   if (flag==1){
      RPM=pulsos*10*60;                   //Overflow de 0.1s
      VEL=RPM*0.08;                       //RADIO ES DE 8 CM
      printf(lcd_putc,"%61u RPM",RPM);
      lcd_gotoxy(1,2);
      printf(lcd_putc,"%61u VEL",VEL);
      flag=0;
   }
   
   }
     
   
}

Mi timer el overflow maximo que he encontrado es de 0.1, por eso multiplico por 10 en las rpm

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: VELOCIMETRO CON TIMER0
« Respuesta #14 en: 04 de Mayo de 2015, 08:43:05 »
El printf dejalo dentro.

Ahora vamos a las unidades y formulas:
printf(lcd_putc,"VELOCIDAD KM/H");
VEL=RPM*0.08;

La longitud de la circunferencia es igual a 2 * pi * radio

asi que VEL = RPM * 2 * pi * 0.08m
aproximadamente

VEL = RPM(vuelta/min) * 0.502654(m/vuelta)

Pero es en m/min, deberias dividirlo sobre 1000 para que te den los km/min y luego multiplicarlo por 60 para que quede como km/h

Vel (m/min) * 1/1000 (km/m) * 60/1 (min/h) = Vel (km/h)

VEL = RPM * 0.030159089  // Formula final para que de Km/h