Autor Tema: ¿como puedo pasar un binario a BCD?  (Leído 11215 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado Thulsa Doom

  • PIC24F
  • *****
  • Mensajes: 771
    • https://electronicadicto.wordpress.com/
¿como puedo pasar un binario a BCD?
« en: 18 de Marzo de 2011, 21:48:09 »
Hola a todos, resulta que estoy intentando hacer un cronómetro con un pic16f876a utilizando el timer1.
he pensado que capturando el dato del timer y pasandolo a bcd se podría representar en un LCD, pero la verdad es que no tengo ni idea de como puedo implementar una rutina que me pase de binario a bcd, a ver si alguien me puede orientar o algo, estoy perdidisimo.

programo en CCS C.

gracias a todos
Más códigos y desarrollos en https://electronicadicto.wordpress.com/ date una vuelta y curiosea un rato...

Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #1 en: 18 de Marzo de 2011, 22:08:23 »
Hola a todos, resulta que estoy intentando hacer un cronómetro con un pic16f876a utilizando el timer1.
he pensado que capturando el dato del timer y pasandolo a bcd se podría representar en un LCD, pero la verdad es que no tengo ni idea de como puedo implementar una rutina que me pase de binario a bcd, a ver si alguien me puede orientar o algo, estoy perdidisimo.

programo en CCS C.

gracias a todos

  Si tenés un dato integer bien podés usar la función itoa (IntegerToAscii) y ya obtenés un string que podés enviar a un LCD tranquilamente.
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas

Desconectado agauss

  • PIC16
  • ***
  • Mensajes: 147
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #2 en: 19 de Marzo de 2011, 04:02:46 »
Si tienes un dato tipo byte en CCS, una forma sencilla seria usando division entera y division modulo:

Código: [Seleccionar]
codigo:

cdato = dato / 100;
xdato = dato % 100;
ddato = xdato / 10;
udato = xdato % 10;

donde:

cdato = centenas
ddato = decenas
udato = unidades


No es el conocimiento, sino el acto de aprendizaje, y no la posesión, sino el acto de llegar allí, que concede el mayor disfrute.
"Carl Friedrich Gauss"

El tacto es el arte de hacer un punto sin hacer un enemigo.
"Isaac Newton"

Desconectado Thulsa Doom

  • PIC24F
  • *****
  • Mensajes: 771
    • https://electronicadicto.wordpress.com/
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #3 en: 19 de Marzo de 2011, 06:32:51 »
Gracias por la ayuda compañeros, pero tengo un problema, resulta que estoy empezando a programar y no sé como enfocar el problema, si pudierais concretar más con un ejemplo o algo así. gracias
Más códigos y desarrollos en https://electronicadicto.wordpress.com/ date una vuelta y curiosea un rato...

Desconectado agauss

  • PIC16
  • ***
  • Mensajes: 147
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #4 en: 19 de Marzo de 2011, 14:57:05 »
Esto es lo mas sencillo que se me ocurre. Se ingresa un valor tipo byte por el puerto B del PIC16F876A a travez de un dipswitch, este dato sera entonces convertido  BCD por la rutina de divisiones entera y modulo y el resultado sera almacenado en los registros cdato, ddato y udato colocados en memoria de usuario en: 0x20, 0x21 y 0x22 respectivamente. Te adjunto el codigo fuente, el archivo compilado y la simulacion en PROTEUS 7.4. Espero te se de utilidad

saludos...

Código: [Seleccionar]
#include <16F876A.H>
#fuses XT,NOWDT,NOPROTECT,NOLVP,PUT
#use delay(clock=4000000)

#byte portb = 0x06

int8 cdato,ddato,udato;
int8 xdato,dato;

#locate cdato = 0x20
#locate ddato = 0x21
#locate udato = 0x22
#locate xdato = 0x23
#locate dato  = 0x24

void main(void)
{
   set_tris_b(0xFF);
   
   while(TRUE)
   {
      dato = portb;
     
      cdato = dato/100;
      xdato = dato%100;
      ddato = xdato/10;
      udato = xdato%10;
   }
}

No es el conocimiento, sino el acto de aprendizaje, y no la posesión, sino el acto de llegar allí, que concede el mayor disfrute.
"Carl Friedrich Gauss"

El tacto es el arte de hacer un punto sin hacer un enemigo.
"Isaac Newton"

Desconectado pocher

  • Moderador Local
  • DsPIC30
  • *****
  • Mensajes: 2568
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #5 en: 19 de Marzo de 2011, 16:02:53 »
Código: [Seleccionar]
// Conversión de hex(binario)(entero) --->  a BCD (1ª forma)(¡funciona fisicamente!)

int hex_bcd(int valor)
{
  return ( valor % 10 + 16 * (valor / 10));
}

/*
int hex_bcd(int binario) //2ª forma (¡funciona fisicamente!)
{
   return (((binario/10) << 4) + binario%10);
}
*/

// Conversión de BCD --->  a hex(binario)(entero)(1ª forma) (¡funciona fisicamente!)

int bcd_hex(int valor)
{
  return ( valor % 16 + 10 * (valor / 16));
}

/*
int bcd_hex(int bcd) //2ª forma (¡funciona fisicamente!)
{
   return (((bcd >> 4)*10) + (bcd & 0x0F));
}
*/

Todas funcionan físicamente (probadas con relojes I2C)

Desconectado agauss

  • PIC16
  • ***
  • Mensajes: 147
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #6 en: 19 de Marzo de 2011, 16:46:24 »
Exelentisimas rutinas. Tomo nota!!!!
No es el conocimiento, sino el acto de aprendizaje, y no la posesión, sino el acto de llegar allí, que concede el mayor disfrute.
"Carl Friedrich Gauss"

El tacto es el arte de hacer un punto sin hacer un enemigo.
"Isaac Newton"

Desconectado Thulsa Doom

  • PIC24F
  • *****
  • Mensajes: 771
    • https://electronicadicto.wordpress.com/
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #7 en: 20 de Marzo de 2011, 16:40:03 »
es que lo quiero hacer con el timer1 para luego cuando me venga el NJU6355, intentar utilizarlo con el codigo que haya hecho
« Última modificación: 20 de Marzo de 2011, 16:43:02 por Thulsa Doom »
Más códigos y desarrollos en https://electronicadicto.wordpress.com/ date una vuelta y curiosea un rato...

Desconectado bigluis

  • Colaborador
  • PIC24F
  • *****
  • Mensajes: 511
    • Tutoriales de Qt C++
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #8 en: 20 de Marzo de 2011, 23:30:58 »
No se si entendi muy bien pero tu no deseas convertir un entero a BCD sino imprimir un valor entero en el LCD.

Para realizar esto solo debes utilizar la funcion printf que se encarga de imprimir datos en el lcd. Por ejemplo

Código: [Seleccionar]
int a=123;
...
lcd_init();
printf(lcd_putc,"valor de a= %u",a);   //Se imprimira en el LCD el valor almacenado en a.

Con la funcion anterior se imprimirá "valor de a= 123" en el lcd.

Por otro lado una forma de realizar un cronometro es imprimiendo los datos cada cierto tiempo (posiblemente cada 1ms). Para ello te recomiendo que utilices la interrupción por desbordamiento del TIMER cada 1ms. Por ejemplo:
Código: [Seleccionar]
int msec,sec,min,hor;
#int_timerX
void imprimir_cronometro(){
   lcd_gotoxy(1,7);     //Imprimira valor en la posicion 1,7
   printf(lcd_putc,"%02u",msec);//Imprime el valor de mseccon ceros
   if(msec++>99){       //incrementa el valor de msec y si es mayor a 99
      msec=0;               //pone msec a 0.
      lcd_gotoxy(1,4);     //Imprimira valor en la posicion 1,4
      printf(lcd_putc,"%02u",min);//Imprime el valor de sec con ceros
      if(sec++>59){
         sec=0;
         lcd_gotoxy(1,1);     //Imprimira valor en la posicion 1,1
         printf(lcd_putc,"%02u",min);//Imprime el valor de min con ceros
         if(min++>60){
            min=0;
            lcd_gotoxy(1,4);     //Imprimira valor en la posicion 1,4
            printf(lcd_putc,"%02u",min);//Imprime el valor de hor con ceros
            if(hor++>23){
               hor=0;
            }
         }
      }
   }
}

Recuerda que antes de utilizar una interrupcion debes habilitarla con la funcion enable_interrupts
« Última modificación: 21 de Marzo de 2011, 00:08:43 por bigluis »
Tutoriales de Qt C++

No es necesario que hagamos Grandes cosas, sino que lo que hagamos sea importante.

SI la NECESIDAD es la MADRE del CONOCIMIENTO, SEGURAMENTE la PEREZA su TÍA.

Cuando el ARTE requiere de PRECISION le llamamos CIENCIA

Desconectado Thulsa Doom

  • PIC24F
  • *****
  • Mensajes: 771
    • https://electronicadicto.wordpress.com/
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #9 en: 22 de Marzo de 2011, 19:36:25 »
He estado probando el código y por lo que veo es solo por software, no utiliza para nada el timer y no sé no me tira bien, me hace cosas raras.
De todas maneras es algo como eso lo que quiero pero no sé cómo hacerlo utilizando el timer1, he estado pensando y me gustaría que me orientaran. Lo necesito por timer ya que el código no va a estar solo, tengo más cosas implementadas y si pongo un cronómetro como ese por software tendré muchos retrasos y me será muy difícil ajustar el tiempo para que sea exacto

No sé si se podrá hacer capturando el dato del timer con valor=get_timer1(); y valor pasarlo a BCD que es lo primero que pensé.
O utilizar la interrupción por desbordamiento e ir incrementando una variable.
La verdad es que estoy algo perdido y necesito que alguien me lo explique y me oriente.
Gracias
Más códigos y desarrollos en https://electronicadicto.wordpress.com/ date una vuelta y curiosea un rato...

Desconectado bigluis

  • Colaborador
  • PIC24F
  • *****
  • Mensajes: 511
    • Tutoriales de Qt C++
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #10 en: 22 de Marzo de 2011, 21:04:44 »
Primero que nada debes aprender como funcionan los TIMER. Los TIMER se incrementan cada vez que ocurre un ciclo o varios ciclos de reloj en dependencia de su preescaler.

Por ejemplo el TIMER0 tiene 8 preescaler distintos 1:1, 1:2, 1:4, 1:8, 1:16, 1:32, 1:64, 1:128 y 1:256. Si por ejemplo escojes el prescaler 1:256 entonces el TIMER0 se incrmentara cada 256 ciclos del oscilador y si tu cristal es de 4 MHz entonces el TIMER0 se incrementara cada 256us, por ello no puedes leer directamente el valor del TIMER0.

Otra cosa importante es que cada vez que el TIMER0 tiene un valor de 255d (0b11111111) y se incrementa su siguiente valor es 0d(0b0000 0000), a esto se le llama desbordamiento del TIMER0, y este activa el flag de interrupcion, y si suponemos igual que antes prescaler 1:256 y Fosc=4MHz entonces la interrupcion ocurrira cada 65ms.

La ecuacion que se utiliza para calcular el tiempo que tarda en realizarce una interrupción por desbordamiento de TIMR0 es la siguiente.

$$T_{desborde} = {4 \over {F_{OSC} }} \cdot T0div\left( {256 - TMR0} \right)

Si deseas que el desborde ocurra cada 1ms entonces debes calcular el valor de TMR0.

$$TMR0 = {{T_{desborde} \cdot F_{OSC} } \over {4 \cdot T0div}} = 256 - {{1ms \times 4MHz} \over {4 \times 8}} = 131

Luego de esto dentro del main debes hacer lo siguiente
Código: [Seleccionar]
void main(void){
   ...
   setup_timer_0(T0_INTERNAL|T0_DIV_8);
   set_timer0(131);
   enable_interrupts(INT_TMR0);
   enable_interrupts(GLOBAL);
   ...
}

Y en la funcion de interrupcion que debe ir arriba del main debes poner lo siguiente
Código: [Seleccionar]
int msec,sec,min,hor;
#int_timerX
void imprimir_cronometro(){
   set_timer0(131);
   lcd_gotoxy(1,7);     //Imprimira valor en la posicion 1,7
   printf(lcd_putc,"%02u",msec);//Imprime el valor de mseccon ceros
   if(msec++>99){       //incrementa el valor de msec y si es mayor a 99
      msec=0;               //pone msec a 0.
      lcd_gotoxy(1,4);     //Imprimira valor en la posicion 1,4
      printf(lcd_putc,"%02u",min);//Imprime el valor de sec con ceros
      if(sec++>59){
         sec=0;
         lcd_gotoxy(1,1);     //Imprimira valor en la posicion 1,1
         printf(lcd_putc,"%02u",min);//Imprime el valor de min con ceros
         if(min++>60){
            min=0;
            lcd_gotoxy(1,4);     //Imprimira valor en la posicion 1,4
            printf(lcd_putc,"%02u",min);//Imprime el valor de hor con ceros
            if(hor++>23){
               hor=0;
            }
         }
      }
   }
}

Debido a que en los lenguajes de alto nivel es imposible saber cuanto tarda con exactitud cada instrucción deberas modificar el valor de TIMER0 hasta que la temporización sea de 1ms, es decir debes cambiar el valor de 131 a otro.
Tutoriales de Qt C++

No es necesario que hagamos Grandes cosas, sino que lo que hagamos sea importante.

SI la NECESIDAD es la MADRE del CONOCIMIENTO, SEGURAMENTE la PEREZA su TÍA.

Cuando el ARTE requiere de PRECISION le llamamos CIENCIA

Desconectado Thulsa Doom

  • PIC24F
  • *****
  • Mensajes: 771
    • https://electronicadicto.wordpress.com/
Re: ¿como puedo pasar un binario a BCD?
« Respuesta #11 en: 27 de Marzo de 2011, 17:49:33 »
Pues he de daros las gracias ya he entendido como funcionan las interrupciones de los timers, tenía un poco de lio, gracias por el ejemplo me ha servido, lo he tenido que modificar bastante pero ya funciona, gracias de nuevo
Más códigos y desarrollos en https://electronicadicto.wordpress.com/ date una vuelta y curiosea un rato...


 

anything