Water Tank Level and Water Volume with ESPHome

I am using this water flow:
https://www.tomsonelectronics.com/products/1-inch-water-flow-sensor-yf-g1-dn25

Code:

esphome:
name: water_level
platform: ESP8266
board: nodemcuv2

wifi:
ssid: “xxxxxxxxxxxx”
password: “xxxxxxxxxxxx”

#Optional manual IP
manual_ip:
static_ip: 192.168.1.39
gateway: 192.168.1.1
subnet: 255.255.255.0

#Enable fallback hotspot (captive portal) in case wifi connection fails
ap:
ssid: “Water Level Fallback Hotspot”
password: “xxxxxxxxxxxxxx”

captive_portal:

#Enable logging
logger:

#Enable Home Assistant API
api:
password: “xxxxxxxxxxxxx”

ota:
password: “xxxxxxxxxxxxx”

sensor:

  • filters:
    lambda: |-
    static float total_pulses = 0.0;
    total_pulses += x * 1 / 60.0;
    id(lifetime_counter).publish_state(total_pulses / 27);
    return x ;
    id: water_pulse
    internal: true
    name: “Pulse Counter”
    pin: GPIO14
    platform: pulse_counter
    update_interval: 5s

  • id: lifetime_counter
    name: “Water Total”
    platform: template
    unit_of_measurement: L
    accuracy_decimals: 4

  • accuracy_decimals: 4
    icon: “mdi:water”
    id: water_flow_rate
    lambda: “return (id(water_pulse).state /27);”
    name: “Water Flow Rate”
    platform: template
    unit_of_measurement: L/min
    update_interval: 5s

  • platform: ultrasonic
    trigger_pin: GPIO1
    echo_pin: GPIO3
    name: “Water Tank Level”
    unit_of_measurement: “%”
    accuracy_decimals: 0
    update_interval: 5s
    filters:

    • lambda: return ((((x100)-20)-(140-20))/(140-20))-100;
    • filter_out: nan
  • platform: ultrasonic
    trigger_pin: GPIO1
    echo_pin: GPIO3
    update_interval: 5s
    name: “Water Tank Volume”
    unit_of_measurement: “l”
    accuracy_decimals: 0
    filters:

    • lambda: return ((((x100)-20)-(140-20))/(140-20))-3000;
    • filter_out: nan
3 Likes

still facing some problems in measuring the exact flow, need support from the experts…

*I have it working, but readings go from 1.2m to 1.02m in height. with results in 38% to 51% in the readings. *

*Anyway to do an average sensor or something like that? *

How do you calibrate the screw on the ultrasound PCB?

any other thing to improve readings?

.
.
.

Finding the real problem, my sensor won’t read past 1.1 meeter. any advice? it is a JSN-SR04T

Does the voltage level match the input voltage for the ESP8266 or do you need a voltage divider? I see you wired it directly so was curious…

Edit: Did some research and found this. Will apply for the ESP8266 also.

3 Likes

Hi Nawafbana, can you share GPIO configuration with NodeMCU please?

Hello, im not sure, what numbers i need. Can you help me pls?
My tank:
Tank diameter 2,65m
Height from the bottom of the tank at which the sensor is 2m

Thank you
Ivica

hello I am soooo close,
I have been trying to find the right way to do this for a while now and i found your code yesterday. My results seems promising but i am positive the results are off.
I think something is wrong in my lambda filters but I can’t figure what part.

  • im using the HC-sr04 for testing but will use the waterfproof for realworld (automatic drip irrigation system)
  • from sensor to bottom of “test bucket”: 68cm
  • from sensor to max water level: 33cm (22cm away plus safety)

Here’s the important bit of my code, hope you or someone can help me:

sensor:     
  - platform: ultrasonic
    trigger_pin: GPIO 5
    echo_pin: GPIO 4
    name: 'Water tank Level'
    unit_of_measurement: '%'
    accuracy_decimals: 0
    update_interval: 5s
    icon: mdi:water
    filters:
      - lambda: return ((((x*100)-33)-(68-33))/(68-33))*-100;
      - filter_out: nan
  - platform: ultrasonic
    trigger_pin: GPIO 5
    echo_pin: GPIO 4
    update_interval: 5s
    name: 'Water Tank Volume'
    unit_of_measurement: 'l'
    accuracy_decimals: 2
    icon: mdi:water
    filters:
      - lambda: return ((((x*100)-33)-(68-33))/(68-33))*-1000;
      - filter_out: nan

I am getting 105% and 955.5l: Testing in a food grade 20litres plastic bucket which has about 1 liter of water in the bottom…

I really can’t figure out what’s wrong with the code… trying different sensor placement while waiting for a response.

Thanks in advance.

lambda: return ((((x100)-33)-(68-33))/(68-33))-1000
I finally understand, the problem is that you left the value 1000l in the code. It is the value between the maximum amount of water and the bottom of the tank. So you have a 20 liter bucket set up as a 1000 liter tank. Try set -20.

1 Like

Hi Nawafbana

Thank you for posting this. I’m a bit of a newbie and while I have a level sensor set up and measuring I have tried to compile the sketch you posted but fail.

Can you please tell me how you compiled the sketch.

Thanks in advance

Tony

Can someone help make my formula perfect?
I now have my new/“almostfinal” setup finished (sensor hooked up, tank, pumps, tubing flow sensor & flow limiter all in place.
Maybe someone can help me to make it even better.
so here are my infos:

  • EX: 8cm (sensor to max water level)
  • TD: 46 cm (empty bottom of tank)
  • TC:72 Litres (44cm deep (36cm max water level) by 40cm wide by 50cm long tank)
  • Minimum water level (so the pump is still submerged): 13 cm

I still get a 1% error and almost 1 litre error (not so bad but not perfect)
this is the empty tank snapshot:

Screen Shot 2021-04-27 at 12.39.26 AM

heres my code:

sensor:
  - platform: wifi_signal
    name: "WiFi Signal Sensor"
    update_interval: 60s

  - platform: dht
    pin: GPIO 13
    model: dht11
    temperature:
      name: "Temperature_01"
    humidity:
      name: "Humidity_01"

  - platform: ultrasonic
    trigger_pin: GPIO 5
    echo_pin: GPIO 4
    name: 'Water tank Level'
    unit_of_measurement: '%'
    accuracy_decimals: 1
    update_interval: 1s
    icon: mdi:water-percent
    filters:
      - lambda: return ((((x*100)-8)-(46-8))/(46-8))*-100;
      - sliding_window_moving_average:
          window_size: 10 #creates a moving average of the last 10 values
          send_every: 1 #sends the moving average at every measurement (but only if it passes the delta filter below)) 
          send_first_at: 1 #after startup immediately start sending the result rather than wait for the first 10 measurements
      - delta : 0.05 #only send the result if the level difference with the last sent result is higher than this
      - filter_out: nan
      
      
  - platform: ultrasonic
    trigger_pin: GPIO 5
    echo_pin: GPIO 4
    update_interval: 2s
    name: 'Water Tank Volume'
    unit_of_measurement: 'l'
    icon: mdi:cup-water
    accuracy_decimals: 2
    filters:
      - lambda: return ((((x*100)-8)-(46-8))/(46-8))*-70;
      - sliding_window_moving_average:
          window_size: 10 #creates a moving average of the last 10 values
          send_every: 1 #sends the moving average at every measurement (but only if it passes the delta filter below)) 
          send_first_at: 1 #after startup immediately start sending the result rather than wait for the first 10 measurements
      - delta : 0.05 #only send the result if the level difference with the last sent result is higher than this
      - filter_out: nan

Thank you in advance for the help, also i want to give big thanks to everyone in this wonderful community for all the help and learning opportunities!

2 Likes

not a sketch (arduino) its done using esphome…

Thank you very much for nice project. Everything done like described. Everything is working, but… till power-cycle. After power cycle ESP not booting. Only reset (RST–>GND) help to boot again.

my config posted here was working and just stopped out of the blue, now the numbers are all off, and random it seems… connection times out… the whole thing just broke !

what can i do?

I need this for my installation!

So I finally got around to installing this yesterday. I installed sensors on an 800 gal and 400 gal tanks. Here are some pics of my setup.

I also did a sensor calibration at different depths and noticed that as you measure further from the sensor the delta error increases (see table below).

Does anyone know how to apply corrections to output for errors that vary (maybe in lambda function)?

Calibration

3 Likes

Just in case people in this topic haven’t seen it.
As an alternative you can use a pressure sensor. You just throw it in your water tank so that it drops to the bottom and for me it measures the water depth with a precision of about a millimeter!

3 Likes

Cool! A bit pricey but looks like it gets the job done.

Really!!! I cant seem to be able to figure out how to make it work for me!
would you mind sharing that part of your config, i’ve been pulling my on this for days now!
got this model:

using a nodemcu for this

  - platform: pulse_counter
    name: "Flow rate 1-2"
    id: water_flowrate
    pin: 13
    update_interval: 1s
    filters:
    - lambda: return (x / 96.0);
    unit_of_measurement: "L/min"

thank you in advance

I think we’re talking apples and pears.
You are looking for a solution that can measure flow rate.
What I am using is a solution that can measure pressure differences and translate that into water levels (how much water is in the tank).

i posted the wrong code, i have the pressure sensor
and i want to get the volume or at least the percentage of water in my tank…

here’s the right code… its not giving me the plausable results but its my presure sensor code:

  - platform: adc
    pin: A0
    name: "water pressure"
    update_interval: 2s
    unit_of_measurement: "psi"
    icon: "mdi:gauge"
    accuracy_decimals: 1
    filters:
      - multiply: 5.0
      - lambda: return x*43.75-21.875;

my code is wrong and it gives me only psi…

:frowning: i am sort of a newbie in esphome and i could take all the help because ,my grow is ongoing and this isnt working and its not good…

thanks!

I just got the dfrobot weatherproof ultrasonic sensor in replacement for the HC…

would you mind sharing your config, i want to re-start from someone elses config, i need to get this working asap.

thanks