El programa del grup 3 té present la posició del potenciòmetre per escollir entre dos modes de funcionament. En el primer mode, quan es prem el polsador presenta el número que ha triat aleatòriament entre 1 i 6 mentre sona una melodia. Un cop finalitzada la melodia, els LED romanen indicant el número i espera que es premi altre cop el polsador.
En el segon mode, quan es prem el polsador mostra una seqüència amb els LED i després presenta el número que ha triat aleatòriament entre 1 i 9. Els LED romanen indicant el número i espera que es premi altre cop el polsador.
El programa d'aquest grup és el següent:
#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 Nombre Retard1 ; Variables de retard Retard2 Ret Analogica ; Variable on es guarda el valor de l'entrada analògica Mode1 ; Variables on es guarda la configuració de bits necessària Mode2 ; per encendre els LED quan es mostren els números. Mode3 Mode4 ValPR2 ; Aquí hi guardarem el valor de PR2 ValCCPR1L ; Aquí hi guardarem el valor de CCPR1L ValDC1B ; Aquí hi guardarem el valor de DC1B ValCCP1CON ; Aquí hi guardarem el valor de CCP1CON endc
org 0 Inici bsf STATUS,RP0 ; Tria el banc 1 movlw b'10000000' ; Configuració de Timer0 movwf OPTION_REG ; Ho guarda al registre de configuració del Timer0 clrf TRISB ; Posa el port B com a sortida clrf TRISC ; Posa el port C com a sortida movlw 0xFF ; Posa l'acumulador a FFh (tot uns) movwf TRISA ; Posa tots els bits del port A com a entrada movlw b'00010000' ; Posa el conversor a 1/8 de la freqüència movwf ADCON1 ; Copia W a la configuració del conversor A/D movlw b'00100000' ; Definim com volem les E/S del port C movwf TRISC ; RC5 (sortida del PWM) com a entrada bcf STATUS,RP0 bsf STATUS,RP1 ; Tria el banc 2 movlw 0xFF ; Posa l'acumulador a FFh (tot uns) movwf ANSEL ; Configura AN0-AN7 com entrades analògiques bcf STATUS,RP0 bcf STATUS,RP1 ; Tria el banc 0 movlw b'00000001' ; activa el conversor A/D connectat a AN0 movwf ADCON0 ; amb el resultat justificat per l'esquerra clrf PORTB clrf PORTC movlw b'00000000' movwf Mode1 movwf Mode2 movwf Mode3 movwf Mode4 movlw b'00001100' ; Configura el PWM, bits P1M (bits 7-6) a 00 mode senzill ; DC1B = 00 (bits 5-4) els dos bits de menys pes són 0 ; CCP1M = 11xx en mode senzill els bit 0 i 1 no afecten movwf ValCCP1CON ; Ho guarda per fer-ho servir més tard movwf CCP1CON ; Ho posa com a configuració del PWM movlw b'00000011' ; Configura el Timer 2 ; bits T2KCPS (bits 1-0) a 11 prescalat de 16 ; bit 2 (TMR2ON) a 0, Timer aturat ; Postscaler TOUTPS (bits 6-3) no afecten al PWM movwf T2CON ; Ho posa com a configuració del Timer 2 Polsador movf Mode1,w movwf PORTB ; Posa Mode1 al port B (1) movf Mode3,w movwf PORTC ; Posa Mode3 al port C (2) nop nop nop movf Mode2,w movwf PORTB ; Posa Mode2 al port B / Mode 1 hi ha estat durant 4 us (microsegons) movf Mode4,w movwf PORTC ; Posa Mode4 al port C / Mode 3 hi ha estat durant 4 us btfsc PORTA,3 goto Polsador ; Torna a Polsador clrf PORTB clrf PORTC call RetM Pols btfss PORTA,3 ; Mira si està desactivada l'entrada A3 ; Si està desactivada, no fa la instrucció següent ; Fa la instrucció si l'entrada està activada goto Pols ; Si no està premut, torna a Polsador call RetM nop ; espera un microsegon nop ; espera un microsegon nop ; espera un microsegon nop ; espera un microsegon nop ; espera un microsegon, en total 5 bsf ADCON0,GO ; Inicia la conversió btfsc ADCON0,GO ; Quan el bit sigui 0 la conversió haurà acabat goto $-1 ; repetim la línia fins que deixi de ser 1 movf ADRESH,w ; Permuta els nibbles dels bits superiors movwf Analogica movlw b'01111110' subwf Analogica,w ; W = variable - W, C = 1 si variable >= W btfss STATUS,C ; Si C=1 salta goto GenerarSis ; si Analogica < 126 va a GenerarSis goto Generar ; si Analogica >= 126 va a Generar (bucle que genera números de 1 a 9) GenerarSis ; Genera números de l'1 al 6 movf TMR0,w andlw b'00000111' movwf Nombre movlw b'00000110' subwf Nombre,w ; W = variable - W, C = 1 si variable >= W btfss STATUS,C ; Si C=1 salta goto seq1 ; si Nombre < 6 va a seq1 (seqüència musical) goto GenerarSis ; si el Nombre >= 6 agafa un altre número seq1 movlw .141 ; Valor que correspon aproximadament a re3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .71 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .0 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaCorxera ; Toca la nota configurada movlw .158 ; Valor que correspon aproximadament a do3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .79 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .2 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaSemiCorxera ; Toca la nota configurada movlw .158 ; Valor que correspon aproximadament a do3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .79 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .2 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaSemiCorxera ; Toca la nota configurada movlw .141 ; Valor que correspon aproximadament a re3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .71 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .0 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaCorxera ; Toca la nota configurada movlw .158 ; Valor que correspon aproximadament a do3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .79 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .2 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaCorxera ; Toca la nota configurada call RetM movlw .126 ; Valor que correspon aproximadament a fa3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .63 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .2 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaCorxera ; Toca la nota configurada movlw .118 ; Valor que correspon aproximadament a sol3 movwf ValPR2 ; Ho posem com a valor de PR2 movlw .59 ; Valor que correspon a un cicle del 50 % movwf ValCCPR1L ; Valor de CCPR1L movlw .2 ; Valor dels bits de menys pes del CCP movwf ValDC1B ; Valor de DC1B call TocaCorxera ; Toca la nota configurada call RetM ; Espera 0,2 goto Visualitzar seq2 movlw b'01000000' movwf PORTB call RetM clrf PORTB movwf PORTC call RetM clrf PORTC movlw b'10010000' movwf PORTB call RetM clrf PORTB movlw b'01010000' movwf PORTC call RetM clrf PORTC movlw b'10000000' movwf PORTB call RetM clrf PORTB movwf PORTC call RetM clrf PORTC movlw b'01010000' movwf PORTB call RetM clrf PORTB movlw b'10010000' movwf PORTC call RetM clrf PORTC goto Visualitzar Generar ; Genera números de l'1 al 9 movf TMR0,w andlw b'00001111' movwf Nombre movlw b'00001001' subwf Nombre,w ; W = variable - W, C = 1 si variable >= W btfss STATUS,C ; Si C=1 salta goto seq2 ; si Nombre < 9 va a seq 2 (seqüència lumínica) goto Generar ; si el Nombre >= 9 agafa un altre número Visualitzar movlw b'00001000' xorwf Nombre,w ; Compara Nombre amb 8, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Nou movlw b'00000111' xorwf Nombre,w ; Compara Nombre amb 7, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Vuit movlw b'00000110' xorwf Nombre,w ; Compara Nombre amb 6, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Siete movlw b'00000101' xorwf Nombre,w ; Compara Nombre amb 5, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Sis movlw b'00000100' xorwf Nombre,w ; Compara Nombre amb 4, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Cinc movlw b'00000011' xorwf Nombre,w ; Compara Nombre amb 3, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Quatre movlw b'00000010' xorwf Nombre,w ; Compara Nombre amb 2, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Tres movlw b'00000001' xorwf Nombre,w ; Compara Nombre amb 1, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Dos movlw b'00000000' xorwf Nombre,w ; Compara Nombre amb 0, si son iguals s'activa Z btfsc STATUS,Z ; Si no son iguals salta goto Un Un movlw b'00100000' movwf Mode1 movwf Mode2 movlw b'00000000' movwf Mode3 movwf Mode4 goto Polsador ; Torna al polsador Dos movlw b'11000000' movwf Mode1 movwf Mode2 movlw b'00000000' movwf Mode3 movwf Mode4 goto Polsador ; Torna al polsador Tres movlw b'11100000' movwf Mode1 movwf Mode2 movlw b'00000000' movwf Mode3 movwf Mode4 goto Polsador ; Torna al polsador Quatre movlw b'11000000' movwf Mode1 movlw b'00010000' movwf Mode2 movlw b'00000000' movwf Mode3 movwf Mode4 goto Polsador ; Torna al polsador Cinc movlw b'11000000' movwf Mode1 movlw b'00110000' movwf Mode2 movlw b'00000000' movwf Mode3 movwf Mode4 goto Polsador ; Torna a polsador Sis clrf PORTC movlw b'11000000' movwf Mode1 movlw b'00010000' movwf Mode2 movwf Mode3 movlw b'00000000' movwf Mode4 goto Polsador ; Torna al polsador Siete movlw b'11100000' movwf Mode1 movlw b'00010000' movwf Mode2 movwf Mode3 movlw b'00000000' movwf Mode4 goto Polsador ; Torna al polsador Vuit movlw b'11000000' movwf Mode1 movwf Mode3 movlw b'00010000' movwf Mode2 movwf Mode4 goto Polsador ; Torna al polsador Nou movlw b'11000000' movwf Mode1 movwf Mode3 movlw b'00110000' movwf Mode2 movwf Mode4 goto Polsador ; Torna al polsador
RetM ; Funció de retard de 0,2 s decfsz Retard1,f goto RetM decfsz Retard2,f goto RetM return corxera decfsz Retard1,f goto corxera decf Retard2,f decfsz Retard2,f goto corxera return semicorxera decfsz Retard1,f goto semicorxera decf Retard2,f decf Retard2,f decf Retard2,f decfsz Retard2,f goto semicorxera return TocaSemiCorxera movf ValPR2,w ; Valor de PR2 per a la nota desitjada bsf STATUS,RP0 ; Tria el banc 1 bsf TRISC,5 ; Posem RC5 (sortida del PWM) com a entrada movwf PR2 ; Ho posem com a comparació al Timer 2 bcf STATUS,RP0 ; Tria el banc 0 movf ValCCP1CON,w ; Agafa la configuració de CCP1CON andlw b'11001111' ; Posa els bits que corresponen a DC1B a zero per precaució movwf ValCCP1CON ; I ho torna a guardar swapf ValDC1B,w ; Agafa el valor que ha d'anar a DC1B ; I el guarda, permutat, a W ; Els dos bits han de quedar a les posicions 4-5 andlw b'00110000' ; Posa els altres sis bits a zero per precaució iorwf ValCCP1CON,w ; I ho afegeix a CCP1CON movwf CCP1CON ; Ho posa com a configuració del PWM movf ValCCPR1L,w ; Valor de CCPR1L movwf CCPR1L ; Registre que ens dona l'amplada de tON bcf PIR1,TMR2IF ; Desactiva el bit d'interrupció del Timer 2 bsf T2CON,TMR2ON ; Activa el Timer 2 ; No convé engegar el PWM fins que el Timer 2 no ha fet un cicle btfss PIR1,TMR2IF ; Espera l'activació del bit d'interrupció del Timer 2 goto $-1 bsf STATUS,RP0 ; Tria el banc 1 bcf TRISC,5 ; Posem RC5 (sortida del PWM) com a sortida bcf STATUS,RP0 ; Tria el banc 0 call semicorxera ; Espera bsf STATUS,RP0 ; Tria el banc 1 bsf TRISC,5 ; Posem RC5 (sortida del PWM) com a entrada ; Fem silenci bcf STATUS,RP0 ; Tria el banc 0 call semicorxera ; Espera return TocaCorxera movf ValPR2,w ; Valor de PR2 per a la nota desitjada bsf STATUS,RP0 ; Tria el banc 1 bsf TRISC,5 ; Posem RC5 (sortida del PWM) com a entrada movwf PR2 ; Ho posem com a comparació al Timer 2 bcf STATUS,RP0 ; Tria el banc 0 movf ValCCP1CON,w ; Agafa la configuració de CCP1CON andlw b'11001111' ; Posa els bits que corresponen a DC1B a zero per precaució movwf ValCCP1CON ; I ho torna a guardar swapf ValDC1B,w ; Agafa el valor que ha d'anar a DC1B ; I el guarda, permutat, a W ; Els dos bits han de quedar a les posicions 4-5 andlw b'00110000' ; Posa els altres sis bits a zero per precaució iorwf ValCCP1CON,w ; I ho afegeix a CCP1CON movwf CCP1CON ; Ho posa com a configuració del PWM movf ValCCPR1L,w ; Valor de CCPR1L movwf CCPR1L ; Registre que ens dona l'amplada de tON bcf PIR1,TMR2IF ; Desactiva el bit d'interrupció del Timer 2 bsf T2CON,TMR2ON ; Activa el Timer 2 ; No convé engegar el PWM fins que el Timer 2 no ha fet un cicle btfss PIR1,TMR2IF ; Espera l'activació del bit d'interrupció del Timer 2 goto $-1 bsf STATUS,RP0 ; Tria el banc 1 bcf TRISC,5 ; Posem RC5 (sortida del PWM) com a sortida bcf STATUS,RP0 ; Tria el banc 0 call corxera ; Espera call semicorxera bsf STATUS,RP0 ; Tria el banc 1 bsf TRISC,5 ; Posem RC5 (sortida del PWM) com a entrada ; Fem silenci bcf STATUS,RP0 ; Tria el banc 0 call corxera ; Espera return end

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