Controlling relay with switches

i want to control a relay module using a switch button but my code seems to always have something wrong, everytime i upload it the relay gets activated automatically and arduino is not reading the switch.

there are 3 switches where eachs controls activates the relay in a different sequence that makes a buzzer buzz in that sequence

the switch also is a 3 pin switch fyi

const int SWITCH_1_PIN = 2;
const int SWITCH_2_PIN = 3;
const int SWITCH_3_PIN = 4;
const int RELAY_PIN = 5;

// Define states for each switch
enum SwitchState {
  OFF,
  SWITCH_1_ON,
  SWITCH_2_ON,
  SWITCH_3_ON
};

SwitchState switchState = OFF;
unsigned long relayStartTime = 0;

// Function declaration
void handleSwitch(int switchPin, SwitchState switchOnState, unsigned long onDuration, unsigned long offDuration, unsigned long onDuration2, unsigned long loopDuration);

void setup() {
  Serial.begin(9600); // Initialize serial communication
  Serial.println("Program starting...");

  pinMode(SWITCH_1_PIN, INPUT_PULLUP);
  pinMode(SWITCH_2_PIN, INPUT_PULLUP);
  pinMode(SWITCH_3_PIN, INPUT_PULLUP);
  pinMode(RELAY_PIN, OUTPUT);
  digitalWrite(RELAY_PIN, HIGH); // Initially turn off the relay
}

void loop() {
  handleSwitch(SWITCH_1_PIN, SWITCH_1_ON, 5000, 115000, 0, 120000);
  handleSwitch(SWITCH_2_PIN, SWITCH_2_ON, 5000, 1000, 1000, 114000);
  handleSwitch(SWITCH_3_PIN, SWITCH_3_ON, 1000, 4000, 5000, 109000);
}

void handleSwitch(int switchPin, SwitchState switchOnState, unsigned long onDuration, unsigned long offDuration, unsigned long onDuration2, unsigned long loopDuration) {
  if (digitalRead(switchPin) == LOW) {
    if (switchState == OFF) {
      // Switch is turned ON
      switchState = switchOnState;
      relayStartTime = millis();
      digitalWrite(RELAY_PIN, LOW); // Activate the relay
    }
  } else {
    // Switch is turned OFF
    if (switchState != OFF) {
      digitalWrite(RELAY_PIN, HIGH); // Deactivate the relay
      switchState = OFF;
    }
  }

  // Check if it's time to loop (considering off time)
  if (millis() - relayStartTime >= loopDuration) {
    relayStartTime = millis();
    digitalWrite(RELAY_PIN, LOW); // Activate the relay
    switchState = switchOnState;
  }
}

hi @miguelvc welcome to the forum.

I'm looking through the tiny window, and I only see one

SwitchState switchState = OFF;

a global variable that seems to be shared amongst all the switches. I think this might be the source of some trouble.

Also, you pass alotta arguments. That can work, but it might make sense for you to look into handling all the information for each switch/relay using a struct variable that can package up all the info that might like to travel around together, it would make things a bit easier, like now when you might need to add another for switchState.

Maybe you went too far down one road when a detour would have given you better tools to tackle this.

At a glance, it does look like you have something plausible beginning to take shape.

I look later when I am in the lab.

a7

1 Like

I will take a SWAG and by looking at the schematic you did NOT post A high turns on the relay. Change your setup to "digitalWrite(RELAY_PIN_LOW);

1 Like

i wrote like that because the relay module is low when activated and high when deactivated

You are not debouncing your switches. Since all loop() is doing is checking the switches, they can bounce a bit and your code will toggle things on/off until the switch settles down. Not good for relays.

@miguelvc debouncing will be important. For now, you can use a cheap trick and just put a brief delay in your loop() function. This will mean the switches are looked at only periodically, much slower than any bouncing, effectively removing that as an issue for the nonce.

I also focused on one switch, and sped things up a bit, viz:

void loop() {

  handleSwitch(SWITCH_1_PIN, SWITCH_1_ON, 1000, 7000, 0, 12000);  // life too short

//  handleSwitch(SWITCH_1_PIN, SWITCH_1_ON, 5000, 115000, 0, 120000);
//  handleSwitch(SWITCH_2_PIN, SWITCH_2_ON, 5000, 1000, 1000, 114000);
//  handleSwitch(SWITCH_3_PIN, SWITCH_3_ON, 1000, 4000, 5000, 109000);

  delay(50);    // poor man's debounce
}

I added Serial.print statements all over to see the values of the variables and to be able to observe the flow through your code. TBH I can't make heads or tails of it.

Do you have an earlier version of this code where you were able to control one relay with one pushbutton, either with or without using a function that you want to get working for any switch you call it with?

Also, you only have one relay, so I assume you intend to close only one switch at a time. If that is the case, one switchState will suffice.

I'm a bit confused because of all the occurences of "switch", "state" and "duration". If you would be so kind as to describe how all those variables are supposed to work to make a sequence (using only one button) perhaps your code would make sense and we could see what is wrong.

Just say what is supposed to happen when just one switch is closed and how the numbers make that switch's pattern.

a7

You have 3 switches, each switch has a pin connected to an input pin, where is the other pin(s) connected?

You have 3 switches and each switch has 3 pins. Is that correct?
Post a diagram showing how the switches are connected.

i want to have 3 switch buttons where each of them activates a relay for a period of time, because theres a buzzer connected to the relay.

switch 1 activates the relay for 5 seconds repeating every two minutes while the switch is on

switch 2 activates the relay for 5 seconds the deactivates and activates for 1 second then deactivates then activates again for 1 second repeating every 2 minutes while the switch is on

switch 3 activates the relay for 1 second then deactivates then activates for 5 seconds then deactivates the activates for 1 second repeating every 2 minutes while the switch is on

Please read your own description. It is full of typos and even making assumptions is somewhat ambiguous.

But lemme see if I get it:

As long as a switch is closed

Switch 1: 5 seconds on, 115 seconds off

Switch 2: 5 seconds on, 1 second off, 1 second on, 1 second off, 1 second on, 121 seconds off

Switch 3: 1 second on, 5 seconds off, 5 seconds on, 1 second off, 118 seconds off

Perhaps a timing diagram with time on the X axis and relay activation on the Y axis, one line for each of the three switches, would clarify.

I have a headache.

a7

1 Like

1 Like

i apologize for the typos.

But yes, you are correct, that’s what each switch is supposed to do

Hello miguelvc

What´s the task of this sketch in real life?

it’s a buzzer for a sailboat, and each of those 3 sounds represents a different state, like Making way under power, Under sail and anchored

Well reading your description and then reading mine I don't think it's been nailed down.

Are you planning to do all of any kind of standard boats noises, like I found here? It details a few, but perhaps there are just a handful.

https://www.boat-ed.com/indiana/studyGuide/Sound-Signals-Used-to-Alert-or-Warn/10101602_35232/

Maybe if you hunted down someone's description it would make sense. Or use language similar to what I linked, presumably long is five seconds and short is one second and there's either one or five seconds between blasts.

It would also be beneficial to have your entire plan made before trying to fix the code you have.

@paulpaulson"s virtual aspirin hasn't taken effect yet. :expressionless:

Or draw it like I suggested. Confirm or fix, and add any other signal patterns you want to do:

a7

i plan to make only those 3 signals.

yes your drawing is correct apart from signal 3 where the seconds signal (the long one) is also one second after the first short signal

Please draw it out like I did.

Although I am almost sure, words just aren't working for me. You've said a previous word description was correct, obvsly it was not.

It's never too early to start using timing diagrams, even for a simple case this. Imagine if you had just posted one with your #1 above!

TIA

a7

Did the best i could

Is this definition in accordance with COLREG Rule 34 Manoeuvring and warning signals?

1 Like

yes