En els exemples anteriors els LED s'encenien a un ritme que marcaven uns bucles de retard que teníem en el programa. Això volia dir que la major part del temps el processador estava fent bucles. En aquest exemple, en lloc de tenir el microcontrolador ocupat fent bucles per comptar el temps, fem que un temporitzador físic (timer) s'encarregui de comptar el temps. En el nostre cas farem servir el Timer1 que és un comptador de 16 bits. Quan funciona com a temporitzador, agafa la sortida del rellotge del microcontrolador (període d'un microsegon), el divideix per un factor d'escala i el fa servir per incrementar el registre TMR1 (bytes TMR1L i TMR1H). Quan aquest registre arriba a zero s'activa un bit en un altre registre.
En aquest exemple cada cop que Timer1 acabi de comptar incrementarem la variable Visualit i en copiarem el resultat sobre els LED. Li hem posat un prescalador de 8, de manera que s'incrementa cada 8 μs i ha de comptar 65536; per tant, fara una rotació cada 0,52 s.
#include <p16F690.inc> __config (_INTRC_OSC_NOCLKOUT&_WDT_OFF&_PWRTE_OFF&_MCLRE_OFF&_CP_OFF&_BOR_OFF&_IESO_OFF&_FCMEN_OFF)
cblock 0x20 Visualit ; Una variable on guardem el que mostraran els LED endc
org 0 Inici bsf STATUS,RP0 ; Tria el banc 1 clrf TRISC ; Posa tots els bits del port C com a sortida bcf STATUS,RP0 ; Tria el banc 0 movlw b'00110001' ; Configuració de Timer1 ; 11 - Factor d'escala de 8 ; I el posem en marxa movwf T1CON ; Ho guarda al registre de configuració del Timer1 bcf PIR1,TMR1IF ; Desactivem el bit de fi del temporitzador clrf Visualit ; Posa Visualit a 0 movf Visualit,w ; Copia Visualit a l'acumulador movwf PORTC ; I ho posa als LED Bucle btfss PIR1,TMR1IF ; Mira si Timer1 ha arribat a zero ; Si hi ha arribat, no fa la instrucció següent goto Bucle ; Si no hi ha arribat, repeteix la instrucció bcf PIR1,TMR1IF ; Si ha arribat, desactivem el bit incf Visualit,f ; Incrementem Visualit movf Visualit,w ; Copia Visualit a l'acumulador movwf PORTC ; I ho posa als LED goto Bucle ; Repetim-ho... end
Veiem com els LED van comptant de 0 (0000) a 15 (1111) i quan acaben tornen a començar. Però ho fan a una velocitat relativament ràpida. Per aconseguir un desplaçament lent dels LED també podem fer servir un comptador de manera que només canviem els LED cada un cert nombre de cicles de Timer1 i així aconseguir una velocitat més precisa. També podem variar el nombre de cicles que fa Timer1 posant-li un valor determinat al registres TMR1L i TMR1H en el moment de començar; entre les dues coses, podríem ajustar el temps com volguéssim.
En el següent programa mantenim el pre-escalat de 8 vol dir que cada increment del comptador són 8 μs. Si volem que el final del temporitzador sigui cada 0,05 s (és a dir cada 50 000 μs) ens caldrà comptar fins a 50 000 /8 = 6250. Per posar aquest valor, farem:
TMR1 = 65536 - 6250 = 59286 TMR1H = 59286 / 256 = 231 TMR1L = 59286 % 256 = 150
En el programa següent el temporitzador acaba cada 0,05 s, com hem calculat, i la rotació dels LED es fa cada 20 cops, o sigui cada segon:
#include <p16F690.inc> __config (_INTRC_OSC_NOCLKOUT&_WDT_OFF&_PWRTE_OFF&_MCLRE_OFF&_CP_OFF&_BOR_OFF&_IESO_OFF&_FCMEN_OFF)
cblock 0x20 Visualit ; Una variable on guardem el que mostraran els LED Compta ; Variable per comptar el nombre de cicles endc
org 0 Inici bsf STATUS,RP0 ; Tria el banc 1 clrf TRISC ; Posa tots els bits del port C com a sortida bcf STATUS,RP0 ; Tria el banc 0 clrf Visualit ; Posa Visualit a 0 movf Visualit,w ; Copia Visualit a l'acumulador movwf PORTC ; I ho posa als LED movlw .20 ; Canviarem els LED cada 20 cicles de Timer1 movwf Compta ; Guarda el valor a Compta movlw .231 ; Inicialitza el Timer1 movwf TMR1H movlw .150 movwf TMR1L bcf PIR1,TMR1IF ; Desactivem el bit de fi del temporitzador movlw b'00110001' ; Configuració de Timer1 ; 11 - Factor d'escala de 8 ; I el posem en marxa movwf T1CON ; Ho guarda al registre de configuració del Timer1 Bucle btfss PIR1,TMR1IF ; Mira si Timer1 ha arribat a zero ; Si hi ha arribat, no fa la instrucció següent goto Bucle ; Si no hi ha arribat, repeteix la instrucció bcf T1CON,TMR1ON ; Atura momentàniament el Timer1 movlw .231 ; Inicialitza el Timer1 movwf TMR1H movlw .150 movwf TMR1L bsf T1CON,TMR1ON ; Torna a engegar el Timer1 bcf PIR1,TMR1IF ; Si ha arribat, desactivem el bit decfsz Compta,f ; Decrementem Compta goto Bucle ; Si no és zero, torna a esperar el Timer1 incf Visualit,f ; Incrementem Visualit movf Visualit,w ; Copia Visualit a l'acumulador movwf PORTC ; I ho posa als LED movlw .20 ; Tornem a posar el nombre de cicles movwf Compta ; Guarda el valor a Compta goto Bucle ; Repetim-ho... end

Aquesta obra d'Oriol Boix està llicenciada sota una llicència no importada Reconeixement-NoComercial-SenseObraDerivada 3.0.