Come faccio a far controllare while più volte?

Salve ho un problema con un progetto con Arduino, si tratta di un prototipo di cassaforte che sfrutta un servo motore come serratura. ho un problema con il codice perché vorrei che quando premo il pulsante si apre la serratura si spegne il led rosso, si accende quello verde e si accendono 2 led bianchi. fin quì ci ero riuscito ma dopo tutto questo, il sensore di luminosità (fotoresistore) faccia chiudere la serratura, essendoci buio quando la porta e chiusa. Il comando while controlla solo una volta il resistore. spero mi possiate aiutare. ecco il codice

int pulsante = 7;
int statop = 0;
int light;
int prova;

#include <Servo.h>
#define PIN_SERVO 10

Servo servo;

void setup() {

  servo.attach(PIN_SERVO);
  Serial.begin(9600);
  pinMode (pulsante, INPUT);
  pinMode (11, OUTPUT);
  pinMode (12, OUTPUT);
  pinMode (9, OUTPUT);
  pinMode (6, OUTPUT);
  pinMode (5, OUTPUT);
  servo.write(180);
  digitalWrite (12, HIGH);
}

void loop() {
  prova = 5;



  light = analogRead(A0);
  statop = digitalRead (pulsante);

  if (statop == HIGH) {

    servo.write(70);
    digitalWrite (12, LOW);
    digitalWrite (9, HIGH);
    digitalWrite (11, HIGH);
    digitalWrite (5, HIGH);
    digitalWrite (6, HIGH);
    delay (1100);
    digitalWrite (11, LOW);
    prova = 9;

  }
}
while (prova == 9) {
  prova = 9;
  if (light < 50) {

    digitalWrite (5, LOW);
    digitalWrite (6, LOW);
    digitalWrite (9, LOW);
    servo.write(180);
    digitalWrite (12, HIGH);
    digitalWrite (11, HIGH);
    delay (900);
    digitalWrite (11, LOW);
    prova = 10;
  }

}

Ti segnalo che, nella sezione in lingua Inglese, si può scrivere solo in Inglese ... quindi, per favore, la prossima volta presta più attenzione in quale sezione metti i tuoi post; questa volta esso è stato spostato, da un moderatore della sezione di lingua Inglese, nella sezione di lingua Italiana ... la prossima volta potrebbe venire direttamente eliminato.

Grazie.

A quanto detto da pert aggiungo ...

... cortesemente, come prima cosa, leggi attentamente il REGOLAMENTO della sezione Italiana del forum, (... e, per evitare future possibili discussioni/incomprensioni, prestando sempre molta attenzione al punto 15), dopo di che, come da suddetto regolamento (punto 16.7), fai la tua presentazione NELL'APPOSITA DISCUSSIONE spiegando bene quali esperienze hai in elettronica e programmazione, affinché noi possiamo conoscere la tua esperienza ed esprimerci con termini adeguati.

Grazie,

Guglielmo

P.S.: Ti ricordo che, purtroppo, fino a quando non sarà fatta la presentazione nell’apposita discussione, nel rispetto del succitato regolamento nessuno ti risponderà (eventuali risposte o tuoi ulteriori post, verrebbero temporaneamente nascosti), quindi ti consiglio di farla al più presto. :wink:

P.P.S.: Evitate di utilizzare la traduzione automatica fatta dal browser ... vi impedisce di capire la lingua della sezione dove andate a scrivere ...

Inoltre, per cortesia, indenta correttamente il programma con CTRL+T nell'IDE e mettilo al posto di quello che hai pubblicato usando la "matita" in basso (modifica).
Benvenuto! :slight_smile:

Ok grazie

ciao...così com'è scritto il while() è fuori dal loop()...magari sbaglio però meglio se verifichi.

detto questo, analizzando il solo while():

while (prova == 9) {
  prova = 9; // questo mi pare inutile
  light = analogRead(A0); // devi aggiungere questa verifica.
  if (light < 50) {

    digitalWrite (5, LOW);
    digitalWrite (6, LOW);
    digitalWrite (9, LOW);
    servo.write(180);
    digitalWrite (12, HIGH);
    digitalWrite (11, HIGH);
    delay (900);
    digitalWrite (11, LOW);
    prova = 10;
  }

}
1 Like

Grazie mille :ok_hand:

il problema ora è un'altro.
su "if (light < 50)" ho messo 5 che va più che bene perché arriva fino a 10 il resistore con la porta aperta, ma si chiude lo stesso senza alcun motivo ho provato anche a cambiare banda ma niente. per favore aiutatemi ne sto uscendo pazzo.

hai verificato cosa ti ritorna il sensore nelle varie situazioni?

Si, con la porta della cassaforte aperta il valore oscilla dai 7 ai 10 (ho provato anche mettendo meno di 5 ma lo stesso) invece a porta chiusa tra 1 e 0.

ok...penso che il problema stia nel "ritardo" al refresh dell'ADC...prova a fare la verifica sulla media delle letture invece che una lettura puntuale...penso che 6-7 letture possano andare...

Non sono molto esperto, potresti dirmi praticamente o in altre parole come fare? Comunque grazie

guarda se questo ti è di aiuto:


uint16_t valoreMedio; // variabile che conterrà la media

bool media(uint16_t& _media); // prototipo funzione

void setup() {
  Serial.begin(115200);

}

void loop() {
  if (media(valoreMedio)) { //verifico se eseguita nuova media
    Serial.println(valoreMedio); //stampo nuova media
  }

}

bool media(uint16_t& _media ) {
  static uint32_t localMillis; // per scandire la lettura
  static uint8_t localPos = 0; //posizione dove salvare il valore
  static uint16_t valoreArray[10] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; //array che conterrà la media
  if (millis() - localMillis > 50) { // leggo ogni 50 ms
    localMillis = millis();
    valoreArray[localPos] = analogRead(A0);
    localPos++;
  }
  if (localPos == 10) { //se ho popolato l'array
    _media = 0; //azzero media precedente
    uint32_t locSomma = 0;
    for (uint8_t i = 0; i < 10; i++) {
      locSomma += valoreArray[i]; //sommo i valore dell'array
    }
    _media = locSomma / 10; // divido per avere il valore medio
    localPos = 0;
    return true; //nuova media disponibile
  } else {
    return false; //nuova media non disponibile
  }
}

Ciao
Dovresti pubblicare il programma attuale e spiegare come hai collegato la fotoresistenza.

Non sbagli, e se avesse indentato correttamente il codice (anche sol con il comando Ctrl-T dell'IDE) se ne sarebbe accorto da solo... :wink:

Appena arrivo a casa provo, comunque grazie

Scusate, la prossima volta farò più attenzione prima fi venire quì.

... più che altro impara ad usare sempre il comando dell'IDE che indenta correttamente il codice (questo lo si fa premendo ctrlT su un PC o cmd T su un Mac, sempre all'interno del IDE).

Un codice ben indentato ti fa saltare subito agli occhi eventuali errori di parentesi messe fuori posto o prioprio mancati :wink:

Guglielmo

1 Like

Non è questione di fare attenzione, non preoccuparti, chiunque può avere una svista o scrivere qualcosa, soprattutto se nuovo della programmazione. Ma ci sono tanti casi, come questo, dove imparando ad indentare correttamente (facendosi aiutare all'inizio dell'IDE stesso, col comando Ctrl-T) si può notare più facilmente anche solo ad occhio che qualcosa non va.
Usa Ctrl-T, e poi cerca di mantenere questo tipo di indentazione, vedrai che sarà molto più facile capire certi problemi.

1 Like

Quindi subito dopo
if (localPos == 10) {
Devo far chiudere il servo giusto