Home Assistant Unofficial Reference 2024.12.1
light.py
Go to the documentation of this file.
1 """Support for LCN lights."""
2 
3 from collections.abc import Iterable
4 from functools import partial
5 from typing import Any
6 
7 import pypck
8 
10  ATTR_BRIGHTNESS,
11  ATTR_TRANSITION,
12  DOMAIN as DOMAIN_LIGHT,
13  ColorMode,
14  LightEntity,
15  LightEntityFeature,
16 )
17 from homeassistant.config_entries import ConfigEntry
18 from homeassistant.const import CONF_DOMAIN, CONF_ENTITIES
19 from homeassistant.core import HomeAssistant
20 from homeassistant.helpers.entity_platform import AddEntitiesCallback
21 from homeassistant.helpers.typing import ConfigType
22 
23 from .const import (
24  ADD_ENTITIES_CALLBACKS,
25  CONF_DIMMABLE,
26  CONF_DOMAIN_DATA,
27  CONF_OUTPUT,
28  CONF_TRANSITION,
29  DOMAIN,
30  OUTPUT_PORTS,
31 )
32 from .entity import LcnEntity
33 from .helpers import InputType
34 
35 PARALLEL_UPDATES = 0
36 
37 
39  config_entry: ConfigEntry,
40  async_add_entities: AddEntitiesCallback,
41  entity_configs: Iterable[ConfigType],
42 ) -> None:
43  """Add entities for this domain."""
44  entities: list[LcnOutputLight | LcnRelayLight] = []
45  for entity_config in entity_configs:
46  if entity_config[CONF_DOMAIN_DATA][CONF_OUTPUT] in OUTPUT_PORTS:
47  entities.append(LcnOutputLight(entity_config, config_entry))
48  else: # in RELAY_PORTS
49  entities.append(LcnRelayLight(entity_config, config_entry))
50 
51  async_add_entities(entities)
52 
53 
55  hass: HomeAssistant,
56  config_entry: ConfigEntry,
57  async_add_entities: AddEntitiesCallback,
58 ) -> None:
59  """Set up LCN light entities from a config entry."""
60  add_entities = partial(
61  add_lcn_entities,
62  config_entry,
63  async_add_entities,
64  )
65 
66  hass.data[DOMAIN][config_entry.entry_id][ADD_ENTITIES_CALLBACKS].update(
67  {DOMAIN_LIGHT: add_entities}
68  )
69 
71  (
72  entity_config
73  for entity_config in config_entry.data[CONF_ENTITIES]
74  if entity_config[CONF_DOMAIN] == DOMAIN_LIGHT
75  ),
76  )
77 
78 
80  """Representation of a LCN light for output ports."""
81 
82  _attr_supported_features = LightEntityFeature.TRANSITION
83  _attr_is_on = False
84  _attr_brightness = 255
85 
86  def __init__(self, config: ConfigType, config_entry: ConfigEntry) -> None:
87  """Initialize the LCN light."""
88  super().__init__(config, config_entry)
89 
90  self.outputoutput = pypck.lcn_defs.OutputPort[config[CONF_DOMAIN_DATA][CONF_OUTPUT]]
91 
92  self._transition_transition = pypck.lcn_defs.time_to_ramp_value(
93  config[CONF_DOMAIN_DATA][CONF_TRANSITION] * 1000.0
94  )
95  self.dimmabledimmable = config[CONF_DOMAIN_DATA][CONF_DIMMABLE]
96 
97  self._is_dimming_to_zero_is_dimming_to_zero = False
98 
99  if self.dimmabledimmable:
100  self._attr_color_mode_attr_color_mode = ColorMode.BRIGHTNESS
101  else:
102  self._attr_color_mode_attr_color_mode = ColorMode.ONOFF
103  self._attr_supported_color_modes_attr_supported_color_modes = {self._attr_color_mode_attr_color_mode}
104 
105  async def async_added_to_hass(self) -> None:
106  """Run when entity about to be added to hass."""
107  await super().async_added_to_hass()
108  if not self.device_connectiondevice_connection.is_group:
109  await self.device_connectiondevice_connection.activate_status_request_handler(self.outputoutput)
110 
111  async def async_will_remove_from_hass(self) -> None:
112  """Run when entity will be removed from hass."""
113  await super().async_will_remove_from_hass()
114  if not self.device_connectiondevice_connection.is_group:
115  await self.device_connectiondevice_connection.cancel_status_request_handler(self.outputoutput)
116 
117  async def async_turn_on(self, **kwargs: Any) -> None:
118  """Turn the entity on."""
119  if ATTR_BRIGHTNESS in kwargs:
120  percent = int(kwargs[ATTR_BRIGHTNESS] / 255.0 * 100)
121  else:
122  percent = 100
123  if ATTR_TRANSITION in kwargs:
124  transition = pypck.lcn_defs.time_to_ramp_value(
125  kwargs[ATTR_TRANSITION] * 1000
126  )
127  else:
128  transition = self._transition_transition
129 
130  if not await self.device_connectiondevice_connection.dim_output(
131  self.outputoutput.value, percent, transition
132  ):
133  return
134  self._attr_is_on_attr_is_on_attr_is_on = True
135  self._is_dimming_to_zero_is_dimming_to_zero = False
136  self.async_write_ha_stateasync_write_ha_state()
137 
138  async def async_turn_off(self, **kwargs: Any) -> None:
139  """Turn the entity off."""
140  if ATTR_TRANSITION in kwargs:
141  transition = pypck.lcn_defs.time_to_ramp_value(
142  kwargs[ATTR_TRANSITION] * 1000
143  )
144  else:
145  transition = self._transition_transition
146 
147  if not await self.device_connectiondevice_connection.dim_output(
148  self.outputoutput.value, 0, transition
149  ):
150  return
151  self._is_dimming_to_zero_is_dimming_to_zero = bool(transition)
152  self._attr_is_on_attr_is_on_attr_is_on = False
153  self.async_write_ha_stateasync_write_ha_state()
154 
155  def input_received(self, input_obj: InputType) -> None:
156  """Set light state when LCN input object (command) is received."""
157  if (
158  not isinstance(input_obj, pypck.inputs.ModStatusOutput)
159  or input_obj.get_output_id() != self.outputoutput.value
160  ):
161  return
162 
163  self._attr_brightness_attr_brightness_attr_brightness = int(input_obj.get_percent() / 100.0 * 255)
164  if self._attr_brightness_attr_brightness_attr_brightness == 0:
165  self._is_dimming_to_zero_is_dimming_to_zero = False
166  if not self._is_dimming_to_zero_is_dimming_to_zero and self._attr_brightness_attr_brightness_attr_brightness is not None:
167  self._attr_is_on_attr_is_on_attr_is_on = self._attr_brightness_attr_brightness_attr_brightness > 0
168  self.async_write_ha_stateasync_write_ha_state()
169 
170 
172  """Representation of a LCN light for relay ports."""
173 
174  _attr_color_mode = ColorMode.ONOFF
175  _attr_supported_color_modes = {ColorMode.ONOFF}
176  _attr_is_on = False
177 
178  def __init__(self, config: ConfigType, config_entry: ConfigEntry) -> None:
179  """Initialize the LCN light."""
180  super().__init__(config, config_entry)
181 
182  self.outputoutput = pypck.lcn_defs.RelayPort[config[CONF_DOMAIN_DATA][CONF_OUTPUT]]
183 
184  async def async_added_to_hass(self) -> None:
185  """Run when entity about to be added to hass."""
186  await super().async_added_to_hass()
187  if not self.device_connectiondevice_connection.is_group:
188  await self.device_connectiondevice_connection.activate_status_request_handler(self.outputoutput)
189 
190  async def async_will_remove_from_hass(self) -> None:
191  """Run when entity will be removed from hass."""
192  await super().async_will_remove_from_hass()
193  if not self.device_connectiondevice_connection.is_group:
194  await self.device_connectiondevice_connection.cancel_status_request_handler(self.outputoutput)
195 
196  async def async_turn_on(self, **kwargs: Any) -> None:
197  """Turn the entity on."""
198  states = [pypck.lcn_defs.RelayStateModifier.NOCHANGE] * 8
199  states[self.outputoutput.value] = pypck.lcn_defs.RelayStateModifier.ON
200  if not await self.device_connectiondevice_connection.control_relays(states):
201  return
202  self._attr_is_on_attr_is_on_attr_is_on = True
203  self.async_write_ha_stateasync_write_ha_state()
204 
205  async def async_turn_off(self, **kwargs: Any) -> None:
206  """Turn the entity off."""
207  states = [pypck.lcn_defs.RelayStateModifier.NOCHANGE] * 8
208  states[self.outputoutput.value] = pypck.lcn_defs.RelayStateModifier.OFF
209  if not await self.device_connectiondevice_connection.control_relays(states):
210  return
211  self._attr_is_on_attr_is_on_attr_is_on = False
212  self.async_write_ha_stateasync_write_ha_state()
213 
214  def input_received(self, input_obj: InputType) -> None:
215  """Set light state when LCN input object (command) is received."""
216  if not isinstance(input_obj, pypck.inputs.ModStatusRelays):
217  return
218 
219  self._attr_is_on_attr_is_on_attr_is_on = input_obj.get_state(self.outputoutput.value)
220  self.async_write_ha_stateasync_write_ha_state()
None __init__(self, ConfigType config, ConfigEntry config_entry)
Definition: light.py:86
None async_turn_on(self, **Any kwargs)
Definition: light.py:117
None async_turn_off(self, **Any kwargs)
Definition: light.py:138
None input_received(self, InputType input_obj)
Definition: light.py:155
None input_received(self, InputType input_obj)
Definition: light.py:214
None async_turn_off(self, **Any kwargs)
Definition: light.py:205
None async_turn_on(self, **Any kwargs)
Definition: light.py:196
None __init__(self, ConfigType config, ConfigEntry config_entry)
Definition: light.py:178
None add_entities(AsusWrtRouter router, AddEntitiesCallback async_add_entities, set[str] tracked)
IssData update(pyiss.ISS iss)
Definition: __init__.py:33
None async_setup_entry(HomeAssistant hass, ConfigEntry config_entry, AddEntitiesCallback async_add_entities)
Definition: light.py:58
None add_lcn_entities(ConfigEntry config_entry, AddEntitiesCallback async_add_entities, Iterable[ConfigType] entity_configs)
Definition: light.py:42