Reading it on an ESP32
An ESP32's ADC measures against its own reference, reads only to about 3.1 V at the Arduino core's default setting, and is least straight near both ends. So the sketch reads calibrated millivolts, assumes VCC is 3.3 V, and uses an ADC1 pin.
Its own reference
On an Uno, the ADC's full scale is VCC, and a count is a fraction of VCC. Why VCC cancels out is about why that makes the arithmetic easy. An ESP32 and an ESP32-S3 do not work that way. Their ADC measures against a reference inside the chip, so a count is a voltage, not a fraction of VCC, and the Uno's shortcut does not apply.
So the sketch in counts to
degrees takes a
different first step on an ESP32. It calls analogReadMilliVolts, which reads
the pin and converts the count to millivolts with calibration data stored in
the chip at the factory. It then divides by VCC_MV, 3300 unless you measure
your own 3V3 pin, to get back to the fraction the divider works in. The rest of
the chain is the same.
A range that stops short
At the Arduino core's default setting, the ESP32's ADC reads from 0 to about 3.1 V, not to 3.3 V. SIGNAL rises as it gets colder, so the cold end is the one that runs out. Slide the temperature down: below about −26 °C SIGNAL is past the top of the range, and every colder temperature reads the same.
Near both ends of its range the ESP32's converter is also at its least
straight. The calibration behind analogReadMilliVolts corrects much of that,
but a reading close to either end is still the least trustworthy on the
scale. For this block that means very hot and very cold. Room temperature
sits comfortably in the middle, around 1.6 V.
ADC1 only
The classic ESP32 has two converters. ADC2 is shared with the radio, and while Wi-Fi is on its readings fail. GPIO 34, the pin used in this book, is on ADC1, which keeps working. So is GPIO 4 on the ESP32-S3: its ADC1 is GPIO 1 to 10.
In MicroPython
The MicroPython sketch does the same thing with read_uv, which returns
calibrated microvolts, and sets the ADC's attenuation to its widest with
adc.atten(ADC.ATTN_11DB). Without that line MicroPython's ESP32 ADC stops
near 1 V, and a room-temperature SIGNAL is off the top.
When it does not work
It is part of the ESP32 Arduino core, in the 2.x and 3.x releases. An older core, or a board package that is not Espressif's, may not have it. Update the core in the Boards Manager. On an Uno or a Pico the sketch never calls it: the #if sends them down the analogRead path.
SIGNAL is on an ADC2 pin. On the classic ESP32 the radio uses ADC2 while Wi-Fi is on, and readings from it fail or return rubbish. Move SIGNAL to an ADC1 pin: GPIO 34 here, or any of GPIO 32 to 39.
The 3V3 rail is not exactly 3.3 V. Measure it with a multimeter at the 3V3 pin while the board runs, and put the reading into VCC_MV. Each per cent the rail is off moves the answer by about half a degree near 25 °C.
SIGNAL has climbed past the top of the ADC's range, about 3.1 V, and every colder reading returns the same number. The block's divider was not chosen for a freezer. On an Uno, whose ADC reads all the way to VCC, the same block keeps going.
Edit this page — content/books/ntc-thermistor/reading-it-on-an-esp32.mdx
Questions about this product
See what other owners have asked, and read their solutions.
NTC Thermistor
Loading discussions…
Discuss this article
Ask about this page. The answer stays here, on the page it belongs to, for whoever hits the same wall next.