Quando si progetta un prototipo, più o meno complesso, prima o poi si fa sentire l’esigenza di disporre di tante porte di ingresso. Ad esempio, in un ipotetico progetto che pilota un display LCD, possono esserci diversi tasti: un tasto può essere adibito alla selezione della modalità operativa, un altro a far scorrere il cursore a destra, un altro ancora a farlo scorrere nella direzione opposta, un altro ancora a confermare i dati, e cosi via. In questo modo, in breve tempo, tutte le porte sono utilizzate per l’interazione degli eventi con l’operatore e ben presto ci si deve occupare di come ottimizzare il progetto, se non addirittura di eliminare qualche importante funzione.
Le possibili soluzioni
Il progettista, a questo punto, ha a disposizione alcune soluzioni, al fine di risolvere il problema. Lo scopo principale è infatti quello di non sacrificare né la funzionalità del sistema, né tanto meno la praticità. La possibilità allora da seguire potrebbe essere quella di adottare una MCU provvista di molte porte. In questo modo aumentano i costi di realizzazione, dal momento che un microcontrollore dotato di tanti ingressi costa di più. Aumentano anche i costi dei cablaggi e delle connessioni, in quanto si devono prevedere un numero elevato di pulsanti e relativi collegamenti.
La soluzione proposta in questo articolo è molto economica (figura 1 e 2). Infatti:
- non sono necessari tanti pulsanti ma ne basta uno solo;
- non sono necessari MCU provvisti di unità di acquisizione A/D;
- non si deve realizzare un multi-partitore di precisione;
- l’ingresso realizzato è “digitale”, pertanto tutte le variabili di impedenza e di velocità sono ampiamente rispettate;
- è possibile implementare il metodo anche con un modello minimale di microcontrollore;
- la codifica dell’algoritmo è un tantino più difficoltosa, ma ne vale la pena.
Il metodo proposto
Per far sì che con un solo tasto possano essere eseguite tante funzioni si deve agire sulla “misura temporale” della pressione dello stesso (tabella 1). In altre parole, a seconda di quanto tempo il tasto è premuto, si modifica la funzione eseguita. In parole povere si conteggia il tempo durante il quale il tasto è premuto. Un esempio concreto potrebbe essere il seguente:
- se il tasto viene premuto solamente per un attimo, si cambia la modalità operativa del sistema;
- se il tasto viene premuto per circa mezzo secondo, si spegne il sistema;
- se il tasto viene premuto per più di due secondi, si entra nella configurazione a menù.
Come si vede abbiamo implementato ben tre funzioni distinte e indipendenti utilizzando solamente un tasto al posto di tre. Si immagini quindi il notevole risparmio per le applicazioni più sofisticate (figura 3).
Come rilevare la durata di una pressione
Il metodo di rilevazione del tempo di pressione è abbastanza semplice. Si tratta infatti di implementare un “ciclo infinito” di attesa, nel quale, oltre a leggere lo stato di una porta di ingresso, viene anche conteggiato un particolare parametro legato al tempo. Normalmente questo parametro (tick) è molto breve, nell’ordine delle decine di millisecondi. Quando finalmente il tasto è premuto, l’esecuzione del programma termina, restituendo la quantità di impulsi accumulati. Basterà quindi esaminare tale valore e comportarsi di conseguenza. Con questo metodo possono essere previste tante funzioni con un solo tasto, ma si capisce bene che un numero elevato di esse renderebbe l’evento critico, a meno che l’operatore sia tanto preciso nel calcolare mentalmente la durata esatta del tempo che scorre.
Un esempio pratico
Implementiamo adesso il metodo realizzando un piccolo sistema pratico e funzionante. Esso è composto dalle seguenti componenti hardware:
- una fila di otto diodi LED;
- un pulsante normalmente aperto.
Il suo comportamento prevede semplicemente l’utilizzo di questo solo pulsante. E’ la differenza temporale della pressione a stabilire la funzione da eseguirsi: diverse tempistiche di durata della pigiata sul tasto determinano un comportamento diverso. Il sistema prevede le seguenti modalità:
- all’accensione, tutti i LED sono spenti;
- in assenza di pressione del tasto, lo stato dei LED resta immutato;
- tenendo premuto per un tempo brevissimo il pulsante (T<400 mS), si accendono i primi 4 LED;
- tenendo premuto per un tempo meno breve il pulsante, ma non troppo (T>=400 mS AND T<800 mS), si accendono gli ultimi 4 LED;
- tenendo premuto per un tempo di circa 1 secondo (T>=800 mS AND T<1200 mS), tutti i diodi LED si illuminano;
- tenendo premuto per un tempo maggiore di 2 secondi (T>=2000 mS), tutti i diodi LED si spengono.
Di seguito il lista.
program tasto rem ****************************** rem * UN TASTO, TANTE FUNZIONI * rem * di GIOVANNI DI MARIA * rem * MikroBasic PRO 1.45 * rem ****************************** dim tick as word ‘Conteggio in attesa trisb=0 ‘PortB tutta in output trisa=1 ‘PortA.0 in input portb=0 ‘Spegne i Led while 1 ‘Ciclo infinito while porta.0=0 ‘Attende finche’ PREMO il tasto nop wend tick=0 while porta.0=1 ‘Attende finche’ LASCIO il tasto tick=tick+1 delay_ms(10) wend if tick<40 then ‘Pressione brevissima portb=15 end if if (tick>=40) AND (tick<80) then ‘Pressione media di mezzo sec. portb=240 end if if (tick>=80) AND (tick<120) then ‘Pressione di circa 1 sec. portb=255 end if if tick>=200 then ‘Pressione di almeno 2 sec. portb=0 end if
Listato 1 |
In programmazione, non basta conoscere a memoria tutte le funzioni e la loro finalità, per saper realizzare un programma. Occorre, invece, avere chiaro in mente un metodo risolutivo e l’algoritmo da seguire.
Per ogni soluzione ci sono tanti rimedi, l’importante è scegliere quello migliore e meno costoso da un punto di vista computazione e non 🙂
E’ un esempio ottimo per far capire come sfruttare al meglio gli IO di una MCU. Nella realtà dei progetti si ha sempre un numero di operazioni che vanno comunque svolte e non si può rimanere solo ad attendere la pressione del pulsante. Con qualche trucco si riesce ad usare un contatore di base dei tempi (SyStick) e controllare quando è stato premuto il pulsante. Si salva il valore del SysTick alla prima pressione e si restituire l’evento di durata quando il pulsante si rilascia. In questo modo il programma non è bloccante e si possono eseguire i normali task dell’applicazione.
La stessa procedura può essere usata per il solito programma per l’antirimbalzo della pressione di un pulsante.
Credo ci sia un errore nello schema elettrico di fig.1 in quanto lo switch manda a gnd l’alimentazione. La resistenza da 10k dovrebbe andare a gnd ed essere collegata al nodo tra switch e pin 17.
Grazie della segnalazione, ho messo un ERRATA sull’immagine.
Grazie della segnalazione. Schema corretto.
Era un bellissimo esempio di “Corto Circuito” !!! :-)))))
Grazie della segnalazione!
salve a tutti, non ho ben chiaro il concetto di “tick”.
Da quel che ho capito rappresenta ” l’unita di misura “del tempo in un microcontrollare.
Nella vita reale, noi umani, possiamo prendere ad esempio come unita un secondo od un minuto, in funzione di ciò che dobbiamo misurare a seconda della durata di tempo da misurare.
Allo stesso modoper i micro, possiamo “impostare” l’unita di tempo con cui misurare un evento.
Quello che nella vita reale puo essere un secondo o un minuto nei mucroc prende il nome di “tick” la cui durata può assumere qualsiasi valore.E’ corretto?
Ritornando ali’articolo sopra, il tempo di durata della pressione del pulsante sarà uguale a:
numero tick ix durata di tick
ove tick puo assumere qualsiasi valore es 1,5 microsec, 10 millisec…
Sbaglio qualcosa?
grazie per l’attenzione