I have a ball valve with 2 limit switchesas an input, a button to control it (open or close) through an esp32. The 2 outputs are routed too 2 mosfet, one for open one for close. There's an OLED screen connected to the esp
When the button is HIGH the valve opens and the limit switch for open turns HIGH for the duration until fully open or when button LOW the limit switch for close stays HIGH for the duration until fully close
The problem i have that i cannot figure out how to present the different valve states on the oled screen. presenting open or close on the screen is not a problem, but if for example the valve fails, i want it to represent that on the screen as is shown in the program.
Valve operation is working without a problem. (open or close)
Any help would be appreciated
#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // OLED display width, in pixels
#define SCREEN_HEIGHT 32 // OLED display height, in pixels
#define OLED_RESET -1
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
const int Switch = 17;
const int PinOpen = 18;
const int PinClose = 19;
const int LOPEN = 23;
const int LCLOSE = 26;
long unsigned previousMillis1 = 0;
long unsigned previousMillis = 0;
long unsigned interval = 8000;
boolean enabled;
boolean enabled1;
void setup() {
display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
display.display();
pinMode(Switch, INPUT);
pinMode(PinOpen, OUTPUT);
pinMode(PinClose, OUTPUT);
pinMode(LOPEN, INPUT);
pinMode(LCLOSE, INPUT);
display.clearDisplay();
}
void loop() {
int button = digitalRead(Switch);
int limitclose = digitalRead(LCLOSE);
int limitopen = digitalRead(LOPEN);
if (button == HIGH) {
digitalWrite(PinOpen, HIGH); //
digitalWrite(PinClose, LOW); //
} else {
digitalWrite(PinOpen, LOW); //
digitalWrite(PinClose, HIGH); //
}
if (limitclose == HIGH && button == LOW) {
enabled = true;
previousMillis = millis();
}
if (limitclose == HIGH && button == LOW) {
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println("closing");
display.display();
} else if (limitclose == LOW && button == LOW) {
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println("close");
display.display();
} else if (enabled) {
if (millis() - previousMillis >= interval) {
previousMillis = millis();
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println("fail to close");
display.display();
}
}
if (limitopen == HIGH && button == HIGH && zsh == LOW) {
enabled1 = true;
previousMillis1 = millis();
}
if (limitopen == HIGH && button == HIGH) {
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println("opening");
display.display();
} else if (limitopen == LOW && button == HIGH) {
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println("open");
display.display();
} else if (enabled1) {
if (millis() - previousMillis1 >= interval) {
previousMillis1 = millis();
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println("fail to open");
display.display();
}
}
delay(100);
}
you need to monitor the state of both limit switches and the button, then update the display accordingly. Here's how you can modify your existing code to achieve this:
Define variables to track the state of the valve (open, closed, opening, closing, fail to open, fail to close).
Update these variables based on the readings from the limit switches and the button.
Display the current state on the OLED screen.
Here's the modified part of your loop() function:
void loop() {
int buttonState = digitalRead(Switch);
int limitCloseState = digitalRead(LCLOSE);
int limitOpenState = digitalRead(LOPEN);
// Handle opening process
if (buttonState == HIGH && limitOpenState == LOW) {
digitalWrite(PinOpen, HIGH);
digitalWrite(PinClose, LOW);
displayStatus("Opening...");
} else if (buttonState == HIGH && limitOpenState == HIGH) {
displayStatus("Open");
} else if (buttonState == HIGH && limitOpenState == HIGH && (millis() - previousMillis1) >= interval) {
displayStatus("Fail to Open");
}
// Handle closing process
if (buttonState == LOW && limitCloseState == LOW) {
digitalWrite(PinOpen, LOW);
digitalWrite(PinClose, HIGH);
displayStatus("Closing...");
} else if (buttonState == LOW && limitCloseState == HIGH) {
displayStatus("Closed");
} else if (buttonState == LOW && limitCloseState == HIGH && (millis() - previousMillis) >= interval) {
displayStatus("Fail to Close");
}
delay(100);
}
// Function to display status on OLED
void displayStatus(String status) {
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(WHITE);
display.setCursor(0, 14);
display.println(status);
display.display();
}
In this modification, I've added a new function displayStatus to encapsulate the logic for displaying the status text on the OLED screen. This function takes a string as input and displays it on the screen. This makes the code cleaner and easier to maintain.
Remember to declare previousMillis1 and interval variables at the beginning of your script, similar to how you've declared previousMillis.
This code should now properly reflect the state of the valve on the OLED screen, including any failure conditions.
Command the valve to open and start a 12 Second timer.
Display "valve opening",
Stop motor when valve open limit switch activates, display"valve open".
If timer expires before valve open limit switch activates, stop motor and display "valve fault".
Seems you use one logic on the "open" limit and the opposite logic on the "close" limit.
Is this correct or is it a drawing stuff up????
i.e. if the valve is open or closed (only 2 possibilities) then if the same logic were applied, one or the other limit would be shown as closed in the (standard) power down schematic.
I'm referring to your drawing .......... re-read my comment.
Appears drawing is wrong.
...and please learn how to present drawings ...left right ...top bottom.....power rail and ground locations. otherwise it's not a drawing, just a chook scratch.