Sei sulla pagina 1di 12

Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

sciamannalucio.it

Arduino: encoder conta impulsi-giri


motore - Sciamanna Lucio
Autore dell'articolo: Lucio Sciamanna
13-17 minuti

A cosa serve un conta impulsi?

Un conta impulsi serve a contabilizzare gli impulsi elettrici che


arrivano da sensori, cioè a stabilirne la quantità in base ad una
unità di tempo. I sensori normalmente sono dei contagiri del motore
(encoder), oppure dei sensori di posizione. Servo nei robot per
stabilire il tragitto percorso e la direzione da prendere.

Il conta impulsi può servire per contare le persone che entrano in


una stanza o in una fiera. Ci sono misuratori di energia che
emettono impulsi in proporzione ai Watt consumati. Attualmente
anche i contatori di acqua e gas possono presentare delle uscite a
impulsi per il conteggio dei consumi.

Ci sono dei potenziometri che all’interno hanno un encoder rotativo


per stabilirne la posizione. Vengono utilizzati in abbinamento ad un
microprocessore, come Arduino, per cambiare numeri nelle
memorie o menù nei display.

Come funziona un conta impulsi

Il conta impulsi può essere diviso in almeno tre parti principali:

la base dei tempi T in cui vengono contabilizzati gli impulsi elettrici

la sezione elettronica che somma i singoli impulsi S

il circuito di ingresso che adatta il segnale entrante e lo rende


compatibile con la sezione elettronica che esegue il conteggio A

La base dei tempi può essere fissa con un certo lasso di tempo,
oppure senza tempo. In quest’ultimo caso il contatore di impulsi è
assoluto, e conteggia fino a quando non viene spento/azzerato.
Ogni impulso incrementa un contatore, aumentando il numero
memorizzato. Quando è terminato il tempo massimo per la conta il
numero viene visualizzato su un display o altro dispositivo di
visualizzazione. Il contatore ed il timer vengono azzerati e si
ricomincia a contare gli impulsi in ingresso.

1 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

La sezione che somma gli impulsi, via via che arrivano


all’ingresso, può essere di tipo elettromeccanico, oppure elettronica
a circuiti integrati o a microprocessore. Un particolare conta impulsi
di tipo elettromeccanico lo potresti trovare in casa tua sotto forma di
interruttore per le luci di casa. Quando si hanno più di 3 punti luce
da accendere/spegnere si utilizza un particolare dispositivo, il relè
passo passo, che ad ogni impulso ricevuto attiva o disattiva un relè.
In passato i mouse sfruttavano gli encoder ottici per contare gli
spostamenti in base agli impulsi ricevuti.

Arduino e encoder – mouse

Il circuito di adattamento del segnale di ingresso è da usare quando


la tensione dell’impulso è maggiore della tensione di alimentazione
del circuito integrato/microprocessore che conta gli impulsi. Un
semplice partitore di tensione può essere, in molti casi, sufficiente.

Come contare i giri del motore con Arduino e un


encoder

Per contare i giri di un motore dobbiamo accoppiare al rotore un


encoder rotativo. Nella immagine un motore è stato dotato di un
disco che alterna parti nere a parti trasparenti. Un sensore di
prossimità ad infrarossi riconosce quando viene a contatto con una
superficie nera, e quando invece la superficie è trasparente
(passaggio di luce).

2 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

Arduino e encoder – encoder fai da te

Arduino e encoder – sensore di prossimità a infrarossi

Si creano così degli impulsi di luce che, attraverso il sensore di


prossimità, diventano impulsi elettrici. Se conti gli impulsi puoi
calcolare la posizione angolare del disco, e di conseguenza del
rotore (la parte che gira del motore).

Per calcolare la velocità basta contare gli impulsi ogni TOT di


tempo, utilizzando un timer. Facendo un esempio pratico possiamo
ipotizzare che il disco ha 36 spicchi colorati di nero e 36 di
trasparente. Questo significa che, per ogni giro completo dell’asse
del motore, la fotocellula (sensore di prossimità ad infrarossi)
genera 36 impulsi elettrici. Se nell’intervallo di tempo di 1 secondo
conto 360 impulsi significa che il motore ha compiuto 10 giri in un
secondo (600 RPM giri per minuto).

Così facendo conosciamo la velocità, ma non la direzione con cui


gira il motore. Per sapere anche questo dobbiamo avere due
fotocellule, messe in due posizioni diverse. Quando il perno
dell’encoder viene ruotato si formano due segnali elettrici in
quadratura, definiti così perchè sono sfasati tra loro di 90° elettrici.
Questi due impulsi forniscono la velocità, con cui ruota il perno, ma
anche la direzione calcolata “vedendo” quale dei due impulsi arriva
prima dell’altro. I segnali vengono chiamati A e B.

Arduino e encoder – segnale elettrico a quadratura

3 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

Come programmare Arduino per usare un encoder

Abbiamo visto che i due segnali elettrici A e B vanno “interpretati”.

Se sei interessato a misurare solo la velocità/spostamento del


motore basta contare il totale degli impulsi in un dato arco di tempo.

Se ti serve conoscere anche la direzione dello spostamento


allora dovrai misurare sia il numero degli impulsi, sia la fase tra gli
impulsi A e B.

In alcuni casi non serve calcolare la velocità, ma solo di quale


quantità è stato ruotato il perno di un encoder. In questi casi non
serve tenere conto del tempo trascorso, e questo semplifica il
programma di Arduino. Ci sono almeno due modi per rilevare il
numero degli impulsi prodotti da un encoder:

con il metodo “polling”: ogni TOT tempo (una quantità di tempo


definita a priori nel programma) si misura lo stato elettrico dei pin di
ingresso a cui è collegato l’encoder. Si decodifica lo stato che varia
nel tempo e si estrapola l’informazione. Con questo metodo si deve
decidere a priori, ed in base al tipo/velocità del segnale elettrico, il
timer che “sveglia” la misura dello stato dei segnali elettrici. Si
possono perdere scatti/spostamento perchè il microprocessore sta
eseguendo altre parti del programma. Si possono utilizzare
indistintamente tutti i pin della scheda Arduino.

con il metodo “interrupt”: ogni volta che all’ingresso del pin c’è
una variazione del segnale elettrico viene chiamata una funzione
speciale “interrupt” (alle volte definita ISR). Questa funzione è
speciale perchè ha la priorità massima, cioè il microprocessore
della scheda Arduino ferma la riga di comando che sta eseguendo
per eseguire la funzione “interrupt”. Si devono utilizzare solo i pin
che possono diventare interrupt hardware: per esempio nella
scheda Arduino UNO solo il pin 2 e 3 digitali sono fisicamente
collegati agli interrupt esterni INT0 (digital pin 2) e INT1 (digital pin
3). Nel caso vuoi utilizzare un qualsiasi pin della scheda Arduino
UNO allora puoi usare una libreria chiamata PinChangeInt.

il diagramma temporale delle variazioni del segnale elettrico di un


encoder incrementale a quadratura le vedi nella figura che segue.
CW significa senso orario, mentre CCW significa senso anti-orario:

4 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

arduino e encoder – segnale elettrico encoder a quadratura

Schema elettrico ARDUINO senza e con de-bounce

Lo schema più semplice è utilizzare il rotary encoder direttamente


collegato ai pin digitali 2 e 3 della scheda Arduino (attivando le
resistenze di pull-up). Se si ha la possibilità è meglio implementare
il circuito di de-bounce che elimina i falsi contatti, i quali possono
provocare un conteggio errato degli impulsi dell’encoder
(consigliato).

Arduino e encoder – collegamento elettrico pratico

Il circuito dell’immagine che segue ha due versioni di de-bounce. A


sinistra quella più elaborata che utilizza un filtro RC. A destra
vengono utilizzati dei solo condensatori. Dalle mie prove pratiche è
risultato sufficiente un solo condensatore da 10nF tra pin 2 e GND,
e pin 4 e GND.

5 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

arduino e encoder – schema elettrico con debounce

PROGRAMMA Arduino per calcolare il numero di


impulsi encoder con metodo “interrupt”

Propongo un programma per Arduino UNO che ho utilizzato con un


encoder ALPS dotato di pulsante.

Ogni volta che viene ruotato l’encoder i segnali elettrici cambiano in


funzione del verso di rotazione. Nelle due immagini che seguono
ho rappresentato il diagramma temporale. Le frecce indicano la
variazione del segnale. Il programma utilizza i pin 2 e 4 per
calcolare gli scatti dell’encoder, ed il pin 3 per rilevare l’attivazione
del pulsante. I segnali elettrici provenienti dall’encoder rotativo sono
filtrati con 3 condensatori ceramici da 10 nF (nano Farad) collegati
tra i pin 2, 3 e 4 e il pin GND della scheda Arduino.

Ogni volta che viene ruotato l’encoder il programma invia il totale


aggiornato degli scatti effettuati sulla porta seriale. Ogni volta che
viene premuto il pulsante viene scritto sulla porta seriale “pulsante
premuto” e viene azzerato il totale degli scatti. Puoi vedere cosa
succede attivando il “Monitor seriale” nella IDE, interfaccia di
programmazione, di Arduino.

Arduino e encoder – segnale elettrico scatto in senso ORARIO

6 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

Arduino e encoder – segnale elettrico scatto in senso ANTI


ORARIO

// Programma che utilizza un rotary encoder a quadratura


// il pin A dell'encoder va collegato al pin 2 di Arduino
// il pin B dell'encoder va collegato al pin 4 di Arduino
// il pin del pulsante va collegato al pin 3 di Arduino
// i rimanenti pin dell'encoder vanno collegati al pin GND di Arduino
//
// vengono utilizzati 3 condensatori ceramici da 10 nF per creare
// il circuito elettrico di de-
bounce che evita i falsi contatti
//
// www.sciamannalucio.it
//
// Pin utilizzati per gli ingressi dell'encoder
#define encoder0PinA 2
#define encoder0PinSwitch 3
#define encoder0PinB 4
volatile char encoder0Pos = 0;
volatile boolean encoder0Switch = 0;
unsigned int tmp = 0;

// imposta i dati iniziali del programma


void setup() {
// I pin sono impostati come ingresso e viene
// attivata la resistenza di pull-up
// la logica è NEGATIVA
// utilizzare condensatore da 10nF tra il Pin e la GND
pinMode(encoder0PinA, INPUT_PULLUP);
pinMode(encoder0PinB, INPUT_PULLUP);
pinMode(encoder0PinSwitch, INPUT_PULLUP);
// Il pin attiva l'interrupt hardware sul fronte di salita
attachInterrupt(digitalPinToInterrupt(encoder0PinA),
doEncoderA, RISING);
// Il pin attiva l'interrupt hardware sul fronte di salita
attachInterrupt(digitalPinToInterrupt(encoder0PinSwitch),
doSwitch, RISING);
// Attiva la comunicazione seriale 115200 baud
Serial.begin (115200);
}

void loop(){

7 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

// Ogni volta che l'encoder fa uno scatto


// entra nel IF e invia alla seriale lo stato
dell'encoder
if (tmp != encoder0Pos) {
Serial.println(encoder0Pos, DEC);
tmp = encoder0Pos;
}
if (encoder0Switch) {
Serial.println("Pulsante premuto");
encoder0Switch = 0; // riarma il trigger del
pulsante
encoder0Pos = 0; // azzera il contatore degli
impulsi di rotazione
}
}
// Il pin A dell'encoder ha variato il suo stato elettrico
void doEncoderA(){
if(digitalRead(encoder0PinB)) encoder0Pos--;
else encoder0Pos++;
}
// Il pin abbinato al pulsante dell'encoder ha variato il suo stato el
void doSwitch(){
encoder0Switch = 1;
}

Mappatura Pin di un encoder rotativo con pulsante

Vista dall’alto di un rotary encoder con l’associazione tra il nome del


Pin e la sua posizione.

Arduino e encoder – mappatura pin di un encoder rotativo con

8 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

pulsante

vista di lato dell’encoder rotativo.

Arduino e e ncoder – pin rotary encoder con pulsante

Schema elettrico SENZA utilizzare Arduino

E chi non vuole utilizzare Arduino come fa? Ci sono circuiti integrati
che fungono da contatore di impulsi. Puoi vedere il circuito elettrico
utilizzabile anche con un encoder a quadratura. Gli integrati
utilizzabili sono il 74190 (versione con uscita BCD per
collegamento diretto a display decimali) e 74191 per uscita binaria
e puoi scaricare cliccando sul link datasheet_74190_191_counter.
Questi integrati sono in tecnologia TTL e pertanto vanno alimentati
con una tensione di 5 Volt. Se vogliamo utilizzare una tensione di
alimentazione fino a 15 Volt usiamo gli integrati CMOS
datasheet_cd40192_cd40193. Questo circuito può essere utilizzato
per dividere la frequenza di un encoder per un numero che varia tra
2 e 256, basta collegarsi alle uscite U1-Q0 (divisione per 2), U1-Q1
(divisione per 4), U1-Q2 (divisione per 8), U1-Q3 (divisione per 16),
U2-Q0 (divisione per 32), U2-Q1 (divisione per 64), U2-Q2
(divisione per 128) e U2-Q3 (divisione per 256). Si devono
utilizzare gli integrati con uscita binaria 74191 oppure cd40193.

9 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

Arduino e encoder – schema elettrico versione senza


microprocessore

Segnali elettrici di un rotary encoder

Ho usato l’oscilloscopio per vedere, nella pratica, come le tensioni


e i segnali elettrici di un encoder rotativo cambiano in funzione di
come viene girata la sua manopola.

Il rotary encoder è girato in senso orario con un movimento lento. Il


segnale elettrico A da zero diventa 5 Volt. Passati 5 millisecondi
anche il segnale B diventa 5 Volt. Tutti i segnali sono a logica
positiva. Quando utilizzate Arduino e i resistori di pull-up contenuti
nei pin la logica diventa negativa, cioè i segnali passano da 5 Volt a
zero.

Arduino e encoder – segnale elettrico CW lento

Il rotary encoder è girato in senso orario con un movimento veloce.


Nello stesso tempo del caso precedente, avvengono 15 variazioni
di segnale, che corrispondono ad altrettanti scatti dell’encoder
totativo.

10 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

Arduino e encoder – segnale elettrico CW veloce

Qui vediamo un ingrandimento temporale del segnale elettrico più


veloce.

Arduino e encoder – segnale elettrico CW veloce ingrandimento

In questo caso l’encoder rotativo l’ho girato in senso anti-orario.


Puoi verificare come la teoria è confermata: il segnale B arriva
prima, temporalmente parlando, del segnale A.

Arduino e encoder – segnale elettrico CCW lento

Link a risorse di approfondimento:

cosa sono e come utilizzare gli encoder

datasheet incremental encoder Bourns PEC11 con interruttore

tutorial completo sugli encoder rotativi fai da te

encoder incrementale: teoria ed applicazioni

11 di 12 08/12/2018, 14:02
Arduino: encoder conta impulsi-giri motore - Sciamanna Lucio

rotary encoder Arduino library

come utilizzare un encoder con microprocessore PIC

Pubblicità

12 di 12 08/12/2018, 14:02

Potrebbero piacerti anche