ZigbeeElectricalMeasurement
About
The ZigbeeElectricalMeasurement
class provides an endpoint for electrical measurement devices in Zigbee networks. This endpoint implements the Zigbee Home Automation (HA) standard for power monitoring and electrical measurement.
Features: * AC and DC electrical measurements * Voltage, current, and power monitoring * Power factor measurement * Multi-phase support * Configurable measurement ranges * Automatic reporting capabilities * Integration with common endpoint features (binding, OTA, etc.) * Zigbee HA standard compliance
Use Cases: * Smart power monitoring * Energy monitoring systems * Solar panel monitoring * Battery monitoring systems * Electrical load monitoring
Common API
Constructor
ZigbeeElectricalMeasurement
Creates a new Zigbee electrical measurement endpoint.
ZigbeeElectricalMeasurement(uint8_t endpoint);
endpoint
- Endpoint number (1-254)
DC Electrical Measurement
addDCMeasurement
Adds a DC measurement type to the endpoint.
bool addDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE measurement_type);
measurement_type
- DC measurement type constant (ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_DC_MEASUREMENT_TYPE_POWER)
This function will return true
if successful, false
otherwise.
setDCMeasurement
Sets the DC measurement value for a specific measurement type.
bool setDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE measurement_type, int16_t value);
measurement_type
- DC measurement type constant (ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_DC_MEASUREMENT_TYPE_POWER)value
- Measurement value
This function will return true
if successful, false
otherwise.
setDCMinMaxValue
Sets the minimum and maximum values for a DC measurement type.
bool setDCMinMaxValue(ZIGBEE_DC_MEASUREMENT_TYPE measurement_type, int16_t min, int16_t max);
measurement_type
- DC measurement type constant (ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_DC_MEASUREMENT_TYPE_POWER)min
- Minimum valuemax
- Maximum value
This function will return true
if successful, false
otherwise.
setDCMultiplierDivisor
Sets the multiplier and divisor for scaling DC measurements.
bool setDCMultiplierDivisor(ZIGBEE_DC_MEASUREMENT_TYPE measurement_type, uint16_t multiplier, uint16_t divisor);
measurement_type
- DC measurement type constant (ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_DC_MEASUREMENT_TYPE_POWER)multiplier
- Multiplier valuedivisor
- Divisor value
This function will return true
if successful, false
otherwise.
setDCReporting
Sets the reporting configuration for DC measurements.
bool setDCReporting(ZIGBEE_DC_MEASUREMENT_TYPE measurement_type, uint16_t min_interval, uint16_t max_interval, int16_t delta);
measurement_type
- DC measurement type constant (ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_DC_MEASUREMENT_TYPE_POWER)min_interval
- Minimum reporting interval in secondsmax_interval
- Maximum reporting interval in secondsdelta
- Minimum change required to trigger a report
This function will return true
if successful, false
otherwise.
reportDC
Manually reports a DC measurement value.
bool reportDC(ZIGBEE_DC_MEASUREMENT_TYPE measurement_type);
measurement_type
- DC measurement type constant (ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_DC_MEASUREMENT_TYPE_POWER)
This function will return true
if successful, false
otherwise.
AC Electrical Measurement
addACMeasurement
Adds an AC measurement type for a specific phase.
bool addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE measurement_type, ZIGBEE_AC_PHASE_TYPE phase_type);
measurement_type
- AC measurement type constant (ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_MEASUREMENT_TYPE_POWER_FACTOR, ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY)phase_type
- Phase type constant (ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, ZIGBEE_AC_PHASE_TYPE_A, ZIGBEE_AC_PHASE_TYPE_B, ZIGBEE_AC_PHASE_TYPE_C)
This function will return true
if successful, false
otherwise.
setACMeasurement
Sets the AC measurement value for a specific measurement type and phase.
bool setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE measurement_type, ZIGBEE_AC_PHASE_TYPE phase_type, int32_t value);
measurement_type
- AC measurement type constant (ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_MEASUREMENT_TYPE_POWER_FACTOR, ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY)phase_type
- Phase type constant (ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, ZIGBEE_AC_PHASE_TYPE_A, ZIGBEE_AC_PHASE_TYPE_B, ZIGBEE_AC_PHASE_TYPE_C)value
- Measurement value
This function will return true
if successful, false
otherwise.
setACMinMaxValue
Sets the minimum and maximum values for an AC measurement type and phase.
bool setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE measurement_type, ZIGBEE_AC_PHASE_TYPE phase_type, int32_t min, int32_t max);
measurement_type
- AC measurement type constant (ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_MEASUREMENT_TYPE_POWER_FACTOR, ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY)phase_type
- Phase type constant (ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, ZIGBEE_AC_PHASE_TYPE_A, ZIGBEE_AC_PHASE_TYPE_B, ZIGBEE_AC_PHASE_TYPE_C)min
- Minimum valuemax
- Maximum value
This function will return true
if successful, false
otherwise.
setACMultiplierDivisor
Sets the multiplier and divisor for scaling AC measurements.
bool setACMultiplierDivisor(ZIGBEE_AC_MEASUREMENT_TYPE measurement_type, uint16_t multiplier, uint16_t divisor);
measurement_type
- AC measurement type constant (ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_MEASUREMENT_TYPE_POWER_FACTOR, ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY)multiplier
- Multiplier valuedivisor
- Divisor value
This function will return true
if successful, false
otherwise.
setACPowerFactor
Sets the power factor for a specific phase.
bool setACPowerFactor(ZIGBEE_AC_PHASE_TYPE phase_type, int8_t power_factor);
phase_type
- Phase type constant (ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, ZIGBEE_AC_PHASE_TYPE_A, ZIGBEE_AC_PHASE_TYPE_B, ZIGBEE_AC_PHASE_TYPE_C)power_factor
- Power factor value (-100 to 100)
This function will return true
if successful, false
otherwise.
setACReporting
Sets the reporting configuration for AC measurements.
bool setACReporting(ZIGBEE_AC_MEASUREMENT_TYPE measurement_type, ZIGBEE_AC_PHASE_TYPE phase_type, uint16_t min_interval, uint16_t max_interval, int32_t delta);
measurement_type
- AC measurement type constant (ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_MEASUREMENT_TYPE_POWER_FACTOR, ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY)phase_type
- Phase type constant (ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, ZIGBEE_AC_PHASE_TYPE_A, ZIGBEE_AC_PHASE_TYPE_B, ZIGBEE_AC_PHASE_TYPE_C)min_interval
- Minimum reporting interval in secondsmax_interval
- Maximum reporting interval in secondsdelta
- Minimum change required to trigger a report
This function will return true
if successful, false
otherwise.
reportAC
Manually reports an AC measurement value.
bool reportAC(ZIGBEE_AC_MEASUREMENT_TYPE measurement_type, ZIGBEE_AC_PHASE_TYPE phase_type);
measurement_type
- AC measurement type constant (ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_MEASUREMENT_TYPE_POWER_FACTOR, ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY)phase_type
- Phase type constant (ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, ZIGBEE_AC_PHASE_TYPE_A, ZIGBEE_AC_PHASE_TYPE_B, ZIGBEE_AC_PHASE_TYPE_C)
This function will return true
if successful, false
otherwise.
Example
DC Electrical Measurement
// Copyright 2025 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
/**
* @brief This example demonstrates a Zigbee DC electrical measurement sensor.
*
* The example shows how to use the Zigbee library to create an end device that measures
* DC voltage, current and power using the Electrical Measurement cluster.
*
* The device reports:
* - DC voltage in millivolts (0-5000mV)
* - DC current in milliamps (0-1000mA)
* - DC power in milliwatts (0-5000mW)
*
* Proper Zigbee mode must be selected in Tools->Zigbee mode
* and also the correct partition scheme must be selected in Tools->Partition Scheme.
*
* Please check the README.md for instructions and more detailed description.
*
* Created by Jan Procházka (https://github.com/P-R-O-C-H-Y/)
*/
#ifndef ZIGBEE_MODE_ED
#error "Zigbee end device mode is not selected in Tools->Zigbee mode"
#endif
#include "Zigbee.h"
/* Zigbee DC measurement device configuration */
#define DC_ELECTRICAL_MEASUREMENT_ENDPOINT_NUMBER 1
uint8_t analogPin = A0;
uint8_t button = BOOT_PIN;
ZigbeeElectricalMeasurement zbElectricalMeasurement = ZigbeeElectricalMeasurement(DC_ELECTRICAL_MEASUREMENT_ENDPOINT_NUMBER);
void setup() {
Serial.begin(115200);
Serial.println("Starting...");
// Init button switch
pinMode(button, INPUT_PULLUP);
// Set analog resolution to 10 bits
analogReadResolution(10);
// Optional: set Zigbee device name and model
zbElectricalMeasurement.setManufacturerAndModel("Espressif", "ZigbeeElectricalMeasurementDC");
// Add analog clusters to Zigbee Analog according your needs
zbElectricalMeasurement.addDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE);
zbElectricalMeasurement.addDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT);
zbElectricalMeasurement.addDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE_POWER);
// // Optional: set Min/max values for the measurements
zbElectricalMeasurement.setDCMinMaxValue(ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, 0, 5000); // 0-5.000V
zbElectricalMeasurement.setDCMinMaxValue(ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, 0, 1000); // 0-1.000A
zbElectricalMeasurement.setDCMinMaxValue(ZIGBEE_DC_MEASUREMENT_TYPE_POWER, 0, 5000); // 0-5.000W
// // Optional: set Multiplier/Divisor for the measurements
zbElectricalMeasurement.setDCMultiplierDivisor(ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, 1, 1000); // 1/1000 = 0.001V (1 unit of measurement = 0.001V = 1mV)
zbElectricalMeasurement.setDCMultiplierDivisor(ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, 1, 1000); // 1/1000 = 0.001A (1 unit of measurement = 0.001A = 1mA)
zbElectricalMeasurement.setDCMultiplierDivisor(ZIGBEE_DC_MEASUREMENT_TYPE_POWER, 1, 1000); // 1/1000 = 0.001W (1 unit of measurement = 0.001W = 1mW)
// Add endpoints to Zigbee Core
Zigbee.addEndpoint(&zbElectricalMeasurement);
Serial.println("Starting Zigbee...");
// When all EPs are registered, start Zigbee in End Device mode
if (!Zigbee.begin()) {
Serial.println("Zigbee failed to start!");
Serial.println("Rebooting...");
ESP.restart();
} else {
Serial.println("Zigbee started successfully!");
}
Serial.println("Connecting to network");
while (!Zigbee.connected()) {
Serial.print(".");
delay(100);
}
Serial.println("Connected");
// Optional: Add reporting for DC measurements (this is overridden by HomeAssistant ZHA if connected to its network)
zbElectricalMeasurement.setDCReporting(ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, 0, 30, 10); // report every 30 seconds if value changes by 10 (0.1V)
zbElectricalMeasurement.setDCReporting(ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, 0, 30, 10); // report every 30 seconds if value changes by 10 (0.1A)
zbElectricalMeasurement.setDCReporting(ZIGBEE_DC_MEASUREMENT_TYPE_POWER, 0, 30, 10); // report every 30 seconds if value changes by 10 (0.1W)
}
void loop() {
static uint32_t timeCounter = 0;
static uint8_t randomizer = 0;
// Read ADC value and update the analog value every 2s
if (!(timeCounter++ % 20)) { // delaying for 100ms x 20 = 2s
int16_t voltage_mv = (int16_t)(analogReadMilliVolts(analogPin));
int16_t current_ma = randomizer; //0-255mA
int16_t power_mw = voltage_mv * current_ma / 1000; //calculate power in mW
Serial.printf("Updating DC voltage to %d mV, current to %d mA, power to %d mW\r\n", voltage_mv, current_ma, power_mw);
zbElectricalMeasurement.setDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE, voltage_mv);
zbElectricalMeasurement.setDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT, current_ma);
zbElectricalMeasurement.setDCMeasurement(ZIGBEE_DC_MEASUREMENT_TYPE_POWER, power_mw);
// Analog input supports reporting
zbElectricalMeasurement.reportDC(ZIGBEE_DC_MEASUREMENT_TYPE_VOLTAGE);
zbElectricalMeasurement.reportDC(ZIGBEE_DC_MEASUREMENT_TYPE_CURRENT);
zbElectricalMeasurement.reportDC(ZIGBEE_DC_MEASUREMENT_TYPE_POWER);
randomizer += 10;
}
// Checking button for factory reset and reporting
if (digitalRead(button) == LOW) { // Push button pressed
// Key debounce handling
delay(100);
int startTime = millis();
while (digitalRead(button) == LOW) {
delay(50);
if ((millis() - startTime) > 3000) {
// If key pressed for more than 3secs, factory reset Zigbee and reboot
Serial.println("Resetting Zigbee to factory and rebooting in 1s.");
delay(1000);
Zigbee.factoryReset();
}
}
}
delay(100);
}
AC Electrical Measurement
// Copyright 2025 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
/**
* @brief This example demonstrates Zigbee electrical AC measurement device with multi-phase support.
*
* The example demonstrates how to use Zigbee library to create a router device that measures
* AC electrical parameters like voltage, current, power, power factor and frequency across
* three phases (A, B, C). This allows monitoring of three-phase power systems commonly used
* in industrial and commercial applications.
*
* The device measures:
* - Per phase: voltage, current, power, power factor
* - Shared: frequency (common across all phases)
*
* Proper Zigbee mode must be selected in Tools->Zigbee mode
* and also the correct partition scheme must be selected in Tools->Partition Scheme.
*
* Please check the README.md for instructions and more detailed description.
*
* Created by Jan Procházka (https://github.com/P-R-O-C-H-Y/)
*/
// Recommended to use Router mode, as this type of device is expected to be mains powered.
#ifndef ZIGBEE_MODE_ZCZR
#error "Zigbee coordinator/router mode is not selected in Tools->Zigbee mode"
#endif
#include "Zigbee.h"
/* Zigbee AC measurement device configuration */
#define AC_ELECTRICAL_MEASUREMENT_ENDPOINT_NUMBER 1
uint8_t analogPin = A0;
uint8_t button = BOOT_PIN;
ZigbeeElectricalMeasurement zbElectricalMeasurement = ZigbeeElectricalMeasurement(AC_ELECTRICAL_MEASUREMENT_ENDPOINT_NUMBER);
void onAnalogOutputChange(float analog_output) {
Serial.printf("Received analog output change: %.1f\r\n", analog_output);
}
void setup() {
Serial.begin(115200);
Serial.println("Starting...");
// Init button switch
pinMode(button, INPUT_PULLUP);
// Set analog resolution to 10 bits
analogReadResolution(10);
// Optional: set Zigbee device name and model
zbElectricalMeasurement.setManufacturerAndModel("Espressif", "ZigbeeElectricalMeasurementAC");
// Add analog clusters to Zigbee Analog according your needs
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_A);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_A);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_A);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_B);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_B);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_B);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_C);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_C);
zbElectricalMeasurement.addACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_C);
zbElectricalMeasurement.addACMeasurement(
ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY, ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC
); // frequency is not phase specific (shared)
// Recommended: set Multiplier/Divisor for the measurements (common for all phases)
zbElectricalMeasurement.setACMultiplierDivisor(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, 1, 100); // 1/100 = 0.01V (1 unit of measurement = 0.01V = 10mV)
zbElectricalMeasurement.setACMultiplierDivisor(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, 1, 1000); // 1/1000 = 0.001A (1 unit of measurement = 0.001A = 1mA)
zbElectricalMeasurement.setACMultiplierDivisor(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, 1, 10); // 1/10 = 0.1W (1 unit of measurement = 0.1W = 100mW)
zbElectricalMeasurement.setACMultiplierDivisor(ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY, 1, 1000); // 1/1000 = 0.001Hz (1 unit of measurement = 0.001Hz = 1mHz)
// Optional: set Min/max values for the measurements
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_A, 0, 30000); // 0-300.00V
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_A, 0, 10000); // 0-10.000A
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_A, 0, 32000); // 0-3200.0W
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_B, 0, 30000); // 0-300.00V
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_B, 0, 10000); // 0-10.000A
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_B, 0, 32000); // 0-3200.0W
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_C, 0, 30000); // 0-300.00V
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_C, 0, 10000); // 0-10.000A
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_C, 0, 32000); // 0-3200.0W
zbElectricalMeasurement.setACMinMaxValue(ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY, ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, 0, 65000); // 0-65.000Hz
// Add endpoints to Zigbee Core
Zigbee.addEndpoint(&zbElectricalMeasurement);
Serial.println("Starting Zigbee...");
// When all EPs are registered, start Zigbee in Router mode
if (!Zigbee.begin(ZIGBEE_ROUTER)) {
Serial.println("Zigbee failed to start!");
Serial.println("Rebooting...");
ESP.restart();
} else {
Serial.println("Zigbee started successfully!");
}
Serial.println("Connecting to network");
while (!Zigbee.connected()) {
Serial.print(".");
delay(100);
}
Serial.println("Connected");
}
void loop() {
static uint32_t timeCounter = 0;
static uint8_t randomizer = 0;
// Read ADC value and update the analog value every 2s
if (!(timeCounter++ % 20)) { // delaying for 100ms x 20 = 2s
uint16_t voltage = 23000 + randomizer; // 230.00 V
uint16_t current = analogReadMilliVolts(analogPin); // demonstrates approx 0-3.3A
int16_t power = ((voltage / 100) * (current / 1000) * 10); //calculate power in W
uint16_t frequency = 50135; // 50.000 Hz
Serial.printf("Updating AC voltage to %d (0.01V), current to %d (mA), power to %d (0.1W), frequency to %d (mHz)\r\n", voltage, current, power, frequency);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_A, voltage);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_A, current);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_A, power);
// Phase B demonstrates phase shift
current += 500;
voltage += 500;
power = ((voltage / 100) * (current / 1000) * 10); //calculate power in W
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_B, voltage);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_B, current);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_B, power);
// Phase C demonstrates phase shift
current += 500;
voltage += 500;
power = ((voltage / 100) * (current / 1000) * 10); //calculate power in W
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_C, voltage);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_C, current);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_C, power);
zbElectricalMeasurement.setACMeasurement(ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY, ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC, frequency);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_A);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_A);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_A);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_B);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_B);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_B);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_VOLTAGE, ZIGBEE_AC_PHASE_TYPE_C);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_CURRENT, ZIGBEE_AC_PHASE_TYPE_C);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_POWER, ZIGBEE_AC_PHASE_TYPE_C);
zbElectricalMeasurement.reportAC(ZIGBEE_AC_MEASUREMENT_TYPE_FREQUENCY, ZIGBEE_AC_PHASE_TYPE_NON_SPECIFIC);
randomizer += 10;
}
// Checking button for factory reset and reporting
if (digitalRead(button) == LOW) { // Push button pressed
// Key debounce handling
delay(100);
int startTime = millis();
while (digitalRead(button) == LOW) {
delay(50);
if ((millis() - startTime) > 3000) {
// If key pressed for more than 3secs, factory reset Zigbee and reboot
Serial.println("Resetting Zigbee to factory and rebooting in 1s.");
delay(1000);
Zigbee.factoryReset();
}
}
}
delay(100);
}