Gareggiamo in prontezza di riflessi con un gioco per 5 concorrenti, dove più rapidamente premiamo il nostro pulsante, prima il nostro punto luminoso arriva al traguardo.
I tempi dei primordiali giochi elettronici basati su contatori, pulsanti e strisce di LED comuni sembrano lontani.
Ancor più da quando la comparsa dei videogame prima, e dei giochi su PC dopo, hanno reso disponibili animazioni 3D e giochi in Rete che solo una ventina di anni fa erano impensabili.
Eppure anche dei gadget, dei giochi semplici composti da LED e pulsanti hanno la loro logica e i loro estimatori tutt’oggi.
Ecco perché abbiamo deciso di realizzare il progetto descritto in queste pagine, con il quale vi invitiamo a riscoprirne il fascino.
Si tratta di un hardware tutto-sommato semplice che fa uso di una scheda Arduino, di un set di pulsanti, di un display e di una striscia di LED NeoPixel.
Insieme compongono una sorta di pista luminosa sulla quale un minimo di due e un massimo di cinque concorrenti possono gareggiare in prontezza di riflessi e velocità di esecuzione facendo correre il proprio punto luminoso dalla partenza all’arrivo.
Per un numero massimo di tre giri di pista, vedendo chi riesce ad arrivare primo al traguardo.
Il funzionamento del gioco è essenziale: per avviare una partita (o manche, se vi piacciono i termini ricercati…) si deve premere il pulsante di avvio, quindi il display a matrice di cui è dotato mostra la scritta che annuncia il conto alla rovescia e prepara i giocatori al momento in cui potranno partire.
Più esattamente, il display mostra in sequenza 3, 2, 1, cadenzati e accompagnati da note musicali emesse dal cicalino.
Esaurito il conteggio, il display visualizza il messaggio di via (GO) e a questo punto i partecipanti al gioco potranno premere ciascuno il proprio pulsante, ripetutamente, con la massima frequenza possibile per far avanzare il proprio punto luminoso sulla pista formata dalla strip NeoPixel.
Riconoscibile dal colore (allo scopo ognuno dei pulsanti dei giocatori andrà colorato analogamente al rispettivo punto luminoso sulla strip a LED), per andare più forte degli altri.
Ad ogni giro compiuto dal concorrente più avanti il display ne darà notifica con un messaggio tipo 1/3 LAP, indicando quale giro è stato completato su quanti giri complessivi (il firmware ne prevede 3, ma è possibile cambiare tale valore).
Chi taglia il traguardo per primo verrà indicato dal display e la manche avrà termine.
Per avviarne un’altra, al solito, bisognerà ripremere il pulsante di avvio e attendere la partenza comunicata dal display.
Il progetto
#define COLOR1 track.Color(255,0,0) #define COLOR2 track.Color(0,255,0) #define COLOR3 track.Color(0,0,255) #define COLOR4 track.Color(255,255,255) #define COLOR5 track.Color(255,255,0)
Potete comunque ridefinirli a vostro piacimento scrivendo i corrispondenti valori tra 0 e 255 tra parentesi.
Ricordando che 0 corrisponde alla minima luminosità del rispettivo colore e 255 alla massima e che il primo numero è relativo al rosso, il secondo al verde e il terzo al blu.
Resta inteso che dovrete scegliere colori facilmente distinguibili l’uno dall’altro.
Perché diversamente i giocatori faticheranno a capire in che punto della “pista” si trova, istante per istante, il proprio corridore luminoso.
Il progetto prevede la visualizzazione dei messaggi ai concorrenti mediante un display a matrice di 8×8 punti composto da LED rossi.
Per visualizzare la pista e i concorrenti esegue il pilotaggio di 900 LED NeoPixel; anche questo valore può essere modificato dallo sketch per accorciare, addensare, diradare o allungare la pista luminosa.
Adottando una strip a LED tipo la 2846-STRIP300LED della Futura Elettronica, composta da 300 LED RGB con densità di 60 LED per metro, otterremo una “pista” lunga 15 metri.
Mentre utilizzandone una 2846-STRIP150LED con 30 LED/metro avremo la lunghezza raddoppiata, ossia 30 metri e diodo RGB più spaziati.
La lunghezza della strip può causare un affievolimento della luce emessa da quelli più lontani.
Ragion per cui per piste molto lunghe è consigliabile ripetere l’alimentazione all’inizio e alla fine.
Comunque l’assorbimento, considerando che si accendono solo 5 LED RGB alla volta, non è tale da far diventare rilevante tale problema.
Ad ogni modo, tramite l’apposita istruzione dello sketch è possibile scegliere un numero differente di LED da pilotare, magari minore, visto che 900 ci sembrano già molti.
I pulsanti che abbiamo scelto sono quelli Arcade della Futura Elettronica (codice tipo 6168-COM09338), che dispongono di un microswitch a 3 terminali (comune, normalmente aperto e normalmente chiuso).
Di cui collegheremo solo comune e normalmente aperto.
Li abbiamo voluti sia per la loro robustezza e idoneità all’uso nei giochi elettronici, sia perché sono disponibili in vari colori e quindi facilmente abbinabili alle luci dei concorrenti.
Inoltre possono essere facilmente montati su un pannello.
Il display utilizzato per fornire le segnalazioni visive è un display a matrice:
- 4 display a matrice 8×8 con MAX7219
- LED rossi a catodo comune e gestiti dall’integrato controller MAX7219 (codice 8300-YB302).
Può essere controllato da Arduino tramite un’interfaccia SPI semplificata che fa capo ai pin DIN (ingresso dati), CS (seleziona l’indirizzo nel caso siano connessi più display) e CLK (clock della comunicazione seriale).
Con esso possono essere visualizzati lettere, cifre e simboli.
Per quanto riguarda le strip NeoPixel, il microcontrollore di Arduino Mega le pilota generando sequenzialmente le stringhe di dati dirette ognuna a un diodo RGB.
A una velocità sufficientemente elevata da seguire, per un massimo di cinque “corridori luminosi”, la pressione dei cinque pulsanti alla massima velocità prevista.
Per farvi comprendere come avviene il pilotaggio dei LED NeoPixel è opportuno richiamare la tecnologia NeoPixel, che prevede LED RGB con controller a bordo, facilmente integrabili nell’ambiente Arduino grazie a librerie proprietarie che Adafruit (www.adafruit.com) rende disponibili.
I LED NeoPixel possono essere collegati in cascata in modo che la linea dati da uno passi al successivo.
Ognuno può essere gestito individualmente tramite un apposito comando inserito nella stringa seriale e può produrre fino a 256 tonalità del proprio colore, determinando un totale di 16.777.216 combinazioni di colore.
Il canale dati usato per la comunicazione con i LED NeoPixel e quindi con le strip è simile al tipo One-Wire.
L’alimentazione prevista per i LED NeoPixel è a 5 volt; la comunicazione avviene a un massimo di 800 kbps.
Per ogni strip di LED è possibile impostare a piacimento la frequenza di refresh, in modo da rendere impercettibili determinati giochi di luce.
Ogni LED intelligente è collegato in cascata, dato che la linea dati entrante nel terminale DI esce dal DO, che ne ripete i dati da un controller all’altro.
L’alimentazione è a 5 volt (V della strip), che nel nostro caso non vengono forniti da Arduino Mega ma direttamente dalla scheda di alimentazione, che ha a bordo un jack DC e da cui parte l’alimentazione di tutto il circuito, display e Arduino compresi.
Il protocollo di comando del sistema NeoPixel prevede l’invio di gruppi di tre byte in una stringa di 24 bit.
Ognuna delle quali contiene lo stato di illuminazione di ciascun colore base (prima gli otto bit del verde, poi quelli del rosso e infine quelli del blu).
Il firmware
Diamo adesso uno sguardo allo sketch alla base del nostro gioco, che non riportiamo per intero essendo abbastanza corposo; chi lo vorrà potrà scaricarlo dal nostro sito www.elettronicain.it insieme ai file del progetto. Ci limeteremo a descriverne i punti salienti qui di seguito.
Al solito abbiamo una fase iniziale di inclusione delle librerie per la gestione della strip NeoPixel e del display a matrice (MAX7219), nonché quella per il bus SPI utilizzato nella comunicazione:
#include <Adafruit_NeoPixel.h> #include <MD_Parola.h> #include <MD_MAX72xx.h> #include <SPI.h>
Segue poi la parte della definizione del numero di LED da pilotare, che sostanzialente rappresentano la lunghezza della pista di gioco:
#define MAXLED 900 // MAX LEDs actives on strip
Se desiderate modificare la lunghezza potete farlo cambiando il numero che segue MAXLED, attualmente corrispondente a 900; comunque tale quantità ci sembra più che sufficiente a rappresentare uno spostamento abbastanza fluido anche su una pista lunga come quella del prorotipo.
Andiamo avanti con l’analisi del firmware dove, dopo la definizione del numero di LED NeoPixel troviamo la definizione degli I/O della Arduino Mega, ossia questa orzione di codice:
#define PIN_LED A0 #define PIN_P1 7 // switch player 1 to PIN and GND #define PIN_P2 6 // switch player 2 to PIN and GND #define PIN_P3 5 // switch player 3 to PIN and GND #define PIN_P4 4 // switch player 4 to PIN and GND #define PIN_P5 2 // switch player 5 to PIN and GND #define PIN_AUDIO 3 // through CAP 2uf to speaker 8 ohms #define PIN_START 8 // switch start to PIN and GND
Qui vediamo che la gestione dei NeoPixel è affidata all’A0, da cui usciranno le stringhe di dati, mentre i pulsanti dei concorrenti sono gestiti dai pin digitali 7, 6, 5, 4 e 2; l’uscita per il cicalino è collegata al pin digitale 3, dal quale uscirà il segnale digitale la cui frequenza dipenderà dalle note da riprodurre, mentre la lettura del pulsante di START (avvio di una manche) sarà affidata all’I/O digitale 8.
Viene poi la definizione della linea di comunicazione destinata al display a matrice, i cui pin sono il 9 per i dati, l’11 per il clock e il 10 per il CS (Chip Select); si definisce anche il tipo di display affinché possa essere correttamente gestito dalla relativa libreria MD_MAX72xx.h.
Troviamo anche tutte le altre impostazioni riguardanti la comunicazione con il display a matrice di punti attraverso il bus seriale opportunmente settato:
#define HARDWARE_TYPE MD_MAX72XX::FC16_HW #define MAX_DEVICES 4 #define CLK_PIN 11 #define DATA_PIN 9 #define CS_PIN 10 #define BUF_SIZE 15 char curMessage[BUF_SIZE] = { “” }; int sortValues[5] = {0,0,0,0,0}; int NPIXELS=MAXLED; // leds on track int nplayer=5; long newmillis=0; int lapstime=2000; boolean flag_racing=0;
Andiamo oltre e vediamo la sezione dello sketch dove sono definiti i colori dei singoli concorrenti, ognuno abbinato a un pulsante:
#define COLOR1 track.Color(255,0,0) #define COLOR2 track.Color(0,255,0) #define COLOR3 track.Color(0,0,255) #define COLOR4 track.Color(255,255,255) #define COLOR5 track.Color(255,255,0)
Come già spiegato, i tre numeri tra parentesi sono le percentuali di accensione dei colori R, G, B ossia 0 corrisponde a spento e 255 al 100% (massima luminosità); se volete modificare i colori potete farlo cambiando la composizione attraverso questi tre numeri, ricordando, a chi non sa come vengono composte le singole tinte cromatiche con rosso, verde e blu, che esistono siti web che permettono di vedere il colore risultante come apparirà (dato che gli schermi di Personal Computer, tablet e smartphone funzionano in RGB…) semplicemente inserendo i tre valori di R, G e B.
Uno di questi è https://www.w3schools.com.
Per quanto riguarda il numero di giri componenti una partita, viene definito dall’istruzione:
byte loop_max=3; //total laps race
Questo sarà lo stesso visualizzato sul display a matrice alla partenza di ogni manche (vale a dire una volta premuto il pulsante START) e verrà decrementato progressivamente al passaggio per l’inizio della striscia NeoPixel; potrete modificarlo cambiando il numero dopo il simbolo di uguale.
Realizzazione pratica
Bene, chiarito ciò, possiamo passare alle note costruttive.
Ricordiamo che il progetto prevede il semplice assemblaggio di dispositivi già pronti e che l’unica saldatura richiesta sarà quella dei fili sulla strip NeoPixel.
Il tutto andrà interconnesso rispettando lo schema di cablaggio illustrato in queste pagine.
Resistenza in serie al pin A0
- La resistenza indicata nello schema con valore 330 ohm andrà scelta sulla base del tipo di controller impiegato nei LED NeoPixel.
- Se utilizzate strip con controller WS2812 (ad esempio, il modello 2846-STRIP300LED venduto da Futura Elettronica), dovrete modificarne il valore a 500 ohm.
- Per strip con chip WS2813, il valore indicato (330 ohm) sarà corretto.
- In ogni caso, il resistore sarà da 1/4 di watt con tolleranza al 5% o meno.
Filtraggio dell’alimentazione
- Conviene filtrare l’alimentazione della strip saldando un condensatore elettrolitico da 1.000 µF/16V nei contatti dove arriva dal jack DC.
Alimentazione e connessioni
- Le linee di alimentazione di Arduino Mega, del display a matrice di LED e della strip NeoPixel dovranno confluire su un connettore jack.
- Questo jack può essere montato su una scheda o di tipo volante, rammentando che:
- Il contatto centrale andrà connesso al polo positivo.
- L’esterno al polo negativo.
- L’alimentatore richiesto deve avere le seguenti caratteristiche:
- Uscita stabilizzata a 5 volt.
- Capacità di erogare una corrente di circa 3 ampere.
- Terminazione con un cavetto dotato di jack DC idoneo e polarità positiva sul contatto interno.
Assemblaggio del contenitore
- L’elettronica potrà essere alloggiata in un contenitore, preferibilmente in plastica.
- Sul contenitore andranno ricavati:
- Tre fori: uno per il jack DC, uno per il pulsante di START (manovrato dal conduttore del gioco), e uno per il cicalino (per consentire l’udibilità del suono).
- Una cava sulla parete frontale per visualizzare il display a matrice di LED, da fissare internamente con colonnine distanziali e staffe.
- Le foto del prototipo, riportate nelle pagine del progetto, possono fornire un’idea per la realizzazione.
Collegamento della strip NeoPixel
- La strip può essere fissata e vincolata all’interno del contenitore, lasciando uscire i tre fili di collegamento attraverso un foro sul fianco o sul retro.
- Se desiderate portare all’esterno i tre fili di collegamento, ricordate che il filo dei dati non può essere più lungo di un paio di metri.
Seguendo queste indicazioni, il progetto sarà completato con successo e funzionerà correttamente.
I pulsanti potranno essere collocati ciascuno in un contenitore proprio, per esempio una scatola stagna da impianti elettrici, fissata poi al tavolo dove si stenderà la strip NeoPixel; quest’ultima e i pulsanti dovranno essere collegati con fili in guaina di lunghezza adeguata che confluiranno in un passaggio ricavato nel contenitore, per poi raggiungere Arduino Mega e il circuito intorno ad esso.
Nel nostro prototipo abbiamo optato per contenitori individuali stampati in 3D della forma visibile nelle foto, il cui interno è cablato come mostra la Fig. 2.
Conclusioni
Bene, con questo abbiamo terminato: crediamo di avervi passato tutte le informazioni necessarie a realizzare questo magnifico gioco di abilità, quindi sta a voi svilupparlo, fisicamente, nella maniera più suggestiva e accattivante possibile, dando alla strip di LED RGB il percorso e lo sviluppo che più vi aggrada, magari appoggiandovi a una struttura realizzata allo scopo su un tavolo o una parete, ma anche al suolo.
Se intendete utilizzare il progetto in un ambiente un po’ rumoroso e ritenete che il suono del cicalino sia debole, potete collegare al pin di Arduino Mega una breakout amplificatore come ad esempio il
Modulo AMPLIFICATORE audio 2,8 watt mono in classe D (codice 8220-MM209) della Futura Elettronica (www.futurashop.it) che può pilotare un altoparlante. Oppure utilizzate una pastiglia piezo di grandi dimensioni o un altoparlante piezo.
Se invece non vuoi realizzarlo, esiste un nuovo kit per realizzare un MiniLedRacing
Ciò detto, non ci resta che augurarvi buon divertimento con il vostro LED Race!