Ebben a leckében a demópanel nyomógombja szolgál a LED-ek léptetésére.
Fájlok: ITT.
Megtanuljuk:
- a #define használatát, hogy SFR-eknek és SFR biteknek hangzatosabb nevet adhassunk,
- hogyan használjunk egy lábat digitális bemenetként, ha a lábon ADC is elérhető
- a PORTx SFR használatát egy láb állapotának beolvasásához,
- a mechanikus pergés szoftveres kezelésének egy módját.
Ebben a leckében egy külön header fájl is van (04 Switch Input.h), melyben a #define direktíva segítségével jobb elnevezéseket adhatunk a portlábaknak és a konstansoknak.
#define Switch_Pin PORTBbits.RB0
#define DetectsInARow 5
Mint más fordítók, úgy a C18 is behelyettesíti a definiált értékeket fordításidőben. Ne feledjuk a header fájlt "include"-olni a forrásunkban (04 Switch Input.c)!
#include "04 Switch Input.h" //header file
A pergésmentesítésről:
A mechanikus kapcsolók sokszor megtalálhatóak beágyazott rendszereknél, mivel olcsók, egyszerűen működnek és megbízhatók, bár némelyik gyakran elég zajos. Ez a pergés, ami a gomb megnyomásakor jön létre. Lenyomáskor a kapcsolat többször összeér/megszakad, akár százszor is, mielőtt elérné a végleges állapotot. Így egy egyszerű gombnyomás több különböző gombnyomásként jelenik meg a vezérlő számára. Mint amikor a távirányítóval csatornát váltanál a TV-n, és egy helyett kettőt, vagy akár három csatornát is ugrik a készülék.
Klasszikus megoldás ennek elkerülésére, ha kiszűrjük a gyors váltakozást egy RC taggal, vagy RS logikával. Ezek mind hatékonyak, de extra költséget jelentenek mind pénzügyileg, mind a helyigény miatt. Szoftveres pergésmentesítésnél ezek a problémák nem állnak fenn.
Egy egyszerű megoldás, ha megnyomáskor mintavételezzük a kapcsolót, amíg stabil állapotba nem ér. Ez általában 5 ms körül mozog.
E leckében 1 ms-ként megnézzük a kapcsoló állapotát, várunk 5 ugyanolyan mintára, ha ez bekövetkezik, akkor a vezérlőnk érzékeli, hogy megnyomtuk a gombot. Noha a demópanelen található gomb nem pereg sokat, ez jó módja a gyakorlásnak.
Lássuk a forráskódot!
/** V A R I A B L E S *************************************************/
#pragma udata // declare statically allocated uinitialized variables
unsigned char LED_Display; // 8-bit variable
/** D E C L A R A T I O N S *******************************************/
#pragma code // declare executable instructions
void main (void)
{
unsigned char Switch_Count = 0;
LED_Display = 1; // init
TRISD = 0b00000000; // PORTD 7:0 mind kimenet (0)
INTCON2bits.RBPU = 0; // PORTB belso felhuzoellenallas bekapcsolasa
WPUBbits.WPUB0 = 1; // RB0 felhuzasa
ANSELH = 0x00; // AN8-12 digitalis bemenet(AN12 RB0n)
TRISBbits.TRISB0 = 1; // PORTB bit 0 bemenet(1)
while (1)
{
LATD = LED_Display; // LED_Display erteket kiirjuk PORTD-re
LED_Display <<= 1; // eltoljuk a kijelzot eggyel
if (LED_Display == 0)
LED_Display = 1; //ha tulcsordultunk, ujra beallitjuk az elsot
while (Switch_Pin != 1);// varunk a nyomogomb elengedesere
Switch_Count = 5;
do
{ // figyeljuk a nyomogombot 5 egymas utani alacsony ertekert
if (Switch_Pin == 0)
{ // lenyomott allapot felismerve
Switch_Count++;
}
else
{
Switch_Count = 0;
}
Delay10TCYx(25); // delay 250 ciklus = 1ms.
} while (Switch_Count < DetectsInARow);
}
}
A programban 2 változót deklaráltunk (globálisként a LED_Display-t, és lokálisként a Switch_Count-ot). A globális változók a 3. lecke szerint dedikált helyre kerülnek, a lokálisak a software stack-be, és csak a függvény meghívásától a visszatérésig léteznek.
A demópanel kapcsolója az RB0 I/O lábra kapcsolódik, amit alapesetben Vdd-re húz egy belső felhúzóellenállás. Ha a gombot megnyomjuk, az lehúzza RB0-t Vss-re.
A PORTx SFR-t használjuk egy bemeneti láb állapotának kiolvasására. Tehát a PORTBbits.RB0 olvasása az RB0 láb aktuális értékét adja nekünk. Ne feledd, a header fájlban ezt Switch_Pin-ként definiáltuk, így ezt használjuk!
A PIC18F45K20 RB0 lába osztozik az AN12 analóg bemenettel. Ezeket a lábakat digitális vagy analóg bemenetté állíthatjuk. Ez fontos, mert mi digitális bemenetként használjuk ezt a lábat. Ha analógként lenne beállítva, mindig 0-t olvasnánk aktuális állapotnak. A beállításokat az ANSEL és az ANSELH SFR-eken végezhetjük el.
0-ba állítjuk az ANSELH minden bitjét a digitális üzemmódhoz: ANSELH = 0x00;
Mostmár használhatjuk RB0-t digitális bemenetként, tehát a TRISBbits.TRISB0 = 1 beállításra van szükségünk.
A futófény:
Ebben a leckében egyszerűbben shifteljük a LED-eket (Na ez már shiftregiszter!), mint a hármasban. A 04 Switch Input.c egy bitet állít be a LED_Display-ben, melyet aztán a LATD-re írunk, és eggyel shifteljük, amikor a kijelzőt frissítjük. A bit végül túlcsordul az MSB-nél (Most Significant Bit - Legnagyobb Helyiértékű Bit), szóval ezt figyeljük, és újra 1-re állítjuk a LED_Display értékét.
(Az I/O lábakról további információkat a PIC18F45K20 adatlapjában (DS41303) találhattok.)
Fordítsuk le, és égessük be a kódot piciny vezérlőnkbe!
Ha minden jól ment, akkor most van egy léptethető shiftregiszterünk, amit gyorsan nyomogatva futófényként használhatnánk (de minek nyomogassunk, írjunk rá időzítőt!!).
A cikk még nem ért véget, lapozz!
Értékeléshez bejelentkezés szükséges!