class SomfyCover(SomfyEntity, RestoreEntity, CoverEntity): """Representation of a Somfy cover device.""" def __init__(self, coordinator, device_id, optimistic): """Initialize the Somfy device.""" super().__init__(coordinator, device_id) self.categories = set(self.device.categories) self.optimistic = optimistic self._closed = None self._is_opening = None self._is_closing = None self._cover = None self._create_device() def _create_device(self) -> Blind: """Update the device with the latest data.""" self._cover = Blind(self.device, self.coordinator.client) @property def supported_features(self) -> int: """Flag supported features.""" supported_features = 0 if self.has_capability("open"): supported_features |= SUPPORT_OPEN if self.has_capability("close"): supported_features |= SUPPORT_CLOSE if self.has_capability("stop"): supported_features |= SUPPORT_STOP if self.has_capability("position"): supported_features |= SUPPORT_SET_POSITION if self.has_capability("rotation"): supported_features |= (SUPPORT_OPEN_TILT | SUPPORT_CLOSE_TILT | SUPPORT_STOP_TILT | SUPPORT_SET_TILT_POSITION) return supported_features async def async_close_cover(self, **kwargs): """Close the cover.""" self._is_closing = True self.async_write_ha_state() try: # Blocks until the close command is sent await self.hass.async_add_executor_job(self._cover.close) self._closed = True finally: self._is_closing = None self.async_write_ha_state() async def async_open_cover(self, **kwargs): """Open the cover.""" self._is_opening = True self.async_write_ha_state() try: # Blocks until the open command is sent await self.hass.async_add_executor_job(self._cover.open) self._closed = False finally: self._is_opening = None self.async_write_ha_state() def stop_cover(self, **kwargs): """Stop the cover.""" self._cover.stop() def set_cover_position(self, **kwargs): """Move the cover shutter to a specific position.""" self._cover.set_position(100 - kwargs[ATTR_POSITION]) @property def device_class(self): """Return the device class.""" if self.categories & BLIND_DEVICE_CATEGORIES: return CoverDeviceClass.BLIND if self.categories & SHUTTER_DEVICE_CATEGORIES: return CoverDeviceClass.SHUTTER return None @property def current_cover_position(self): """Return the current position of cover shutter.""" if not self.has_state("position"): return None return 100 - self._cover.get_position() @property def is_opening(self): """Return if the cover is opening.""" if not self.optimistic: return None return self._is_opening @property def is_closing(self): """Return if the cover is closing.""" if not self.optimistic: return None return self._is_closing @property def is_closed(self) -> bool: """Return if the cover is closed.""" is_closed = None if self.has_state("position"): is_closed = self._cover.is_closed() elif self.optimistic: is_closed = self._closed return is_closed @property def current_cover_tilt_position(self) -> int: """Return current position of cover tilt. None is unknown, 0 is closed, 100 is fully open. """ if not self.has_state("orientation"): return None return 100 - self._cover.orientation def set_cover_tilt_position(self, **kwargs): """Move the cover tilt to a specific position.""" self._cover.orientation = 100 - kwargs[ATTR_TILT_POSITION] def open_cover_tilt(self, **kwargs): """Open the cover tilt.""" self._cover.orientation = 0 def close_cover_tilt(self, **kwargs): """Close the cover tilt.""" self._cover.orientation = 100 def stop_cover_tilt(self, **kwargs): """Stop the cover.""" self._cover.stop() async def async_added_to_hass(self): """Complete the initialization.""" await super().async_added_to_hass() if not self.optimistic: return # Restore the last state if we use optimistic last_state = await self.async_get_last_state() if last_state is not None and last_state.state in ( STATE_OPEN, STATE_CLOSED, ): self._closed = last_state.state == STATE_CLOSED
class SomfyCover(SomfyEntity, CoverEntity): """Representation of a Somfy cover device.""" def __init__(self, device, api, optimistic): """Initialize the Somfy device.""" super().__init__(device, api) self.cover = Blind(self.device, self.api) self.optimistic = optimistic self._closed = None async def async_update(self): """Update the device with the latest data.""" await super().async_update() self.cover = Blind(self.device, self.api) def close_cover(self, **kwargs): """Close the cover.""" if self.optimistic: self._closed = True self.cover.close() def open_cover(self, **kwargs): """Open the cover.""" if self.optimistic: self._closed = False self.cover.open() def stop_cover(self, **kwargs): """Stop the cover.""" self.cover.stop() def set_cover_position(self, **kwargs): """Move the cover shutter to a specific position.""" self.cover.set_position(100 - kwargs[ATTR_POSITION]) @property def current_cover_position(self): """Return the current position of cover shutter.""" position = None if self.has_capability("position"): position = 100 - self.cover.get_position() return position @property def is_closed(self): """Return if the cover is closed.""" is_closed = None if self.has_capability("position"): is_closed = self.cover.is_closed() elif self.optimistic: is_closed = self._closed return is_closed @property def current_cover_tilt_position(self): """Return current position of cover tilt. None is unknown, 0 is closed, 100 is fully open. """ orientation = None if self.has_capability("rotation"): orientation = 100 - self.cover.orientation return orientation def set_cover_tilt_position(self, **kwargs): """Move the cover tilt to a specific position.""" self.cover.orientation = 100 - kwargs[ATTR_TILT_POSITION] def open_cover_tilt(self, **kwargs): """Open the cover tilt.""" self.cover.orientation = 0 def close_cover_tilt(self, **kwargs): """Close the cover tilt.""" self.cover.orientation = 100 def stop_cover_tilt(self, **kwargs): """Stop the cover.""" self.cover.stop()
class SomfyCover(SomfyEntity, RestoreEntity, CoverEntity): """Representation of a Somfy cover device.""" def __init__(self, coordinator, device_id, api, optimistic): """Initialize the Somfy device.""" super().__init__(coordinator, device_id, api) self.categories = set(self.device.categories) self.optimistic = optimistic self._closed = None self._is_opening = None self._is_closing = None self.cover = None self._create_device() def _create_device(self): """Update the device with the latest data.""" self.cover = Blind(self.device, self.api) async def async_close_cover(self, **kwargs): """Close the cover.""" self._is_closing = True self.async_write_ha_state() try: # Blocks until the close command is sent await self.hass.async_add_executor_job(self.cover.close) self._closed = True finally: self._is_closing = None self.async_write_ha_state() async def async_open_cover(self, **kwargs): """Open the cover.""" self._is_opening = True self.async_write_ha_state() try: # Blocks until the open command is sent await self.hass.async_add_executor_job(self.cover.open) self._closed = False finally: self._is_opening = None self.async_write_ha_state() def open_cover_slowly(self): """Open slowly the cover.""" self.cover.set_position(0, low_speed=True) def close_cover_slowly(self): """Close slowy the cover.""" self.cover.set_position(100, low_speed=True) def stop_cover(self, **kwargs): """Stop the cover.""" self.cover.stop() def set_cover_position(self, **kwargs): """Move the cover shutter to a specific position.""" self.cover.set_position(100 - kwargs[ATTR_POSITION]) def set_cover_position_slowly(self, position: int): """Move the cover shutter to a specific position slowly.""" self.cover.set_position(100 - position, low_speed=True) @property def device_class(self): """Return the device class.""" if self.categories & BLIND_DEVICE_CATEGORIES: return DEVICE_CLASS_BLIND if self.categories & SHUTTER_DEVICE_CATEGORIES: return DEVICE_CLASS_SHUTTER return None @property def current_cover_position(self): """Return the current position of cover shutter.""" position = None if self.has_capability("position"): position = 100 - self.cover.get_position() return position @property def is_opening(self): """Return if the cover is opening.""" if not self.optimistic: return None return self._is_opening @property def is_closing(self): """Return if the cover is closing.""" if not self.optimistic: return None return self._is_closing @property def is_closed(self): """Return if the cover is closed.""" is_closed = None if self.has_capability("position"): is_closed = self.cover.is_closed() elif self.optimistic: is_closed = self._closed return is_closed @property def current_cover_tilt_position(self): """Return current position of cover tilt. None is unknown, 0 is closed, 100 is fully open. """ orientation = None if self.has_capability("rotation"): orientation = 100 - self.cover.orientation return orientation def set_cover_tilt_position(self, **kwargs): """Move the cover tilt to a specific position.""" self.cover.orientation = 100 - kwargs[ATTR_TILT_POSITION] def open_cover_tilt(self, **kwargs): """Open the cover tilt.""" self.cover.orientation = 0 def close_cover_tilt(self, **kwargs): """Close the cover tilt.""" self.cover.orientation = 100 def stop_cover_tilt(self, **kwargs): """Stop the cover.""" self.cover.stop() async def async_added_to_hass(self): """Complete the initialization.""" await super().async_added_to_hass() if not self.optimistic: return # Restore the last state if we use optimistic last_state = await self.async_get_last_state() if last_state is not None and last_state.state in ( STATE_OPEN, STATE_CLOSED, ): self._closed = last_state.state == STATE_CLOSED