Skip to content
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions homeassistant/components/switchbot/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,11 @@
Platform.LOCK,
Platform.SENSOR,
],
SupportedModels.BLIND_TILT.value: [
Platform.COVER,
Platform.BINARY_SENSOR,
Platform.SENSOR,
],
}
CLASS_BY_DEVICE = {
SupportedModels.CEILING_LIGHT.value: switchbot.SwitchbotCeilingLight,
Expand All @@ -60,6 +65,7 @@
SupportedModels.LIGHT_STRIP.value: switchbot.SwitchbotLightStrip,
SupportedModels.HUMIDIFIER.value: switchbot.SwitchbotHumidifier,
SupportedModels.LOCK.value: switchbot.SwitchbotLock,
SupportedModels.BLIND_TILT.value: switchbot.SwitchbotBlindTilt,
}


Expand Down
2 changes: 2 additions & 0 deletions homeassistant/components/switchbot/const.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ class SupportedModels(StrEnum):
MOTION = "motion"
HUMIDIFIER = "humidifier"
LOCK = "lock"
BLIND_TILT = "blind_tilt"


CONNECTABLE_SUPPORTED_MODEL_TYPES = {
Expand All @@ -36,6 +37,7 @@ class SupportedModels(StrEnum):
SwitchbotModel.CEILING_LIGHT: SupportedModels.CEILING_LIGHT,
SwitchbotModel.HUMIDIFIER: SupportedModels.HUMIDIFIER,
SwitchbotModel.LOCK: SupportedModels.LOCK,
SwitchbotModel.BLIND_TILT: SupportedModels.BLIND_TILT,
}

NON_CONNECTABLE_SUPPORTED_MODEL_TYPES = {
Expand Down
84 changes: 83 additions & 1 deletion homeassistant/components/switchbot/cover.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,9 @@

from homeassistant.components.cover import (
ATTR_CURRENT_POSITION,
ATTR_CURRENT_TILT_POSITION,
ATTR_POSITION,
ATTR_TILT_POSITION,
CoverDeviceClass,
CoverEntity,
CoverEntityFeature,
Expand All @@ -32,7 +34,10 @@ async def async_setup_entry(
) -> None:
"""Set up Switchbot curtain based on a config entry."""
coordinator: SwitchbotDataUpdateCoordinator = hass.data[DOMAIN][entry.entry_id]
async_add_entities([SwitchBotCurtainEntity(coordinator)])
if isinstance(coordinator.device, switchbot.SwitchbotBlindTilt):
async_add_entities([SwitchBotBlindTiltEntity(coordinator)])
else:
async_add_entities([SwitchBotCurtainEntity(coordinator)])


class SwitchBotCurtainEntity(SwitchbotEntity, CoverEntity, RestoreEntity):
Expand Down Expand Up @@ -102,3 +107,80 @@ def _handle_coordinator_update(self) -> None:
self._attr_is_closed = self.parsed_data["position"] <= 20
self._attr_is_opening = self.parsed_data["inMotion"]
self.async_write_ha_state()


class SwitchBotBlindTiltEntity(SwitchbotEntity, CoverEntity, RestoreEntity):
"""Representation of a Switchbot."""

_device: switchbot.SwitchbotBlindTilt
_attr_device_class = CoverDeviceClass.BLIND
_attr_supported_features = (
CoverEntityFeature.OPEN_TILT
| CoverEntityFeature.CLOSE_TILT
| CoverEntityFeature.STOP_TILT
| CoverEntityFeature.SET_TILT_POSITION
)
CLOSED_UP_THRESHOLD = 80
CLOSED_DOWN_THRESHOLD = 20

def __init__(self, coordinator: SwitchbotDataUpdateCoordinator) -> None:
"""Initialize the Switchbot."""
super().__init__(coordinator)
self._attr_is_closed = None

async def async_added_to_hass(self) -> None:
"""Run when entity about to be added."""
await super().async_added_to_hass()
last_state = await self.async_get_last_state()
if not last_state or ATTR_CURRENT_TILT_POSITION not in last_state.attributes:
return

self._attr_current_cover_tilt_position = last_state.attributes.get(
ATTR_CURRENT_TILT_POSITION
)
self._last_run_success = last_state.attributes.get("last_run_success")
if (_tilt := self._attr_current_cover_position) is not None:
self._attr_is_closed = (_tilt < self.CLOSED_DOWN_THRESHOLD) or (
_tilt > self.CLOSED_UP_THRESHOLD
)

async def async_open_cover_tilt(self, **kwargs: Any) -> None:
"""Open the tilt."""

_LOGGER.debug("Switchbot to open blind tilt %s", self._address)
self._last_run_success = bool(await self._device.open())
self.async_write_ha_state()

async def async_close_cover_tilt(self, **kwargs: Any) -> None:
"""Close the tilt."""

_LOGGER.debug("Switchbot to close the blind tilt %s", self._address)
self._last_run_success = bool(await self._device.close())
self.async_write_ha_state()

async def async_stop_cover_tilt(self, **kwargs: Any) -> None:
"""Stop the moving of this device."""

_LOGGER.debug("Switchbot to stop %s", self._address)
self._last_run_success = bool(await self._device.stop())
self.async_write_ha_state()

async def async_set_cover_tilt_position(self, **kwargs: Any) -> None:
"""Move the cover tilt to a specific position."""
position = kwargs.get(ATTR_TILT_POSITION)

_LOGGER.debug("Switchbot to move at %d %s", position, self._address)
self._last_run_success = bool(await self._device.set_position(position))
self.async_write_ha_state()

@callback
def _handle_coordinator_update(self) -> None:
"""Handle updated data from the coordinator."""
_tilt = self.parsed_data["tilt"]
self._attr_current_cover_tilt_position = _tilt
self._attr_is_closed = (_tilt < self.CLOSED_DOWN_THRESHOLD) or (
_tilt > self.CLOSED_UP_THRESHOLD
)
self._attr_is_opening = self.parsed_data["motionDirection"]["opening"]
self._attr_is_closing = self.parsed_data["motionDirection"]["closing"]
self.async_write_ha_state()
2 changes: 1 addition & 1 deletion homeassistant/components/switchbot/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"domain": "switchbot",
"name": "SwitchBot",
"documentation": "https://www.home-assistant.io/integrations/switchbot",
"requirements": ["PySwitchbot==0.36.4"],
"requirements": ["PySwitchbot==0.37.1"],
"config_flow": true,
"dependencies": ["bluetooth_adapters"],
"codeowners": [
Expand Down
2 changes: 1 addition & 1 deletion requirements_all.txt
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ PyRMVtransport==0.3.3
PySocks==1.7.1

# homeassistant.components.switchbot
PySwitchbot==0.36.4
PySwitchbot==0.37.1

# homeassistant.components.transport_nsw
PyTransportNSW==0.1.1
Expand Down
2 changes: 1 addition & 1 deletion requirements_test_all.txt
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ PyRMVtransport==0.3.3
PySocks==1.7.1

# homeassistant.components.switchbot
PySwitchbot==0.36.4
PySwitchbot==0.37.1

# homeassistant.components.transport_nsw
PyTransportNSW==0.1.1
Expand Down