Puss button does not respond if a delay is used

In loop (), I read the data from the sensors every minute and print it out on the LCD. I have a delay between measuring different sensors so that the text on the display stays visible longer. The problem is that when using delay and therefore minute data, pressing the HIGH button does not work, because in loop () it is at the beginning and responds best outside the minute data when the sensors do not measure.

Can't the reaction of pressing the button be solved outside the loop, so that the pressing works without what happens in the loop? To work right away without any circumstances?

The solution is to remove delay() and instead track elapsed time using millis() so the rest of loop() can keep doing useful things. It is a common pitfall. There is even an example in the IDE - BlinkWithoutDelay (File->examples->02.digital->BlinkWithoutDelay)

There is also a nice tutorial about how to break your code up to do small chunks at a time: several things at the same time

Agree, it is a simple enough matter.

Please post your code, or a smaller similar example showing how your current concept is interfering with the desired behaviour.

Because there's as many ways to do it wrong as there are ways to do it differently, so give us a lot at what you've managed to do sofar.

a7

Using millis() for timing tutorials:
Several things at a time.
Beginner's guide to millis().
Blink without delay().

I use Delay mainly for LCD (1602) to display text long enough. But then the push button doesn't work :frowning:

void loop() {
Reload = digitalRead(RELOAD_DATA_PIN);
if (Reload == HIGH)
{
    // something will be done 
} 

// every 1 minutes
if (millis() - timeMinute >= 60000 || timeMinute == 0) {
timeMinute = millis();

Pressure = bme280.getPressure(); 
lcd.clear();
lcd.print("BME280 pressure:");
lcd.setCursor(0, 1);
lcd.print(Pressure);
delay(3000);

Temp = sht.getTemperature();
lcd.clear();
lcd.print("SHT3x temp:");
lcd.setCursor(0, 1);
lcd.print(Temp);
delay(3000);
}

} // loop

Look in the several things at a time tutorial to see how different things can be done at their own times. Those delay() calls mess up the millis() timing. Get rid of delays completely.

When you post code, post the whole code.

1 Like

Hi @cevepe
You can use external interrupt to detect button press.
Interrupt remain available even during delays().

RV mineirin

@ruilviana, if that will work highly depends on what needs to happen when the button is pressed.

LCD has its own scanning circuitry and display controller. The display will be showing the users data all the time without any interruption. So, there is no need to insert any time delay at all.

you don't need delay.

just switch the contet of the display .

This switches between to LCD contents:

void updateLCD()
{
  const uint16_t interval = 60000;     // update Intervall in milliseconds
  static uint32_t previousMillis = 0;  // timestamp last update
  static byte state = 0;               // which "screen" is to display
  uint32_t currentMillis = millis();   

  if (currentMillis - previousMillis >= interval)
  {
    previousMillis = currentMillis;
    switch (state)
    {
      case 0:                          // show screen 0
        Pressure = bme280.getPressure();
        lcd.clear();
        lcd.print("BME280 pressure:");
        lcd.setCursor(0, 1);
        lcd.print(Pressure);
        state = 1; // show screen 1 next time
        break;
      case 1:                          // show screen 1
        Temp = sht.getTemperature();
        lcd.clear();
        lcd.print("SHT3x temp:");
        lcd.setCursor(0, 1);
        lcd.print(Temp);
        state = 0;
        break;
    }
  }
}

and call

updateLCD();

in your loop().