delay vs millis

ho creato questa piccola funzione per creare un ritardo da inserire dove voglio:

void Ritardo()
{
  //ritardo di 10 secondi
  for(byte Ciclo = 0; Ciclo <= 10; Ciclo++)
  {
    delay(1000);
  }
}

però per 10 secondi è tutto fermo.
ho visto che per ovviare il problema posso utilizzare millis… vi chiedo come posso riscrivere la stessa funzione ma utilizzando millis?
grazie

Studia QUI ;)

Guglielmo

P.S. : Queste domande NON vanno in Megatopic !!! Al limite in Generale o in Software !!!

ok grazie in effetti non è la sezione giusta, qualche moderatore dovrà spostarla e me ne scuso. tornando al mio problema già avevo visto qualcosa del genere, però non sono riuscito a farlo: mi spiego il tuo esempio fa lampeggiare un led, io invece voglio che, per esempio, dopo la pressione di un tasto venga acceso un led per 10 secondi e per poi spegnersi. quando il loop ricomincia il led deve rimanere spento, se si preme di nuovo il pulsante si riaccende.

questo è il codice:

if (buttonPremuto == HIGH)   // se pulsante premuto
  {
    digitalWrite(13, HIGH); //accende il led
    Ritardo(); //per 10 secondi
  }
  else 
    digitalWrite(13, LOW); //spegne il led
  }

dovrei modificare questo in modo tale che durante i 10 secondi in cui il led è acceso, arduino possa svolgere altre funzioni:...una che mi servirebbe è: premendo un altro pulsante possa spegne il led prima dei dieci secondi. anora grazie

L'esempio che Leo fa è molto chiaro ... ... ti devi salvare il momento (millis) in cui hai fatto una cosa (nell'esempio previousMillis) e poi, ad ogni ciclo, devi confrontare il tempo attuale con il tempo salvato e, se passato il tempo che vuoi (interval), fare quello che desideri ...

if (millis() - previousMillis > interval) {
  fai_quello_che_devi_fare;
  previousMillis = millis();
}

... prova ad adattarlo al tuo caso ;)

Guglielmo

 if (buttonPremuto == HIGH) {
   if(currentMillis - previousMillis > interval) {
    previousMillis = currentMillis; // save the last time you blinked the LED
    digitalWrite(13, HIGH);
  }
  else
    digitalWrite(13, LOW); //spegne il led
  }

perchè non funziona? come dovrebbe funzionare: se premo il pulsante, si accende il led per un tempo che stabilisco in interval e poi si spegne; se non premo il pulsante resta spento

Ma hai applicato una routine di debounce ??? Perché altrimenti tu credi di premere e lasciare il pulsante, ma in verità i rimbalzi fanno si che la cosa venga letta molte volte come tante pressioni e rilasci !!!

...ed in ogni caso fatti un diagrammino di flusso di ciò che vuoi fare, poi lo traduci in C ... perché mi sembra che sia proprio sbagliata la logica ;)

Guglielmo

P.S. : E metti TUTTO il codice completo, perché con gli spezzoni è difficle capire cosa altro c'è dietro !

questo è ilcodice completo:

int buttonPremuto;
unsigned long previousMillis = 0;        
unsigned long interval = 10000;  

void setup() {
  pinMode(13, OUTPUT); 
  pinMode(9, INPUT);  
}

void loop() {
  unsigned long currentMillis = millis();
  buttonPremuto = digitalRead(9);

  if (buttonPremuto == HIGH) {
   if(currentMillis - previousMillis > interval) {
    previousMillis = currentMillis; 
    digitalWrite(13, HIGH);
  }
  else
    digitalWrite(13, LOW); //spegne il led
  }
}

come dovrebbe funzionare: premo il pulsante e il led rimane acceso per 10 secondi e poi si spegne.

qualche aiuto? grazie

Devi separare le 2 cose, ossia la lettura del pulsante ed il conto alla rovescia di 10 secondi. Metti 2 if, uno dietro l'altro, nel loop. Nel primo leggi lo stato del pulsante. Se è stato premuto, cambi di valore ad una variabile di stato, accendi il led e memorizzi la lettura di millis. Nel secondo leggi lo stato di questa variabile e se è uguale ad un certo valore, fai il confronto fra millis corrente e millis salvato nel precedente if. Quando è uguale o maggiore a 10000 (10 s), spengi il led e rimetti la variabile di stato al valore di partenza, in modo che il primo if torni attivo.

unsigned long currentMillis;
unsigned long previousMillis=0; 
int stato=LOW;   
unsigned long interval = 10000;  
int buttonPremuto;

void setup() {  
  pinMode(13, OUTPUT); 
  pinMode(9, INPUT);  
}

void loop(){
  currentMillis = millis();
  buttonPremuto = digitalRead(9);


if ((buttonPremuto == HIGH) and (stato==LOW)) {
   
    previousMillis = currentMillis; 
    stato=HIGH;
    digitalWrite(13, HIGH);
  }
  else if ((buttonPremuto == LOW) and (stato==HIGH) ){
    if (currentMillis - previousMillis > interval) {
    digitalWrite(13, LOW); //spegne il led
    stato=LOW;
    }
  }
}

ok ci siamo quasi…
se continuo a tenere premuto il pulsante il led resta acceso. come posso fare per far spegnere il led noostante io tenga premuto il pulsante?
ancora grazie

Non devi mettere l'else. Come ti avevo detto, devi fare 2 if distinti. Il primo controlla solo se il pulsante è premuto e se la variabile di stato è su false. Con entrambe le condizioni vere, entri nel blocco dell'if, dove metti la variabile di stato su true e fai le altre 2 cose (salvataggio di millis e accensione led). A questo punto in questo if non ci entri più finché la variabile di stato è true, quindi ignori la pressione del pulsante continua. Inoltre currentMillis non ti serve.

void loop(){
if ((digitalRead(9) == HIGH) and (stato==LOW)) {
    previousMillis = millis(); 
    stato=HIGH;
    digitalWrite(13, HIGH);
}
if (stato==HIGH) {
  if (millis() - previousMillis > interval) {
    digitalWrite(13, LOW); //spegne il led
    stato=LOW;
  }
}