Controlling LED based on time elapsed between Push Button presses

Please note, if this has been placed in the wrong area of the forum, then please forgive me. This is my very first post.

I am trying to mimic CPR using a push button. The time elapsed between presses should be 1-2 seconds. If the user is pressing at the required rate, an green LED would be set HIGH.

If the user is too quick or too slow, a red LED would be set HIGH instead.

I've been trying to manipulate this code that I found at baldengineer.com (an extremely helpful site)

//Global Variables
const byte BUTTON=2; // our button pin
const byte LED=13; // LED (built-in on Uno)
 
unsigned long buttonPushedMillis; // when button was released
unsigned long ledTurnedOnAt; // when led was turned on
unsigned long turnOnDelay = 200;//wait to turn on LED
unsigned long turnOffDelay = 400; // turn off LED after this time
bool ledReady = false; // flag for when button is let go
bool ledState = false; // for LED is on or not.
 
void setup() {
 pinMode(BUTTON, INPUT_PULLUP);
 pinMode(LED, OUTPUT);
 digitalWrite(LED, LOW);
 Serial.begin(9600);
}
 
void loop() {
 // get the time at the start of this loop()
 unsigned long currentMillis = millis(); 
 
 // check the button
 if (digitalRead(BUTTON) == LOW) {
  // update the time when button was pushed
  buttonPushedMillis = currentMillis;
  ledReady = true;
  
 }
  
 // make sure this code isn't checked until after button has been let go
 if (ledReady) {
   //this is typical millis code here:
   if ((unsigned long)(currentMillis - buttonPushedMillis) >= turnOnDelay) {
     // okay, enough time has passed since the button was let go.
     digitalWrite(LED, HIGH);
    
     
     // setup our next "state"
     ledState = true;
     // save when the LED turned on
     ledTurnedOnAt = currentMillis;
     // wait for next button press
     ledReady = false;
   }
 }

  
 // see if we are watching for the time to turn off LED
 if (ledState) {
   // okay, led on, check for now long
   if ((unsigned long)(currentMillis - ledTurnedOnAt) >= turnOffDelay) {
     ledState = false;
     digitalWrite(LED, LOW);
    
   }
 }
}

The code flashes a single LED, if the user presses too quickly it won't flash, however any speed past the accepted time and the LED flash.

I've been trying for hours to make this work for my benefits, but I am making no progress.

Any help or advice would be HUGELY appreciated.

You say you tried, but I don't see that... What have you tried and what went wrong?

And a small tip, drop that sketch and make your own. You can learn from that sketch be editing a sketch to do something else rarely is easier / gives you nice code.

Just set out what need to happen.

  • Get the time between button presse. millis() is here of great help
  • Check the time between presses and turn on the right led.

PS, I would say the range of 1 to 2 seconds is to big... If been learned to do it 100 to 120 times a minute.

I tried adding this code in order to turn the LED on.

if ((unsigned long)(currentMillis - buttonPushedMillis) >= turnOnDelay &&   (unsigned long)(currentMillis - buttonPushedMillis)    <= turnOffDelay) {
     // okay, enough time has passed since the button was let go.
     digitalWrite(LED, HIGH);
     Serial.print("Keep pressing at this pace\n\n");

and this to turn the LED off

if ((unsigned long)(currentMillis - buttonPushedMillis) >= turnOnDelay &&   (unsigned long)(currentMillis - buttonPushedMillis)    <= turnOffDelay) {
     // okay, enough time has passed since the button was let go.
     digitalWrite(LED, HIGH);
     Serial.print("Keep pressing at this pace\n\n");

I am struggling to measure the millis() of the button press and make certain actions happen during the appropriate time between presses.

And I know I will need to make my own sketch, but this was the first sketch I found on the internet that pushed me in the right direction.

georgewnewton:
And I know I will need to make my own sketch, but this was the first sketch I found on the internet that pushed me in the right direction.

Then I'll suggest now is a good moment :wink:

And why do you want to know when a led is turned on? All you want to do is turn it on (or off) isn't it?

After a set amount of time of CPR being delivered (i.e. green LED being HIGH for 30 seconds), a 3rd output would indicate that the CPR was successful.

Could you please help on how to measure the time between button presses?

Detect the change in state (IS pressed is not the same as BECAME pressed) and note down the time. To make it all easy I would grab a library like Bounce2. And simply save the time of that moment.

And as for the third led, alright, but that's the same as the first button press :wink:

And you might also want a timeout (let say, no button press for 5 seconds) to turn everything off again.

And like I said, I'm learned to give 30 presses at 100 to 120 presses/minute. So 600ms to 500ms between presses. 1 every 2 seconds is wayyyy to slow.