How to solve the problem of ON-OFF switches ?

Hi, I write a code to control the water level sensor. There are 3 stages of the sequences:

  • Stage 1: When switch1 is ON, the sensor will detect the level. (when it is minimum, the valveInlet will ON)(when it is maximum, the ValveInlet will OFF) stage1 include LED red, buzzer.
  • Stage 2: When switch2 is ON, components from stages1 will OFF. Then, the ValveDrain will ON within a minute. LED yellow will ON.
  • Stage 3: both switch1 &2 is OFF, LCD print "Detecting Water level.."

Here problem is when I test on the physical components, the sensor detection is slow. And, when S2 ispressed, the stage2 not operated.
Here I attached my code and my simple circuit schematic. How to improve it?

//projectEI fye
#include <LiquidCrystal.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>


// Set the LCD address to 0x27 for a 16 chars and 2 line display
LiquidCrystal_I2C lcd(0x27, 16, 2);

//defining cup Anemometer
// First Frame
byte wind1[] = {
  B00000,
  B00000,
  B00000,
  B00011,
  B00111,
  B00111,
  B00111,
  B00011
};

byte wind2[] = {
  B11111,
  B11111,
  B01110,
  B00000,
  B00000,
  B00000,
  B00000,
  B00000
};

byte wind3[] = {
  B00000,
  B00000,
  B00000,
  B00000,
  B00000,
  B01110,
  B11111,
  B11111
};

byte wind4[] = {
  B11000,
  B11100,
  B11100,
  B11100,
  B11000,
  B00000,
  B00000,
  B00000,
};


// Second Frame
byte wind5[] = {
  B00000,
  B00000,
  B00000,
  B00000,
  B01000,
  B11100,
  B11110,
  B01111
};

byte wind6[] = {
  B00001,
  B00011,
  B00111,
  B01110,
  B00000,
  B00000,
  B00000,
  B00000
};

byte wind7[] = {
  B00000,
  B00000,
  B00000,
  B00000,
  B00010,
  B00111,
  B01111,
  B11110
};

byte wind8[] = {
  B11110,
  B01111,
  B00111,
  B00010,
  B00000,
  B00000,
  B00000,
  B00000
};


const int waterlevelsensor = A0;  //A0 as water level sensor
int sensorValue = 0; //a variable for the sensor
int ledGreen = 3;   //set LED green to D3
int buzzer = 4;     //set buzzer and LED red to D4
const int ValveInlet = 8; //set solenoid valve1 (inlet) to pin8
const int ValveDrain = 9; //set solenoid valve1 (drain) to pin9
int switch1 = 1;    //set Rockerswitch (1) to D1
int switch2 = 2;    //set Rockerswitch (2) to D2
int switch1State = 0;
int switch2State = 0;

void setup() {
  // declare pin  to be an input:
  pinMode(switch1,INPUT);
  pinMode(waterlevelsensor,INPUT);
  //digitalWrite(switch1,LOW);   
 
  pinMode(ledGreen,OUTPUT);  
  pinMode(buzzer,OUTPUT);    //set Buzzer and LED Red to D4 as output
  pinMode(ValveInlet, OUTPUT); //set Solenoid valve as output pin
  Serial.begin(9600);
  
    // initialize the LCD
    lcd.begin();
    lcd.noBlink();
    lcd.setCursor(1,0);
    lcd.print("POLITEKNIK PSA");
    delay(2500);
    lcd.setCursor(3,1);
    lcd.print("Shah Alam ");
    delay(3000);
    lcd.clear();
    
    lcd.noBacklight(); // turn off backlight
    lcd.backlight();  // Turn on the blacklight and print a message.
    lcd.clear();

    lcd.setCursor(2,0);
    lcd.print("Water Level");
    delay(1500);
    lcd.setCursor(0,1);
    lcd.print("Detecting System");
    delay(2000);
    lcd.clear();
    lcd.setCursor(0,0);  
    lcd.print("for PlasmaThawer");
    delay(2000);
    lcd.clear();
    lcd.setCursor(0,0);  
    lcd.print("Helmer QuickThaw");
    delay(1000);
    lcd.setCursor(5,1);
    lcd.print("(DH4)");
    delay(3000);
    lcd.clear();

}

// the loop routine runs over and over again forever:
void updatelcd() {

//if the RockerSwitch is 0, no mode (standby mode) is selected:
    digitalWrite(3,LOW);
    digitalWrite(4,LOW);
    lcd.clear();
    //------------------
      //creating all the characters
    lcd.createChar(1 , wind1); //Numbering should start at 1, not 0
    lcd.createChar(2 , wind2);
    lcd.createChar(3 , wind3);
    lcd.createChar(4 , wind4);
    lcd.createChar(5 , wind5);
    lcd.createChar(6 , wind6);
    lcd.createChar(7 , wind7);
    lcd.createChar(8 , wind8);
    delay(1000);
  
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.write(1);
    lcd.setCursor(0,1);
    lcd.write(2);
    lcd.setCursor(1,0);
    lcd.write(3);
    lcd.setCursor(1,1);
    lcd.write(4);
    lcd.setCursor(3,0);
    lcd.print("Detecting");
    lcd.setCursor(3,1);
    lcd.print("water level");
    delay(500);
    lcd.clear();
    
    lcd.setCursor(0,0);
    lcd.write(5);
    lcd.setCursor(0,1);
    lcd.write(6);
    lcd.setCursor(1,0);
    lcd.write(7);
    lcd.setCursor(1,1);
    lcd.write(8);
    lcd.setCursor(3,0);
    lcd.print("Detecting");
    lcd.setCursor(3,3);
    lcd.print("Water level..");
    delay(500);
    lcd.clear(); 
}

void loop(){
 int switch1State_ON=digitalRead(switch1==HIGH);
 int switch1State_OFF=digitalRead(switch1==LOW);

 updatelcd(); ///here
//if the switch1 is presssed, Mode 1 for detecting and refilling the water:
  while (digitalRead(switch1State_ON)) 
  {
  int sensorValue = analogRead(waterlevelsensor);
  sensorValue = analogRead(waterlevelsensor);
  Serial.print("sensor = ");
  Serial.print(sensorValue);
  Serial.print("\n");
  delay(10);
  lcd.clear();
  
{ if (10<=sensorValue<=100) //Minimum Level 
  lcd.setCursor(4,0);
  lcd.print("Mode 1");
  delay(500);
  {
  int i=0;

   lcd.backlight();
   lcd.setCursor(1,0);
   lcd.print(" Water level:");
   delay(500);
   lcd.setCursor(2,1);
   lcd.print("Minimum...");
      digitalWrite(ValveInlet,HIGH);
      delay(15000); 
      digitalWrite(ValveInlet, LOW);
      delay(500);
  do{
   i++;
    tone(buzzer, 450);
    delay(200);
    noTone(buzzer);
    delay(100);
    
    }
    while(i<2);
    delay(200);
    lcd.clear();
} 
   
    if(101<=sensorValue<=720) //Maximum level
  {
    int i=0;
    lcd.setCursor(1,0);
    lcd.print(" Water level:");
    delay(500);
    lcd.setCursor(2,1);
    lcd.print("Maximum...");

    digitalWrite(ValveInlet, LOW);
    digitalWrite(4,LOW);
    digitalWrite(3,HIGH);
    delay(1000);
    digitalWrite(3,LOW);
    delay(100);
    digitalWrite(3,HIGH);
    delay(100);
    digitalWrite(3,LOW);
    delay(50);
    lcd.clear();
    }
  }

//if the switch2 is presssed, Mode 2 for draining the water:
  while(switch2State==HIGH)
  { lcd.setCursor(4,0);
    lcd.print("Mode 2");
    digitalWrite(ValveDrain, HIGH);   //the draining valve is open
    delay(3000);
    digitalWrite(ValveDrain, LOW);    //the draining valve is closed after 3secs
    lcd.setCursor(1,0);
    lcd.print(" Draining");
    delay(500);
    lcd.setCursor(3,1);
    lcd.print("water...");
    lcd.clear();
  }

//if both switches 1&2 are ON:
  while (digitalRead(switch1State==LOW)&&digitalRead(switch2State==LOW))
  {
    lcd.clear();
    lcd.print("Finished");
    digitalWrite(ledGreen,LOW);
    digitalWrite(buzzer,LOW);
    digitalWrite(ValveInlet, LOW);
    updatelcd();
  }
}}```
![EI Sketching 2_bb|510x500](upload://sotHOxlcdK8ZvbhgSgJ8CdlFik2.png)
![Screenshot (2603)|690x388](upload://drVaJbQG3GwYxPOp4TyV6YfL0cL.png)

Can't see any schematics yet.

Build a state machine.

Remove the delays or reduce them to close to nothing.

Hello foong_yee

I have checked the code a little.

This sketch seems to have grown organically through nested and dupilcate function calls. This leads to spaghetti code and nodes in the logic that are functionally undesirable.

What to do.
There are two options.
Debug, using multiple Serial.println()'s to see what happens under different conditions. Nodes can be solved this way, but new ones can also be created in the process.
The second option is to rearrange the sketch. Based on the IPO model, structure the desired function of the sketch into basic functions. Take a sheet of paper and a pencil and draw a programme structure to identify the required functions, e.g. button, timer and display functions. All these functions can be coded and tested separately. To complete the project, you also need to design a control structure that uses events to call the above functions. In this way keep in mind to design objects and related services thus handle input/output actions.
That is all that needs to be done. Try them out.

Have a nice day and enjoy coding in C++.

Hi, Thank you for replying.
I've tried to understand what you mentioned, but I actually a beginner to use Arduino. Do you mean add another Serial.printIn() at the maximum detection there ?
May you help me to modify the sketch?

Thank you very muchπŸ‘πŸ», I already changed these parts:

if((sensorValue>=10)&&(sensorValue<=100))

else if((sensorValue>=101)&&(sensorValue<=720))

Hi, @foong_yee
Thanks for the Fritzy, but a proper schematic would be better.

Can we please have a circuit diagram?
An image of a hand drawn schematic will be fine, include ALL power supplies, component names and pin labels.

Thanks.. Tom.. :smiley: :+1: :coffee: :australia:

Breadboard layout from post#9.
The two solenoid circuits don't have a ground connection to the Arduino.
Leo..

already added in the Fritzing. Thank you so much :+1:t2:

Hi,
Can you please post images of your project?
So we can see your component layout and protoboard configuration.

Thanks... Tom.. :smiley: :+1: :coffee: :australia:

all the single components I tested it, well functioning.
When I run my sketch to this circuit, the problems occurred as I mentioned above.

Hi,
Thanks for the image.

Are you switching pins 1 and 2.
Pin 1 is a programming pin so move and reprogram for another pin possibly pin 5.

You are switching the two inputs to gnd, you need to have pullup resistors to pull the input HIGH when your switch is OPEN.
You do not have a pinMode for switch2.

You can do this in software.

pinMode(switch1,INPUT_PULLUP);
pinMode(switch21,INPUT_PULLUP);

Thanks.. Tom.. :smiley: :+1: :coffee: :australia:

1 Like

I can't see through the spaghetty if the Arduino ground is connected to 12volt negative.

I do see that you haven't used any current limiting resistors on the LEDs.

Pin1 can't be used for a switch.
Pin0 and pin1 are already used by the USB<>Serial chip.

A buzzer in series with a LED, and connected to 12volt ground..?
Leo..

Hi TomGeorge, I will change the pins for that two switches to pin5 & pin6 as you & Wawa (post 16) mentioned pin1 can't be used for a switch.
What I understand from the link you sent is I want both switches in the default state is LOW, so it supports to use of an external pull-down resistor (Arduino Uno has no built-in pull-down resistor), am I right? :thinking:
OR can I just use "pinMode(switch5,INPUT_PULLUP);" and "if(switch1State==LOW)" read the switch state when its is LOW when I press it ?
OR an external pull-down resistor is more reliable for my project?

Hi Wawa, I already added a 220 ohm resistor for LED yellow.
Do I need one 220 ohm for pin4 connection? (pin 4 is LED red + buzzer)

I connect the 5V gnd to 12V gnd so it could share the same way. Does this make circuit wrong?

A buzzer in series with a LED, and connected to 12volt ground..?

No, it supports the use of a PULL UP resistor, so when the switch is OPEN the input is pulled HIGH.
When you close the switch to gnd, the input will go LOW.

Yes, leave your switch between input and gnd, use the pinMode to activate the internal PULLUPs.

Did you develop your code in stages and write code to test your switches before advancing further into your code?

Develop your code in stages, and get each stage working before going onto the next.
Then when all stages are working , add them together ONE at a time, each time getting the new code to work.

Tom.. :smiley: :+1: :coffee: :australia:

Did you develop your code in stages and write code to test your switches before advancing further into your code?

No, I never learnt STAGES before. How to make STAGE for my coding?

I would connect a LED+resistor to one pin, and the buzzer to another pin,
assuming the buzzer can be driven directly with a pin. Spread the load.
Remember that max pin current of an Uno should be kept below 20mA (40mA absolute max).

TomGeorge meant that you should build things in small steps.
Test each stage of the build, before moving to the next feature you add.
Leo..

1 Like

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.