// =====================================
// PIN DEFINITIONS
// =====================================
#define TRIG_PIN 5
#define ECHO_PIN 18
#define GREEN_LED 14
#define YELLOW_LED 27
#define RED_LED 26
// =====================================
// SCALED PHYSICAL MODEL (SMALL CONTAINER)
// =====================================
const float SENSOR_HEIGHT = 20.0; // cm (sensor above container bottom)
// Flood thresholds (cm)
const float SAFE_LEVEL = 8.0;
const float DANGER_LEVEL = 14.0;
// =====================================
// STATE VARIABLES (FOR MODELING)
// =====================================
float prevWaterLevel = 0.0;
unsigned long prevTime = 0;
// =====================================
// SETUP
// =====================================
void setup() {
Serial.begin(115200);
pinMode(TRIG_PIN, OUTPUT);
pinMode(ECHO_PIN, INPUT);
pinMode(GREEN_LED, OUTPUT);
pinMode(YELLOW_LED, OUTPUT);
pinMode(RED_LED, OUTPUT);
Serial.println("ESP32 Flood Prediction Simulation Started");
}
// =====================================
// ULTRASONIC DISTANCE FUNCTION
// =====================================
long getDistance() {
digitalWrite(TRIG_PIN, LOW);
delayMicroseconds(2);
digitalWrite(TRIG_PIN, HIGH);
delayMicroseconds(10);
digitalWrite(TRIG_PIN, LOW);
long duration = pulseIn(ECHO_PIN, HIGH, 30000); // 30 ms timeout
long distance = duration * 0.034 / 2;
return distance;
}
// =====================================
// MAIN LOOP
// =====================================
void loop() {
unsigned long currentTime = millis();
float deltaTime = (currentTime - prevTime) / 1000.0; // seconds
long distance = getDistance();
// Convert distance to water level
float waterLevel = SENSOR_HEIGHT - distance;
// Clamp to physical limits
if (waterLevel < 0) waterLevel = 0;
if (waterLevel > SENSOR_HEIGHT) waterLevel = SENSOR_HEIGHT;
// ===============================
// RATE OF RISE (cm/s)
// ===============================
float rate = 0.0;
if (deltaTime > 0) {
rate = (waterLevel - prevWaterLevel) / deltaTime;
}
// ===============================
// TIME-TO-DANGER PREDICTION
// ===============================
float timeToDanger = -1; // invalid by default
if (rate > 0 && waterLevel < DANGER_LEVEL) {
timeToDanger = (DANGER_LEVEL - waterLevel) / rate;
}
// ===============================
// SERIAL OUTPUT (SIMULATION VIEW)
// ===============================
Serial.print("Distance: ");
Serial.print(distance);
Serial.print(" cm | Water Level: ");
Serial.print(waterLevel);
Serial.print(" cm | Rate: ");
Serial.print(rate);
Serial.print(" cm/s | ");
if (timeToDanger > 0) {
Serial.print("Time to danger: ");
Serial.print(timeToDanger);
Serial.println(" s");
} else {
Serial.println("Time to danger: N/A");
}
// ===============================
// LED FLOOD STATUS LOGIC
// ===============================
if (waterLevel < SAFE_LEVEL) {
// SAFE
digitalWrite(GREEN_LED, HIGH);
digitalWrite(YELLOW_LED, LOW);
digitalWrite(RED_LED, LOW);
}
else if (waterLevel < DANGER_LEVEL) {
// WARNING
digitalWrite(GREEN_LED, LOW);
digitalWrite(YELLOW_LED, HIGH);
digitalWrite(RED_LED, LOW);
}
else {
// DANGER
digitalWrite(GREEN_LED, LOW);
digitalWrite(YELLOW_LED, LOW);
digitalWrite(RED_LED, HIGH);
}
// ===============================
// STORE PREVIOUS VALUES
// ===============================
prevWaterLevel = waterLevel;
prevTime = currentTime;
delay(1000); // 1 second update interval
}