add HA climate control with cool for SRC thermostat controls

This commit is contained in:
proddy
2025-12-14 21:10:29 +01:00
parent 6bc40ce2e1
commit bc870b2aa2
2 changed files with 39 additions and 38 deletions

View File

@@ -1701,9 +1701,9 @@ std::string EMSdevice::get_metrics_prometheus(const int8_t tag) {
// Helper function to check if a device value type is supported for Prometheus metrics
auto is_supported_type = [](uint8_t type) -> bool {
return type == DeviceValueType::BOOL || type == DeviceValueType::UINT8 || type == DeviceValueType::INT8
|| type == DeviceValueType::UINT16 || type == DeviceValueType::INT16 || type == DeviceValueType::UINT24
|| type == DeviceValueType::UINT32 || type == DeviceValueType::TIME || type == DeviceValueType::ENUM;
return type == DeviceValueType::BOOL || type == DeviceValueType::UINT8 || type == DeviceValueType::INT8 || type == DeviceValueType::UINT16
|| type == DeviceValueType::INT16 || type == DeviceValueType::UINT24 || type == DeviceValueType::UINT32 || type == DeviceValueType::TIME
|| type == DeviceValueType::ENUM;
};
// Dynamically reserve memory for the result
@@ -2086,17 +2086,6 @@ void EMSdevice::mqtt_ha_entity_config_create() {
uint16_t count = 0;
const char * const ** mode_options = nullptr;
// if it's a thermostat go fetch the list of modes
if (device_type() == EMSdevice::DeviceType::THERMOSTAT) {
for (auto & dv : devicevalues_) {
// make sure it's a type DeviceValueType::ENUM
if ((dv.type == DeviceValueType::ENUM) && !strcmp(dv.short_name, FL_(mode)[0])) {
// get options
mode_options = dv.options;
break;
}
}
}
// check the state of each of the device values
// create the discovery topic if if hasn't already been created, not a command (like reset) and is active and visible
@@ -2109,6 +2098,18 @@ void EMSdevice::mqtt_ha_entity_config_create() {
bool needs_update = !has_config_created || (haclimate_value == 1 ? has_climate_no_rt : !has_climate_no_rt);
if (needs_update) {
// if it's a thermostat go fetch the list of modes
if (device_type() == EMSdevice::DeviceType::THERMOSTAT) {
for (auto & dv : devicevalues_) {
// make sure it's a type DeviceValueType::ENUM
if ((dv.type == DeviceValueType::ENUM) && !strcmp(dv.short_name, FL_(mode)[0])) {
// get options
mode_options = dv.options;
break;
}
}
}
bool has_room_temp = (haclimate_value == 1);
if (Mqtt::publish_ha_climate_config(dv, has_room_temp, mode_options, false)) {
if (has_room_temp) {
@@ -2130,9 +2131,12 @@ void EMSdevice::mqtt_ha_entity_config_create() {
create_device_config = false; // only create the main config once
count++;
}
// SRC thermostats mapped to connect/src1/...
if (dv.tag >= DeviceValueTAG::TAG_SRC1 && dv.tag <= DeviceValueTAG::TAG_SRC16 && !strcmp(dv.short_name, FL_(selRoomTemp)[0])) {
Mqtt::publish_ha_climate_config(dv, true, mode_options, false);
// add all modes - auto, heat, off, cool
// https://github.com/emsesp/EMS-ESP32/issues/2636
Mqtt::publish_ha_climate_config(dv, true, nullptr, false);
}
#ifndef EMSESP_STANDALONE

View File

@@ -1367,42 +1367,39 @@ bool Mqtt::publish_ha_climate_config(const DeviceValue & dv, const bool has_room
// map EMS modes to HA climate modes
// EMS modes: auto, manual, heat, off, night, day, nofrost, eco, comfort, cool)
// HA supports: auto, off, cool, heat, dry, fan_only
// we map day and manual to heat
bool found_auto = true;
bool found_heat = true;
bool found_off = true;
bool found_cool = true;
if (mode_options != nullptr) {
// scan through mode_options and add to modes
bool found_auto = false;
bool found_heat = false;
bool found_off = false;
bool found_cool = false;
for (uint8_t i = 0; i < Helpers::count_items(mode_options); i++) {
const char * mode = mode_options[i][0]; // take EN
if (!strcmp(mode, FL_(auto)[0])) {
found_auto = true;
} else if (!strcmp(mode, FL_(heat)[0]) || !strcmp(mode, FL_(day)[0]) || !strcmp(mode, FL_(manual)[0])) {
found_heat = true;
found_heat = true; // we map day and manual to heat
} else if (!strcmp(mode, FL_(off)[0])) {
found_off = true;
} else if (!strcmp(mode, FL_(cool)[0])) {
found_cool = true;
}
}
}
// only add modes if we found at least one
if (found_auto || found_heat || found_off || found_cool) {
JsonArray modes = doc["modes"].to<JsonArray>();
if (found_auto) {
modes.add("auto");
}
if (found_heat) {
modes.add("heat");
}
if (found_off) {
modes.add("off");
}
if (found_cool) {
modes.add("cool");
}
}
// only add modes if we found at least one
JsonArray modes = doc["modes"].to<JsonArray>();
if (found_auto) {
modes.add("auto");
}
if (found_heat) {
modes.add("heat");
}
if (found_off) {
modes.add("off");
}
if (found_cool) {
modes.add("cool");
}
add_ha_dev_section(doc.as<JsonObject>(), devicename, nullptr, nullptr, nullptr, false); // add dev section