ciao a tutti voglio realizzare 2 campanelli con 2 buzzer cosi devono funzionare:
PULSANTE A fa suonare il BUZZER A e mai BUZZER B
PULSANTE B fa suonare il BUZZER B e mai BUZZER a
sequenza voluta
premo PULSANTE
suona BUZZER
rilascio il pulsante prima di 3 secondi
BUZZER smette di suonare
non rilascio il PULSANTE
BUZZER smette dopo 3 secondi
ho provato diversi sketch ma tutti non facevano al caso
il buzzer suona al comando e smette dopo il tempo e dopo aver rilasciato il pulsante
in alcuni casi se 1 pulsante è premuto l'altro buzzer non suona. cercando su internet mi pare di aver capito che il delay blocca il ciclo quindi conviene usare il millis.
cercato sketch con millis ma il risultato non e cambiato.pero nelle mie prove se un pulsante rimaneva premuto l'altro funzionava
Io farei in questo modo!
1)Uso un if else per ogni pulsante, in questo modo posso ottenere, se il pulsante è premuto suono, else altrimenti arresto il suono.
All'interno dell'if con la funzione millis() comincio il conteggio di 3 secondi, se sono passati interrompo il suono
Esempio per un pulsante, da duplicare per gestire due pulsanti, quindi due variabili per il tempo:
unsigned long tempo1=0; //variabile globale dichiarata ad di fuori di ogni funzione
byte suono1=1;
void loop(){
if(digitalRead(pulsante)==HIGH){
if(suono1==1){
tone(pin, frequency);
}
if(millis()-tempo1>=3000){// Passati 3 secondi
notone(pin); //fermo il suono
suono1=0;// rendo falsa la condizione cosi il programma non esegue piu tone
}
}else{
suono1=1; // Abilito il suono se si preme il pulsante
tempo1=millis(); // Prendo il tempo attuale
notone(pin); // Se non premo il pulsante arresto il suono
}// end if
}// end loop()
torn24:
ho tolto un po di righe vuote, un po sono rimaste ma penso renda più leggibile
Essendoci due buzzer da gestire con 'tone' (di cui se non sbaglio solo uno alla volta può essere attivo), mi sembra più "sicura" una logica in cui 'notone' venga invocato solo se serve, e non ad ogni ciclo di loop quando il pulsante non è attivo:
unsigned long tempo1 = 0;
byte suono1 = 1;
void loop()
{
if (digitalRead(pulsante) == HIGH) // se pulsante premuto
{
if (suono1 == 1) // accende se spento
{
tone(pin, frequency);
tempo1 = millis();
suono1 = 2;
}
else if (suono1==2 && (millis()-tempo1 >= 3000)) // spegne se timeout
{
notone(pin);
suono1 = 3;
}
}
else // se pulsante non premuto
{
if (suono1 == 2) { notone(pin); } // spegne se acceso
suono1 = 1;
}
}
La variabile suono1 indica le seguenti situazioni:
1 = non premuto, buzzer spento
2 = premuto, buzzer acceso
3 = premuto, buzzer spento per timeout
torn24:
a me non veniva spontaneo risolvere con una macchina a stati
Eppure l'hai scritta, ne ho solo aggiunto uno Forse intendevi dire che non la avevi pensata esplicitamente a stati, ma in realtà quando c'è anche una sola variabile flag come 'tone1' il codice è già una macchina a stati (cioè l'esecuzione non dipende solo ed esclusivamente dagli ingressi attuali ma anche da quello che è successo prima).