-
Notifications
You must be signed in to change notification settings - Fork 3.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix various logic for ZBT-CCTSwitch-D0001 + add new device Ecosmart-ZBT-A19-CCT-Bulb #826
Conversation
* Update devices.js * Update devices.js * update
* added Bitron Wall Thermostat * added Bitron fromZigbee convertes bitron_battery (should be usefull for all bitron battery powered devices) bitron_thermostat_att_report bitron_thermostat_dev_change * Update fromZigbee.js * Update devices.js * Update devices.js * Update devices.js * Update fromZigbee.js * Update toZigbee.js i changed the calculation of the input values so that you can also set half degrees. before: 21.3 -> 21.0 21.4 -> 21.0 21.5 -> 22.0 now: 21.3 -> 21.5 21.4 -> 21.5 21.5 -> 21.5 * Update fromZigbee.js * added temperature_display_mode + running_state * Update devices.js * Trailing spaces * Update fromZigbee.js * Update fromZigbee.js * Update fromZigbee.js * Update devices.js * Update devices.js
* GLEDOPTO GL-B-008Z * HGZB-20-DE https://www.amazon.de/Intelligente-Steckdose-kompatibel-SmartThings-Steuerung/dp/B07GYG5GRP * Update devices.js * Update devices.js * Update devices.js * FB56-ZCW11HG1.2 https://uploads.tapatalk-cdn.com/20190106/dcf0f59343233342d004319d05c04bc0.jpg * FB56-ZCW11HG1.2 * FB56-ZCW11HG1.2 i miss this device * rebase * Update devices.js
* Update device.js to include Nue HGZB-01A Device is a mains inline zigbee light controller with brightness. Amazon link: https://www.amazon.com/gp/product/B07FBD96DG/ref=oh_aui_detailpage_o01_s00?ie=UTF8&psc=1 Added and tested device per: https://koenkk.github.io/zigbee2mqtt/how_tos/how_to_support_new_devices.html * remove extranious tab that fails check * Fixed the rest of the tabs - still figuring this out... sorry. * adding space back... * Update devices.js
* Add device support for iCasa Zigbee 3.0 Dimmer * Update devices.js
* Add Iris 3326-L motion and temperature sensor * Use scoped zcl-id * Only package needed files * refactor: Use a Map for findByZigbeeModel * Add `extend` attribute The attribute shallow-merges the model object, with the explicitly defined properties taking precidence Converted all uses of `generic` to `extend` format.
* added Hue Power-on Converter tested with GU10. needs Firmware 1.46 hue_power_on_behavior // default / enable / disable / configure hue_power_on_behavior, // default = 1 // on - lamps on after power loss with configured brightness, color temperature, color // off - lamps off after power loss // recover - lamps on after power loss with last state hue_power_on_brightness // brightness when hue_power_on_behavior = on, same settings as brightness converter // default = 255 hue_power_on_color_temperature // color temperature when hue_power_on_behavior = on, same settings as colortemp converter // default = 366 to-do: hue_power_on_color (must be added by someone with appropriate bulb) * Update toZigbee.js * Hue specific settings generic hue settings with power-on converter * Update toZigbee.js * fixed 'null' values as discussed here: Koenkk/zigbee2mqtt#848 * Update fromZigbee.js * Update fromZigbee.js * Update toZigbee.js * Update devices.js * Update devices.js
* fixed 'null' values in thermostat converters. as discussed here: Koenkk/zigbee2mqtt#848 * Update fromZigbee.js * Update fromZigbee.js * Update fromZigbee.js * Update fromZigbee.js * Update fromZigbee.js * Update fromZigbee.js
Also updates the brightness hold/release logic.
Fixes the following error FAIL test/index.test.js index.js ✓ Find device by model ID (6ms) ✓ Find device by model ID with strange characters 1 (1ms) ✓ Find device by model ID with strange characters 2 ✓ Find device by model ID with strange characters 3 (1ms) ✓ Find device by model ID without strange characters (1ms) ✓ Find device by model ID null (1ms) ✕ Verify devices.js definitions (132ms) ● index.js › Verify devices.js definitions TypeError: Cannot convert undefined or null to object at Function.keys (<anonymous>) 63 | const converter = device.fromZigbee[converterKey]; 64 | > 65 | const keys = Object.keys(converter); | ^ 66 | verifyKeys(['cluster', 'type', 'convert'], keys, converterKey); 67 | 68 | if (4 != converter.convert.length) { at keys (test/index.test.js:65:37) at Array.forEach (<anonymous>) at forEach (test/index.test.js:62:44) at Array.forEach (<anonymous>) at Object.forEach (test/index.test.js:47:17)
This is great. Amazingly, I've been working on a very similar approach. However, it doesn't try to merge the actions of button 3 and 4. The reason being that this was how the remote was designed (button 4 is a memory recall that can be programmed to hold 3 states) and allows for greater generality. This is of interest to me since I use Node Red as my main platform, giving me full control over the messages. Here is the alternative implementation: Button 1 (Pressed Twice):
Button 2 (Pressed 8 times)
Button 3 (Pressed 7 times)
Button 4 (Pressed Once)
Note that Button 4 generates TWO messages. This is how the remote was designed. However, one message may be attributed to a physical button (button: MEMORY) and the other to a virtual button (button: VIRTUAL) In my opinion, this provides the most general use case for this remote. The underlying functionality of the remote is preserved, including state and memory recall. In addition, it is possible to identify the physical buttons begin pushed by looking for buttons ON/OFF, DIM, CCT and MEMORY and ignoring messages associated with button VIRTUAL. I've also come up with an elegant way of differentiating between button 3 and button 4 messages that does not rely on sequence number and is much simpler:
Being late to the party, I didn't create a pull request. If there is interest in this implementation and it is accepted in the main code by @Koenkk, I would be happy to create a PR (after further cleaning up the code) |
Thanks for the feedback! I was actually thinking of an approach similar to this as well. I wanted to try and find middle ground in trying to align with current implementation I noticed in the convertors. The one for the Philips dimmer switch is pretty extensive... I like the 'button' and 'action' approach actually. Makes more sense. Going with that logic would it make more sense to say: Since we're implying the first half of the 'action' from the button, would it be redundant? Perhaps I'm making this more complicated than it is already. My approach was to try and expose as much of the remote's actions as possible to home assistant and then work out my automation for the key presses there. As for button 4, I'm inclined to want to merge the two command sequences mostly for a smoother transition effect. I tested paring the bulbs directly and recalling the memory commands and there's a noticeable delay in moving to the light level and then switching to color_temp. I found the approach to combine in Z2M easier than having to create a convoluted template in HA. Anyhow, not sure any of this matters as it's not guaranteed my PR will even get merged. Waiting feedback from @Koenkk 👍 |
Many automations in HA are set up to split '_' based on `attribute`, `direction`, `action`. Trying to keep the splits consistent.
I agree that having both a "Button" and an "Action" message has some redundancy to it, but it allows for two separate use cases. The first being to ignore state information and only use the information of which button was pressed, making it a generic remote. I think that's what the current converter aims to to. Just like you, and I am amazed by how our thinking is aligned, I found this too restrictive, so I looked for a way to also pass along the state information. Basically, translate the zigbee info to mqtt as closely as the remote generates it. I agree that generating two messages, even though the remote does that by design, is problematic and that combining the two messages into one would be ideal. |
I continued working on this and here is my latest suggested implementation. It consistently produce a action [ON, OFF, DIM_UP, DIM_DOWN, CT_UP, CT_DOWN, SCENE] and a button name [ON/OFF, DIM, CCT, MEMORY]. In addition, it includes STATES (brightness, color_temp, state, transition_time). As discussed, it only generates 1 message when button 4 is pressed (level/brightness is combined with color_temp in button 3 in from the second message). It doesn't rely on seq number and the only assumption it makes is that the messages are always in the same order (seems reasonable). Note that when button 4 is pressed, the state is forced to ON since this is a scene setting brightness and color temp. Button 1
Button 2
Button 3
Button 4This button recalls 3 stored states of [brightness, color_temp], aka a SCENE
The implementation is now very tidy:
|
Looks great! I cleaned up my PR a little more to align with the 'button' and 'action' approach from your suggestion. I didn't mess with the actual values being sent for brightness/color_temp. Trying to leave that as close to the original values as possible. I was debating with calling the recall button "scenes" as well, but that'd be a misnomer as scenes are handled different in the Zigbee spec, and didn't want to confuse the two. Even though it's technically a "scene". I've also implemented the hold and release functions for brightness/color_temp. Button 1 (power on/off){"button":"power","action":"on"}
{"button":"power","action":"off"} Button 2 (brightness up/down hold/release)up/down{"brightness":127,"transition":0.3,"button":"brightness","action":"brightness_up"}
{"brightness":191,"transition":0.3,"button":"brightness","action":"brightness_up"}
{"brightness":254,"transition":0.3,"button":"brightness","action":"brightness_up"}
{"brightness":191,"transition":0.3,"button":"brightness","action":"brightness_down"}
{"brightness":127,"transition":0.3,"button":"brightness","action":"brightness_down"}
{"brightness":64,"transition":0.3,"button":"brightness","action":"brightness_down"} hold/release{"button":"brightness","action":"brightness_down_hold"}
{"button":"brightness","action":"brightness_down_release","duration":780}
{"button":"brightness","action":"brightness_up_hold"}
{"button":"brightness","action":"brightness_up_release","duration":1782} Button 3 (colortemp up/down hold/release)up/down{"colortemp":222,"transition":0.3,"button":"colortemp","action":"colortemp_up"}
{"colortemp":254,"transition":0.3,"button":"colortemp","action":"colortemp_up"}
{"colortemp":285,"transition":0.3,"button":"colortemp","action":"colortemp_up"}
{"colortemp":370,"transition":0.3,"button":"colortemp","action":"colortemp_up"}
{"colortemp":285,"transition":0.3,"button":"colortemp","action":"colortemp_down"}
{"colortemp":254,"transition":0.3,"button":"colortemp","action":"colortemp_down"}
{"colortemp":22,"transition":0.3,"button":"colortemp","action":"colortemp_down"} hold/release{"button":"colortemp","action":"colortemp_down_hold"}
{"button":"colortemp","action":"colortemp_down_release","duration":780}
{"button":"colortemp","action":"colortemp_up_hold"}
{"button":"colortemp","action":"colortemp_up_release","duration":1782} Button 4 (memory recall){"color_temp":222,"transition":0.3,"button":"memory","action":"recall","brightness":127}
{"color_temp":153,"transition":0.3,"button":"memory","action":"recall","brightness":254}
{"color_temp":370,"transition":0.3,"button":"memory","action":"recall","brightness":191} |
Sounds good! Note that I've also added the state to on/off in the messages. It's redundant for button 1, but it allows for the on/off state to be kept in the other messages, since action gets over-written. Also, in the Scene/Recall mode, that state is forced to ON, which is what you would expect it to do. Also, I noticed that you divided the transition_time by 10. Why is that? I looked at the other converter and none do this. I did modify one of the input, which the the color temperature to make it to Kelvin but just noticed that I should have multiplied color_temp by 17.6 (instead of 10), because the bulb ranges from 2700K to 6500K and the color_temp ranges form 153 to 370, which means Temp in Kelvin = color_temp * 17.6. Not sure about the value of sending Kelvins instead of current 8 bit value. BTW, do you know if the remote sends out battery state? I didn't see any messages related to it and find that surprising because most battery devices do. Maybe I'll submit an alternative pull request and let @Koenkk decide which one he wants to go with (I think that handling the messages separately as done above makes the code more tidy and readable). |
I left the state portion out since z2m sends out the state for any commands that require it (i.e. brightness, color_temp, color, etc.).
So, for most of my code I was actually using a sniffer to see the actual codes being sent. The remote sends out a transition time, but it sends it as "0.3" seconds in Wireshark. I converted it back to the original. Perhaps there's a reason @Koenkk is setting it to 3 seconds? I'm not sure. But I tried to keep that value as is. As I'd like my actions to happen instantly and again, close to what the remote is sending.
My initial PR had a generic battery state, however upon inspection of the traffic from the remote I didn't see any mention of battery. Which is really odd for battery devices. I'll keep checking the traffic to see if it just reports it much later. |
Just adding to this. I know you said you're currently using Node Red for your automation, but figured others using Home Assistant might want to use this in their setup. OverviewThis setup assumes naming your remotes the same as your devices/groups but with the topic "remote" preceding it. It also assumes the topic being published to is Example 1: (control single device) Example 2: (control a group) I name my device/groups with their respective category as preceding topics as it helps me identify it better in Home Assistant for various trigger/automation. - id: 'cct_switch_d0001'
alias: Zigbee Remote
trigger:
- platform: mqtt
topic: zigbee2mqtt/remote/#
condition:
- condition: and
conditions:
- condition: template
value_template: '{{ trigger.payload_json[''action''] | length > 1 }}'
- condition: template
value_template: '{{ ''hold'' not in trigger.payload_json[''action''] and ''release''
not in trigger.payload_json[''action''] }}'
action:
- data_template:
payload_template: |
{% set remote_payload = {} %}
{% if 'action' in trigger.payload -%}
{% if trigger.payload_json.click == 'power' -%}
{% set remote_payload = {"state": "toggle" } %}
{% else %}
{% set remote_payload = {"brightness": trigger.payload_json.brightness,"color_temp": trigger.payload_json.color_temp} %}
{%- endif %}
{{ remote_payload | tojson }}
{%- else -%}
{{ trigger.payload }}
{%- endif %}
topic: '{{ "zigbee2mqtt/" + trigger.topic.split(''/'')[2:] | join(''/'') + "/set" }}'
service: mqtt.publish
initial_state: true NOTE: This will perform all functions of the remote EXCEPT the "hold/release" actions. That requires a little more work and likely be an App Daemon or scripted. |
Last update. Reverting the |
Thanks! |
Thanks for merging this in! Currently working on getting the brightness/color_temp hold+release working for the bulbs. Will push out a PR for that next. |
I wish github had notified me of this whole conversation - I was just about to rework my PR along the same general lines as this one. I contributed #822 , but it was definitely a quick and dirty first pass, and I wasn't happy with it. It was bothering me that data from the remote was being thrown away. I'm happy to see you all followed-through and cleaned it up and added the functionality to please both mindsets (i.e. receiving actual commands vs. the button numbers) around using this remote. As for battery, SmartThings and Hubitat both can receive battery notices with some of the generic Zigbee handlers. I attempted to write a native Hubitat handler before understanding that group messaging wasn't supported by Hubitat - and I did get it reporting battery, but only after I sent binding requests (probably to the standard power cluster 0x0001, since one of the generic handlers on Hubitat also received battery messages). |
* Cleanup: variable rename * Cleanup: move requestQueue to separate file, rename variables * Adapt data types in tests
UPDATE: Updated PR to now also include hold/release for color_temp. No. 5 below
This is an attempt to enhance PR #822. Currently, it only maps generic actions to the buttons (i.e. 'button_1','button_2', etc). It should align with the actions/clicks corresponding to what's listed on the remote (power on/off, brightness up/down/hold/release, color_temp up/down, recall command sequence). This will also provide easier integration into various automation platforms (HA/Mozilla)
The following is the new behavior:
1.)
button_1
->click: power_(on|off)
2.)
button_2
->action: brightness_(up|down)
(brightness
value is also provided)3.)
button_2
(hold/release) ->brightness_(up|down)_(hold|release)
(NEW FEATURE)4.)
button_3
->click: color_temp_(up|down)
(color temp
value is also provided)5.)
button_3
(hold/release) ->color_temp_(up|down)_(hold|release)
(NEW FEATURE)6.)
button_4
->action: action_recall
(since this is a two part command brightness/color, it will combine into one payload withbrightness
andcolor_temp
)Power On/Off
Brightness Up/Down (brightness increments/decrements in both direction rather than cycling from the beginning)
Brightness hold/release
Color Temp Up/Down (same logic as brightness up/down)
Recalling from 3 brightness+color_temp settings (Remote stores 3)
NOTE: There were some cosmetic changes as well to functions to make it more readable, and corrected the manufacturer name. This remote is made by Leedarson vs. Ecosmart (Home Depot). It's just bundled in the same box.