Using timer with long and BWOD to the same output

Need help withe this code, please.
Be aware, that I'm an hobbyist and only use Arduino occasionally for small projects.
I'm usinig Arduino Nano for this project.
The purpose is to control a blower and a valve together so that the blower runs for lets say 45 sec.
I'm using relays for blower/valve and they are activated by a PID sensor.
When the blower runs, I want the valve to run in pulses.
I use the long (Timer) controlled by a potentiometer and BlinkWithOutDelay (BWOD) for pulsing/intervalls.
I had it up running with only one set of blower/valve, but when I add one set more, I'm running into problems.
Problem:

  1. Setting the timer with the potentiometer, the values sometimes affect each other.
  2. The relayPin4 (it's actually a LED in this test setup) blinks all the time when the program isn't running and it seems, that it blinks with the frequency of the two 200ms delays in the TIMER 1 & 2 section.

Because my lack of programming skills, I hope would be so kind to help me, and I hope I have explained it so it is understandable. :woozy_face:
Thanks in advance!

#define potPin4 A3      // Time 1 
#define potPin5 A4      // Time 2 

#define pirPin1 2       // PIR 1 sensor 
#define pirPin2 3       // PIR 2 sensor 

//#define relayPin1 9    // Blower 1 (Relay for AC 220V)
//#define relayPin2 10    // Blower 2 (Relay for AC 220V)
//#define relayPin3 11    // Valve 1 (Relay for DC 12V)
//#define relayPin4 12    // Valve 2 (Relay for DC 12V)
const int relayPin1 = 9;    // Blower 1 (Relay for AC 220V)
const int relayPin2 = 10;    // Blower 2 (Relay for AC 220V)
const int relayPin3 = 11;    // Valve 1 (Relay for DC 12V)
const int relayPin4 = 12;    // Valve 2 (Relay for DC 12V)
//#define ledPin 13       // Test LED Onboard

int pirState1 = LOW;
int pirState2 = LOW;

int relayValue1 = 0;
int relayValue2 = 0;
int relayValue3 = 0;
int relayValue4 = 0;

int relayState1 = 0;
int relayState2 = 0;
int relayState3 = 0;
int relayState4 = 0;
int val = 0;

#define pirType1 'L' // PIR trigger type. L for low and H for high
#define pirType2 'L' // PIR trigger type. L for low and H for high

#define relayType1 'L' // Relay trigger type. L for low and H for high
#define relayType2 'L' // Relay trigger type. L for low and H for high
#define relayType3 'L' // Relay trigger type. L for low and H for high
#define relayType4 'L' // Relay trigger type. L for low and H for high

//--------- TIMER:
//because the time below is in millisecond, 1000ms=1 second, 1000x60=60000 is 1 minuets. 60x60x1000=3600000 is 1 hour
//const long maxTime = 30000;// maximum timer time in milliseconds. for one minute =60000, 1 hours =3600000
//const long minTime = 3000; // miniimum timer time in milliseconds
const long maxTime1 = 30000;// maximum timer time in milliseconds. for one minute =60000, 1 hours =3600000
const long minTime1 = 3000; // miniimum timer time in milliseconds
const long maxTime2 = 30000;// maximum timer time in milliseconds. for one minute =60000, 1 hours =3600000
const long minTime2 = 3000; // miniimum timer time in milliseconds


long duration1;
long duration2;
long duration3;
long duration4;
int potValue4;
int potValue5;
long rememTime1;
long rememTime2;
long rememTime3;
long rememTime4;

//--------- BWOD:

// Variables will change:
//int relayState1 = LOW;             // ledState used to set the LED
unsigned long previousMillis1 = 0;        // will store last time LED was updated
//int relayState2 = LOW;             // ledState used to set the LED
unsigned long previousMillis2 = 0;        // will store last time LED was updated
//int relayState3 = LOW;             // ledState used to set the LED
unsigned long previousMillis3 = 0;        // will store last time LED was updated
//int relayState4 = LOW;             // ledState used to set the LED
unsigned long previousMillis4 = 0;        // will store last time LED was updated

// for the pulse led....
// the follow variables is a long because the time, measured in miliseconds,
// will quickly become a bigger number than can be stored in an int.
unsigned long interval1;           // interval at which to blink (milliseconds)
unsigned long onTime1 = 100;
unsigned long offTime1 = 100;

unsigned long interval2;           // interval at which to blink (milliseconds)
unsigned long onTime2 = 250;
unsigned long offTime2 = 100;

unsigned long interval3;           // interval at which to blink (milliseconds)
unsigned long onTime3 = 100;
unsigned long offTime3 = 100;

unsigned long interval4;           // interval at which to blink (milliseconds)
unsigned long onTime4 = 100;
unsigned long offTime4 = 100;

void setup()
{
  Serial.begin(9600);// initialize serial monitor with 9600 baud

  pinMode(pirPin1, INPUT);     // PIR Input
  pinMode(pirPin2, INPUT);     // PIR Input
  pinMode(relayPin1, OUTPUT);  //Relay for BLOWER 1
  pinMode(relayPin2, OUTPUT);  //Relay for BLOWER 2
  pinMode(relayPin3, OUTPUT);  //Relay for VALVE 1
  pinMode(relayPin4, OUTPUT);  //Relay for VALVE 2


  if (pirType1 == 'L')
  {
    digitalWrite(relayPin1, LOW);// turn the OFF and keep it OFF
    //Serial.println("MOTOR 1 Timer");
    //Serial.println("Motor 1 Type: LOW Trigger");
  } else {
    digitalWrite(relayPin1, HIGH);// turn the relay OFF and keep it OFF
    //Serial.println("MOTOR 1 Timer");
    //Serial.println("Motor 1 Type: HIGH Trigger");
  }

  if (pirType2 == 'L')
  {
    digitalWrite(relayPin2, LOW);// turn the OFF and keep it OFF
    //  Serial.println("MOTOR 1 Timer");
    //  Serial.println("Motor 1 Type: LOW Trigger");
  } else {
    digitalWrite(relayPin2, HIGH);// turn the relay OFF and keep it OFF
    //  Serial.println("MOTOR 1 Timer");
    //  Serial.println("Motor 1 Type: HIGH Trigger");
  }

  if (relayType1 == 'L')
  {
    digitalWrite(relayPin1, LOW);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin1, HIGH);// turn the relay OFF and keep it OFF
  }

  if (relayType2 == 'L')
  {
    digitalWrite(relayPin2, LOW);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin2, HIGH);// turn the relay OFF and keep it OFF
  }

  if (relayType3 == 'L')
  {
    digitalWrite(relayPin3, HIGH);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin3, LOW);// turn the relay OFF and keep it OFF
  }

  if (relayType4 == 'L')
  {
    digitalWrite(relayPin4, LOW);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin4, HIGH);// turn the relay OFF and keep it OFF
  }

}


void loop() {
  {
    // here is where you'd put code that needs to be running all the time.
    pulseRelay1(); //bwod
    pulseRelay2(); //bwod


    //######## TIMER 1 Blower 1 and Valve 1 #########
    potValue4 = analogRead(potPin4) / 2;  // reads the value of the potentiometer (value between 0 and 1023)
    duration1 = map(potValue4, 0, 102, minTime1, maxTime1);// convert A0 value to time set at minTime and maxTime
    if (digitalRead(pirPin1) == HIGH)
    {
      rememTime1 = millis();
      relayState1 = 1;
      controlRelay1();// send command to turn the relay ON
    }
    if (  (millis() - rememTime1) > duration1 )
    {
      relayState1 = 0;
      controlRelay1();
    }
    Serial.print("Time Relay 1 : ");
    Serial.print(duration1 / 1000);
    Serial.println(" Seconds");
    delay(200); // wait for 200 milliseconds
  }

  //######## TIMER 2 Blower 2 and Valve 2 #########
  potValue5 = analogRead(potPin5) / 2;  // reads the value of the potentiometer (value between 0 and 1023)
  duration2 = map(potValue5, 0, 102, minTime2, maxTime2);// convert A0 value to time set at minTime and maxTime
  if (digitalRead(pirPin2) == HIGH)
  {
    rememTime2 = millis();
    relayState2 = 1;
    controlRelay2();// send command to turn the relay ON
  }
  if (  (millis() - rememTime2) > duration2 )
  {
    relayState2 = 0;
    controlRelay2();
  }
  Serial.print("Time Relay 2 : ");
  Serial.print(duration2 / 1000);
  Serial.println(" Seconds");
  delay(200); // wait for 200 milliseconds
}


//######## CONTROL Blower 1 and Valve 1 #########
void controlRelay1() {
  if (pirType1 == 'L')
  {
    if (relayState1 == 1)
    {
      digitalWrite(relayPin1, LOW); // turn OFF RELAY Blower 1
      digitalWrite(relayPin3, HIGH); // turn OFF RELAY Valve 1
      //Serial.println("Relay and valve 1 is ON");

    } else {
      digitalWrite(relayPin1, HIGH);// Turn ON RELAY Blower 1
      digitalWrite(relayPin3, LOW);// Turn ON RELAY Valve 1
      //Serial.println("====RELAY 1 and valve 1 is OFF");
    }

  }
}

//######## CONTROL Blower 2 and Valve 2 #########
void controlRelay2() {
  if (pirType2 == 'L')
  {
    if (relayState2 == 1)
    {
      digitalWrite(relayPin2, LOW); // turn OFF RELAY Blower 1
      digitalWrite(relayPin4, HIGH); // turn OFF RELAY Valve 1
      //Serial.println("Relay and valve 1 is ON");

    } else {
      digitalWrite(relayPin2, HIGH);// Turn ON RELAY Blower 1
      digitalWrite(relayPin4, LOW);// Turn ON RELAY Valve 1
      //Serial.println("====RELAY 1 and valve 1 is OFF");
    }

  }
}


void pulseRelay1()
{
  // check to see if it's time to blink the LED; that is, if the
  // difference between the current time and last time you blinked
  // the LED is bigger than the interval at which you want to
  // blink the LED.
  //Serial.println("in pulseLED");
  unsigned long currentMillis = millis();

  if (currentMillis - previousMillis1 > interval1) {
    // save the last time you blinked the LED
    previousMillis1 = currentMillis;

    // if the LED is off turn it on and vice-versa:
    if (relayState1 == HIGH)
    {
      relayState1 = LOW;
      // set the interval to how long it must stay on
      interval1 = onTime1;
    }
    else
    {
      relayState1 = HIGH;
      // set the interval to how long it must stay off
      interval1 = offTime1;
    }

    // set the LED with the ledState of the variable:
    digitalWrite(relayPin3, relayState1);
  }
}

void pulseRelay2()
{
  // check to see if it's time to blink the LED; that is, if the
  // difference between the current time and last time you blinked
  // the LED is bigger than the interval at which you want to
  // blink the LED.
  //Serial.println("in pulseLED");
  unsigned long currentMillis = millis();

  if (currentMillis - previousMillis2 > interval2) {
    // save the last time you blinked the LED
    previousMillis2 = currentMillis;

    // if the LED is off turn it on and vice-versa:
    if (relayState2 == HIGH)
    {
      relayState2 = LOW;
      // set the interval to how long it must stay on
      interval2 = onTime2;
    }
    else
    {
      relayState2 = HIGH;
      // set the interval to how long it must stay off
      interval2 = offTime2;
    }

    // set the LED with the ledState of the variable:
    digitalWrite(relayPin4, relayState2);
  }
}

Hello
I´ve read you sketch and tried to understand your approach.
As pseudo code I understood:

if(pir) (blower on and valve pulse) else (blower of and valve off)

Put all relevant information into a struct{} once. This data struct is used in:
Add first design simple functions to control the blower and valve, e.g. void blower(bool state) and valve(bool state). A timer, based on BWOD, will controll all periodic activities.

Thank you for the reply!

So, If I understand you correctly, you say that BWOD isn't the right way to go for this and I should use bool instead?

BWOD is the right way. The timer will generate a BOOL for a time-triggered event

Argh, sorry, I'm realy feeling stupid in programming language

My first approach was to make the time with a potmeter for one relay.
Then I did the BWOD for the secound relay and combined those two.
That seemed to work as I expected.

#define potPin4 A3      // Time 1 
#define potPin5 A4      // Time 2 

#define pirPin1 2       // PIR 1 sensor 
#define pirPin2 3       // PIR 2 sensor 

#define relayPin1 9    // Blower 1 (Relay for AC 220V)
#define relayPin2 10    // Blower 2 (Relay for AC 220V)
#define relayPin3 11    // Valve 1 (Relay for DC 12V)
#define relayPin4 12    // Valve 2 (Relay for DC 12V)
//#define ledPin 13       // Test LED Onboard

int pirState1 = LOW;
int pirState2 = LOW;

int relayValue1 = 0;
int relayValue2 = 0;
int relayValue3 = 0;
int relayValue4 = 0;

int relayState1 = 0;
int relayState2 = 0;
int relayState3 = 0;
int relayState4 = 0;
int val = 0;

#define pirType1 'L' // PIR trigger type. L for low and H for high
#define pirType2 'L' // PIR trigger type. L for low and H for high

#define relayType1 'L' // Relay trigger type. L for low and H for high
#define relayType2 'L' // Relay trigger type. L for low and H for high
#define relayType3 'L' // Relay trigger type. L for low and H for high
#define relayType4 'L' // Relay trigger type. L for low and H for high

//--------- TIMER:
//because the time below is in millisecond, 1000ms=1 second, 1000x60=60000 is 1 minuets. 60x60x1000=3600000 is 1 hour
const long maxTime = 30000;// maximum timer time in milliseconds. for one minute =60000, 1 hours =3600000
const long minTime = 3000; // miniimum timer time in milliseconds

long duration1;
long duration2;
long duration3;
long duration4;
int potValue4;
int potValue5;
long rememTime1;
long rememTime2;
long rememTime3;
long rememTime4;

//--------- BWOD:

// Variables will change:
//int relayState1 = LOW;             // ledState used to set the LED
unsigned long previousMillis1 = 0;        // will store last time LED was updated
//int relayState2 = LOW;             // ledState used to set the LED
unsigned long previousMillis2 = 0;        // will store last time LED was updated
//int relayState3 = LOW;             // ledState used to set the LED
unsigned long previousMillis3 = 0;        // will store last time LED was updated
//int relayState4 = LOW;             // ledState used to set the LED
unsigned long previousMillis4 = 0;        // will store last time LED was updated

// for the pulse led....
// the follow variables is a long because the time, measured in miliseconds,
// will quickly become a bigger number than can be stored in an int.
unsigned long interval1;           // interval at which to blink (milliseconds)
unsigned long onTime1 = 100;
unsigned long offTime1 = 100;

unsigned long interval2;           // interval at which to blink (milliseconds)
unsigned long onTime2 = 100;
unsigned long offTime2 = 100;

unsigned long interval3;           // interval at which to blink (milliseconds)
unsigned long onTime3 = 100;
unsigned long offTime3 = 100;

unsigned long interval4;           // interval at which to blink (milliseconds)
unsigned long onTime4 = 100;
unsigned long offTime4 = 100;

void setup()
{
  Serial.begin(9600);// initialize serial monitor with 9600 baud

  pinMode(pirPin1, INPUT);     // PIR Input
  pinMode(pirPin2, INPUT);     // PIR Input
  pinMode(relayPin1, OUTPUT);  //Relay for BLOWER 1
  pinMode(relayPin2, OUTPUT);  //Relay for VALVE 1
  pinMode(relayPin3, OUTPUT);  //Relay for BLOWER 2
  pinMode(relayPin4, OUTPUT);  //Relay for VALVE 2


  if (pirType1 == 'L')
  {
    digitalWrite(relayPin1, LOW);// turn the OFF and keep it OFF
    //Serial.println("MOTOR 1 Timer");
    //Serial.println("Motor 1 Type: LOW Trigger");
  } else {
    digitalWrite(relayPin1, HIGH);// turn the relay OFF and keep it OFF
    //Serial.println("MOTOR 1 Timer");
    //Serial.println("Motor 1 Type: HIGH Trigger");
  }

  if (pirType2 == 'L')
  {
    digitalWrite(relayPin2, LOW);// turn the OFF and keep it OFF
    //  Serial.println("MOTOR 1 Timer");
    //  Serial.println("Motor 1 Type: LOW Trigger");
  } else {
    digitalWrite(relayPin2, HIGH);// turn the relay OFF and keep it OFF
    //  Serial.println("MOTOR 1 Timer");
    //  Serial.println("Motor 1 Type: HIGH Trigger");
  }

  if (relayType1 == 'L')
  {
    digitalWrite(relayPin1, LOW);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin1, HIGH);// turn the relay OFF and keep it OFF
  }

  if (relayType2 == 'L')
  {
    digitalWrite(relayPin2, LOW);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin2, HIGH);// turn the relay OFF and keep it OFF
  }

  if (relayType3 == 'L')
  {
    digitalWrite(relayPin3, HIGH);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin3, LOW);// turn the relay OFF and keep it OFF
  }

  if (relayType4 == 'L')
  {
    digitalWrite(relayPin4, LOW);// turn the relay OFF and keep it OFF
  } else {
    digitalWrite(relayPin4, HIGH);// turn the relay OFF and keep it OFF
  }

}


void loop()
{
  // here is where you'd put code that needs to be running all the time.
  pulseRelay1(); //bwod
 // pulseRelay2(); //bwod


  //######## TIMER 1 Blower 1 and Valve 1 #########
  potValue4 = analogRead(potPin4) / 2;  // reads the value of the potentiometer (value between 0 and 1023)
  duration1 = map(potValue4, 0, 102, minTime, maxTime);// convert A0 value to time set at minTime and maxTime
  if (digitalRead(pirPin1) == HIGH)
  {
    rememTime1 = millis();
    relayState1 = 1;
    controlRelay1();// send command to turn the relay ON
  }
  if (  (millis() - rememTime1) > duration1 )
  {
    relayState1 = 0;
    controlRelay1();
  }
  Serial.print("Time Relay 1 : ");
  Serial.print(duration1 / 1000);
  Serial.println(" Seconds");
  delay(200); // wait for 200 milliseconds
}


//######## CONTROL Blower 1 and Valve 1 #########
void controlRelay1() {
  if (pirType1 == 'L')
  {
    if (relayState1 == 1)
    {
      digitalWrite(relayPin1, LOW); // turn OFF RELAY Blower 1
      digitalWrite(relayPin3, HIGH); // turn OFF RELAY Valve 1
      //Serial.println("Relay and valve 1 is ON");

    } else {
      digitalWrite(relayPin1, HIGH);// Turn ON RELAY Blower 1
      digitalWrite(relayPin3, LOW);// Turn ON RELAY Valve 1
      //Serial.println("====RELAY 1 and valve 1 is OFF");
    }

  }
}

void pulseRelay1()
{
  // check to see if it's time to blink the LED; that is, if the
  // difference between the current time and last time you blinked
  // the LED is bigger than the interval at which you want to
  // blink the LED.
  //Serial.println("in pulseLED");
  unsigned long currentMillis = millis();

  if (currentMillis - previousMillis1 > interval1) {
    // save the last time you blinked the LED
    previousMillis1 = currentMillis;

    // if the LED is off turn it on and vice-versa:
    if (relayState1 == HIGH)
    {
      relayState1 = LOW;
      // set the interval to how long it must stay on
      interval1 = onTime1;
    }
    else
    {
      relayState1 = HIGH;
      // set the interval to how long it must stay off
      interval1 = offTime1;
    }

    // set the LED with the ledState of the variable:
    digitalWrite(relayPin3, relayState1);
  }
}

Then I tried to add the code for two more relays. That is were I'm getting lost and I think I must have overlooked or missing something.

If you can see what I'm doing wrong, can you please give a hint?
Maybe like an code example from my sketch.
I will really appreciate that an again sorre for my lack of skills

I'm closing this thread - Btw, no solution

Cheers folks

If you say so. :roll_eyes:

Generally the most sensible choice. :+1: