Skip to content

Commit 0aada09

Browse files
feat(zigbee): Support min/max setting for Analog EP (#11451)
* feat(zigbee): Support min max for Analog EP * feat(zigbee): Use cfloat FLT_MAX * ci(pre-commit): Apply automatic fixes --------- Co-authored-by: pre-commit-ci-lite[bot] <117423508+pre-commit-ci-lite[bot]@users.noreply.github.com>
1 parent 0007815 commit 0aada09

File tree

3 files changed

+91
-0
lines changed

3 files changed

+91
-0
lines changed

libraries/Zigbee/examples/Zigbee_Analog_Input_Output/Zigbee_Analog_Input_Output.ino

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,9 @@ void setup() {
7272
zbAnalogDevice.setAnalogOutputDescription("Fan Speed (RPM)");
7373
zbAnalogDevice.setAnalogOutputResolution(1);
7474

75+
// Set the min and max values for the analog output which is used by HA to limit the range of the analog output
76+
zbAnalogDevice.setAnalogOutputMinMax(-10000, 10000); //-10000 to 10000 RPM
77+
7578
// If analog output cluster is added, set callback function for analog output change
7679
zbAnalogDevice.onAnalogOutputChange(onAnalogOutputChange);
7780

libraries/Zigbee/src/ep/ZigbeeAnalog.cpp

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
#include "ZigbeeAnalog.h"
22
#if CONFIG_ZB_ENABLED
3+
#include <cfloat>
34

45
ZigbeeAnalog::ZigbeeAnalog(uint8_t endpoint) : ZigbeeEP(endpoint) {
56
_device_id = ESP_ZB_HA_SIMPLE_SENSOR_DEVICE_ID;
@@ -20,6 +21,8 @@ bool ZigbeeAnalog::addAnalogInput() {
2021
"Analog Input";
2122
uint32_t application_type = 0x00000000 | (ESP_ZB_ZCL_AI_GROUP_ID << 24);
2223
float resolution = 0.1; // Default resolution of 0.1
24+
float min = -FLT_MAX; // Default min value for float
25+
float max = FLT_MAX; // Default max value for float
2326

2427
esp_err_t ret = esp_zb_analog_input_cluster_add_attr(esp_zb_analog_input_cluster, ESP_ZB_ZCL_ATTR_ANALOG_INPUT_DESCRIPTION_ID, (void *)default_description);
2528
if (ret != ESP_OK) {
@@ -39,11 +42,24 @@ bool ZigbeeAnalog::addAnalogInput() {
3942
return false;
4043
}
4144

45+
ret = esp_zb_analog_input_cluster_add_attr(esp_zb_analog_input_cluster, ESP_ZB_ZCL_ATTR_ANALOG_INPUT_MIN_PRESENT_VALUE_ID, (void *)&min);
46+
if (ret != ESP_OK) {
47+
log_e("Failed to set min value: 0x%x: %s", ret, esp_err_to_name(ret));
48+
return false;
49+
}
50+
51+
ret = esp_zb_analog_input_cluster_add_attr(esp_zb_analog_input_cluster, ESP_ZB_ZCL_ATTR_ANALOG_INPUT_MAX_PRESENT_VALUE_ID, (void *)&max);
52+
if (ret != ESP_OK) {
53+
log_e("Failed to set max value: 0x%x: %s", ret, esp_err_to_name(ret));
54+
return false;
55+
}
56+
4257
ret = esp_zb_cluster_list_add_analog_input_cluster(_cluster_list, esp_zb_analog_input_cluster, ESP_ZB_ZCL_CLUSTER_SERVER_ROLE);
4358
if (ret != ESP_OK) {
4459
log_e("Failed to add Analog Input cluster: 0x%x: %s", ret, esp_err_to_name(ret));
4560
return false;
4661
}
62+
4763
_analog_clusters |= ANALOG_INPUT;
4864
return true;
4965
}
@@ -76,6 +92,8 @@ bool ZigbeeAnalog::addAnalogOutput() {
7692
"Analog Output";
7793
uint32_t application_type = 0x00000000 | (ESP_ZB_ZCL_AO_GROUP_ID << 24);
7894
float resolution = 1; // Default resolution of 1
95+
float min = -FLT_MAX; // Default min value for float
96+
float max = FLT_MAX; // Default max value for float
7997

8098
esp_err_t ret =
8199
esp_zb_analog_output_cluster_add_attr(esp_zb_analog_output_cluster, ESP_ZB_ZCL_ATTR_ANALOG_OUTPUT_DESCRIPTION_ID, (void *)default_description);
@@ -96,6 +114,18 @@ bool ZigbeeAnalog::addAnalogOutput() {
96114
return false;
97115
}
98116

117+
ret = esp_zb_analog_output_cluster_add_attr(esp_zb_analog_output_cluster, ESP_ZB_ZCL_ATTR_ANALOG_OUTPUT_MIN_PRESENT_VALUE_ID, (void *)&min);
118+
if (ret != ESP_OK) {
119+
log_e("Failed to set min value: 0x%x: %s", ret, esp_err_to_name(ret));
120+
return false;
121+
}
122+
123+
ret = esp_zb_analog_output_cluster_add_attr(esp_zb_analog_output_cluster, ESP_ZB_ZCL_ATTR_ANALOG_OUTPUT_MAX_PRESENT_VALUE_ID, (void *)&max);
124+
if (ret != ESP_OK) {
125+
log_e("Failed to set max value: 0x%x: %s", ret, esp_err_to_name(ret));
126+
return false;
127+
}
128+
99129
ret = esp_zb_cluster_list_add_analog_output_cluster(_cluster_list, esp_zb_analog_output_cluster, ESP_ZB_ZCL_CLUSTER_SERVER_ROLE);
100130
if (ret != ESP_OK) {
101131
log_e("Failed to add Analog Output cluster: 0x%x: %s", ret, esp_err_to_name(ret));
@@ -376,4 +406,58 @@ bool ZigbeeAnalog::setAnalogOutputResolution(float resolution) {
376406
return true;
377407
}
378408

409+
bool ZigbeeAnalog::setAnalogOutputMinMax(float min, float max) {
410+
if (!(_analog_clusters & ANALOG_OUTPUT)) {
411+
log_e("Analog Output cluster not added");
412+
return false;
413+
}
414+
415+
esp_zb_attribute_list_t *analog_output_cluster =
416+
esp_zb_cluster_list_get_cluster(_cluster_list, ESP_ZB_ZCL_CLUSTER_ID_ANALOG_OUTPUT, ESP_ZB_ZCL_CLUSTER_SERVER_ROLE);
417+
if (analog_output_cluster == nullptr) {
418+
log_e("Failed to get analog output cluster");
419+
return false;
420+
}
421+
422+
esp_err_t ret = esp_zb_cluster_update_attr(analog_output_cluster, ESP_ZB_ZCL_ATTR_ANALOG_OUTPUT_MIN_PRESENT_VALUE_ID, (void *)&min);
423+
if (ret != ESP_OK) {
424+
log_e("Failed to set min value: 0x%x: %s", ret, esp_err_to_name(ret));
425+
return false;
426+
}
427+
428+
ret = esp_zb_cluster_update_attr(analog_output_cluster, ESP_ZB_ZCL_ATTR_ANALOG_OUTPUT_MAX_PRESENT_VALUE_ID, (void *)&max);
429+
if (ret != ESP_OK) {
430+
log_e("Failed to set max value: 0x%x: %s", ret, esp_err_to_name(ret));
431+
return false;
432+
}
433+
return true;
434+
}
435+
436+
bool ZigbeeAnalog::setAnalogInputMinMax(float min, float max) {
437+
if (!(_analog_clusters & ANALOG_INPUT)) {
438+
log_e("Analog Input cluster not added");
439+
return false;
440+
}
441+
442+
esp_zb_attribute_list_t *analog_input_cluster =
443+
esp_zb_cluster_list_get_cluster(_cluster_list, ESP_ZB_ZCL_CLUSTER_ID_ANALOG_INPUT, ESP_ZB_ZCL_CLUSTER_SERVER_ROLE);
444+
if (analog_input_cluster == nullptr) {
445+
log_e("Failed to get analog input cluster");
446+
return false;
447+
}
448+
449+
esp_err_t ret = esp_zb_cluster_update_attr(analog_input_cluster, ESP_ZB_ZCL_ATTR_ANALOG_INPUT_MIN_PRESENT_VALUE_ID, (void *)&min);
450+
if (ret != ESP_OK) {
451+
log_e("Failed to set min value: 0x%x: %s", ret, esp_err_to_name(ret));
452+
return false;
453+
}
454+
455+
ret = esp_zb_cluster_update_attr(analog_input_cluster, ESP_ZB_ZCL_ATTR_ANALOG_INPUT_MAX_PRESENT_VALUE_ID, (void *)&max);
456+
if (ret != ESP_OK) {
457+
log_e("Failed to set max value: 0x%x: %s", ret, esp_err_to_name(ret));
458+
return false;
459+
}
460+
return true;
461+
}
462+
379463
#endif // CONFIG_ZB_ENABLED

libraries/Zigbee/src/ep/ZigbeeAnalog.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,10 @@ class ZigbeeAnalog : public ZigbeeEP {
4141
bool setAnalogOutputDescription(const char *description);
4242
bool setAnalogOutputResolution(float resolution);
4343

44+
// Set the min and max values for the analog Input/Output
45+
bool setAnalogOutputMinMax(float min, float max);
46+
bool setAnalogInputMinMax(float min, float max);
47+
4448
// Use to set a cb function to be called on analog output change
4549
void onAnalogOutputChange(void (*callback)(float analog)) {
4650
_on_analog_output_change = callback;

0 commit comments

Comments
 (0)