Sending unit installed on tank

A wireless Fuel Tank monitor

I saw an excellent write-up on how to monitor fuel levels in an oil tank using ultrasonic sensors over on hackaday.  In his blog, alaskanshade details how he used Arduino and an ultrasonic sensor to log the data and measure fuel levels.  I really like the idea of monitoring fuel levels using this setup, so I had to give it a try.  I also wanted to incorporate the following design goals:

  1. Perform all-wireless data acquisition
  2. Ability to see current fuel level on the internet/web-page
  3. Log all data to a sql database/web-server using deviceLogger
  4. Battery life should last a long time, at least six months without having to change batteries

Forgive my lack of drawing skills, here is a diagram of the whole system:

deviceLogger system

In a nutshell, the process works like this:

  1. The sending unit pings the tank with the ultrasonic sensor and calculates the gallons (see attached gist for code, I found some code online that I adapted for use here. I’d give credit, but I can’t remember which site(s?) I found it on anymore)
  2. The entire system shuts down using the excellent LowPower library for Arduino.  After about one minute, it wakes back up and does another measurement.  After 15 measurements/minutes we send the current running median (another great Arduino Library) of the measurements. At this point, the whole process repeats.
  3. On the receiving end, there is an Arduino with an nrf24l01 module and ethernet shield (see my previous post on getting these two to work together if needed).  The receiver publishes some text/xml to a web page.
  4. The deviceLogger reader script periodically checks this page for new data.  It then writes the data to a mySQL database.  The deviceLogger php application then serves up the graphs and current data.

I ended up using one of my protoBoard pcbs on this project, and it worked out very well.  It fit perfectly in the 2″ pvc that I used to build the sensor housing.  Here’s some images from the build:

This shows a 4-AA battery holder, but I've since swapped it out for a 3-AA holder
The complete setup, all components. I later switched to a 3-AAA holder instead.


tank reader protoboard
This is a custom PCB I call a protoBoard. It basically just maps most of the atmega328’s pins to solder pads/screw-term pads.
You can see the snoot that was added to avoid the ‘multipathing’ issues that I experienced previously. Works great!
The ultrasonic sensor at the bottom of the unit.
PVC sheet cut to shape for bottom of the sending unit (You can find this material at a sign-supply shop)
Bottom of the unit with 1/2″ PVC installed for snoot.
Everything fit inside the 2″ PVC easily.
Top cap is just a slip fitting. I suppose you could use screw-on version if you cared to.

tankReader4 tankReader2

Sending unit uses 2" PVC to connect to tank.
Sending unit installed on tank.

Sending unit installed on tank

One thing that I noticed in the course of this project was that I was getting some strange readings from time to time, and sometimes readings would just be completely off from what I knew to be the current tank depth.  I had a theory that some of the erroneous readings may have been caused by multiple echoes bouncing off of the many internal facets of the tank (multipathing).  I decided to try adding a ‘snoot’ of 1/2″ pvc pipe to the end of the ultrasonic sensor to better guide the send signal towards the surface I actually wanted to measure (the fuel sitting at rest in the tank).  This seems to work very well.  Once I placed the snoot on the sensor, I immediately began receiving good readings without error.  I do still have some bad-value rejection and median-smoothing in the Arduino sketch though.  And as you can see from the screenshots, I still get fluctuations in the ultrasonic readings that work out to about a +/- 1 gallon level of accuracy over the course of a day:

This is the summary screen on deviceLogger
This is the summary screen on deviceLogger


You can see that there is still some fluctuation in readings even when rejecting bad values and median-smoothing
You can see that there is still some fluctuation in readings even when rejecting bad values and median-smoothing. I think to expect anything more would be a little unreasonable for a sensor that cost about $1.25

I also made a few modifications to the newPing library settings that changed the amount of time delay between pings on the ping_median() method.  This was done because the aforementioned multipathing/echo issues seem to present themselves once again if you don’t wait long enough between pings.  I adjusted the time from 29ms up to 1000ms.

As mentioned above, the sketch also uses the excellent LowPower library.  I used LowPower to power down the Atmega328 for about a minute at a time between readings.    This should allow the three AAA batteries to last about one year before needing to be replaced.

If you want to use this code, but have a different sized tank, you should be able to adjust the values for variables ‘tankHeight, tankWidth, and tankLength’.  As long as your tank maintains standard ob-round dimensions/shape, it should work fine.

Here’s the sketches:

9 thoughts on “A wireless Fuel Tank monitor”

  1. Hello,
    I was just wondering how you got around the hc-sr04 being 5v ?,are you using a step up module also or does the module work with the 3 aaa batteries and would the sensor not lose its accuracy and drop off as the voltage in the batteries decrease,im doing a similar project at the moment and thought you may have encountered this problem along the way


    1. Robert,
      My understanding is that the minimum voltage for the hc-sr04 is 4.5v. I do fully expect to see the sensor produce errors when the batteries start dying. Because of a design error on my part, the rf24 is getting significantly more voltage than it should be (I didn’t select an appropriate low-dropout regulator, but out of curiosity, or laziness, I left it as is), so I am hesitant to bump the voltage much unless I need to. I did also try this for a while with a 4 AA setup and nimh batteries. I think that would be a fine solution as well.

      1. Shane,

        Thanks for the quick reply ,like i said id been working on something similar and it was interesting to hear how you were getting around the problem of voltage using just 3 aa or aaa,keep up the good work arduino projects are always so interesting to see how people tweek them.


  2. This sounds like exactly what I’ve been planning to do, but haven’t had the time to do more than order the parts and watch them sitting on my desk. How do you think the size and shape of the tank would influence the results? The tanks that I need to monitor are almost all rectangular in shape. I’d love to talk to you a little more in depth about this project if you have time.

  3. Very nice but does sensor not get damage with liquids over long time? why not make a dip stick, inside the stick you can put reed sensors with magnet float on out side. then you can monitor oil, petrol, diesel or water on the move. no damage to sensor.

  4. Hi,

    I have a similar project with the same components, but I have some troubles, could you please send me your contact information, I need your help…


  5. I’m also working on an HC-SR04-based oil tank system. My tank is buried, so I’m using a hard-wired interface. One issue I’ve seen is HC-SR04 failure after a few months of use. I suspect that condensation in the tank is killing the sensor. Need to solve this since digging up the sensor every few months is not an option.

    How have you made out, long term, using the HC-SR04 in an oil tank environment?

    1. Hi,

      Just found this site. Was searching for risk in using electronic sensors in fuel/petrol measurement. However, you can use Waterproof Ultrasonic Module JSN-SR04T for your project. I hope it does not fail on months as HC-SR04.
      I haven’t used it yet. Just ordered some and yet to arrive for my project.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>