Incrémenter décrémenter une variable avec boutons poussoirs

Bonjour

Je souhaiterai incrémenter ou décrémenter une variable à l'aide de boutons poussoirs
Concrètement il s'agirait de régler la pression atmosphérique du jour pour utiliser le capteur de pression BMP280.

J'ai déjà bidouillé un code à partir de codes déjà existants pour lire les informations du capteur BMP280 sur un écran OLED en I2C.
(j'y ai aussi ajouté un module RTC3231 pour l'heure et un pont diviseur de tension pour connaitre le niveau de la batterie).

Tout cela marche bien mais je suis obligé de connecter la carte arduino au PC et la reprogrammer si je veux ajuster la pression atmosphérique.

Mon idée est d'ajouter au montage 2 boutons poussoirs : un pour augmenter et un pour diminuer la valeur de la pression atmosphérique.

Mes piètres connaissances de l'IDE m'amènent à vous demander si vous une idée pour réaliser la chose.

Désolé pour ce style un peu fouillis et merci d'avance

PS : je voulais mettre le code mais le message semble trop long

Je ne comprends pas ce que tu veux faire : on ne peut pas régler la pression atmosphérique, elle vaut ce qu'elle vaut et est mesurée par un baromètre... ou un capteur

Désolé, je me suis très mal exprimé.
En fait c'est la pression atmosphérique au niveau de la mer (qu'on nomme QNH) que je voudrai régler en fonction des données du jour, car cette pression varie en fonction de plusieurs facteurs comme entre autre la température.
Dans l'exemple pour le capteur BP280, par défaut cette pression est à 1013,25 HPa. Ce qui correspond au niveau moyen de la mer.
C'est à partir de cette pression qu'on peut déterminer l'altitude par rapport au niveau de la mer en à un endroit donné en comparant les 2 pressions : celle du niveau de la mer et celle du point où on veut mesurer l'altitude.
Mais cette valeur peut changer en fonction des conditions du jour. Pour avoir une altitude correcte il faut donc connaitre le QNH local. C'est le calage altimétrique.

Enfin bref, QNH ou autre chose peu importe. Ce que j'aimerai savoir c'est s'il est possible de modifier une variable, un peu comme augmenter le volume sonore ou régler l'heure d'un réveil.

bonjour,
déjà fais un code avec incrémentation ou décrémentation via 2 boutons
que ce soit un qnh,une variable x ou y le principe est le même.

un antirebond pour les boutons, input pullup en interne ou via un autre moyen externe

x variable du compteur
si boutonA appuyé===> x = x+1 ou x++
si boutonB appuyé===> x = x-1 ou x--
afficher x

Pour plus d'info sur le bouton poussoir, voir ici

infobarquee:
bonjour,
déjà fais un code avec incrémentation ou décrémentation via 2 boutons
que ce soit un qnh,une variable x ou y le principe est le même.

un antirebond pour les boutons, input pullup en interne ou via un autre moyen externe

x variable du compteur
si boutonA appuyé===> x = x+1 ou x++
si boutonB appuyé===> x = x-1 ou x--
afficher x

Merci pour ta réponse.
C'est justement ce que je ne sais pas faire !

Il manque encore des infos. Ton explication sur le QNH est très claire, merci.

Si tu veux modifier une variable pour lui donner cette valeur de QNH avec une paire de boutons (+ et -), et si tu veux une précision de 0.01 HPa, tu risque d'avoir beaucoup d'appuis à faire sur ces boutons. Rattraper 0.5 HPa par pas de 0.01 demande 50 appuis...

Donc, j'imagine qu'il te faudrait une paire de boutons pour +/-1 HPa, une autre paire pour +/- 0.1 HPa et une autre pour +/- 0.01 HPa ?

Enfin, il te faudra certainement un afficheur pour te montrer où tu en es. Un truc comme ça

Pour apprendre la programmation avec bouton poussoir, tu as un tuto ici que tu peux déjà essayer. Le INPUT_PULLUP indiqué par Infobarquee est bien expliqué ici

Bon soyez indulgents...
J'ai essayer d'écrire un code Pas eu le t
emps de tester avec un montage.
Qu'en pensez vous ?

int pressionQNH=1013.25; // QNH initialisée à la pression standard
int pinBouton1; // Bouton poussoir 1 branché en pul up sur le pin 1
int pinBouton2; // Bouton poussoir 2 branché en pul up sur le pin 2

void setup() {
  pinBouton1 = 2;
  pinBouton2 = 2;
  

 
  //définition des modes

  pinMode(pinBouton1, INPUT); 

  
  pinMode(pinBouton2, INPUT); 
  Serial.begin(9600);



}

void loop() {
  //lecture de l'état du bouton et stockage dans etatBouton

  boolean etatBouton1 = digitalRead(pinBouton1);
  boolean etatBouton2 = digitalRead(pinBouton2);
  //test des conditions

  if (etatBouton1==HIGH)//test si bouton appuyé

  {

    pressionQNH=pressionQNH+0.25;

  }

  if (etatBouton2==LOW)//test si bouton levé

  {

    pressionQNH=pressionQNH-0.25;

  }

  delay(100); //petite attente

  Serial.print(pressionQNH);
  delay(2000);

}

C'est pas mal pour un début :slight_smile:
Voici une version corrigée :

float pressionQNH = 1013.25; // QNH initialisée à la pression standard
int pinBouton1 = 2; // Bouton poussoir 1 branché en pullup sur le pin 2
int pinBouton2 = 3; // Bouton poussoir 2 branché en pullup sur le pin 3

void setup() {
  //définition des modes
  pinMode(pinBouton1, INPUT_PULLUP);
  pinMode(pinBouton2, INPUT_PULLUP);
  Serial.begin(9600);
}

void loop() {
  //lecture de l'état du bouton et stockage dans etatBouton
  boolean etatBouton1 = digitalRead(pinBouton1);
  boolean etatBouton2 = digitalRead(pinBouton2);
  //test des conditions
  if (etatBouton1 == LOW) //test si bouton 1 appuyé
  {
    pressionQNH = pressionQNH + 0.25;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(30);
  }
  if (etatBouton2 == LOW) //test si bouton 2 appuyé
  {
    pressionQNH = pressionQNH - 0.25;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(30);
  }
}

Tes erreurs :

  • Un int est un entier, donc pas de chiffre après la virgule. Il te faut un float
  • Les pins 0 et 1 sont réservées à la liaison série avec le PC, prends d'autres pins pour tes boutons (2 et 3 par exemple)
  • INPUT_PULLUP pas INPUT
  • Un bouton en PULLUP renvoie LOW s'il est appuyé. Donc les tests se font tous les deux sur LOW
  • Ton code affichait le QNH en permanence, même si aucun bouton n'est appuyé. Ça remplit la console pour rien : ici on n'affiche que lorsque le QNH est changé.
  • Enfin, ton delay(2000) risquait de te faire louper des appuis : autant l'ôter.
    Si tu vois un comportement bizarre lors de l'appui des boutons, augmente la valeur des delay(30).

lesept:
Il manque encore des infos. Ton explication sur le QNH est très claire, merci.

Si tu veux modifier une variable pour lui donner cette valeur de QNH avec une paire de boutons (+ et -), et si tu veux une précision de 0.01 HPa, tu risque d’avoir beaucoup d’appuis à faire sur ces boutons. Rattraper 0.5 HPa par pas de 0.01 demande 50 appuis…

Donc, j’imagine qu’il te faudrait une paire de boutons pour +/-1 HPa, une autre paire pour +/- 0.1 HPa et une autre pour +/- 0.01 HPa ?

Enfin, il te faudra certainement un afficheur pour te montrer où tu en es. Un truc comme ça
[

Pour apprendre la programmation avec bouton poussoir, tu as un tuto ici que tu peux déjà essayer. Le INPUT_PULLUP indiqué par Infobarquee est bien expliqué ici

Merci. En fait sur le montage déjà existant, j’utilise un écran OLED en I2C pour afficher l’altitude, la pression atmosphérique, la témpérature (renseignés par le capteur BMP280), l’heure (module RTC3231) et le niveau de la batterie (pont diviseur de tension).

Ci-joint la photo du montage (ne prenez pas peur, je sais c’est moche)

lesept:
C'est pas mal pour un début :slight_smile:
Voici une version corrigée :

float pressionQNH = 1013.25; // QNH initialisée à la pression standard

int pinBouton1 = 2; // Bouton poussoir 1 branché en pullup sur le pin 2
int pinBouton2 = 3; // Bouton poussoir 2 branché en pullup sur le pin 3

void setup() {
  //définition des modes
  pinMode(pinBouton1, INPUT_PULLUP);
  pinMode(pinBouton2, INPUT_PULLUP);
  Serial.begin(9600);
}

void loop() {
  //lecture de l'état du bouton et stockage dans etatBouton
  boolean etatBouton1 = digitalRead(pinBouton1);
  boolean etatBouton2 = digitalRead(pinBouton2);
  //test des conditions
  if (etatBouton1 == LOW) //test si bouton 1 appuyé
  {
    pressionQNH = pressionQNH + 0.25;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(30);
  }
  if (etatBouton2 == LOW) //test si bouton 2 appuyé
  {
    pressionQNH = pressionQNH - 0.25;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(30);
  }
}



Tes erreurs :

- Un int est un entier, donc pas de chiffre après la virgule. Il te faut un float
- Les pins 0 et 1 sont réservées à la liaison série avec le PC, prends d'autres pins pour tes boutons (2 et 3 par exemple)
- INPUT_PULLUP pas INPUT
- Un bouton en PULLUP renvoie LOW s'il est appuyé. Donc les tests se font tous les deux sur LOW
- Ton code affichait le QNH en permanence, même si aucun bouton n'est appuyé. Ça remplit la console pour rien : ici on n'affiche que lorsque le QNH est changé.
- Enfin, ton delay(2000) risquait de te faire louper des appuis : autant l'ôter.
Si tu vois un comportement bizarre lors de l'appui des boutons, augmente la valeur des delay(30).

Merci !
Je vais essayer ça avec un montage

J’ai donc fait le montage (2 boutons poussoirs montés avec résistances en pull_up) et essayé avec le code de lesept
Ca marche mais j’ai un problème. Pour un appui sur le bouton poussoir la valeur pressionQNH est modifiée tant que le doigt reste appuyé. J’ai essayé de modifier la valeur à additionner ou soustraire. Au lieu de 0.25 j’ai mis 0.01 mais le réglage reste difficile et peu précis.
Y a t il un moyen de prendre en compte juste le nombre d’appui sur le bouton poussoir ?

Ci-joint une capture d’écran du moniteur série après un seul appui très bref sur un des boutons poussoirs

Capture Appui bouton poussoir pour régler le QNH.PNG

hello
et avec ce rajout

float pressionQNH = 1013.25; // QNH initialisée à la pression standard
int pinBouton1 = 2; // Bouton poussoir 1 branché en pullup sur le pin 2
int pinBouton2 = 3; // Bouton poussoir 2 branché en pullup sur le pin 3

void setup() {
  //définition des modes
  pinMode(pinBouton1, INPUT_PULLUP);
  pinMode(pinBouton2, INPUT_PULLUP);
  Serial.begin(9600);
}

void loop() {
  //lecture de l'état du bouton et stockage dans etatBouton
  boolean etatBouton1 = digitalRead(pinBouton1);
  boolean etatBouton2 = digitalRead(pinBouton2);
  //test des conditions
  if (etatBouton1 == LOW) //test si bouton 1 appuyé
  {
  while(!digitalRead(pinBouton1){;} //attend que BP1 soit relaché
    pressionQNH = pressionQNH + 0.25;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(30);
  }
  if (etatBouton2 == LOW) //test si bouton 2 appuyé
  {
  while(!digitalRead(pinBouton2){;}//attend que BP2 soit relaché
    pressionQNH = pressionQNH - 0.25;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(30);
  }
}

Bonsoir,

Il faut raisonner en événement et pas en niveau logique.

L'astuce est de détecter quand le bouton poussoir change d'état puis de vérifier si il a été relâché, si oui on exécute des instructions.

if (!digitalRead(monboutonpousoir)) {
 // Temporisation bloquante (obligatoire!) 
 delay(xxx);
 
 if(digitalRead(PUSH_BUTTON_PIN_1)) {
                        
 // faire qqch ici

 }
  
 }

Trop bon ! il fallait juste modifier les délais dans cette partie du code :

if (etatBouton1 == LOW) //test si bouton 1 appuyé
  {
    pressionQNH = pressionQNH + 0.01;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(1000);
  }
  if (etatBouton2 == LOW) //test si bouton 2 appuyé
  {
    pressionQNH = pressionQNH - 0.01;
    Serial.print("Pression QNH : ");
    Serial.println(pressionQNH,2);
    delay(1000);
  }

Ce délai était initialement à 30 millisecondes, je l'ai mis à 1 seconde : impec !

Et ça marche avec mon altimètre !

Merci encore pour l'aide.

Petite question subsidiaire. Ma carte étant alimentée par une pile 9V ne serait il pas plus judicieux pour économiser la pile de monter les boutons poussoirs avec des résistance en pull_down plutôt qu'en pull_up ?

Oui effectivement cela marche mais ce n'est pas la solution optimale parce que tu viens ralentir tous ton système a 1Hz.

Petite question subsidiaire. Ma carte étant alimentée par une pile 9V ne serait il pas plus judicieux pour économiser la pile de monter les boutons poussoirs avec des résistance en pull_down plutôt qu'en pull_up ?

Les piles 9V ont une tres faible capacité (~200mAh), pour cette raison elles ne durent pas dans le temps. Je te conseil d'utiliser des accumulateurs Ni-Mh.

-Standby:
Oui effectivement cela marche mais ce n’est pas la solution optimale parce que tu viens ralentir tous ton système a 1Hz.

Les piles 9V ont une tres faible capacité (~200mAh), pour cette raison elles ne durent pas dans le temps. Je te conseil d’utiliser des accumulateurs Ni-Mh.

Merci pour le conseil. Pourrais-tu m’expliquer pour le 1Hz ?

Pour ceux que ça intéresse je mets le code et une photo du montage avec le capteur BMP280 les 2 boutons poussoirs montés avec des résistances en pull_up et l’écran OLED connecté en I2C. Le tout branché sur une carte nano.

float pressionQNH = 1013.25; // QNH initialisée à la pression standard
int pinBouton1 = 2; // Bouton poussoir 1 branché en pullup sur le pin 2
int pinBouton2 = 3; // Bouton poussoir 2 branché en pullup sur le pin 3
#include <Wire.h>
#include <SPI.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BMP280.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define OLED_RESET 4
Adafruit_SSD1306 display(OLED_RESET);
#define BMP_SCK 13
#define BMP_MISO 12
#define BMP_MOSI 11 
#define BMP_CS 10
Adafruit_BMP280 bmp; // I2C
//Adafruit_BMP280 bmp(BMP_CS); // hardware SPI
//Adafruit_BMP280 bmp(BMP_CS, BMP_MOSI, BMP_MISO,  BMP_SCK);

void setup() {
  //définition des modes
  pinMode(pinBouton1, INPUT_PULLUP);
  pinMode(pinBouton2, INPUT_PULLUP);
  Serial.begin(9600);
  Serial.println(F("BMP280 test"));
  if (!bmp.begin(0x76)) {  
    Serial.println(F("Could not find a valid BMP280 sensor, check wiring!"));
    while (1);
}

  display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  display.display();
  delay(2000);
  display.clearDisplay();
}

void loop() {
  //lecture de l'état du bouton et stockage dans etatBouton
  boolean etatBouton1 = digitalRead(pinBouton1);
  boolean etatBouton2 = digitalRead(pinBouton2);
  //test des conditions
  if (etatBouton1 == LOW) //test si bouton 1 appuyé
  {
    pressionQNH = pressionQNH + 0.25;
    //Serial.print("Pression QNH : ");
    //Serial.println(pressionQNH,2);
    delay(500);
  }
  if (etatBouton2 == LOW) //test si bouton 2 appuyé
  {
    pressionQNH = pressionQNH - 0.25;
    //Serial.print("Pression QNH : ");
    //Serial.println(pressionQNH,2);
    delay(500);
  }
    //Serial.print(F("Temperature = "));
    //Serial.print(bmp.readTemperature());
    //Serial.println(" *C");
    //Serial.print(F("Pressure = "));
    //Serial.print(bmp.readPressure());
    //Serial.println(" Pa");
    //Serial.print(F("Approx altitude = "));
    //Serial.print(bmp.readAltitude(pressionQNH)); // (NASSER) l'altitude est donnée en fonction de la pression QNH qui peut être réglée avec les 2 boutons poussoirs
    //Serial.println(" m");
    //Serial.println();
    //Serial.print("Pression QNH : ");
    //Serial.println(pressionQNH,2);
    //delay(2000);

    display.setTextSize(2);
   display.setTextColor(WHITE);
   display.setCursor(0,0);
   display.print(bmp.readAltitude(pressionQNH));
   display.println(" m");
   display.print("QNH"); // (NASSER)  QNH réglable avec les boutons poussoirs 
   display.println(pressionQNH);
   display.display();
   delay(1000);
   display.clearDisplay();
}

Le 1Hz vient de ta ligne dans le traitement des boutons
delay(1000);Essaye de diminuer cette valeur qui est très surestimée : 100 ou 200 devraient suffire

lesept:
Le 1Hz vient de ta ligne dans le traitement des boutons
delay(1000);Essaye de diminuer cette valeur qui est très surestimée : 100 ou 200 devraient suffire

Désolé j’ai pas saisi