Skip to content

Commit bd85e61

Browse files
committed
added led device and brightness control
1 parent 16ba04a commit bd85e61

File tree

5 files changed

+54
-13
lines changed

5 files changed

+54
-13
lines changed

custom_components/hyperhdr_control/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
2626
manufacturer="HyperHDR",
2727
name=f"HyperHDR ({entry.data[CONF_HOST]})",
2828
model="HyperHDR LED Controller",
29-
sw_version="1.2.0",
29+
sw_version="1.3.0",
3030
)
3131

3232
await hass.config_entries.async_forward_entry_setups(entry, PLATFORMS)

custom_components/hyperhdr_control/button.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ def device_info(self) -> DeviceInfo:
5353
manufacturer="HyperHDR",
5454
name=f"HyperHDR ({self._host})",
5555
model="HyperHDR LED Controller",
56-
sw_version="1.2.0",
56+
sw_version="1.3.0",
5757
)
5858

5959
async def async_press(self) -> None:

custom_components/hyperhdr_control/manifest.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
"codeowners": [],
77
"requirements": ["aiohttp", "zeroconf"],
88
"iot_class": "local_polling",
9-
"version": "1.1.0",
9+
"version": "1.3.0",
1010
"config_flow": true,
1111
"zeroconf": ["_hyperhdr-http._tcp.local."],
1212
"logo": "https://raw.githubusercontent.com/johnneerdael/hyperhdr_control/main/hyperhdr_control-logo.png"

custom_components/hyperhdr_control/number.py

Lines changed: 38 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44
import json
55
import logging
66
from typing import Any
7+
import asyncio
8+
from datetime import datetime, timedelta
79

810
import aiohttp
911
import async_timeout
@@ -18,6 +20,8 @@
1820

1921
_LOGGER = logging.getLogger(__name__)
2022

23+
THROTTLE_DELAY = 1.0 # Delay in seconds between API calls
24+
2125
async def async_setup_entry(
2226
hass: HomeAssistant,
2327
entry: ConfigEntry,
@@ -46,6 +50,10 @@ def __init__(self, entry_id: str, host: str, port: int) -> None:
4650
self._attr_native_step = 1
4751
self._attr_mode = NumberMode.SLIDER
4852
self._attr_native_unit_of_measurement = PERCENTAGE
53+
self._last_update = datetime.min
54+
self._pending_value = None
55+
self._update_lock = asyncio.Lock()
56+
self._update_task = None
4957

5058
@property
5159
def device_info(self) -> DeviceInfo:
@@ -55,11 +63,38 @@ def device_info(self) -> DeviceInfo:
5563
manufacturer="HyperHDR",
5664
name=f"HyperHDR ({self._host})",
5765
model="HyperHDR LED Controller",
58-
sw_version="1.2.0",
66+
sw_version="1.3.0",
5967
)
6068

69+
async def _delayed_update(self) -> None:
70+
"""Handle the delayed update of the brightness value."""
71+
try:
72+
while True:
73+
async with self._update_lock:
74+
if self._pending_value is None:
75+
self._update_task = None
76+
return
77+
78+
value = self._pending_value
79+
self._pending_value = None
80+
81+
await self._set_brightness(value)
82+
await asyncio.sleep(THROTTLE_DELAY)
83+
except Exception as error:
84+
_LOGGER.error("Error in delayed update: %s", error)
85+
self._update_task = None
86+
6187
async def async_set_native_value(self, value: float) -> None:
62-
"""Set the brightness value."""
88+
"""Set the brightness value with throttling."""
89+
async with self._update_lock:
90+
self._pending_value = value
91+
self._attr_native_value = value
92+
93+
if self._update_task is None:
94+
self._update_task = asyncio.create_task(self._delayed_update())
95+
96+
async def _set_brightness(self, value: float) -> None:
97+
"""Send the brightness value to HyperHDR."""
6398
request_data = {
6499
"command": "adjustment",
65100
"adjustment": {
@@ -73,9 +108,7 @@ async def async_set_native_value(self, value: float) -> None:
73108
url = f"http://{self._host}:{self._port}/json-rpc"
74109
async with async_timeout.timeout(10):
75110
async with session.get(url, params={"request": json.dumps(request_data)}) as response:
76-
if response.status == 200:
77-
self._attr_native_value = value
78-
else:
111+
if response.status != 200:
79112
_LOGGER.error("Failed to set brightness: %s", response.status)
80113
except (aiohttp.ClientError, TimeoutError) as error:
81114
_LOGGER.error("Error setting brightness: %s", error)

custom_components/hyperhdr_control/switch.py

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,10 @@
1818

1919
_LOGGER = logging.getLogger(__name__)
2020

21+
# Define component names as constants
22+
COMP_VIDEOGRABBER = "VIDEOGRABBER"
23+
COMP_LEDDEVICE = "LEDDEVICE"
24+
2125
async def async_setup_entry(
2226
hass: HomeAssistant,
2327
entry: ConfigEntry,
@@ -28,8 +32,8 @@ async def async_setup_entry(
2832
port = entry.data[CONF_PORT]
2933

3034
async_add_entities([
31-
HyperHDRSwitch(entry.entry_id, host, port, "VIDEOGRABBER", "USB Capture"),
32-
HyperHDRSwitch(entry.entry_id, host, port, "LEDDEVICE", "LED Output")
35+
HyperHDRSwitch(entry.entry_id, host, port, COMP_VIDEOGRABBER, "USB Capture"),
36+
HyperHDRSwitch(entry.entry_id, host, port, COMP_LEDDEVICE, "LED Output")
3337
], True)
3438

3539
class HyperHDRSwitch(SwitchEntity):
@@ -53,7 +57,7 @@ def device_info(self) -> DeviceInfo:
5357
manufacturer="HyperHDR",
5458
name=f"HyperHDR ({self._host})",
5559
model="HyperHDR LED Controller",
56-
sw_version="1.2.0",
60+
sw_version="1.3.0",
5761
)
5862

5963
async def async_turn_on(self, **kwargs: Any) -> None:
@@ -77,14 +81,18 @@ async def _set_state(self, state: bool) -> None:
7781
try:
7882
async with aiohttp.ClientSession() as session:
7983
url = f"http://{self._host}:{self._port}/json-rpc"
84+
_LOGGER.debug("Sending request to %s: %s", url, json.dumps(request_data))
8085
async with async_timeout.timeout(10):
8186
async with session.get(url, params={"request": json.dumps(request_data)}) as response:
8287
if response.status == 200:
8388
self._attr_is_on = state
89+
_LOGGER.debug("Successfully set %s state to %s", self._component, state)
8490
else:
85-
_LOGGER.error("Failed to set state: %s", response.status)
91+
_LOGGER.error("Failed to set state for %s: %s", self._component, response.status)
92+
response_text = await response.text()
93+
_LOGGER.error("Response: %s", response_text)
8694
except (aiohttp.ClientError, TimeoutError) as error:
87-
_LOGGER.error("Error setting state: %s", error)
95+
_LOGGER.error("Error setting state for %s: %s", self._component, error)
8896

8997
async def async_update(self) -> None:
9098
"""Update the state of the switch."""

0 commit comments

Comments
 (0)