Hello, I made an esphome component for ESP32 to measure electric power through ADC.
It is inspired to the good old Emonlib, which is found in almost all DIY energy monitors.
I kept the power estimation algorithm, but I cut some rough edges, making it sleeker and easier to configure.
Technical details
This component leverages DMA on the ADC peripheral in ESP32 chips. This allows for a much higher sample rate (20kHz), which in turn leads to almost perfectly synchronized samples, thus releasing the need for a phase calibration parameter (_PHASECAL in Emonlib) and making the result in theory more precise (I have not tested its precision, since I do not own precise measurement equipment).
On the other side it requires esp-idf v5.x or newer, which is at the moment not officially supported by the ESPHome project. It apparently works, but still could break something.
It is now in a beta state. There are some open points. Any feedback, help, feature request, performance benchmark or code contribution is highly appreciated.
Here is a sample configuration if you want to give it a try:
...
esp32:
board: esp32dev
framework:
type: esp-idf
platform_version: https://github.com/platformio/platform-espressif32.git
version: 5.2.1
external_components:
- source: github://Petapton/esphome@emon
components: [ emon ]
sensor:
- platform: emon
v_input:
pin: GPIO34
attenuation: 2.5dB
cal: 2.121e-1
i_input:
pin: GPIO35
attenuation: 2.5dB
cal: 2.8798e-2
data_interval: 1s
voltage:
name: "Emon P1 Voltage"
current:
name: "Emon P1 Current"
active_power:
name: "Emon P1 Active Power"
apparent_power:
name: "Emon P1 Apparent Power"
power_factor:
name: "Emon P1 Power Factor"
button:
# Reboot in safe mode before OTA updates
- platform: safe_mode
name: "Safe Mode"
...
Known issues
- OTA update does not work unless booted in safe mode. This is most likely due to the fact that the ADC peripheral generates frequent interrupts, making the OTA process time out.