Skip to content
This repository has been archived by the owner on Oct 11, 2022. It is now read-only.

Added Ambient light #105

Merged
merged 4 commits into from
Oct 17, 2020
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
28 changes: 22 additions & 6 deletions custom_components/home_connect_beta/api.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
"""API for Home Connect bound to HASS OAuth."""

from asyncio import run_coroutine_threadsafe
import logging
from asyncio import run_coroutine_threadsafe

import homeconnect
from homeconnect.api import HomeConnectError
Expand All @@ -13,8 +13,10 @@

from .const import (
BSH_ACTIVE_PROGRAM,
BSH_AMBIENTLIGHTENABLED,
BSH_POWER_OFF,
BSH_POWER_STANDBY,
COOKING_LIGHTING,
SIGNAL_UPDATE_ENTITIES,
)

Expand Down Expand Up @@ -179,6 +181,19 @@ def get_light_entity(self):
return {
"device": self,
"desc": "Light",
"ambient" : None,
}


class DeviceWithAmbientLight(HomeConnectDevice):
"""Device that has ambient lighting."""

def get_ambientlight_entity(self):
"""Get a dictionary with info about the ambient lighting."""
return {
"device": self,
"desc": "AmbientLight",
"ambient" : True,
}


Expand Down Expand Up @@ -216,8 +231,6 @@ def get_entity_info(self):
}




class WasherDryer(DeviceWithDoor, DeviceWithPrograms):
"""Washer class."""

Expand Down Expand Up @@ -273,7 +286,7 @@ def get_entity_info(self):
}


class Dishwasher(DeviceWithDoor, DeviceWithPrograms):
class Dishwasher(DeviceWithDoor, DeviceWithAmbientLight, DeviceWithPrograms):
"""Dishwasher class."""

PROGRAMS = [
Expand Down Expand Up @@ -303,13 +316,15 @@ class Dishwasher(DeviceWithDoor, DeviceWithPrograms):

def get_entity_info(self):
"""Get a dictionary with infos about the associated entities."""
ambientlight_entity = self.get_ambientlight_entity()
door_entity = self.get_door_entity()
program_sensors = self.get_program_sensors()
program_switches = self.get_program_switches()
return {
"binary_sensor": [door_entity],
"switch": program_switches,
"sensor": program_sensors,
"light": [ambientlight_entity]
}


Expand Down Expand Up @@ -430,7 +445,7 @@ def get_entity_info(self):
return {"switch": program_switches, "sensor": program_sensors}


class Hood(DeviceWithLight, DeviceWithPrograms):
class Hood(DeviceWithLight, DeviceWithAmbientLight, DeviceWithPrograms):
"""Hood class."""

PROGRAMS = [
Expand All @@ -442,12 +457,13 @@ class Hood(DeviceWithLight, DeviceWithPrograms):
def get_entity_info(self):
"""Get a dictionary with infos about the associated entities."""
light_entity = self.get_light_entity()
ambientlight_entity = self.get_ambientlight_entity()
program_sensors = self.get_program_sensors()
program_switches = self.get_program_switches()
return {
"switch": program_switches,
"sensor": program_sensors,
"light" : [light_entity],
"light" : [light_entity, ambientlight_entity]
}


Expand Down
10 changes: 9 additions & 1 deletion custom_components/home_connect_beta/const.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,16 @@
BSH_POWER_STANDBY = "BSH.Common.EnumType.PowerState.Standby"
BSH_ACTIVE_PROGRAM = "BSH.Common.Root.ActiveProgram"
BSH_OPERATION_STATE = "BSH.Common.Status.OperationState"

COOKING_LIGHTING = "Cooking.Common.Setting.Lighting"
COOKING_LIGHTINGBRIGHTNESS = "Cooking.Common.Setting.LightingBrightness"

BSH_AMBIENTLIGHTENABLED = "BSH.Common.Setting.AmbientLightEnabled"
BSH_AMBIENTLIGHTBRIGHTNESS = "BSH.Common.Setting.AmbientLightBrightness"
BSH_AMBIENTLIGHTCOLOR = "BSH.Common.Setting.AmbientLightColor"
BSH_AMBIENTLIGHTCOLOR_CUSTOMCOLOR = "BSH.Common.EnumType.AmbientLightColor.CustomColor"
BSH_AMBIENTLIGHTCUSTOMCOLOR = "BSH.Common.Setting.AmbientLightCustomColor"

BSH_DOOR_STATE = "BSH.Common.Status.DoorState"
BSH_PAUSE = "BSH.Common.Command.PauseProgram"
BSH_RESUME = "BSH.Common.Command.ResumeProgram"
Expand All @@ -28,4 +36,4 @@

ATTR_PROGRAM = "program"
ATTR_KEY = "key"
ATTR_VALUE = "value"
ATTR_VALUE = "value"
128 changes: 107 additions & 21 deletions custom_components/home_connect_beta/light.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,25 @@

from homeconnect.api import HomeConnectError

import homeassistant.util.color as color_util
from homeassistant.components.light import (
ATTR_BRIGHTNESS,
LightEntity,
ATTR_HS_COLOR,
SUPPORT_BRIGHTNESS,
SUPPORT_COLOR,
LightEntity,
)

from .const import COOKING_LIGHTING, COOKING_LIGHTINGBRIGHTNESS, DOMAIN
from .const import (
BSH_AMBIENTLIGHTBRIGHTNESS,
BSH_AMBIENTLIGHTCOLOR,
BSH_AMBIENTLIGHTCOLOR_CUSTOMCOLOR,
BSH_AMBIENTLIGHTCUSTOMCOLOR,
BSH_AMBIENTLIGHTENABLED,
COOKING_LIGHTING,
COOKING_LIGHTINGBRIGHTNESS,
DOMAIN,
)
from .entity import HomeConnectEntity

_LOGGER = logging.getLogger(__name__)
Expand All @@ -35,11 +47,23 @@ def get_entities():
class HomeConnectLight(HomeConnectEntity, LightEntity):
"""Light for Home Connect."""

def __init__(self, device, desc):
def __init__(self, device, desc, ambient):
"""Initialize the entity."""
super().__init__(device, desc)
self._state = None
self._brightness = None
self._hs_color = None
self._ambient = ambient
if self._ambient:
self._brightnesskey = BSH_AMBIENTLIGHTBRIGHTNESS
self._key = BSH_AMBIENTLIGHTENABLED
self._customcolorkey = BSH_AMBIENTLIGHTCUSTOMCOLOR
self._colorkey = BSH_AMBIENTLIGHTCOLOR
else:
self._brightnesskey = COOKING_LIGHTINGBRIGHTNESS
self._key = COOKING_LIGHTING
self._customcolorkey = None
self._colorkey = None

@property
def is_on(self):
Expand All @@ -51,22 +75,68 @@ def brightness(self):
"""Return the brightness of the light."""
return self._brightness

@property
def hs_color(self):
"""Return the color property."""
return self._hs_color

@property
def supported_features(self):
"""Flag supported features."""
if self._ambient:
return SUPPORT_BRIGHTNESS | SUPPORT_COLOR
return SUPPORT_BRIGHTNESS

async def async_turn_on(self, **kwargs):
"""Switch the light on / change brightness."""
if ATTR_BRIGHTNESS in kwargs:
"""Switch the light on, change brightness, change color."""
if self._ambient:
if ATTR_BRIGHTNESS in kwargs or ATTR_HS_COLOR in kwargs:
try:
await self.hass.async_add_executor_job(
self.device.appliance.set_setting,
self._colorkey,
BSH_AMBIENTLIGHTCOLOR_CUSTOMCOLOR,
)
except HomeConnectError as err:
_LOGGER.error("Error while trying selecting customcolor: %s", err)
if self._brightness != None:
brightness = 10 + ceil(self._brightness / 255 * 90)
if ATTR_BRIGHTNESS in kwargs:
brightness = 10 + ceil(kwargs[ATTR_BRIGHTNESS] / 255 * 90)

hs_color = self._hs_color
if ATTR_HS_COLOR in kwargs:
hs_color = kwargs[ATTR_HS_COLOR]

if hs_color != None:
rgb = color_util.color_hsv_to_RGB(*hs_color, brightness)
hex = color_util.color_rgb_to_hex(rgb[0], rgb[1], rgb[2])
try:
await self.hass.async_add_executor_job(
self.device.appliance.set_setting,
self._customcolorkey,
"#" + hex,
)
except HomeConnectError as err:
_LOGGER.error("Error while trying setting the color: %s", err)
self._state = False
else:
_LOGGER.debug("Tried to switch light on for: %s", self.name)
try:
await self.hass.async_add_executor_job(
self.device.appliance.set_setting, self._key, True,
)
except HomeConnectError as err:
_LOGGER.error("Error while trying to turn on ambient light: %s", err)
self._state = False

elif ATTR_BRIGHTNESS in kwargs:
_LOGGER.debug("Tried to change brightness for: %s", self.name)
"""Convert Home Assistant brightness (0-255) to Home Connect brightness (10-100)"""
"""Convert Home Assistant brightness (0-255) to Home Connect brightness (10-100)."""
brightness = 10 + ceil(kwargs[ATTR_BRIGHTNESS] / 255 * 90)
try:
await self.hass.async_add_executor_job(
self.device.appliance.set_setting,
COOKING_LIGHTINGBRIGHTNESS,
brightness,
self.device.appliance.set_setting, self._brightnesskey, brightness,
)
except HomeConnectError as err:
_LOGGER.error("Error while trying set the brightness: %s", err)
Expand All @@ -76,19 +146,20 @@ async def async_turn_on(self, **kwargs):
_LOGGER.debug("Tried to switch light on for: %s", self.name)
try:
await self.hass.async_add_executor_job(
self.device.appliance.set_setting, COOKING_LIGHTING, True,
self.device.appliance.set_setting, self._key, True,
)
except HomeConnectError as err:
_LOGGER.error("Error while trying to turn on light: %s", err)
self._state = False

self.async_entity_update()

async def async_turn_off(self, **kwargs):
"""Switch the light off."""
_LOGGER.debug("tried to switch light off for: %s", self.name)
try:
await self.hass.async_add_executor_job(
self.device.appliance.set_setting, COOKING_LIGHTING, False,
self.device.appliance.set_setting, self._key, False,
)
except HomeConnectError as err:
_LOGGER.error("Error while trying to turn off light: %s", err)
Expand All @@ -97,18 +168,33 @@ async def async_turn_off(self, **kwargs):

async def async_update(self):
"""Update the light's status."""
if self.device.appliance.status.get(COOKING_LIGHTING, {}).get("value") is True:
if self.device.appliance.status.get(self._key, {}).get("value") is True:
self._state = True
elif (
self.device.appliance.status.get(COOKING_LIGHTING, {}).get("value") is False
):
elif self.device.appliance.status.get(self._key, {}).get("value") is False:
self._state = False
else:
self._state = None
brightness = self.device.appliance.status.get(COOKING_LIGHTINGBRIGHTNESS, {})
if brightness is None:
self._brightness = None
else:
self._brightness = ceil((brightness.get("value") - 10) * 255 / 90)

_LOGGER.debug("Updated, new light state: %s", self._state)
_LOGGER.debug("Updated, new brightness: %s", self._brightness)

if self._ambient:
color = self.device.appliance.status.get(self._customcolorkey, {})

if not color:
self._hs_color = None
self._brightness = None
else:
colorvalue = color.get("value")[1:]
rgb = color_util.rgb_hex_to_rgb_list(colorvalue)
hsv = color_util.color_RGB_to_hsv(rgb[0], rgb[1], rgb[2])
self._hs_color = [hsv[0], hsv[1]]
self._brightness = ceil((hsv[2] - 10) * 255 / 90)
_LOGGER.debug("Updated, new brightness: %s", self._brightness)

else:
brightness = self.device.appliance.status.get(self._brightnesskey, {})
if brightness is None:
self._brightness = None
else:
self._brightness = ceil((brightness.get("value") - 10) * 255 / 90)
_LOGGER.debug("Updated, new brightness: %s", self._brightness)