Archivi tag: modulazione

Robot Pet Therapy: costruiamo un drawdio


Recentemente mi è capitato di partecipare ad una riunione presso il Dipartimento di Informatica di Torino, in merito alle possibili soluzioni elettroniche/informatiche in campo educativo per un progetto legato ad alcune attività presso un museo di Torino. Poiché l’invito mi è arrivato improvviso e visto che recentemente sono entrato a far parte del CTS di Torino, ho pensato di illustrare brevemente il mio tentativo di recupero adottato tempo fa con un allievo con un profilo autistico utilizzando “l’elettronica creativa”

Ho mostrato due dispositivi:

  • un drawdio realizzato con un NE555
  • un secondo di cui ve ne parlerò tra qualche giorno in quanto in fase di miglioramento da parte di alcuni miei allievi.

Le due sperimentazioni fanno parte del progetto di Robot Pet Therapy

Drawdio

La parola Drawdio deriva dall’unione delle due parole:

  • (to) Draw: disegnare
  • Audio

è un dispositivo in grado di produrre suono mentre si disegna ed il suono emesso è funzione della quantità di grafite presente sul foglio.
Oltre ad emettere suono mentre si disegna e possibile realizzare varianti del dispositivo per suonare con l’acqua oppure “sentire” i diversi suoni emessi da diversi materiali, in realtà ciò che percepiamo e la variaione di resistenza che sussiste tra gli elettrodi e il materiale.
Il dispositivo ha degli impieghi interessantissimi soprattutto in un contesto educativo.

Prima di continuare vi invito a vedere i filmati che seguono:

Il sito di riferimento è: http://web.media.mit.edu/~silver/drawdio/ su cui trovate esempi e se desiderate anche un PCB per la realizzazione del circuito stampato, io ho utilizzato una basetta millefori e in cira 30 minuti ho saldato e realizzato il primo prototipo mostrato in questo articolo.

Come spesso ho avuto modo di affermare gli attegiamenti di protobullissmo in una classe creano scarso legame tra gli allievi e spesso mi è capitato di vivere in classi in cui si formano fazioni e forti rivalità.
Per spezzare questo attegiamento diseducativo tempo fa, con l’aiuto di un allievo diversamente abile abbiamo realizzare un drawdio che ha risolto alcuni problemi, il rendere “suono” i disegni ha incuriosito immediatamente e coinvolto l’intera classe e l’allievo diversamente abile è diventato “protagonista” inoltre. Ho anche sfruttato il dispositivo per creare una catena umana “resistiva” che suonava tutta insieme, questa semplice azione stranamente a incominciato ad aggregare il gruppo classe.
Stringere la mano, toccare la punta del naso o il braccio del compagno di classe per emettere un suono e qualcosa che tocca la sfera personale, ma credo che abbia fatto nascere in loro la consapevolezza di essere individui essenziali per emettere suono e quindi appartenenti ad un gruppo che crea.

Ma come funziona e come si realizza un drawdio?

Schema elettrico e componenti:

Schema di montaggio:

Se non vi occupate di elettronica non è importante capire tutto, potete limitarvi ad acquistare i componenti e saldarli insieme seguendo lo schema elettrico indicato sopra.

Per chi volesse saperne di più questa è la spiegazione.

Per poter emettere il suono durante il disegno bisogna collegare due elettrodi uno alla mina della matita ed uno sulla struttura della matita, toccando con un dito la traccia della matita e con l’altra mano tocchiamo la struttura della matita viene inserita tra i due contatti una resistenza elettrica che varia in funzione della distanza tra il dito sulla traccia e lo spessore della traccia, la variazine di resistenza viene utilizzata per variare la frequenza della nota emessa dal dispositivo.

Affinchè si possa produrre il suono la traccia sul foglio non deve avere interruzioni.

Il circuito elettrico non è altro che un generatore di nota modulabile in frequenza realizzato con un NE555 in configurazione astabile dove però e stata modificata la rete di temporizzazione tra il piedino 7 (discharge) e il 2 e il 6 (trigger e threshold) inserendo la resistenza variabile costituita dalla la matita e dal tratto di grafite.
Non mi dilungherò sul funzionamento interno dell’NE555, (probabilmente lo farò più avanti) è sufficiente per questa spiegazione ricordare che la frequenza del segnale rettangolare dipende dalle resistenze R2, R3 secondo la seguente formula:

[pmath size=16]f=1.44/C3*(R2+2*R3)[/pmath]

Impugnando la matita e collegandola come indicato nello schema (CORPO, PUNTA) e toccando con un dito dell’altra mano la traccia disegnata sul foglio viene inserita una resistenza variabile in serie alla resistenza R3, ciò consente di far dipendere la frequenza del segnale emesso dal tocco del nostro dito e dalla posizione della matita e dallo spessore della matita, infatti maggiore spessore della grafite equivale a minore resistenza, minore spessore della grafite equivale a maggiore resistenza.
L’uscita (pin 3) è collegata ad un piccolo altoparlante da 8 Ohm mediante un condensatore di disaccoppiamento che ha la funzione di bloccare la componente continua nel caso in cui l’oscillatore si fermi.
Quindi disegnando con la matita udiremo un suono che varia di tonalità, suono che si interromperà non appena solleviamo la matita.
Nel circuito ho aggiunto un LED per visualizzare l’accensione del circuito.

Arduino – lezione 06: modulazione di larghezza di impulso (PWM)

Nella precedente lezione abbiamo visto come progettare un controllo presenza in due stanze adiacenti in cui abbiamo utilizzato due pulsanti per simulare due sensori PIR (uno per ogni stanza) e due led per simulare l’accensione delle lampade nelle due stanze.
L’ultimo sketch consentiva di silmulare la seguente situazione per entrambe le stanze:

  • entro nella stanza
  • PIR avverte la mia presenza
  • si accende la luce
  • ritardo lo spegnimento della luce per darmi il tempo di uscire dalla stanza

In questa e nella successiva lezione vorrei giungere alla realizzazione di un comportamento più vicino alla realtà:

  • entro nella stanza
  • PIR avverte la mia presenza
  • si accende in fade la luce
  • esco dalla stanza
  • il PIR non rileva più la mia presenza
  • si spegne in fade la luce

Suddivido la soluzione del problema in due sottoproblemi che risolverò in questa e nella successiva lezione:

  1. funzione fade
  2. funzione controllo presenza

Realizziamo la funzione fade

Se ricordate nella lezione 2 abbiamo realizzato il famoso “blink” lo sketch che accendeva e spegneva in modo continuativo un LED.
Realizziamo nuovamente il circuito ed eseguite lo sketch allegato:

// Esempio 01: fare lampeggiare un LED

#define LED 13                // LED collegato al pin digitale 13

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  digitalWrite(LED, HIGH);   // accende il LED
  delay(1000);               // aspetta 1 secondo
  digitalWrite(LED, LOW);    // spegne il LED
  delay(1000);               // aspetta 1 secondo
}

Provate a ridurre drasticamente il ritardo di accensione e spegnimento, arrivate a 10 millisecondi, quasi non dovreste più pecepire lampeggiare il LED e inoltre dovreste aver notato che la luminosità del LED è diminuita.

// Esempio 02: modulazione di larghezza di impulso (PWM)

#define LED 13                // LED collegato al pin digitale 13

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  digitalWrite(LED, HIGH);   // accende il LED
  delay(10);               // aspetta 10 millisecondi
  digitalWrite(LED, LOW);    // spegne il LED
  delay(10);               // aspetta 10 millisecondi
}

Il motivo per cui si vede illuminare di meno il diodo LED è dovuta alla modulazione di larghezza di impulso in inglese Pulse Width Modulation – PWM, che detta in modo meno tecnico vuol dire che se facciamo lampeggiare un diodo LED ad una frequenza sufficientemente elevata e se cambiamo il rapporto tra il tempo in cui sta acceso ed il tempo in cui sta spento, il nostro occhio non percepirà il lampeggiare del LED ed inoltre a secondo del rapporto del tempo di accensione e spegnimento potremo regolare la luminosità del LED.

Possiamo dire che il PWM è una tecnica per ottenere risultati analogici con mezzi digitali.

Un po’ di teoria: il Duty cycle

Il duty cycle di un onda quadra/rettangolare e il rapporto tra la durata (in secondi) del segnale quando è “alto” ed il periodo totale del segnale. In altre parole è un numero che esprime quant’è la parte di periodo in cui il segnale è alto.

Facendo riferimento al disegno la formula che esprime il duty cycle è:

Ï„/T

dove T è il periodo e τ la parte di periodo in cui il segnale è alto.

Dalla formula potete subito notare che τ può variare da un valore minimo di 0 a un valore massimo pari a T, ciò implica che il valore del duty cycle varia da 0 a 1:

in entrambi i casi siamo in presenza di segnali continui.

Dalla formula possiamo comprendere quindi che il duty cycle è sempre un valore che varia tra 0 e 1.

Il duty cycle è spesso rappresentato in percentuale, D% e per ottenere la percentuale è sufficiente moltiplicare per 100 il rapporto τ/T, dire quindi che il D%=30% vuol dire che per il 30% del periodo totale il segnale si trova a livello alto, come conseguenza possiamo subito dire che il segnale sarà a livello basso per il restante 70% del periodo.

Dire quindi che il duty cycle è del 50% vuol dire che nel periodo T il segnale si mantiene alto per T/2 e per il restante T/2 a livello basso in questo caso siamo quindi in presenza di un’onda quadra.

Passiamo ora alla pratica

Poniamoci nelle seguenti 3 condizioni:

  1. 50% LED acceso e 50% LED spento
    luminosità al 50%
  2. 25% LED acceso e 75% LED spento
    luminosità al 25%
  3. 75% LED acceso e 25% LED spento
    luminosità al 75%

Per realizzare le tre condizioni impostate scegliamo un periodo sufficientemente breve tale da non percepire il lampeggiare del LED:

Poniamo un periodo T = 20ms

  1. 10ms acceso e 10ms spento
  2. 5 ms acceso e 15ms spento
  3. 75 ms acceso e 5ms spento
// Esempio 03: modulazione di larghezza di impulso (PWM) - on: 10ms - off: 10ms

#define LED 13                // LED collegato al pin digitale 13

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  digitalWrite(LED, HIGH);   // accende il LED
  delay(10);               // aspetta 10 millisecondi
  digitalWrite(LED, LOW);    // spegne il LED
  delay(10);               // aspetta 10 millisecondi
}
// Esempio 04: modulazione di larghezza di impulso (PWM) - on: 5ms - off: 15ms

#define LED 13                // LED collegato al pin digitale 13

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  digitalWrite(LED, HIGH);   // accende il LED
  delay(5);               // aspetta 5 millisecondi
  digitalWrite(LED, LOW);    // spegne il LED
  delay(15);               // aspetta 15 millisecondi
}
// Esempio 05: modulazione di larghezza di impulso (PWM) - on: 15ms - off: 5ms

#define LED 13                // LED collegato al pin digitale 13

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  digitalWrite(LED, HIGH);   // accende il LED
  delay(15);               // aspetta 15 millisecondi
  digitalWrite(LED, LOW);    // spegne il LED
  delay(5);               // aspetta 5 millisecondi
}

Dal filmato potete notare la variazione di luminosità nelle tre condizioni:

Con un po’ di esperimenti noterete che la tecnica di variazione della luminosità, utilizzando il ritardo “delay()”, non è il metodo migliore in quanto, non appena inseite altri sensori ad Arduino, oppure inviate dei dati alla seriale, il LED tremolerà nell’attesa che termini la lettura del sensore o la scrittura sulla seriale.

Come evitare questo problema?

Arduino UNO offre la possibilità di usare i pin 3, 5, 6, 9, 10, 11 l’istruzione: analogWrite(), istruzione che consente appunto di far lampeggiare il LED o governare un motore elettrico mentre lo sketch esegue altre istruzioni.

Sintassi:

analogWrite(pin, valore)

dove:

  • pin: è il piedino su cui inviamo il segnale, per Arduino UNO i pin 3, 5, 6, 9, 10, 11
  • valore: è il duty cycle compreso tra 0 (sempre off) a 255 (sempre on)

La funzione non restituisce nessun valore.

Quindi se utilizziamo la funzione analogWrite() per il controllo della luminosità del LED e scriviamo:

analogWrite(11, 0)
il LED collegato al pin 11 avrà una luminosità dello 0% (duty cycle 0%)

// Esempio 06: utilizzo della funzione analgoWrite() - LED spento - (duty cycle 0%)

#define LED 11                // LED collegato al pin digitale 11

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  analogWrite(LED, 0);   // accende il LED
}

analogWrite(11, 64)
il LED collegato al pin 11 avrà una luminosità del 25% (duty cycle 25%)

// Esempio 07: utilizzo della funzione analgoWrite() - LED spento - (duty cycle 25%)

#define LED 11                // LED collegato al pin digitale 11

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  analogWrite(LED, 64);   // accende il LED
}

analogWrite(11, 128)
il LED collegato al pin 11 avrà una luminosità del 50% (duty cycle 50%)

// Esempio 08: utilizzo della funzione analgoWrite() - LED spento - (duty cycle 50%)

#define LED 11                // LED collegato al pin digitale 11

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  analogWrite(LED, 128);   // accende il LED
}

analogWrite(11, 191)
il LED collegato al pin 11 avrà una luminosità del 75% (duty cycle 75%)

// Esempio 09: utilizzo della funzione analgoWrite() - LED spento - (duty cycle 75%)

#define LED 11                // LED collegato al pin digitale 11

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  analogWrite(LED, 191);   // accende il LED
}

analogWrite(11, 255)
il LED collegato al pin 11 avrà una luminosità del 100% (duty cycle 100%)

// Esempio 10: utilizzo della funzione analgoWrite() - LED spento - (duty cycle 100%)

#define LED 11                // LED collegato al pin digitale 11

void setup() {
  pinMode(LED, OUTPUT);       // imposta il pin digitale come output
}

void loop() {
  analogWrite(LED, 255);   // accende il LED
}

Nel filmato allegato potete notare la differenza di luminosità nelle 5 condizioni sopra illustrate.

Imparato come variare la luminosità del LED usando la funzione analogWrite(), vediamo come realizzare il fade del LED ovvero l’accensione e lo spegnimento graduale, attenzione che questo modo di procedere sarà utile anche quando dovremo imparare a variare la velocità di un motorino elettrico.

Lo schetch che vi allego è già presente negli esempi disponibili dal menù: File -> Examples -> 3.Analog -> Fading ne ho variato alcune parti:

// Esempio 11: Fading


#define LED 11              // LED collegato al pin digitale 11
int valoreFade = 0;         // variabile usata per contare in avanti e indietro

void setup()  { 
  pinMode(LED, OUTPUT);     // imposta il pin digitale come output
} 

void loop()  {
  // procede ciclicamente da 0 a 254 (fade in -> aumento luminosità)
  for (valoreFade = 0 ; valoreFade < 255; valoreFade++) { analogWrite(LED, valoreFade); //impostiamo la luminosità del LED delay(10); // aspettiamo 10ms per percepire la viariazione di luminosità, //perché analogWrite è istantaneo } // procede ciclicamente da 255 a 1 (fade out -> diminuzione della luminosità)
  for(valoreFade = 255 ; valoreFade > 0; valoreFade--) {
    analogWrite(LED, valoreFade);      //impostiamo la luminosità del LED
    delay(10);  
    // aspettiamo 10ms per percepire la viariazione di luminosità,
    //perché analogWrite è istantaneo                               
  } 
}

Analizzaimo il codice.

Prendiamo in analisi la prima parte del loop(). All’interno troviamo un primo ciclo for:

...
  // procede ciclicamente da 0 a 254 (fade in -> aumento luminosità)
  for (valoreFade = 0 ; valoreFade < 255; valoreFade++) { 
    analogWrite(LED, valoreFade);      //impostiamo la luminosità del LED
    delay(10);  
    // aspettiamo 10ms per percepire la viariazione di luminosità,
    //perché analogWrite è istantaneo                        
  }
...

Ad ogni ciclo incrementiamo la variabile valoreFade di 1 (valoreFade++) partendo da 0 fino a 254. valoreFade viene utilizzata in analogWrite(LED, valoreFade) per variare il valore del duty cycle ed incrementare la luminosità del LED. Poichè l’azione di analogWrite(LED, valoreFade) è immediata per percepire visivamente la variazione di luminosità introduciamo un piccolo ritardo di 10ms con delay(10). Il ciclo terminerà non appena la condizione valoreFade < 255 non è più vera, cioè valoreFade non più minore di 255.

Il secondo ciclo for consente di diminuire la luminosità:

...
  // procede ciclicamente da 255 a 1 (fade out -> diminuzione della luminosità)
  for(valoreFade = 255 ; valoreFade > 0; valoreFade--) {
    analogWrite(LED, valoreFade);      //impostiamo la luminosità del LED
    delay(10);  
    // aspettiamo 10ms per percepire la viariazione di luminosità,
    //perché analogWrite è istantaneo                               
  } 
...

Ad ogni ciclo la variabie valoreFade viene decrementata di 1 (valoreFade–) facendo decrescere valoreFade da 255 a 1 e di conseguenza la luminosità del LED. Il ciclo terminerà quando la condizione valoreFade > 0 non è più vera.
Usciti da questo secondo ciclo si ripartirà con il primo ciclo for che permetterà nuovamente l’aumento della luminosità del LED.

Nella prossima lezione vedreme come interagire mediante pulsanti sull’intensità luminosità del LED.