Arduino delay time

Hello!

I need a piece of help on code i have, hope you arduino users could advice on this subject.
What i have is ir remote connected to arduino with irlibrary. I found it on the net somewhere, it's great it works

if (irrecv.decode(&results)) {
Serial.println(results.value, HEX);
if (results.value == 0xC03T00CF) {
digitalWrite(PIN1, HIGH); 
delay(5000);
digitalWrite(PIN1, LOW);

Excuse this bit of a code i'll try to explain what i need

When i press the button on remote it will make pin1 to high and after 5 seconds to low. If i press a button while these 5 seconds last it won't do anything until 5 seconds reach the end. how can i make it to interrupt the action for example on 2nd or 3rd second and start the process from the beginning lasting 5 seconds again and so on? so to say i need to make a long lasting loop without interruption - if i press the button many times pin1 should stay high until i stop pressing it.

Advice is much awaited thank you

This is like a re-triggerable monostable. Set up a variable to hold when the time delay should be over, in pseudo code:-
long int endTime;
Then initialises it:-
endTime = millis() + 5000; // 5 seconds delay
Then look for when millis() is greater than end time:-
if(millis() > endTime) { // do what you want at the end }
then test the button:-
if(buttonPressed) { endTime = millis() + 5000; } // reset the 5 seconds delay

wauw that was fast, thank you

i didn't quite understand where to put it though in my code:

endTime = millis() + 5000; // 5 seconds delay
Then look for when millis() is greater than end time:-
if(millis() > endTime) { // do what you want at the end }
then test the button:-
if(buttonPressed) { endTime = millis() + 5000; } // reset the 5 seconds delay

thank you

I would be so happy if someone could tell me where to put the pseudo code in my code i'm new to arduino yet :slight_smile:

Psudo code is just a sketch not the final picture :slight_smile:
before void setup () put
unsigned long endTime;

like so:

unsigned long endTime;
void setup () {

then in stead of:

if (irrecv.decode(&results)) {
Serial.println(results.value, HEX);
if (results.value == 0xC03T00CF) {
digitalWrite(PIN1, HIGH);
delay(5000);
digitalWrite(PIN1, LOW);

You put:

if (irrecv.decode(&results)) {
Serial.println(results.value, HEX);
if (results.value == 0xC03T00CF) {
digitalWrite(PIN1, HIGH);
endTime = millis() + 5000; // 5 seconds delay
}
if(millis() > endTime) { // do what you want at the end 
digitalWrite(PIN1, LOW);
}

of course I assumed that the code example is in the loop, so it is probably most certanly wrong :slight_smile:
if pushing many buttons then you need many variables (1 for each button) to hold the stopwatch timers

Study the "Blink without delay example" sketch at the Arduino.cc

You will get answers by looking at that.

thank you for that i'll check this one out now :slight_smile:

doesn't work as you said, if i press the button keeps looping forever :frowning:

Would you like us to guess what your problem is? Or, would you prefer to post your code, so we can tell?

#include <IRremote.h>

int RECV_PIN = 11;
int PIN_1 = 3;


IRrecv irrecv(RECV_PIN);
decode_results results;

void setup(){
  
  digitalWrite(11,HIGH);
  pinMode(PIN_1, OUTPUT);

  Serial.begin(9600);
  irrecv.enableIRIn(); // Start the receiver
}

int on = 0;
unsigned long last = millis();
unsigned long endTime
  
void loop() {
  if (irrecv.decode(&results)) {
    Serial.println(results.value, HEX);
    if (results.value == 0xC03C00CF) { // If it's been at least 1/4 second since the last
      // IR received, toggle the relay
        if (millis() - last > 250) {
        on = !on;
        digitalWrite(PIN_1, HIGH);
        endTime = millis() + 5000; // 5 seconds delay
        }
        if(millis() > endTime) { // do what you want at the end
        digitalWrite(PIN_1, LOW);
        }
        
      }
        
    
    irrecv.resume(); // Receive the next value
  }
 
      }

That code won't compile and without indentation the code is very difficult to read. Can you auto-format the sketch you ran and post that.

In addition to what mem said, setup is executed once. When the if test is encountered, millis() will not return a value less than endTime, so the digitalWrite is skipped, and loop is called (over and over again).

sorry, i corrected to a full code now

That code is not implementing what I said you should with pseudo code.

i didn't quite understand where to put it though in my code:

Pseudo code is just pretend code intended to give you the idea of what to do. You have to turn it into real code that you can compile and run and you have to put it into the context of your code.

if i press the button keeps looping forever

That is what you asked for:-

how can i make it to interrupt the action for example on 2nd or 3rd second and start the process from the beginning lasting 5 seconds again and so on?

So if you hold the button down forever it will last forever. When you stop holding the button down then 5 seconds after this it will stop.

Is that not what you want?
If not, could you explain again how you want it to work.

Grumpy_Mike, is the code i pasted correct? also i'll try to explain what i want once again with additional details

When i press the button (did forgot to mention that arduino receives C03C00CF code only when the button is released but not when it is pushed, so it will not receive any code while the button is being pushed, you need to release it and then get the code) and it is released Pin_1 goes high for 5 seconds and then stops. That's a simple delay action. Just imagine i press a button pin1 goes high but i interrupt this process let's say on 2nd or 3rd second and push the button again and i need the new action to last for 5 seconds too. In another words the complete scenario should stop when i don't press that button, but if i do every new button push should last 5 seconds no matter if a previous push wasn't complete it should start a new.

Also, if it is possible to make another scenario like if the button was pushed 2 times the delay would be 5+5 seconds, if 3 times - 5+5+5= 15 (make somekind of a buffer)

i guess that's possible the only question is how ::slight_smile:

let's say on 2nd or 3rd second and push the button again and i need the new action to last for 5 seconds too

So if this action is just putting a pin high for 5 seconds. If you push it again (and release it) after 2.5 seconds you need the pin to stay high for 2.5 + 5 seconds? Then if after 3 seconds of this it is pushed again you need another 5 seconds giving you 2.5 + 3 + 5 seconds that the pin remains high. Also any subsequent pushes should keep the pin high for 5 more seconds.
Is that it?

OR do you mean for two buttons pressed in 5 seconds you want 5 + 5 seconds? Three to give you 15 seconds and so on.

Grumpy_Mike, almost there but you gave me even better scenario :slight_smile:

I was telling that

  1. first push = 5 seconds, and if another push takes place before 5 seconds are over second push breaks the first push and counter starts again from 5 seconds. so there's no 5+5 but simply 5 seconds every time the button is pressed and even if the previous action wasn't complete. Hope you understand

  2. was 5+5+5 and so on, like you said

  3. your scenario, like 2,5 + 3 + 5 (sounds great)

Could someone help me out with at least one scenario please? :slight_smile:

It will be easier to help if you can clearly describe the scenario you would like to implement. For example, your code has a ¼ second check, what is that for?
Perhaps you can write out in words exactly what you want to happen when a command is received ( when idle, within a quarter second of a previous command, within the 5 seconds trigger time etc).

ok, 1/4 second check is from another project code (not mine) and when i try to remove it the code gets unworkable

Scenario, like Grumpy_mike offered:

1st action pin_1 goes high and after 5 seconds goes low. If you push it again (and release it) after 2.5 seconds pin stays high for 2.5 + 5 seconds. Then if after 3 seconds of this it is pushed again pin_1 stays high for another 5 seconds giving you 2.5 + 3 + 5 seconds that the pin remains high. Also any subsequent pushes should keep the pin high for 5 more seconds.

that's it

here is a sketch that is somewhat similar that may give you ideas on how to proceed:

const int ledPin = 13;
const int btnPin = 8;
const unsigned long duration = 5000; // 5 seconds

void setup(){

 pinMode(ledPin, OUTPUT);
 pinMode(btnPin, INPUT);
 digitalWrite(btnPin, HIGH); // turn on pullup resistor
 Serial.begin(9600);
}

boolean isActive = false;
unsigned long offTime;


void loop() {
  if (digitalRead(btnPin) == LOW)
  {
    Serial.println("Button Pressed");    
    digitalWrite(ledPin, HIGH);
    isActive = true;
    offTime = millis() + duration;
  }
  else
  {
     if(isActive && millis() >= offTime)
   {
      isActive = false;
      digitalWrite(ledPin, LOW);
   }  
  }
}