Skip to content
Merged
Show file tree
Hide file tree
Changes from all 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
4 changes: 3 additions & 1 deletion homeassistant/components/homekit/type_fans.py
Original file line number Diff line number Diff line change
Expand Up @@ -165,7 +165,9 @@ def update_state(self, new_state):
self.char_direction.set_value(hk_direction)

# Handle Speed
if self.char_speed is not None:
if self.char_speed is not None and state != STATE_OFF:
# We do not change the homekit speed when turning off
# as it will clear the restore state
speed = new_state.attributes.get(ATTR_SPEED)
hk_speed_value = self.speed_mapping.speed_to_homekit(speed)
if hk_speed_value is not None and self.char_speed.value != hk_speed_value:
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/homekit/util.py
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,7 @@ def speed_to_homekit(self, speed):
if speed is None:
return None
speed_range = self.speed_ranges[speed]
return speed_range.target
return round(speed_range.target)

def speed_to_states(self, speed):
"""Map HomeKit speed to Home Assistant speed state."""
Expand Down
26 changes: 26 additions & 0 deletions tests/components/homekit/test_type_fans.py
Original file line number Diff line number Diff line change
Expand Up @@ -304,6 +304,7 @@ async def test_fan_speed(hass, hk_driver, cls, events):
call_set_speed = async_mock_service(hass, DOMAIN, "set_speed")

char_speed_iid = acc.char_speed.to_HAP()[HAP_REPR_IID]
char_active_iid = acc.char_active.to_HAP()[HAP_REPR_IID]

hk_driver.set_characteristics(
{
Expand All @@ -320,12 +321,37 @@ async def test_fan_speed(hass, hk_driver, cls, events):
await hass.async_add_executor_job(acc.char_speed.client_update_value, 42)
await hass.async_block_till_done()
acc.speed_mapping.speed_to_states.assert_called_with(42)
assert acc.char_speed.value == 42
assert acc.char_active.value == 1

assert call_set_speed[0]
assert call_set_speed[0].data[ATTR_ENTITY_ID] == entity_id
assert call_set_speed[0].data[ATTR_SPEED] == "ludicrous"
assert len(events) == 1
assert events[-1].data[ATTR_VALUE] == "ludicrous"

# Verify speed is preserved from off to on
hass.states.async_set(entity_id, STATE_OFF, {ATTR_SPEED: SPEED_OFF})
await hass.async_block_till_done()
assert acc.char_speed.value == 42
assert acc.char_active.value == 0

hk_driver.set_characteristics(
{
HAP_REPR_CHARS: [
{
HAP_REPR_AID: acc.aid,
HAP_REPR_IID: char_active_iid,
HAP_REPR_VALUE: 1,
},
]
},
"mock_addr",
)
await hass.async_block_till_done()
assert acc.char_speed.value == 42
assert acc.char_active.value == 1


async def test_fan_set_all_one_shot(hass, hk_driver, cls, events):
"""Test fan with speed."""
Expand Down