You can measure voltages using the ADC on the ESP8266. This is useful, for example, to measure a battery voltage and thus the state of charge of the battery or a brightness using an LDR and a series resistor.
The ADC of the ESP8266 is somewhat special. Without additional external wiring, this unfortunately can only handle voltages up to max. 1V. It is therefore not possible to determine the voltage of a LiPo battery directly, because the voltage range of a healthy LiPo ranges from 3.2 to 4.2V.
So that the ADC can also measure higher voltages, a trick is used. A voltage divider is used to scale the voltage to be measured down to the possible voltage range of the ADC.
The ADC then measures voltages in the range from 0V to 1V which stand for a higher value on the actual voltage divider. For example, a voltage divider is also installed on the circuit board of the Wemos D1 Mini to measure voltages up to 3.3V. This is practical, but unfortunately it is not enough to measure the voltage of a LiPo, for example.
How you can expand this maximum voltage range of the ADC is described in the following article.
Hints for our lovely english readers: Basically, many of the articles on Nerdiy.de are translations from the original german articles. Therefore, it may happen here and there that some illustrations are not available in english and that some translations are weird/strange/full of mistakes or generally totaly wrong. So if you find some obvious (or also not obvious) mistakes don't hesitate to leave us a hint about that in the comment section.
Also please don't get confused, that instead of a "dot" often a "comma" is used as decimal separator. 🙂
Requirements
Helpful articles:
Before you start this article, you should have worked on the basics of soldering. You can find information on this in the following article.
Electronics—My friend the soldering iron
Tools required:
In the following list you will find all the tools you need to implement this article.
Required material:
In the following list you will find all the parts you need to implement this article.
Safety instructions
I know the following hints are always a bit annoying and seem unnecessary. But unfortunately, many people who knew it "better" from carelessness lost their eyes, fingers or other things or hurt themselves. In comparison, a loss of data is almost not worth mentioning, but even these can be really annoying. Therefore, please take five minutes to read the safety instructions. Even the coolest project is worth no injury or other annoyance. https://www.nerdiy.de/en/sicherheitshinweise/
Affiliate links / advertising links
The links to online stores listed here are socalled affiliate links. If you click on such an affiliate link and store via this link, Nerdiy.de receives a commission from the online store or provider concerned. The price doesn't change for you. If you do your purchases via these links, you will support Nerdiy.de in being able to offer further useful projects in the future. 🙂
How does a voltage divider work?
A simple voltage divider actually always consists of at least two resistors. In the circuit diagram below of the Wemos D1 Mini you can see a voltage divider in the red marked area.
If you are not interested in the function of a voltage divider, you can simply skip this part. 🙂
There are two resistors installed in series. The upper connection "A0" comes from the connection pin "A0" on the Wemos D1 mini board. The voltage to be measured (for example your LiPo) is connected to "A0".
The "ADC" connection then leads to the actual ADC of the ESP8266.
Why do you do this?
We are using a property of a series connection of two resistors here.
For a series connection of two resistors, it is true, among other things, that the ratio of the total voltage to an individual voltage at one of the resistors is equal to the ratio of the total resistance to one of the individual resistors. That sounds complicated at first but is explained in the following. 🙂
In advance: As a formula, the whole thing would look like this:
Formula 1:
or
Formula 1.2:
"U1" and "U2" are the voltages that drop across the resistor "R1" and "R2". "U" is the same as U1 + U2 because in a series connection of (simple ohmic) resistors, the individual voltages add up to the total voltage.
Shorts:
The same applies to the resistors, because the total resistance of a series connection consists of the sum of the individual resistors.
These formulas can now be used quite well in Formula 1 and you get the following:
With this formula you can now understand why these resistance values were selected in the circuit diagram of the Wemos D1 Mini shown above. R1 has the value 220kOhm and R2 the value 100kOhm. With the knowledge that at the point "ADC" (here the ADC of the ESP8266 is connected) a maximum of 1V can be applied, for which maximum voltage the voltage divider can be used.
To do this, the formula must be changed so that the total voltage "U" can be calculated from the given values. The changed formula results in:
Formula 2:
If you use the corresponding values here, the following results:
With the resistance values used in the voltage divider, voltages up to 3.2V can be measured at the ADC.
The practical: If you change these resistance values, you can also measure higher voltages with the ADC. In the following, for example, the voltage of a LiPo.
Voltage divider on the Wemos D1 Mini
So now you know roughly how a voltage divider works and what it can be used for. With this knowledge, we now want to find resistance values for the voltage divider to be able to measure the voltage of a LiPo battery. Its final charge voltage is a maximum of 4.2V. So that we can measure this upper voltage safely, it is advisable to choose a slightly higher voltage. Let's just say 4.3V.
For the usual voltage values of 4.3V, 5V, 9V and 12V, examples for the resistors R1 are already given in the next paragraph. So you can save yourself the math. 🙂
The goal is to determine the resistance values for R1 and R2.
At the same time, we already know that U = 4.3V other U2 = 1V. This leaves only one unknown value to calculate with formula 2, which we have to determine in order to be able to calculate the last open value. But we make it easy for us here and simply set this value. 🙂
We first set R2 to 100kOhm and see what value we get for R1.
When converted, Formula 1 now includes the knowledge gathered
Formula 3:
In this formula we know all (green) values except R1 (red). So we try to change the formula to R1 and get the following:
simplified and converted:
and colored the same accordingly:
In this formula, we now know all the green values and the (red) value we are looking for is right on the right side of the equal sign. 🙂
The desired value for R1 can now be calculated by inserting:
The value for R1 is 330kOhm. So if we replace the 220kOhm resistor on the circuit board of the Wemos D1 Mini with a 330kOhm resistor, the maximum measurable voltage range is expanded from 3.3V to 4.3V and can therefore also measure the complete voltage range of a LiPo battery. 🙂
Formula for calculation:
 U2 is always 1V
 U is the desired maximum measurable voltage eg 4.3V
 You should just select a value for R2. Ideally in a range from 10kOhm to 100kOhm to keep the current through the voltage divider low.
Example values for maximum voltages and the associated resistance values
You can use the following resistance values to expand the maximum measurable voltage of the ADC to the specified voltage.
Maximum measurable voltage: 4.3V
R1=330kOhm, R2=100kOhm
Maximum measurable voltage: 5V:
R1=400kOhm, R2=100kOhm
Maximum measurable voltage: 9V:
R1=200kOhm, R2=25kOhm
Maximum measurable voltage: 12V:
R1=275kOhm, R2=25kOhm
You can now simply replace the marked 0805 resistors R1 and R2 with the resistors you want. 🙂
Configuration in ESPEasy
The conversion of the ADC into a voltage can be done very comfortably in ESPEasy.
Simply set the device "Analog input  internal" as shown.
If you use a maximum voltage other than 4,300V, you must of course adjust this value accordingly. 🙂
Have fun with the project
I hope everything worked as described. If not or you have any other questions or suggestions, please let me know in the comments. Also, ideas for new projects are always welcome. 🙂
P.S. Many of these projects  especially the hardware projects  cost a lot of time and money. Of course I do this because I enjoy it, but if you appreciate that I share this information with you, I would be happy about a small donation to the coffee box. 🙂
Hi, just found your site, that's exactly what I'm looking for. How do I build the whole thing if I want to make the resistors external? I don't think I can do that on the Wemos with the resoldering.
Hey Mathias,
For which voltage range do you want to adapt the voltage divider? Theoretically, you can also change the voltage divider by soldering on suitable external resistors. One would have to calculate. maybe it is even enough to simply use another series resistor (for the upper part of the voltage divider). 🙂
Hi and thanks for your reply. I would like to measure a normal 18650 cell on the Wemos that should serve as a battery. Wouldn't like to solder around on the Wemos, since it's very small. Would like to just build two resistors in front of it if that's possible?
Hey Mathias,
you should be able to do that with just a 100k resistor. You then have to switch it like this:
A0–>100k_resistance–>LiPo_plus  LiPo_minus> GND
Then 3.2V would have to drop at the two series resistors and thus exactly 1V at "R2". Long story short: 4.2V on the LiPo would then correspond to the ADC value of 1023. With the high resistances and the corresponding tolerances, the measurement is probably not super accurate. But it is definitely sufficient to record the fill level of the LiPo. 🙂
Remember that the relationship between LiPo voltage and "level" is not completely linear. And I would also "smooth" the readings a bit using a moving average. Otherwise you could get a "false alarm" at higher loads (and thus voltage dips in the battery voltage). 🙂
Hope it's explained clearly.
Best regards
Fab
Hi! You really built a great site. Very informative and explained in small steps. I'm working with a Wemos for the first time and came across your tutorial while researching the ADC.
I would like to read a level sensor for my cistern. This measures the water column and lets through 420mA depending on the filling level. It is supplied with 24V. Do you have a tip on how I could remodel the input from the Wemos for this?
All the best, Martin
hey martin,
Thanks. 🙂
In principle, you need a suitable resistor. The Wemos Breakout board's ADC can measure voltages from zero to 3.3V. You can use a resistor to convert your sensor's "current signal" into a voltage. I skipped that. A 175 ohm resistor should fit.
You would then have to connect it like this: (The zigzag line is supposed to represent the resistance.) I would also recommend switching a highimpedance (eg 10k) resistor in front of the ADC. 🙂
Sensor_signal 420mA

+————–ESP_ADC

\
/ 175 ohms
\
/





GND
If you want, let me know if it worked. 🙂
Oh and on the ADC you should then be able to measure a voltage proportional to the current flow. The formula U=R*I applies (this is Ohm's law). R is the resistance (i.e. 175Ohm), I the current of the sensor (i.e. a value between 420mA) and U is the voltage that is then measured at the ADC or drops across the resistor. You can also test the circuit without having connected the Wemos. Simply measure the voltage with a multimeter. 🙂
Best regards
Fabian
Hi Fabian,
Many thanks for the help!
Used a precision trimmer as a resistor to calibrate the voltage.
Works great so far, but the values of the ADC jump plus/minus 5 points. I've already set a 100n against ground to stabilize, but that only helps to a limited extent.
If I measure the mA of the sensor like this, this value is stable. Depends on the ADC of the Wemo.
Do you have any tips on how I can smooth this out even better?
Best regards Martin
hey martin,
I am glad, that it worked. Good idea with the precision trimmer. 🙂
An idea how you could smooth that even better (in software) would be a moving average.
This is actually a common procedure if you have a signal that you can read in quickly.
To do this, you simply read out the ADC several times (e.g. 100 times) and then calculate the average of it. Small deviations should then actually be compensated for and no longer be noticeable. 🙂
Best regards
Fabian
Hi,
Thanks for your great info page 🙂
Must have been a lot of work.
Can you do that directly in the Wemos in espeasy
convert to percentage?
Greetings Heiko
Hey Heiko,
Thanks very much. Yes, I've already invested an hour or two here. 😀
Yes, that should work. Here's an article that might help you: https://www.letscontrolit.com/wiki/index.php/EasyFormula
Best regards
Fabian
Hi Fabian, Great article here!! well done 🙂
I have a wemos d1 mini with its original smd resistors R1 220kOhm and R2 100kOhm
I want to measure voltages up to 29.4V (7s battery)
so which resistors you think its better to pick?
solution1= R1 300kOhm + R2 10kOhm (up to 32v) least efficient but best accurate
solution2= R1 680kOhm + R2 20kOhm (up to 36V) low efficient medium accuracy
solution3= R1 470kOhm + R2 10kOhm (up to 49v) = most efficient but least accurate
Please do the math and help me pick the best solution.
Thanks 🙂
Hi Nick,
thanks 🙂
To be honest I would go with solution1. Of course the ~9micro amps could be anyoing (depending on your usecase) but in most cases they shouldnt bother that much.
Or do you plan to build something where this 9µA could be problematic? 🙂
Best regards
Fab
I will just use Wemos D1 Mini with tasmota to monitor my 24V (7s battery) that is charged with a solar panel. HUUUGE thanks for the feedback 🙂
Sounds cool, I think in this case you don't have to care so much about the 9µA 🙂
Good luck with the project. 🙂
Best regards
Fab
RE edit
or you can recommend another combination. I have those metallic resistors: 10Ω, 22Ω, 47Ω, 100Ω, 150Ω, 200Ω, 220Ω, 270Ω, 330Ω, 470Ω, 510Ω, 680Ω, 1KΩ, 2KΩ, 2.2K Ω, 3.3KΩ, 4.7KΩ, 5.1KΩ, 6.8KΩ, 10KΩ, 20KΩ, 47KΩ, 51KΩ, 68KΩ, 100KΩ, 220KΩ, 300KΩ, 470KΩ, 680KΩ, 1M
Hello Fab,
I just checked this article, and unfortunately a few errors crept in...
1.
Formula 2 is wrong!
Instead of Rsum / R2 + U2 = U it should read Rsum/R2 * U2 = U
Regardless of the fact that the line underneath is mathematically incorrect.
330/100+1 would be 4.3 ... and the units are not correct either (kOhm/kOhm cancels out)
Furthermore: Where does the 330 kOhm come from? R1=220 kOhm and R2 = 100 kOhm > therefore Rsum = 320 kOhm and not 330 kOhm
With these ohm values (220 and 100 kOhm) you get over 1 volt at the ADC ... namely 1.03 volts
But I can't judge whether this is already harmful for the analogue input.
2.
Formula 3 is ok so far, but it was not derived from formula 1.2 but from formula 1
(Of course, this has no further influence on the further calculation methods.... mentioned only for clarity)
3.
I can't understand the calculated value for the 175 ohms (inquiry from Martin regarding the level sensor). According to my calculations, the value for the resistor would be around 52 ohms...
Please don't misunderstand my comment...
LG Ralph
Hi Ralph,
thanks for your hints. I corrected the errors that I could understand. 🙂
to 1. What do you mean by the units are wrong? Since the kOhms are shortened, V remains above: [kOhm/kOhm*V=V] That's what it says there, isn't it?
to 3. Your calculation refers to a maximum measurable voltage value of 1V. The Wemos D1 Mini (which Martin addresses in the comment) is a breakout board for the ESP8266. A voltage divider is connected upstream of the ADC (which he explicitly did not want to change). That's why the 175 ohms go very well with the extended measuring range (up to 3.3V) of the Wemos D1 Mini. 🙂
Oh no problem. I'm glad if someone finds a mistake and lets me know. 🙂
Thank you and best regards
Fabian