Zliczanie impulsów encodera inkrementalnego

    -- Sebastian Pawlak, 2003.


Zaprezentowany program zlicza impulsy encodera inkrementalnego w obu kierunkach. Zastosowałem taką konstrukcję algorytmu, która uniemożliwia zliczanie "fałszywych" impulsów powstających np. podczas wibracji wałka encodera.
Na poniższym schemacie zobrazowałem podłączenie encodera do procesora. Dodatkowo należy podłączyć wyświetlacz LCD pod właściwe piny (patrz: program lcd.c)

Schemat podłączeniowy
Schemat podłączeniowy


Kod źródłowy pliku "encoder.c":

/* Encoder
 * Program zlicza i wyswietla na wyswietlaczu impulsy encodera.
 * Sebastian Pawlak, 2003.
 */

#include <stdio.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/signal.h>
#include "lcd.h"

/*#define __AVR_AT90S8535__*/

volatile long int licz = 0;
volatile int flagaA = 0, flagaB = 0;


SIGNAL (SIG_INTERRUPT0)
{
   if (!(inb(PIND) & 16))  /* jesli 0 na kanale B */
        flagaA = 1;
    else                       /* w przeciwnym przypadku (1 na kanale B) */
        flagaB = 1;
}


SIGNAL (SIG_INTERRUPT1)
{
    if (inb(PIND) & 16) {     /* jesli 1 na kanale B */
        if (flagaA)               /* jesli flagaA ustawiona */
            licz++, flagaA = 0;
    } else if (flagaB)            /* jesli flagaB ustawiona */
        licz--, flagaB = 0;
}


int main(void)
{
    char s[16];

    outp(0, DDRD);

    /* Ustawianie przerwan INT 0 i INT1 wyzwalanych zboczem narastajacym
     * i opadajacym.
     */
    outp((1<<INT0)|(1<<INT1), GIMSK);
    outp((1<<ISC01)|(1<<ISC00) | (1<<ISC11), MCUCR);


    initLCD();

    sei();  /* zezwala na przerwania */

    for (;;) {
        cursorHome();
        sprintf(s, "%ld ", licz);
        wypiszLancuch(s);
    }

    return 0;
}
w3cw3c
automatyka przemysłowa