Water leak sensor
-
Finally I made my water leak sensor that I have been dreaming about for a long time now
I used those items:
Enclosure
2 x AA batteris incl holder
nRF24L01+
Home made PCB with ATmega328P-PU
red, green LED
si7021, temp & hum
some capactitors and resistors
Kitchen aluminum foil
Copper wireI am measuring temperature and humidity with a Si7021, measuring battery voltage with voltage divider and internal reference, just to test which one that shows most correct.
/** * The MySensors Arduino library handles the wireless radio link and protocol * between your home built sensors/actuators and HA controller of choice. * The sensors forms a self healing radio network with optional repeaters. Each * repeater and gateway builds a routing tables in EEPROM which keeps track of the * network topology allowing messages to be routed to nodes. * * Created by Henrik Ekblad <henrik.ekblad@mysensors.org> * Copyright (C) 2013-2015 Sensnology AB * Full contributor list: https://github.com/mysensors/Arduino/graphs/contributors * * Documentation: http://www.mysensors.org * Support Forum: http://forum.mysensors.org * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * version 2 as published by the Free Software Foundation. * ******************************* * * REVISION HISTORY * Version 1.0 - Henrik EKblad * */ // Enable and select radio type attached #define MY_RADIO_NRF24 // Enable debug prints to serial monitor #define MY_DEBUG #define MY_NODE_ID 27 #include <SPI.h> #include <MySensors.h> #include <Wire.h> #include <SI7021.h> #define CHILD_SIHUM 0 #define CHILD_SITEMP 1 #define CHILD_BATT 2 #define CHILD_SIDEW 3 #define CHILD_BATTRES 4 #define CHILD_WATER 10 #define CHILD_FAILS 250 #define CHILD_PARENT 251 #define CHILD_DISTANCE 252 #define CHILD_SLEEPTIME 253 //LED int GREEN = 7; int RED = 8; //Water alarm int Interrupt = 1; // pin 3 on UNO/Nano //SleepTime float SleepTime = 30; // Sleep time between reads (in minutes) int OldSleepTime = -1; int SleepTimeLoopCount = 10; //ReadVCC long result; float BatteryVolt; float OldBatteryVolt; int BatteryVoltLoopCount = 5; //ReadVCCRes int sensorValue; float BatteryResVolt; int BATTERY_SENSE_PIN = A2; // select the input pin for the battery sense point //SI7021 SI7021 SI; int SILoopCount = 5; int SIHum; int OldSIHum = -1; float SITemp; float OldSITemp = -1; float SIDew; float OldSIDew = -1; //NRF int Fails = 0; int OldFails = -1; int FailsLoopCount = 10; int OldParentNode = -1; int ParentNodeLoopCount = 10; int OldDistanceNode = -1; int DistanceLoopCount = 10; MyMessage msgSIHum(CHILD_SIHUM, V_HUM); MyMessage msgSITemp(CHILD_SITEMP, V_TEMP); MyMessage msgSIDew(CHILD_SIDEW, V_TEMP); MyMessage msgBatt(CHILD_BATT, V_VOLTAGE); MyMessage msgBattRes(CHILD_BATTRES, V_VOLTAGE); MyMessage msgWater(CHILD_WATER, V_TRIPPED); MyMessage msgFails(CHILD_FAILS, V_VA); MyMessage msgParent(CHILD_PARENT, V_VA); MyMessage msgDistance(CHILD_DISTANCE, V_VA); MyMessage msgSleepTime(CHILD_SLEEPTIME, V_VA); void setup() { //Water Alarm pinMode(3, INPUT_PULLUP); attachInterrupt(Interrupt, Water, FALLING); //Battery measurement analogReference(INTERNAL); // use the 1.1 V internal reference sensorValue = analogRead(BATTERY_SENSE_PIN); // read once to activate the change of reference pinMode(GREEN, OUTPUT); pinMode(RED, OUTPUT); digitalWrite(GREEN, HIGH); digitalWrite(RED, HIGH); delay(200); digitalWrite(GREEN, LOW); digitalWrite(RED, LOW); SI.begin(); } void presentation() { // Send the sketch version information to the gateway and Controller sendSketchInfo("Temp/Humidity/WaterLeak", "20180226"); // Register all sensors to gateway (they will be created as child devices) present(CHILD_SIHUM, S_HUM, "SIHum"); present(CHILD_SITEMP, S_TEMP, "SITemp"); present(CHILD_SIDEW, S_TEMP, "SIDew"); present(CHILD_BATT, S_MULTIMETER, "Volt"); present(CHILD_BATTRES, S_MULTIMETER, "VoltRes"); present(CHILD_WATER, S_WATER_LEAK, "Water Alarm"); present(CHILD_FAILS, S_POWER, "Fails"); present(CHILD_PARENT, S_POWER, "Parent"); present(CHILD_DISTANCE, S_POWER, "Distance"); present(CHILD_SLEEPTIME, S_DIMMER, "SleepTime"); } void loop() { //Voltage readVcc(); sensorValue = analogRead(BATTERY_SENSE_PIN); BatteryResVolt = sensorValue * 0.003363075; //SI read both temperature and humidity si7021_env SIdata = SI.getHumidityAndTemperature(); //SI Humidity SIHum = SIdata.humidityPercent; //Serial.print("SIHum="); //Serial.println(SIHum); if(SIHum >99) { SIHum = 99; } if(SIHum < 1) { SIHum = 0; } //SI Temperature SITemp = SIdata.celsiusHundredths / 100.0; SITemp = round(SITemp*10)/10.0; //Serial.print("SITemp="); //Serial.println(SITemp,1); //SI Dew double a = 17.271; double b = 237.7; double dewtemp = (a * SITemp) / (b + SITemp) + log(SIHum*0.01); SIDew = (b * dewtemp) / (a - dewtemp); //Get SleepTime from controller request(CHILD_SLEEPTIME, V_PERCENTAGE); wait(1000); //Water Alarm int WaterLeak = digitalRead(3); if (WaterLeak == 0){ resend((msgWater.set(1)), 100); } else{ resend((msgWater.set(0)), 100); } //Send data to controller if ((OldBatteryVolt != BatteryVolt) | (BatteryVoltLoopCount >= 5)) { send(msgBatt.set(BatteryVolt, 3)); send(msgBattRes.set(BatteryResVolt, 3)); OldBatteryVolt = BatteryVolt; BatteryVoltLoopCount = 0; } if ((OldSIHum != SIHum) | (OldSITemp != SITemp) | (OldSIDew != SIDew) | (SILoopCount >= 5)) { resend((msgSIHum.set(SIHum)), 1); resend((msgSITemp.set(SITemp, 1)), 1); resend((msgSIDew.set(SIDew, 1)), 1); OldSIHum = SIHum; OldSITemp = SITemp; OldSIDew = SIDew; SILoopCount = 0; } if ((OldParentNode != _transportConfig.parentNodeId) | (ParentNodeLoopCount >= 10)) { resend((msgParent.set(_transportConfig.parentNodeId)),1); OldParentNode = _transportConfig.parentNodeId; ParentNodeLoopCount = 0; } if ((OldDistanceNode != _transportConfig.distanceGW) | (DistanceLoopCount >= 10)) { resend((msgDistance.set(_transportConfig.distanceGW)),1); OldDistanceNode = _transportConfig.distanceGW; DistanceLoopCount = 0; } if ((OldSleepTime != SleepTime) | (SleepTimeLoopCount >= 10)) { resend((msgSleepTime.set(SleepTime,0)),10); OldSleepTime = SleepTime; SleepTimeLoopCount = 0; } if ((OldFails != Fails) | (FailsLoopCount >= 10)) { failsend((msgFails.set(Fails)),1); OldFails = Fails; FailsLoopCount = 0; } BatteryVoltLoopCount++; SILoopCount++; ParentNodeLoopCount++; DistanceLoopCount++; SleepTimeLoopCount++; FailsLoopCount++; digitalWrite(GREEN, HIGH); delay(200); digitalWrite(GREEN, LOW); sleep(SleepTime*60000); //sleep a bit } void readVcc() { //Serial.println("readVcc"); // Read 1.1V reference against AVcc ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1); delay(2); // Wait for Vref to settle ADCSRA |= _BV(ADSC); // Convert while (bit_is_set(ADCSRA, ADSC)); result = ADCL; result |= ADCH << 8; result = 1126400L / result; // Back-calculate AVcc in mV //batteryPcnt = (result - 1900) * 0.090909; BatteryVolt = result / 1000.000; //sendBatteryLevel(batteryPcnt); //Serial.print("battery volt:"); //Serial.println(batteryVolt, 3); //Serial.print("battery percent:"); //Serial.println(batteryPcnt); } void resend(MyMessage & msg, int repeats) { int repeat = 0; int repeatdelay = 0; boolean sendOK = false; while ((sendOK == false) and(repeat < repeats)) { if (send(msg)) { sendOK = true; } else { digitalWrite(RED, HIGH); delay(200); digitalWrite(RED, LOW); Fails++; sendOK = false; Serial.print("Error "); Serial.println(repeat); repeatdelay += 250; repeat++; sleep(repeatdelay); } } } void failsend(MyMessage &msg, int repeats) { int repeat = 0; int repeatdelay = 0; boolean sendOK = false; while ((sendOK == false) and (repeat < repeats)) { if (send(msg)) { Fails = 0; sendOK = true; } else { Fails++; sendOK = false; Serial.print("Error "); Serial.println(repeat); repeatdelay += 250; repeat++; sleep(repeatdelay); } } } void receive(const MyMessage &message) { if (message.sender == 0) { if(message.type == V_PERCENTAGE) { //Serial.println( "V_PERCENTAGE command received..." ); SleepTime = atoi(message.data); if ((SleepTime <= 0) | (SleepTime >= 700)) { SleepTime = 30; } else { SleepTime = SleepTime / 6.6; //Serial.println(SleepTime); if (SleepTime < 1) { SleepTime = 1; } } //Serial.println(SleepTime); } } } void Water() { Serial.println("Water"); resend((msgWater.set(1)), 1000); digitalWrite(GREEN, HIGH); delay(200); digitalWrite(GREEN, LOW); }
-
@flopp said in Water leak:
Finally I made my water leak that I have been dreaming about for a long time now
Sorry, I know this wasn't meant the way it was written, but at first quick read, I had to do a double take. I said to myself, who dreams about making their water leak...
-
@dbemowsk Plumber looking for work ?
-
@zboblamont said in Water leak sensor:
Plumber looking for work ?
NO, but I know some that wouldn't mind the work.
-
@flopp great setup! May I ask what controller you are using and how this works with getting the sleep time from the controller?
-
@helvetian
Thanks.
I am using Domoticz as Controller.
After you first start-up of node you will get a Light device, change this device to Dimmer, then in Setup-Hardware-MySensorsSetup, select Node then select Child for SleepTime and disable Ack.