55
66from dataclasses import asdict , dataclass
77from typing import Any
8+ from packaging .version import Version
89
910from homeassistant .components .climate import (
1011 ENTITY_ID_FORMAT ,
3536 CONF_HA_SENSOR_INDOOR_TEMPERATURE ,
3637 CONF_HA_SENSOR_PREFIX ,
3738 DOMAIN ,
39+ LOGGER ,
3840 LUX_STATE_ICON_MAP ,
3941 LUX_STATE_ICON_MAP_COOL ,
4042 DeviceKey ,
98100}
99101
100102THERMOSTATS : list [LuxtronikClimateDescription ] = [
103+ LuxtronikClimateDescription (
104+ key = SensorKey .HEATING ,
105+ hvac_modes = [HVACMode .HEAT , HVACMode .OFF ],
106+ hvac_mode_mapping = HVAC_MODE_MAPPING_HEAT ,
107+ hvac_action_mapping = HVAC_ACTION_MAPPING_HEAT ,
108+ preset_modes = [PRESET_NONE , PRESET_AWAY , PRESET_BOOST ],
109+ supported_features = ClimateEntityFeature .PRESET_MODE
110+ | ClimateEntityFeature .TURN_OFF # noqa: W503
111+ | ClimateEntityFeature .TURN_ON # noqa: W503
112+ | ClimateEntityFeature .TARGET_TEMPERATURE , # noqa: W503
113+ luxtronik_key = LuxParameter .P0003_MODE_HEATING ,
114+ luxtronik_key_current_temperature = LuxCalculation .C0227_ROOM_THERMOSTAT_TEMPERATURE ,
115+ luxtronik_key_target_temperature = LuxParameter .P1148_HEATING_TARGET_TEMP_ROOM_THERMOSTAT ,
116+ # luxtronik_key_has_target_temperature=LuxParameter
117+ luxtronik_key_current_action = LuxCalculation .C0080_STATUS ,
118+ luxtronik_action_active = LuxOperationMode .heating .value ,
119+ # luxtronik_key_target_temperature_high=LuxParameter,
120+ # luxtronik_key_target_temperature_low=LuxParameter,
121+ icon_by_state = LUX_STATE_ICON_MAP ,
122+ temperature_unit = UnitOfTemperature .CELSIUS ,
123+ visibility = LuxVisibility .V0023_FLOW_IN_TEMPERATURE ,
124+ device_key = DeviceKey .heating ,
125+ min_firmware_version = Version ("3.90.1" ),
126+ ),
101127 LuxtronikClimateDescription (
102128 key = SensorKey .HEATING ,
103129 hvac_modes = [HVACMode .HEAT , HVACMode .OFF ],
122148 temperature_unit = UnitOfTemperature .CELSIUS ,
123149 visibility = LuxVisibility .V0023_FLOW_IN_TEMPERATURE ,
124150 device_key = DeviceKey .heating ,
125- ),
151+ max_firmware_version = Version ("3.90.0" ),
152+ ),
126153 LuxtronikClimateDescription (
127154 key = SensorKey .COOLING ,
128155 hvac_modes = [HVACMode .COOL , HVACMode .OFF ],
@@ -270,38 +297,43 @@ def _handle_coordinator_update(
270297 self ._attr_current_temperature = state_as_number_or_none (temp , 0.0 )
271298 elif key != LuxCalculation .UNSET :
272299 self ._attr_current_temperature = get_sensor_data (data , key )
300+
273301 key_tar = self .entity_description .luxtronik_key_target_temperature
274- if key_tar != LuxParameter .UNSET :
302+ if key_tar == LuxParameter .P1148_HEATING_TARGET_TEMP_ROOM_THERMOSTAT :
303+ self ._attr_target_temperature = get_sensor_data (data , key_tar ) / 10
304+ elif key_tar != LuxParameter .UNSET :
275305 self ._attr_target_temperature = get_sensor_data (data , key_tar )
276- correction_factor = get_sensor_data (
277- data , self .entity_description .luxtronik_key_correction_factor .value , False
278- )
279- # LOGGER.info(f"self._attr_target_temperature={self._attr_target_temperature}")
280- # LOGGER.info(f"self._attr_current_temperature={self._attr_current_temperature}")
281- # LOGGER.info(f"correction_factor={correction_factor}")
282- # LOGGER.info(f"lux_action={lux_action}")
283- # LOGGER.info(f"_attr_hvac_action={self._attr_hvac_action}")
284- if (
285- self ._attr_target_temperature is not None
286- and self ._attr_current_temperature is not None # noqa: W503
287- and self ._attr_current_temperature > 0.0
288- and correction_factor is not None # noqa: W503
289- ):
290- delta_temp = self ._attr_target_temperature - self ._attr_current_temperature
291- correction = round (
292- delta_temp * (correction_factor / 100.0 ), 1
293- ) # correction_factor is in %, so need to divide by 100
294- key_correction_target = (
295- self .entity_description .luxtronik_key_correction_target .value
306+
307+ if key_tar == LuxCalculation .C0228_ROOM_THERMOSTAT_TEMPERATURE_TARGET :
308+ correction_factor = get_sensor_data (
309+ data , self .entity_description .luxtronik_key_correction_factor .value , False
296310 )
297- correction_current = get_sensor_data (data , key_correction_target )
298- # LOGGER.info(f"correction_current={correction_current}")
299- # LOGGER.info(f"correction={correction}")
300- if correction_current is None or correction_current != correction :
301- # LOGGER.info(f'key_correction_target={key_correction_target.split(".")[1]}')
302- _ = self .coordinator .write (
303- key_correction_target .split ("." )[1 ], correction
304- ) # mypy: allow-unused-coroutine
311+ # LOGGER.info(f"self._attr_target_temperature={self._attr_target_temperature}")
312+ # LOGGER.info(f"self._attr_current_temperature={self._attr_current_temperature}")
313+ # LOGGER.info(f"correction_factor={correction_factor}")
314+ # LOGGER.info(f"lux_action={lux_action}")
315+ # LOGGER.info(f"_attr_hvac_action={self._attr_hvac_action}")
316+ if (
317+ self ._attr_target_temperature is not None
318+ and self ._attr_current_temperature is not None # noqa: W503
319+ and self ._attr_current_temperature > 0.0
320+ and correction_factor is not None # noqa: W503
321+ ):
322+ delta_temp = self ._attr_target_temperature - self ._attr_current_temperature
323+ correction = round (
324+ delta_temp * (correction_factor / 100.0 ), 1
325+ ) # correction_factor is in %, so need to divide by 100
326+ key_correction_target = (
327+ self .entity_description .luxtronik_key_correction_target .value
328+ )
329+ correction_current = get_sensor_data (data , key_correction_target )
330+ # LOGGER.info(f"correction_current={correction_current}")
331+ # LOGGER.info(f"correction={correction}")
332+ if correction_current is None or correction_current != correction :
333+ # LOGGER.info(f'key_correction_target={key_correction_target.split(".")[1]}')
334+ _ = self .coordinator .write (
335+ key_correction_target .split ("." )[1 ], correction
336+ ) # mypy: allow-unused-coroutine
305337
306338 super ()._handle_coordinator_update ()
307339
@@ -312,12 +344,19 @@ async def _async_set_lux_mode(self, lux_mode: str) -> None:
312344
313345 async def async_set_temperature (self , ** kwargs : Any ) -> None :
314346 """Set new target temperature."""
315- value = kwargs .get (ATTR_TEMPERATURE )
316- lux_key = LuxParameter .P1148_HEATING_TARGET_TEMP_ROOM_THERMOSTAT
317- data : LuxtronikCoordinatorData | None = await self .coordinator .async_write (
318- lux_key .split ("." )[1 ], int (value * 10 )
319- )
320- self ._handle_coordinator_update (data )
347+ self ._attr_target_temperature = kwargs [ATTR_TEMPERATURE ]
348+ key_tar = self .entity_description .luxtronik_key_target_temperature
349+ LOGGER .info (f"async_set_temperature={ key_tar } ,{ self ._attr_target_temperature } " )
350+ if key_tar == LuxParameter .P1148_HEATING_TARGET_TEMP_ROOM_THERMOSTAT :
351+ data : LuxtronikCoordinatorData | None = await self .coordinator .async_write (
352+ key_tar .split ("." )[1 ], int (self ._attr_target_temperature * 10 )
353+ )
354+ self ._handle_coordinator_update (data )
355+ elif key_tar != LuxCalculation .C0228_ROOM_THERMOSTAT_TEMPERATURE_TARGET :
356+ data : LuxtronikCoordinatorData | None = await self .coordinator .async_write (
357+ key_tar .split ("." )[1 ], int (self ._attr_target_temperature )
358+ )
359+ self ._handle_coordinator_update (data )
321360
322361 async def async_turn_off (self ) -> None :
323362 await self .async_set_hvac_mode (HVACMode .OFF )
0 commit comments