Premetto che i pulsanti per comandare l'ascensore concettualmente sono interni quindi la gestione delle code sarà diversa.
All'inizio l'ascensore sarà a riposo nel piano 1, il display a 7 segmenti mostrerà "1", il LED verde sarà acceso e il LED rosso spento.
L'utente può premere i pulsanti interni dell'ascensore per selezionare il piano a cui desidera andare. Quando uno dei pulsanti viene premuto il motore si muoverà di conseguenza.
Dopo ogni spostamento dell'ascensore il programma aspetterà che l'utente prema un altro pulsante per selezionare il prossimo piano o rimanere fermo.
Collegamenti:
Display a 7 segmenti:
- Segmento A a un pin del microcontrollore o al Pin_Array[0].
- Segmento B a un pin del microcontrollore o al Pin_Array[1].
- Segmento C a un pin del microcontrollore o al Pin_Array[2].
- Segmento D a un pin del microcontrollore o al Pin_Array[3].
- Segmento E a un pin del microcontrollore o al Pin_Array[4].
- Segmento F a un pin del microcontrollore o al Pin_Array[5].
- Segmento G a un pin del microcontrollore o al Pin_Array[6].
- Catodo (pin comune) a terra (GND).
Pulsanti:
- Lato principale dei pulsanti ai pin descritti nel codice (sono 3).
- Collega l'altro lato di ciascun pulsante a terra (GND) o a un resistore di pull-down tra i pin del microcontrollore e GND per evitare letture instabili quando il pulsante non è premuto.
Driver (L293D):
- Il pin di controllo della direzione del motore (Pin_Ponte) deve essere collegato a un pin del microcontrollore.
- Il pin di controllo della velocità del motore (Pin_PWM1 e Pin_PWM2) deve essere collegato a pin del microcontrollore separati (per capire vedi meglio sullo screenshot sottostante).
- Pin di alimentazione del driver (Vcc) e GND rispettivamente a + e -.
Motore CC:
- I pin + e - devono essere collegati al terzo e terzultimo pin del driver (così da essere in grado di invertire la polarità).
Led:
- L'anodo di ciascun LED va a una resistenza (220 ohm) facendo ponte nel pin che lo controlla.
- Il catodo di ciascun LED va direttamente a terra (GND).
Codice:
Scriviamo il codice! All'inizio dichiariamo delle variabili per i componenti usati come i pin dei pulsanti, i LED, i pin PWM un array per il display a 7 segmenti ecc.
Nella funzione setup
che viene eseguita una volta vengono impostate tutte le modalità dei pin come input o output usando pinMode
.
loop
è eseguita in un ciclo e serve per verificare lo stato dei pulsanti e agire di conseguenza.
Scriviamo la funzione visualizzaNumero(Piano)
che serve per visualizzare il numero corrente sul display a 7 segmenti in base al valore di "Piano"
. Si utilizza un array bidimensionale "Array_0"
per definire i segmenti da accendere o spegnere.
digitalRead
è molto importante perché ci permette di leggere gli stati dei pulsanti e memorizzati nelle variabili "StatoPulsante1"
, "StatoPulsante2"
e "StatoPulsante3"
.
Per invertire la polarità del motore vengono disattivati i pin PWM (Pin_PWM1
e Pin_PWM2
) impostati quindi in LOW.
Ad esempio se si preme il tasto 3: all'inizio si verifica se è stato premuto (StatoPulsante3 == HIGH). In caso affermativo il "Piano" viene incrementato gradualmente da 1 a 3 contemporaneamente il LED rosso si accende e il LED verde si spegne. I pin PWM vengono utilizzati per controllare l'alimentazione (in questo caso un motore RC che cambia polarità) e infine arrivati a destinazione il LED rosso viene spento e il verde viene acceso.
#define Pin_PWM1 9
#define Pin_PWM2 10
int Pin_Ponte = 10;
int Piano = 1;
int Pin_LedVerde = A0;
int Pin_LedRosso = A1;
int Pin_Pulsante1 = 13, Pin_Pulsante2 = 12, Pin_Pulsante3 = 11;
int StatoPulsante1, StatoPulsante2, StatoPulsante3;
int Pin_Array[7] = {2, 3, 4, 5, 6, 7, 8};
// display a 7 segmenti
int Array_0[4][7] = {
{1, 1, 1, 1, 1, 1, 0}, // 0
{0, 1, 1, 0, 0, 0, 0}, // 1
{1, 1, 0, 1, 1, 0, 1}, // 2
{1, 1, 1, 1, 0, 0, 1} // 3
};
void setup() {
pinMode(Pin_LedVerde, OUTPUT);
pinMode(Pin_LedRosso, OUTPUT);
pinMode(Pin_Ponte, OUTPUT);
pinMode(Pin_Pulsante1, INPUT);
pinMode(Pin_Pulsante2, INPUT);
pinMode(Pin_Pulsante3, INPUT);
pinMode(Pin_PWM1, OUTPUT);
pinMode(Pin_PWM2, OUTPUT);
Serial.begin(9600);
}
void loop() {
visualizzaNumero(Piano);
StatoPulsante1 = digitalRead(Pin_Pulsante1);
StatoPulsante2 = digitalRead(Pin_Pulsante2);
StatoPulsante3 = digitalRead(Pin_Pulsante3);
digitalWrite(Pin_PWM1, LOW);
digitalWrite(Pin_PWM2, LOW);
// 3
if (StatoPulsante3 == HIGH) {
while (Piano < 3) {
digitalWrite(Pin_LedRosso, HIGH);
digitalWrite(Pin_LedVerde, LOW);
visualizzaNumero(Piano);
digitalWrite(Pin_PWM1, LOW);
digitalWrite(Pin_PWM2, HIGH);
delay(3000);
Piano++;
}
Piano = 3;
digitalWrite(Pin_LedRosso, LOW);
digitalWrite(Pin_LedVerde, HIGH);
}
// 2
if (StatoPulsante2 == HIGH) {
if (Piano > 2) {
while (Piano > 2) {
digitalWrite(Pin_LedRosso, HIGH);
digitalWrite(Pin_LedVerde, LOW);
visualizzaNumero(Piano);
digitalWrite(Pin_PWM1, HIGH);
digitalWrite(Pin_PWM2, LOW);
delay(3000);
Piano--;
}
}
if (Piano < 2) {
while (Piano < 2) {
digitalWrite(Pin_LedRosso, HIGH);
digitalWrite(Pin_LedVerde, LOW);
visualizzaNumero(Piano);
digitalWrite(Pin_PWM1, LOW);
digitalWrite(Pin_PWM2, HIGH);
delay(3000);
Piano++;
}
}
Piano = 2;
digitalWrite(Pin_LedRosso, LOW);
digitalWrite(Pin_LedVerde, HIGH);
}
// 1
if (StatoPulsante1 == HIGH) {
if (Piano > 1) {
while (Piano > 1) {
digitalWrite(Pin_LedRosso, HIGH);
digitalWrite(Pin_LedVerde, LOW);
visualizzaNumero(Piano);
digitalWrite(Pin_PWM1, HIGH);
digitalWrite(Pin_PWM2, LOW);
delay(3000);
Piano--;
}
Piano = 1;
digitalWrite(Pin_LedRosso, LOW);
digitalWrite(Pin_LedVerde, HIGH);
}
}
}
void visualizzaNumero(int numero) {
for (int i = 0; i < 7; i++) {
digitalWrite(Pin_Array[i], Array_0[numero][i]);
}
delay(100);
}
LINK TINKERCAD: