From be356f30eb524ef883455ff3944dd9d366aeb8ef Mon Sep 17 00:00:00 2001 From: "alexei.dolgolyov" Date: Tue, 17 Mar 2026 14:52:50 +0300 Subject: [PATCH] Fix HAOS light color reverting after timeout When HA sets a color via turn_on, also update the source's fallback_color to match. This way when the api_input timeout fires (default 5s), the stream reverts to the same color instead of black. turn_off resets fallback to [0,0,0]. Added coordinator.update_source() for PUT /color-strip-sources/{id}. Co-Authored-By: Claude Opus 4.6 (1M context) --- .../wled_screen_controller/coordinator.py | 15 +++++++++++++++ custom_components/wled_screen_controller/light.py | 13 ++++++++++--- 2 files changed, 25 insertions(+), 3 deletions(-) diff --git a/custom_components/wled_screen_controller/coordinator.py b/custom_components/wled_screen_controller/coordinator.py index 65df416..c52afca 100644 --- a/custom_components/wled_screen_controller/coordinator.py +++ b/custom_components/wled_screen_controller/coordinator.py @@ -384,6 +384,21 @@ class WLEDScreenControllerCoordinator(DataUpdateCoordinator): resp.raise_for_status() await self.async_request_refresh() + async def update_source(self, source_id: str, **kwargs: Any) -> None: + """Update a color strip source's fields.""" + async with self.session.put( + f"{self.server_url}/api/v1/color-strip-sources/{source_id}", + headers={**self._auth_headers, "Content-Type": "application/json"}, + json=kwargs, + timeout=aiohttp.ClientTimeout(total=DEFAULT_TIMEOUT), + ) as resp: + if resp.status != 200: + body = await resp.text() + _LOGGER.error( + "Failed to update source %s: %s %s", + source_id, resp.status, body, + ) + async def update_target(self, target_id: str, **kwargs: Any) -> None: """Update a output target's fields.""" async with self.session.put( diff --git a/custom_components/wled_screen_controller/light.py b/custom_components/wled_screen_controller/light.py index d370f66..4881460 100644 --- a/custom_components/wled_screen_controller/light.py +++ b/custom_components/wled_screen_controller/light.py @@ -114,15 +114,22 @@ class ApiInputLight(CoordinatorEntity, LightEntity): self._source_id, [{"start": 0, "length": 9999, "mode": "solid", "color": scaled}], ) + # Update fallback_color so the color persists beyond the timeout + await self.coordinator.update_source( + self._source_id, fallback_color=scaled, + ) self._is_on = True self.async_write_ha_state() async def async_turn_off(self, **kwargs: Any) -> None: - """Turn off the light by pushing the fallback color.""" - fallback_color = self._get_fallback_color() + """Turn off the light by pushing black and setting fallback to black.""" + off_color = [0, 0, 0] await self.coordinator.push_segments( self._source_id, - [{"start": 0, "length": 9999, "mode": "solid", "color": fallback_color}], + [{"start": 0, "length": 9999, "mode": "solid", "color": off_color}], + ) + await self.coordinator.update_source( + self._source_id, fallback_color=off_color, ) self._is_on = False self.async_write_ha_state()