problème avec temporisation et if/else

bonjour à tous, je suis ultra débutant en arduino et je rencontre un problème que je ne comprend pas.

mon projet est ultra simple:

-un bouton poussoir normalement ouvert (en pull up)

-un servomoteur

je voudrais que quand le bp est pressé le servo se déplace dans un sens et que quand il est relâché il

repart dans sa position d’origine mais seulement après 2 secondes.

voici mon code:

#include <Servo.h>
Servo monservo;


//le bouton est connecté à la broche 2 de la carte Adruino
const int bouton = 2;
//variable qui enregistre l'état du bouton
int etatBouton;
int in1 = 2;

void setup()
{
   digitalWrite(in1, HIGH);
   monservo.attach(10);
   monservo.write(15);
   pinMode(bouton, INPUT); //le bouton est une entrée
   etatBouton = HIGH;//on initialise l'état du bouton comme "relaché
}


void loop() {
 etatBouton = digitalRead(bouton); //Rappel : bouton = 2
 

    
   // Si le bouton est enfoncé,
   if (etatBouton == LOW ) {
     monservo.write(115); //servo 115°
   }
   
    
   else{
     delay (2000);
     monservo.write(10);
     
     
   }
     
  
}

j ai cru comprendre que la tempo “delay” arrêtait tous le programme mais pourquoi s’active t elle quand mon bouton est pressé?

dans mon cas la tempo s’active dans les 2 états du bouton ce que je ne voudrais pas

merci de m’avoir lu.

Jette un œil sur ce tuto tu apprendras à gérer deux boutons sans utiliser delay() pour pouvoir faire autre chose en même temps.

Bonjour,

Le problème c'est que quand le bouton est relaché tu passes ton temps à faire

    delay (2000);
    monservo.write(10);

Il faut que tu fasses cette action uniquement quand le bouton vient d'être relaché. Pour ça, il faut que tu traites le changement d'état du bouton (mémorisation de l'état précédent et comparaison à l'état courant).

kamill:
Bonjour,

Le problème c'est que quand le bouton est relaché tu passes ton temps à faire

    delay (2000);

monservo.write(10);




Il faut que tu fasses cette action uniquement quand le bouton vient d'être relaché. Pour ça, il faut que tu traites le changement d'état du bouton (mémorisation de l'état précédent et comparaison à l'état courant).

ce n'est pas dérangeant dans mon cas enfin je crois, pour expliquer clairement:

c'est pour ouvrir une trappe qui cache des manomètres dans ma voiture, quand je met le contact ça colle un relais dont un contact no est l'entrée de l'arduino , quand ce relais se ré-ouvre (quand je coupe le contact) les mano mettent 2 secondes environs avant de s’éteindre et je voudrais que la trappe se ferme après leurs extinction soit environ 2 secondes. il y a une autre tempo qui coupe l'alimentation de l'arduino après 30 secondes.

donc mon programme est vraiment très simple mais étant un ultra débutant je butte car je ne comprend pas pourquoi la tempo se lance alors que l'arduino na jamais vu l,entrée en low depuis sont démarrage.

je suis sur le tuto très intéressant donné par Zorro_X mais c'est très compliqué pour un néophyte comme moi :smiley:

j’arrive à ça: mais ça ne fonctionne pas du tout je ne trouve pas comment “lancer” la tempo après l’ouverture du bp

#include <Servo.h>
Servo monservo;

// Date pour la gestion du temps
int date;


//le bouton est connecté à la broche 2 de la carte Adruino
const int bouton = 2;
//variable qui enregistre l'état du bouton
int etatBouton;
int in1 = 2;

void setup()
{
    digitalWrite(in1, HIGH);
    monservo.attach(10);
    monservo.write(10);
    pinMode(bouton, INPUT); //le bouton est une entrée
    etatBouton = HIGH;//on initialise l'état du bouton comme "relaché
    Serial.begin(9600);
    date = millis();
    
}


void loop() {
  etatBouton = digitalRead(bouton); //Rappel : bouton = 2
  int dateCourante = millis();
  
  

     
    // Si le bouton est enfoncé,
    if (etatBouton == LOW ) {
      monservo.write(115); //servo 180°
    }
    
     
    else {
      date = dateCourante;
      if( (dateCourante - date) >= 2000 ){
      
      
      monservo.write(10);
      // réinitialiser la date pour compter la prochaine seconde
      
      
      
      
      
      }
    

    }    
    
    
}

ce n'est pas dérangeant dans mon cas enfin je crois, pour expliquer clairement:

Si c'est dérangeant!
Si tu appuies sur ton bouton alors que tu as commencé un delay(2000) et tu as environ 10000 chances contre une que ça arrive, ton action ne sera pas prise en compte avant la fin du délai.
Il faut que tu testes si le bouton vient de changer d'état pour faire l'action.
Comme ceci par exemple

void loop() {
  static int etatPrecedent = HIGH;
  
  etatBouton = digitalRead(bouton); //Rappel : bouton = 2
  if (etatBouton != etatPrecedent)
  {
    // le bouton a changé d'état
    if (etatBouton == LOW ) {
      // Si le bouton est enfoncé,
      monservo.write(115); //servo 115°
    }
    else {
      delay (2000);
      monservo.write(10);
    }
    etatPrecedent = etatBouton;
  }
  delay(20);        // pour anti rebond
}

ha ok j'ai compris , merci pour les explications, je vais continuer a regarder le tuto pour utiliser millis pour pouvoir faire évoluer montage plus tard

C’est une bonne chose de vouloir utiliser millis() si ton programme doit faire autre chose.
Pour ton programme actuel delay() convient (mais c’est toujours intéressant de réfléchir à comment s’en passer).

exactement et ça me permettra d'évoluer vu mes connaissances actuelles, ça ne peut pas faire de mal :smiley:

simsvtec:
je suis sur le tuto très intéressant donné par Zorro_X mais c'est très compliqué pour un néophyte comme moi :smiley:

C'est un tuto pour débutants, je suis donc intéressé par savoir ce que tu n'y comprends pas, pour l'améliorer, merci !