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
29 changes: 25 additions & 4 deletions homeassistant/components/ihc/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,11 @@
from homeassistant.components.binary_sensor import DEVICE_CLASSES_SCHEMA
from homeassistant.components.ihc.const import (
ATTR_IHC_ID, ATTR_VALUE, CONF_AUTOSETUP, CONF_BINARY_SENSOR, CONF_DIMMABLE,
CONF_INFO, CONF_INVERTING, CONF_LIGHT, CONF_NODE, CONF_NOTE, CONF_POSITION,
CONF_SENSOR, CONF_SWITCH, CONF_XPATH, SERVICE_SET_RUNTIME_VALUE_BOOL,
SERVICE_SET_RUNTIME_VALUE_FLOAT, SERVICE_SET_RUNTIME_VALUE_INT)
CONF_INFO, CONF_INVERTING, CONF_LIGHT, CONF_NODE, CONF_NOTE, CONF_OFF_ID,
CONF_ON_ID, CONF_POSITION, CONF_SENSOR, CONF_SWITCH, CONF_XPATH,
SERVICE_SET_RUNTIME_VALUE_BOOL, SERVICE_SET_RUNTIME_VALUE_FLOAT,
SERVICE_SET_RUNTIME_VALUE_INT, SERVICE_PULSE)
from homeassistant.components.ihc.util import async_pulse
from homeassistant.config import load_yaml_config_file
from homeassistant.const import (
CONF_ID, CONF_NAME, CONF_PASSWORD, CONF_TYPE, CONF_UNIT_OF_MEASUREMENT,
Expand Down Expand Up @@ -50,7 +52,10 @@ def validate_name(config):
})


SWITCH_SCHEMA = DEVICE_SCHEMA.extend({})
SWITCH_SCHEMA = DEVICE_SCHEMA.extend({
vol.Optional(CONF_OFF_ID, default=0): cv.positive_int,
vol.Optional(CONF_ON_ID, default=0): cv.positive_int,
})

BINARY_SENSOR_SCHEMA = DEVICE_SCHEMA.extend({
vol.Optional(CONF_INVERTING, default=False): cv.boolean,
Expand All @@ -59,6 +64,8 @@ def validate_name(config):

LIGHT_SCHEMA = DEVICE_SCHEMA.extend({
vol.Optional(CONF_DIMMABLE, default=False): cv.boolean,
vol.Optional(CONF_OFF_ID, default=0): cv.positive_int,
Comment thread
MartinHjelmare marked this conversation as resolved.
vol.Optional(CONF_ON_ID, default=0): cv.positive_int,
})

SENSOR_SCHEMA = DEVICE_SCHEMA.extend({
Expand Down Expand Up @@ -138,6 +145,10 @@ def validate_name(config):
vol.Required(ATTR_VALUE): vol.Coerce(float),
})

PULSE_SCHEMA = vol.Schema({
vol.Required(ATTR_IHC_ID): cv.positive_int,
})


def setup(hass, config):
"""Set up the IHC platform."""
Expand Down Expand Up @@ -197,6 +208,8 @@ def get_manual_configuration(
'product_cfg': {
'type': sensor_cfg.get(CONF_TYPE),
'inverting': sensor_cfg.get(CONF_INVERTING),
'off_id': sensor_cfg.get(CONF_OFF_ID),
'on_id': sensor_cfg.get(CONF_ON_ID),
'dimmable': sensor_cfg.get(CONF_DIMMABLE),
'unit_of_measurement': sensor_cfg.get(
CONF_UNIT_OF_MEASUREMENT)
Expand Down Expand Up @@ -287,6 +300,11 @@ def set_runtime_value_float(call):
value = call.data[ATTR_VALUE]
ihc_controller.set_runtime_value_float(ihc_id, value)

async def async_pulse_runtime_input(call):
"""Pulse a IHC controller input function."""
ihc_id = call.data[ATTR_IHC_ID]
await async_pulse(hass, ihc_controller, ihc_id)

hass.services.register(DOMAIN, SERVICE_SET_RUNTIME_VALUE_BOOL,
set_runtime_value_bool,
schema=SET_RUNTIME_VALUE_BOOL_SCHEMA)
Expand All @@ -296,3 +314,6 @@ def set_runtime_value_float(call):
hass.services.register(DOMAIN, SERVICE_SET_RUNTIME_VALUE_FLOAT,
set_runtime_value_float,
schema=SET_RUNTIME_VALUE_FLOAT_SCHEMA)
hass.services.register(DOMAIN, SERVICE_PULSE,
async_pulse_runtime_input,
schema=PULSE_SCHEMA)
3 changes: 3 additions & 0 deletions homeassistant/components/ihc/const.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@
CONF_NAME = 'name'
CONF_NODE = 'node'
CONF_NOTE = 'note'
CONF_OFF_ID = 'off_id'
CONF_ON_ID = 'on_id'
CONF_POSITION = 'position'
CONF_SENSOR = 'sensor'
CONF_SWITCH = 'switch'
Expand All @@ -20,3 +22,4 @@
SERVICE_SET_RUNTIME_VALUE_BOOL = 'set_runtime_value_bool'
SERVICE_SET_RUNTIME_VALUE_FLOAT = 'set_runtime_value_float'
SERVICE_SET_RUNTIME_VALUE_INT = 'set_runtime_value_int'
SERVICE_PULSE = 'pulse'
45 changes: 32 additions & 13 deletions homeassistant/components/ihc/light.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,10 @@
import logging

from homeassistant.components.ihc import IHC_CONTROLLER, IHC_DATA, IHC_INFO
from homeassistant.components.ihc.const import CONF_DIMMABLE
from homeassistant.components.ihc.const import (
CONF_DIMMABLE, CONF_OFF_ID, CONF_ON_ID)
from homeassistant.components.ihc.util import (
async_pulse, async_set_bool, async_set_int)
from homeassistant.components.ihc.ihcdevice import IHCDevice
from homeassistant.components.light import (
ATTR_BRIGHTNESS, SUPPORT_BRIGHTNESS, Light)
Expand All @@ -26,9 +29,11 @@ def setup_platform(hass, config, add_entities, discovery_info=None):
ihc_key = IHC_DATA.format(ctrl_id)
info = hass.data[ihc_key][IHC_INFO]
ihc_controller = hass.data[ihc_key][IHC_CONTROLLER]
ihc_off_id = product_cfg.get(CONF_OFF_ID)
ihc_on_id = product_cfg.get(CONF_ON_ID)
dimmable = product_cfg[CONF_DIMMABLE]
light = IhcLight(ihc_controller, name, ihc_id, info,
dimmable, product)
light = IhcLight(ihc_controller, name, ihc_id, ihc_off_id, ihc_on_id,
info, dimmable, product)
devices.append(light)
add_entities(devices)

Expand All @@ -41,10 +46,13 @@ class IhcLight(IHCDevice, Light):
an on/off (boolean) resource
"""

def __init__(self, ihc_controller, name, ihc_id: int, info: bool,
dimmable=False, product=None) -> None:
def __init__(self, ihc_controller, name, ihc_id: int, ihc_off_id: int,
ihc_on_id: int, info: bool, dimmable=False,
product=None) -> None:
"""Initialize the light."""
super().__init__(ihc_controller, name, ihc_id, info, product)
self._ihc_off_id = ihc_off_id
self._ihc_on_id = ihc_on_id
self._brightness = 0
self._dimmable = dimmable
self._state = None
Expand All @@ -66,7 +74,7 @@ def supported_features(self):
return SUPPORT_BRIGHTNESS
return 0

def turn_on(self, **kwargs) -> None:
async def async_turn_on(self, **kwargs):
"""Turn the light on."""
if ATTR_BRIGHTNESS in kwargs:
brightness = kwargs[ATTR_BRIGHTNESS]
Expand All @@ -76,17 +84,28 @@ def turn_on(self, **kwargs) -> None:
brightness = 255

if self._dimmable:
self.ihc_controller.set_runtime_value_int(
self.ihc_id, int(brightness * 100 / 255))
await async_set_int(self.hass, self.ihc_controller,
self.ihc_id, int(brightness * 100 / 255))
else:
self.ihc_controller.set_runtime_value_bool(self.ihc_id, True)

def turn_off(self, **kwargs) -> None:
if self._ihc_on_id:
await async_pulse(self.hass, self.ihc_controller,
self._ihc_on_id)
else:
await async_set_bool(self.hass, self.ihc_controller,
self.ihc_id, True)

async def async_turn_off(self, **kwargs):
"""Turn the light off."""
if self._dimmable:
self.ihc_controller.set_runtime_value_int(self.ihc_id, 0)
await async_set_int(self.hass, self.ihc_controller,
self.ihc_id, 0)
else:
self.ihc_controller.set_runtime_value_bool(self.ihc_id, False)
if self._ihc_off_id:
await async_pulse(self.hass, self.ihc_controller,
self._ihc_off_id)
else:
await async_set_bool(self.hass, self.ihc_controller,
self.ihc_id, False)

def on_ihc_change(self, ihc_id, value):
"""Handle IHC notifications."""
Expand Down
5 changes: 5 additions & 0 deletions homeassistant/components/ihc/services.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -24,3 +24,8 @@ set_runtime_value_float:
value:
description: The float value to set.

pulse:
description: Pulses an input on the IHC controller.
fields:
ihc_id:
description: The integer IHC resource ID.
30 changes: 23 additions & 7 deletions homeassistant/components/ihc/switch.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
"""Support for IHC switches."""
from homeassistant.components.ihc import IHC_CONTROLLER, IHC_DATA, IHC_INFO
from homeassistant.components.ihc.const import CONF_OFF_ID, CONF_ON_ID
from homeassistant.components.ihc.util import async_pulse, async_set_bool
from homeassistant.components.ihc.ihcdevice import IHCDevice
from homeassistant.components.switch import SwitchDevice

Expand All @@ -13,39 +15,53 @@ def setup_platform(hass, config, add_entities, discovery_info=None):
devices = []
for name, device in discovery_info.items():
ihc_id = device['ihc_id']
product_cfg = device['product_cfg']
product = device['product']
# Find controller that corresponds with device id
ctrl_id = device['ctrl_id']
ihc_key = IHC_DATA.format(ctrl_id)
info = hass.data[ihc_key][IHC_INFO]
ihc_controller = hass.data[ihc_key][IHC_CONTROLLER]
ihc_off_id = product_cfg.get(CONF_OFF_ID)
ihc_on_id = product_cfg.get(CONF_ON_ID)

switch = IHCSwitch(ihc_controller, name, ihc_id, info, product)
switch = IHCSwitch(ihc_controller, name, ihc_id, ihc_off_id, ihc_on_id,
info, product)
devices.append(switch)
add_entities(devices)


class IHCSwitch(IHCDevice, SwitchDevice):
"""Representation of an IHC switch."""

def __init__(self, ihc_controller, name: str, ihc_id: int,
info: bool, product=None) -> None:
def __init__(self, ihc_controller, name: str, ihc_id: int, ihc_off_id: int,
ihc_on_id: int, info: bool, product=None) -> None:
"""Initialize the IHC switch."""
super().__init__(ihc_controller, name, ihc_id, product)
self._ihc_off_id = ihc_off_id
self._ihc_on_id = ihc_on_id
self._state = False

@property
def is_on(self):
"""Return true if switch is on."""
return self._state

def turn_on(self, **kwargs):
async def async_turn_on(self, **kwargs):
"""Turn the switch on."""
self.ihc_controller.set_runtime_value_bool(self.ihc_id, True)
if self._ihc_on_id:
await async_pulse(self.hass, self.ihc_controller, self._ihc_on_id)
else:
await async_set_bool(self.hass, self.ihc_controller,
self.ihc_id, True)

def turn_off(self, **kwargs):
async def async_turn_off(self, **kwargs):
"""Turn the device off."""
self.ihc_controller.set_runtime_value_bool(self.ihc_id, False)
if self._ihc_off_id:
await async_pulse(self.hass, self.ihc_controller, self._ihc_off_id)
else:
await async_set_bool(self.hass, self.ihc_controller,
self.ihc_id, False)

def on_ihc_change(self, ihc_id, value):
"""Handle IHC resource change."""
Expand Down
22 changes: 22 additions & 0 deletions homeassistant/components/ihc/util.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""Useful functions for the IHC component."""

import asyncio


async def async_pulse(hass, ihc_controller, ihc_id: int):
"""Send a short on/off pulse to an IHC controller resource."""
await async_set_bool(hass, ihc_controller, ihc_id, True)
await asyncio.sleep(0.1)
await async_set_bool(hass, ihc_controller, ihc_id, False)


def async_set_bool(hass, ihc_controller, ihc_id: int, value: bool):
"""Set a bool value on an IHC controller resource."""
return hass.async_add_executor_job(ihc_controller.set_runtime_value_bool,
ihc_id, value)


def async_set_int(hass, ihc_controller, ihc_id: int, value: int):
"""Set a int value on an IHC controller resource."""
return hass.async_add_executor_job(ihc_controller.set_runtime_value_int,
ihc_id, value)