From e6ece4bf6d9d38a5361342a22943233f51485aaa Mon Sep 17 00:00:00 2001 From: Adam Mills Date: Sat, 29 Oct 2016 20:14:28 -0400 Subject: [PATCH] Fix initialization of zwave color bulbs (#4085) * Fix initialization of zwave color bulbs Zwave values can be added to the node in any order. This change allows proper initialization when the multilevel value is added before the color value. * Fix incorrect rename of color command class --- homeassistant/components/light/zwave.py | 72 ++++++++++++++++--------- homeassistant/components/zwave/const.py | 2 + 2 files changed, 49 insertions(+), 25 deletions(-) diff --git a/homeassistant/components/light/zwave.py b/homeassistant/components/light/zwave.py index 346482d3ff6..7e838f97270 100644 --- a/homeassistant/components/light/zwave.py +++ b/homeassistant/components/light/zwave.py @@ -89,13 +89,7 @@ def setup_platform(hass, config, add_devices, discovery_info=None): value.set_change_verified(False) if node.has_command_class(zwave.const.COMMAND_CLASS_SWITCH_COLOR): - try: - add_devices([ZwaveColorLight(value)]) - except ValueError as exception: - _LOGGER.warning( - "Error initializing as color bulb: %s " - "Initializing as standard dimmer.", exception) - add_devices([ZwaveDimmer(value)]) + add_devices([ZwaveColorLight(value)]) else: add_devices([ZwaveDimmer(value)]) @@ -222,33 +216,63 @@ class ZwaveColorLight(ZwaveDimmer): def __init__(self, value): """Initialize the light.""" + from openzwave.network import ZWaveNetwork + from pydispatch import dispatcher + self._value_color = None self._value_color_channels = None self._color_channels = None self._rgb = None self._ct = None - # Currently zwave nodes only exist with one color element per node. - for value_color in value.node.get_rgbbulbs().values(): - self._value_color = value_color - - if self._value_color is None: - raise ValueError("No color command found.") - - for value_color_channels in value.node.get_values( - class_id=zwave.const.COMMAND_CLASS_SWITCH_COLOR, - genre='System', type="Int").values(): - self._value_color_channels = value_color_channels - - if self._value_color_channels is None: - raise ValueError("Color Channels not found.") - super().__init__(value) + # Create a listener so the color values can be linked to this entity + dispatcher.connect( + self._value_added, ZWaveNetwork.SIGNAL_VALUE_ADDED) + self._get_color_values() + + def _get_color_values(self): + """Search for color values available on this node.""" + from openzwave.network import ZWaveNetwork + from pydispatch import dispatcher + + _LOGGER.debug("Searching for zwave color values") + # Currently zwave nodes only exist with one color element per node. + if self._value_color is None: + for value_color in self._value.node.get_rgbbulbs().values(): + self._value_color = value_color + + if self._value_color_channels is None: + for value_color_channels in self._value.node.get_values( + class_id=zwave.const.COMMAND_CLASS_SWITCH_COLOR, + genre=zwave.const.GENRE_SYSTEM, + type=zwave.const.TYPE_INT).values(): + self._value_color_channels = value_color_channels + + if self._value_color and self._value_color_channels: + _LOGGER.debug("Zwave node color values found.") + dispatcher.disconnect( + self._value_added, ZWaveNetwork.SIGNAL_VALUE_ADDED) + self.update_properties() + + def _value_added(self, value): + """Called when a value has been added to the network.""" + if self._value.node != value.node: + return + # Check for the missing color values + self._get_color_values() + + # pylint: disable=too-many-branches def update_properties(self): """Update internal properties based on zwave values.""" super().update_properties() + if self._value_color is None: + return + if self._value_color_channels is None: + return + # Color Channels self._color_channels = self._value_color_channels.data @@ -346,9 +370,7 @@ class ZwaveColorLight(ZwaveDimmer): rgbw += format(colorval, '02x').encode('utf-8') rgbw += b'0000' - if rgbw is None: - _LOGGER.warning("rgbw string was not generated for turn_on") - else: + if rgbw and self._value_color: self._value_color.node.set_rgbw(self._value_color.value_id, rgbw) super().turn_on(**kwargs) diff --git a/homeassistant/components/zwave/const.py b/homeassistant/components/zwave/const.py index 698dad8e063..d30cb6c5f92 100644 --- a/homeassistant/components/zwave/const.py +++ b/homeassistant/components/zwave/const.py @@ -294,8 +294,10 @@ SPECIFIC_TYPE_NOTIFICATION_SENSOR = 1 GENRE_WHATEVER = None GENRE_USER = "User" +GENRE_SYSTEM = "System" TYPE_WHATEVER = None TYPE_BYTE = "Byte" TYPE_BOOL = "Bool" TYPE_DECIMAL = "Decimal" +TYPE_INT = "Int"