AT89S52 příkaz INC, DEC a rotační kodér

Zdravím,
pomocí příkazu INC a DEC lze zvětšovat a zmenšovat čísla o jedno. Lze nějakým způsobem zvětšovat číslo ne v 8bitech ale zvlášť v horních čtyřech bitech a zvlášť v dolních čtyřech bitech? (nevím, zda jsem to správně popsal). Mám dvě 4bitové zařízení a potřeboval bych je nezávisle ovládat zvyšováním o jedno aniž bych musel použít 2 porty.

Dalším oříškem je pro mě použití rotačního kodéru. Trochu chápu princip jak funguje. Akorát nevím, jak bych to mohl programově udělat. Vím, že když točím na jednu stanu, tak jeden výstup je o 90 stupňů posunutý. Tudíž musím říct MCU aby současně vzal data např. z P1.0 a P1.1. Ale jak mu zároveň řeknu, že jeden z nich je pootočený a tudíž bude dělat INC např. v R1 a točením na druhou stranu DEC R1?

Honza

Když ty dva průběhy navzorkuješ tak dostanes několik stavu stavového automatu který pak vyhodnocuješ

  1. 10
  2. 11
  3. 01
  4. 00

  1. 10 (od zacatku)

a podle toho se točíš jednim nebo druhým směrem. Taky se to dá vyhodnocovat jednoduše tak že tě zajímá sestupná nebo náběžná hrana jednoho signálu (A) (tu lze snadno chytit v přerušení) a v okamžiku kdy nastane se jen podívat jaká je hodnota druhého signálu (B) - 1 vlevo, 0 vpravo.

Současné čtení z portu je třeba

MOV A,P1
ANL A,#0x03

a v registru A máš stav dvou spodních bitu.

Přičítání/odečítání půlky bytu :

přičtení/odečtení 1 k dolní polovině :

  1. Vezmeš celý byte
  2. uděláš si kopii
  3. v původním bytu uděláš masku F0h
  4. ke kopii přičteš/odečteš 1
  5. v kopii uděláš masku 0Fh
  6. do původního přidáš pomocí or kopii

přičtení/odečtení 1 k horní polovině :

  1. Vezmeš celý byte
  2. uděláš si kopii
  3. v původním bytu uděláš masku 0Fh
  4. ke kopii přičteš/odečteš 10h
  5. v kopii uděláš masku F0h
  6. do původního přidáš pomocí or kopii

Rotační kodér :
Používám externí přerušení, ale není to nutné. Pokud použiješ přerušení, musíš vyřešit zákmity na úrovni HW (viz.dále). Způsobů je hned několik :

A) Vystačíš si s detekcí jenom jedné hrany - v případě mechanických kodérů je to postačující, protože tyto kodéry (alespoň ty od firmy ALPS, které používám mají v každé poloze aretaci - cvakají). Pro tyto kodéry ostatní způsoby načítání impulzů nejsou vhodné, protože mezi cvaknutími proběhne celý cyklus.

  1. detekuješ náběžnou (nebo sestupnou) hranu. V případě použití přerušení (INT0 nebo INT1) ho nastavíš tak, aby mcu reagoval na jednu z hran, tím máš detekci hrany vyřešenou. Externí přerušení u MCU s architekturou 8051 myslím reaguje na sestupnou hranu nebo na hladinu log. 0 - musíš nastavit reakci na sestupnou hranu.
  2. V okamžiku detekce hrany (nebo v přerušení) zkontroluješ stav druhého pinu a podle jeho hodnoty se rozhodneš, jestli budeš přičítat nebo odečítat.

Další způsoby jsou vhodné pro rotační kodéry magnetické (třeba rotační kodér vytvořený použitím motoru z CD/DVD mechaniky) nebo pro rotační kodéry s optickým snímáním.

B) Detekce obou hran - pokud detekuješ obě hrany, pak v okamžiku detekce hrany musíš zjistit stav obou pinů. Pokud jsou oba v log. 0 nebo oba v log. 1 - přičteš, pokud ne, odečteš (případně přehodíš přičítání a odečítání). Prakticky tím zdvojnásobíš počet impulzů na otáčku.

C) Detekce obou hran na obou signálech - Tady je to prakticky dvojitý postup z bodu B) s tím, že -
po detekci hrany na signálu 1 platí:
pokud signál 1=signál 2, přičteš, jinak odečteš
po detekci hrany na signálu 2 platí:
pokud signál 1=signál 2, odečteš, jinak přičteš
Tímto postupem dostaneš čtyřnásobný počet impulzů na otáčku.

Tady máš ještě odkaz na ošetření zákmitů pro kodér : https://forum.mcontrollers.com/t/osetreni-zakmitu-tlacitka-na-ext-preruseni/2818/1
Hodnoty součástek jsou 68-100 Ohmů pro R a 10n pro kondíky. V tom příspěvku se schématem je chybně uvedených 100n a to je moc. Jinak používám mcu AVR a zapínám interní pull-up rezistory a protože 8051 interní rezistory pravděpodobně nemá, tak musíš ještě přímo ze vstupního pinu na VCC dát odpor tak 20-50 kOhmů. Stejně jako AVRka mají interní pull-up 20-50 kOhmů.

A ještě jedna poznámka :
Kdyby ses náhodou pustil do využití motoru z CD/DVD mechaniky, tak chci upozornit, že tyto mechaniky mají 3 signály - jsou tam 3 HALovy sondy.

Moc díky za odpovědi. Bohužel přerušení a tím pádem ani časovače neovládám, takže nastuduju jak pracovat s časovačem a přerušením a použiju vaší teorii. Mám mechanický kodér ze staré počítačové myšky. Použití motorku jako kodéru? To jsem ještě neslyšel. Ale zkusím nastudovat.
AT89 má kromě portu 0 interní pull-up 10k.

Tady jsou ukázky :
youtube.com/watch?v=avDF0NkG9Vs
youtube.com/watch?v=7QPQVmoT3zA

Mám to odzkoušené, funguje to. Je to malinko složitější, než ten mechanický, zase není nutné ošetřovat zákmity.

Jinak přerušení a časovače je více, než vhodné se naučit, protože to jsou věci, bez kterých se prakticky neobejdeš a které když zvládneš, tak Ti ušetří mraky práce při různých zpracováních vstupů, zobrazování třeba na LED displejích. Když k tomu pak přihodíš PWM, tak v hlavním programu můžeš na 4-mistný LED displej psát zápisem do 4 bytů RAM procesoru a jas displeje řídit zápisem do 1 regisrtu MCU. O všechno ostatní se postará rutina pověšená na přerušeních od časovače a OCR. Mám dokonce uděláno to, že o jas se stará přerušení od AD převodníku, na který mám pověšený fotorezistor. Převodník neustále snímá napětí na děliči fotorezistor/pevný odpor a přečtenou hodnotu zapisuje periodicky do paměti. Odtud si při každém přerušení bere časovač hodnotu, jak dlouho (jakou část periody čítače) má displej svítít. Tím řídím jas LED displeje v závislosti na okolí aniž bych se o to musel starat v hlavním programu.

Nechci Tě od toho odrazovat. Začni pomalu. Nejdřív blikat LEDkou, pak blikat pomocí přerušení a ostatní přijde časem.

Kdysi dááááávno jsem řešil náhradu potenciometru rotačním enkodérem a chtěl jsem použít 89C2051. Nakonec jsem použil jen hw řešení: 2x invertor, 1x D klopný obvod a MCP4011. Inspirace byla zde:

elektronika.kvalitne.cz/ATMEL/ne … coder.html

Po čase, když už to nebylo aktuální jsem našel toto pro 89S8252, třeba to pomůže. Už jsem to ani nezkoušel, ale pro inspiraci by to mohlo stačit.
ENCODER.ZIP (3.03 KB)