TODOPIC

Microcontroladores PIC => Lenguaje C para microcontroladores PIC => Mensaje iniciado por: pablo en 16 de Agosto de 2008, 13:39:04

Título: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 13:39:04
Hola gente.
Tengo apartatito que me arme que tiene un display. Hasta ahora hacia que cuando presione una tecla quede prendido durante un minuto, pero ahora queria que quede siempre prendido.
Tengo entendido que el backlight aparte de horas de uso, calienta y se puede quemar por eso queria usar un timer para hacer una especie de pwm para que no quede siempre prendido.
El tema es que parpadea y no le encuentro la vuelta.
Alguien me podria decir en que estoy fallando.

Muchas gracias.

Código: [Seleccionar]
#int_timer1
clockisr2() {
   if (Intcount == 4)
   {
       output_low(PIN_B0);
   }   
   
   else if(Intcount == 5)
   {
      Intcount = 0;
      output_high(PIN_B0);
   }   
   Intcount++;     
}

Seteos del main.

   set_timer0(0);
   set_timer1(0);
   setup_oscillator(OSC_8MHZ,OSC_INTRC);
   setup_counters(RTCC_INTERNAL, RTCC_DIV_2);
   enable_interrupts(GLOBAL);
   setup_adc(ADC_CLOCK_INTERNAL);
   setup_adc_ports(AN0_TO_AN2);
   set_adc_channel(2);
   enable_interrupts(INT_AD);
   read_adc(ADC_START_ONLY);
   setup_timer_1(T1_INTERNAL | T1_DIV_BY_1);
   enable_interrupts(INT_TIMER0);
   enable_interrupts(INT_TIMER1);
   enable_interrupts(global);


Título: Re: Economizar Backlight
Publicado por: Modulay en 16 de Agosto de 2008, 14:36:25
Si el pic que está usando cuenta con módulo ccp,quizá te venga mejor que lo uses para tu propósito.
Viendo esa rutina de interrupción creo que no está muy bien construída...puedes ir probando a recargar el timer con diferentes valores dentro de la rutina de interrupción para acortar el tiempo entre interrupciones,por ejemplo:

set_timer1(127);
Título: Re: Economizar Backlight
Publicado por: gera en 16 de Agosto de 2008, 15:01:02
Una duda... al final de la interrupcion del timer, no hay q recargarlo nuevamente? o esto se hace automaticamente?
Título: Re: Economizar Backlight
Publicado por: Modulay en 16 de Agosto de 2008, 15:04:51
Hay que recargarlo cada vez...si no lo haces el timer da una vuelta completa (256 ticks si el timer es de 8 bits)
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 16:04:49
Estoy usando un 18f4620 y uno el clock interno. Lamentablemente cuando se me ocurrio esto la placa ya estaba diseñana y la pata que estoy usando para el display no es la del cpp.
Cuantas veces deberia estar entrando al timer por segundo?
O cuantas veces esta entrando asi como esta configurado?

Gracias.
Título: Re: Economizar Backlight
Publicado por: Modulay en 16 de Agosto de 2008, 16:21:16
http://www.todopic.com.ar/foros/index.php?topic=22807.0;topicseen (http://www.todopic.com.ar/foros/index.php?topic=22807.0;topicseen)
Título: Re: Economizar Backlight
Publicado por: MLO__ en 16 de Agosto de 2008, 16:50:39
Hola.

La idea es que tu escojas las veces que se desborde el timer ... los calculos no son muy complicados ( ojo al despejar !!!!  :D :D :D )

Saludos
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 16:57:05
Gracias por ponerle voluntad, pero esto no es lo mio, no laburo de esto.
No entiendo demaciado esas cuentas. Perdon.
Tampoco se si esta muy bien lo que quiero hacer.
Cambie el timer con distintos valores pero sigue parpadeando.
Supongo que hay algo que estoy haciendo mal y no entra la cantidad de veces que necesito para que el ojo no lo vea o no se hace de esta forma.

La utima vez hice esto.
#int_timer1
clockisr2() {
   if (Intcount == 1)
   {
       output_low(PIN_B0);
   }   
   
   else if(Intcount == 2)
   {
      set_timer1(65536);
      Intcount = 0;
      output_high(PIN_B0);
   }   
   Intcount++;     
}

El set_timer lo cambie desde el valor 1 y no note demasiado cambio.
Gracias y no me maten.
Título: Re: Economizar Backlight
Publicado por: gera en 16 de Agosto de 2008, 18:53:27
A ver si entendi bien. Vos queres q el backlight parpadee lo suficientemente rapido como para q el ojo no se de cuenta, y para q no este prendido todo el tiempo y asi dure mas?
Si eso es lo q queres, ponele un valor mas alto al timer (pero no lo satures), y al final de la ISR recargalo, porq si no siempre va a volver a cero.
Proba con esto:

#int_timer1
clockisr2()
{
      set_timer1(0xAAAA);
      PIN_B0=!PIN_B0;
}
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 19:09:26
Es eso lo que quiero, gracias.
Pregunta, cuando te referis a ponerle un valor alto al timer que es? Cuando te referis a recargar al final del ISR es lo que ya hiciste con el set_timer1 ??
Título: Re: Economizar Backlight
Publicado por: gera en 16 de Agosto de 2008, 19:18:38
El valor con el q tenes q recargar el timer depende del periodo q quieras q tenga, y del periodo del clock. Mientras mas alto sea este valor, menos tiempo va a demorar en desbordar el timer.
Sabes q el timer1 desborda a los 0x10000, y sabiendo q cada tick de clock dura x µs, podes calcular cuantos ticks tienen q pasar para q desborde. Si no entendes bien, googlea un poco, hay unas formulitas para calcular el periodo del timer...

El programa q te pase arriba deberia funcionar... probalo
saludos!
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 19:20:28
Si lo probe pero ahora nisiquiera enciende.
Título: Re: Economizar Backlight
Publicado por: gera en 16 de Agosto de 2008, 19:28:22
A todo esto... con q pic estas trabajando? a q frecuencia? como lo tenes conectado?
pueden ser muchas las fuentes del problema, no necesariamente de software.
saludos!
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 19:32:37
Estoy usando clock interno a 8mhz, funciona todo bien, es un controlador que hice que funciona hace tiempo pero queria ahora que el display quede encendido.
El pic es un 18f4620.
Cuando hacia lo que puse arriba parpadeaba constantemente.
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 19:42:32
Hago esto pero si cambio el numero de set_timer no varia nada.
Los seteos de los timers del main que puse arriba estan bien?

#int_timer1
clockisr2()
{

      set_timer1(0xFFFF);
      if(Iluminacion == 1)
         Iluminacion =0 ;
      else
         Iluminacion = 1;
      output_bit(PIN_B0,Iluminacion);
}

Título: Re: Economizar Backlight
Publicado por: gera en 16 de Agosto de 2008, 21:22:52
ese programa me gusta mas ya q no estoy seguro si se puede hacer PIN_B=!PIN_B. Los seteos a simple vista estan bien... sobra el primer enable_interrupts(global); porq despues lo pones mas abajo de nuevo.
Lo q veo es q estas cargando el timer1 con 0xFFFF... te comento q el timer1 no va decreciendo, sino al reves, y cuando llega a 0x10000 desborda. Por lo tanto si lo cargas con 0xFFFF va a desbordar al cabo de 1tick...
Otra cosa q podrias hacer, es usar el modulo pwm.

saludos!
Título: Re: Economizar Backlight
Publicado por: BrunoF en 16 de Agosto de 2008, 21:25:35
Hago esto pero si cambio el numero de set_timer no varia nada.
Los seteos de los timers del main que puse arriba estan bien?

#int_timer1
clockisr2()
{

      set_timer1(0xFFFF);
      if(Iluminacion == 1)
         Iluminacion =0 ;
      else
         Iluminacion = 1;
      output_bit(PIN_B0,Iluminacion);
}



Es demasiada alta la frecuencia de encendido y apado que generás poniendo 0xFFFF en el timer_1.
Además, la instrucción outout_bit(byte,bit) debería ir fuera del if. Así como está no va a apagar nunca.

Vamos a suponer que para que no se note el destello queremos unos 100hz de encendidos y apagados por segundo.
Supongamos un tiempo de trabajo(duty) del 50% para simplificar los cálculos. No creo que sea tan estricto aunque tal vez buscando un duty adecuado economices aún más energía y no se note el parpadeo.

Volviendo: 100 Hz. Entonces queremos que apague y encienda 200 veces en total por segundo...
Vamos a la matematica tan bonita(y que lo lamento, pero intentar programar sin utilizar cálculos matemáticos es como querer escribir un libro sin saber un idioma...). La matemática es la herramienta base de casi todas las ciencias formales.

Entonces: 1 seg / 200 = 5 ms(milisegundos)

Debemos hacer entonces que el pin PORTB,0 invierta su estado cada 5 ms.(Supongo que usas 8Mhz)

T1 = (65536 - precarga) * Preescaler * 4 / Fosc

Sabemos el T1 que deseamos. Es 5 milisegundos(o bien, 5000 us que es lo mísmo)
Has elegido en tu programa un preescaler de 1:1. Probemos a ver si logramos ese número...

Quedaría:

5000us= (65536 - precarga) * 1 * 4 /  8000000 us
5000us= (65536 - precarga) * 1 * 0.5 us
5000us= (65536 - precarga) * 0.5 us
2500= 65536 - precarga
precarga= 65536-2500
precarga=63036

Eso nos haría que el Timer1 desborde cada 5ms.

Entonces, el código quedaría:

#int_timer1
clockisr2()
{
      set_timer1(63036);
      PIN_B0=!PIN_B0;
}

Y debería encender y apagar 100 veces por segundo. 50% del tiempo encendido, 50% del tiempo apagado.
Si deseas cambiar el % de encendido/apagado, deberás cargar al timer1 con valores distintos. Se puede hacer con el mísmo tipo de cálculos.

Saludos.
Título: Re: Economizar Backlight
Publicado por: pablo en 16 de Agosto de 2008, 23:53:43
Muchas gracias a todos por la ayuda que me estan dando.
Acabo de compilar esto y me marca este error.

Excepting LVALUE such como una variable name or * expresion --   PIN_B0=!PIN_B0
Esto no seria lo mismo que hacer esto? De esta forma lo simulo, prende y apaga en un 1 segundo solo 3 veces.

#int_timer1
clockisr2()
{

      set_timer1(63036);
      if(Iluminacion == 1)
         Iluminacion =0 ;
      else
         Iluminacion = 1;
 
     output_bit(PIN_B0,Iluminacion);
}


Si hago esto, no parpadea, pero no estoy seguro de que este alargando la vida del back, osea si realmente esta permaneciendo un tiempo considerable apagado.
Igualmente quiero ver la forma que me estan diciendo ustedes porque realmente no se como hacerlo funcioanar.

#int_timer1
clockisr2()
      output_bit(PIN_B0,0);
      delay_us(200);
      output_bit(PIN_B0,1);
}

Otra duda. Partiendo de esta cuenta.
5000us= (65536 - precarga) * 0.5 us

(65536 - 63036) * 0.5 me da 1250 no 5000us, como llego a este resultado?
Título: Re: Economizar Backlight
Publicado por: BrunoF en 17 de Agosto de 2008, 14:20:45
Otra duda. Partiendo de esta cuenta.
5000us= (65536 - precarga) * 0.5 us

(65536 - 63036) * 0.5 me da 1250 no 5000us, como llego a este resultado?

Pues, fácil...te equivocas...como lo hice yo..y listo! :D :D :D
Ahhh...era para ver si estabas atento a lo que te decia... :D :D
Fuera de broma, me equivoqué. Corregilo.

Saludos

Título: Re: Economizar Backlight
Publicado por: pablo en 17 de Agosto de 2008, 15:40:40
Jaja, bueno, por lo menos quiere decir que entendi lo que me explicaste.
Tengo un problema ahora mas raro.
Hice un programita exclusivo para probar esto y funciona perfecto, desde una precarga de 45000 en adelante. Menor valor de precarga ya se nota el parpadeo.
Ahora el tema es que lo quiero implementar en mi soft y parpadea hasta con la mayor frecuencia.
Estoy usando el timer1 exclusivamente para el back y solo para eso. Puede algun delay del programa o de otro timer interferir en los tiempos del timer1?

Gracias.
Título: Re: Economizar Backlight
Publicado por: BrunoF en 17 de Agosto de 2008, 19:39:35
Si. Puede. Si utilizás demoras o subrutinas durante las cuales el CCS deshabilita las interr, te va a suceder eso.

Fijate que al compilar te deben salir unos mensajes de que el CCS deshabilitó las interr. en ciertas líneas de programa.

Saludos.
Título: Re: Economizar Backlight
Publicado por: pablo en 17 de Agosto de 2008, 20:08:09
Si, aparecio 22 veces. Osea que entonces no voy a poder hacer esto no? El PWM por hard no deberia verse afectado por nada no? Esta seria la unica forma que tengo de hacerlo o hay otro metodo?

De la unica forma que lo logre fue poner un manteniendolo apagado pero no por mas de 200us. Nada.
De esta forma
output_bit(PIN_B0,0);
delay_us(200);
output_bit(PIN_B0,1);
Pero de esta forma no se realmente cuanto tiempo permanece prendido hasta que se vuelve  a apagar.

Se te ocuerre otra forma de hacer esto?