Move set_supported_custom_* out of traits() hot path

- Midea: frost protection preset now set once in on_status_change()
  when autoconf completes, guarded by a flag
- BedJet: custom fan modes and presets moved from traits() to setup()
- Test fixture: use has_custom_fan_mode() instead of nullptr check
This commit is contained in:
J. Nick Koston
2026-03-26 15:36:56 -10:00
parent d54fd0ef69
commit 317db8438c
5 changed files with 20 additions and 14 deletions
@@ -61,6 +61,15 @@ void BedJetClimate::dump_config() {
}
void BedJetClimate::setup() {
// Set custom modes once during setup — stored on Climate base class, wired via get_traits()
this->set_supported_custom_fan_modes(BEDJET_FAN_STEP_NAMES);
this->set_supported_custom_presets({
this->heating_mode_ == HEAT_MODE_EXTENDED ? "LTD HT" : "EXT HT",
"M1",
"M2",
"M3",
});
// restore set points
auto restore = this->restore_state_();
if (restore.has_value()) {
@@ -48,16 +48,8 @@ class BedJetClimate : public climate::Climate, public BedJetClient, public Polli
// Climate doesn't have a "TURBO" mode, but we can use the BOOST preset instead.
climate::CLIMATE_PRESET_BOOST,
});
// Custom fan modes and presets are stored on Climate base class and wired via get_traits()
// It would be better if we had a slider for the fan modes.
this->set_supported_custom_fan_modes(BEDJET_FAN_STEP_NAMES);
// String literals are stored in rodata and valid for program lifetime
this->set_supported_custom_presets({
this->heating_mode_ == HEAT_MODE_EXTENDED ? "LTD HT" : "EXT HT",
"M1",
"M2",
"M3",
});
// Custom fan modes and presets are set once in setup(), stored on Climate base class,
// and wired automatically via get_traits()
traits.set_visual_min_temperature(19.0);
traits.set_visual_max_temperature(43.0);
traits.set_visual_temperature_step(1.0);
+6 -2
View File
@@ -24,6 +24,12 @@ template<typename T> void update_property(T &property, const T &value, bool &fla
}
void AirConditioner::on_status_change() {
// Set frost protection custom preset once when autoconf completes
if (this->base_.getAutoconfStatus() == dudanov::midea::AUTOCONF_OK &&
this->base_.getCapabilities().supportFrostProtectionPreset() && !this->frost_protection_set_) {
this->set_supported_custom_presets({Constants::FREEZE_PROTECTION});
this->frost_protection_set_ = true;
}
bool need_publish = false;
update_property(this->target_temperature, this->base_.getTargetTemp(), need_publish);
update_property(this->current_temperature, this->base_.getIndoorTemp(), need_publish);
@@ -99,8 +105,6 @@ ClimateTraits AirConditioner::traits() {
traits.add_supported_fan_mode(ClimateFanMode::CLIMATE_FAN_HIGH);
if (this->base_.getAutoconfStatus() == dudanov::midea::AUTOCONF_OK) {
Converters::to_climate_traits(traits, this->base_.getCapabilities());
if (this->base_.getCapabilities().supportFrostProtectionPreset())
this->set_supported_custom_presets({Constants::FREEZE_PROTECTION});
}
if (!traits.get_supported_modes().empty())
traits.add_supported_mode(ClimateMode::CLIMATE_MODE_OFF);
@@ -55,6 +55,7 @@ class AirConditioner : public ApplianceBase<dudanov::midea::ac::AirConditioner>,
ClimateModeMask supported_modes_{};
ClimateSwingModeMask supported_swing_modes_{};
ClimatePresetMask supported_presets_{};
bool frost_protection_set_{false};
Sensor *outdoor_sensor_{nullptr};
Sensor *humidity_sensor_{nullptr};
Sensor *power_sensor_{nullptr};
@@ -44,10 +44,10 @@ class LegacyClimate : public climate::Climate, public Component {
if (call.get_target_temperature().has_value()) {
this->target_temperature = *call.get_target_temperature();
}
if (call.get_custom_fan_mode() != nullptr) {
if (call.has_custom_fan_mode()) {
this->set_custom_fan_mode_(call.get_custom_fan_mode());
}
if (call.get_custom_preset() != nullptr) {
if (call.has_custom_preset()) {
this->set_custom_preset_(call.get_custom_preset());
}
this->publish_state();