Dimming duration values not sent to bound devices when switching on/off

I’ve got a blue series 2-1 switch bound via group associations to some Juno recessed wafer lights. No matter what I do, I cannot get the lights to dim at anything other than their default rate from the inovelli switch, when turning on or off.

I’m running firmware 2.08, ZHA, and homeassistant 2022.12.1.

If I send commands to the light directly, using the light.turn_on service in HA, with a duration parameter, then they respect that parameter, which leads me to believe the problem is on the inovelli side. I’m trying to do everything as close to the raw zigbee protocol as possible, to eliminate any possible bugs in zha or the quirks library.

This seems very similar to [BUG?] Association not sending 'duration' parameter with MultilevelSet(value,duration) commands, although that was on the zwave switch, so it’s a separate implementation of the same erroneous behavior.

Has anyone else gotten this to work? I think I’ve got a zigbee sniffer around somewhere, if I can find it, I’d be able to see what the actual packets are.

What doesn’t help is the lack of documentation around what endpoints 1 and 2 are for on the blue series switches. Does anybody know which is for what? At this point I’m just trying all the combinations I can think of.

One oddity that’s perhaps related is that when I have a binding for cluster 8 (level control) but not for cluster 6 (on/off), and the light is on, and I hold down on the paddle, it gets dimmer. But if I hold up on the paddle, it doesn’t get brighter. Adding cluster 6 to the binding resolves it, so it’s mostly just an oddity.

I’ve confirmed the problem with the following steps:

Given: (shared setup for all tests)

  1. Install firmware 2.08
  2. Factory reset switch
  3. Enable smart bulb mode
  4. Change parameter 1 to 50, for a 5 second slow fade, just to make it obvious that it’s not matching. Leave parameters 2 through 8 at 127, to match parameter 1.
  5. Bind a zigbee bulb via either a group or individually.


  • The light is off, and I turn it on by pressing up on the paddle, I observe that (x) the blue LED bar takes the expected 5 seconds to fade to full, but the light comes on much faster. (I expect the light to be in sync with the bar)
  • The light is on, and I turn it off by pressing down on the paddle, I observe the same thing: the LED bar takes the expected 5 seconds to fade to off, but the light turns off much faster.
  • When the light is on, and I hold up or down, the light and LED bar fade together, at the same rate, as expected.

When I inspect my binding, I see that the zigbee bulb is bound to the inovelli switch four times: endpoint 1 cluster 6, endpoint 2 cluster 6, endpoint 1 cluster 8, endpoint 2 cluster 8.

1 Like

EP1 should not be bound from the switch to the bulbs, EP1 is for commands being sent to the switch, from the coordinator, switches that are bound to it and so on. EP2 can be though of as the ‘remote’ cluster and should be bound to the bulbs (this would be on the other device’s EP1, so EP2 on switch > EP1 on bulb/switch/group, etc). I’d have to double check, but I believe this got cleaned up in ZHA so that those are the only options you should see.

Are you able to remove the bindings currently set and redo them just from EP2 on the Blue > EP1 on a Juno bulb and re-test?

1 Like

In ZHA, under Manage Zigbee Device → Clusters, I see that the blue switch reports the following clusters:


What you said about EP1 and EP2 is the first description I’ve found about what the difference is between the two endpoints, and why there are two. But it also seems unnecessary. Isn’t that segregation precisely why the zigbee standard defines both “in” and “out” clusters separately? What advantage is there to having a separate endpoint, and to defining an “out” cluster for both endpoint 1 and 2? Or is the inclusion of the endpoint 1 “out” clusters a mistake? It looks like one of the changes made in the quirks file for the VZM31SN is adjusting the signature of which clusters are supported for which endpoints.

Binding just EP2 on clusters 6 and 8 results in on/off control only, with no dimming control. (EDIT: I no longer observe this. I’m going to chalk it up to me making a mistake about what was actually bound to what) Binding just EP1 on clusters 6 and 8 results in no control at all.

When actually binding EP2 should only have a few options, you select On/Off and LevelControl. That should be all that is required.

Chack is right. EP1 is the receipt side and EP2 is the controller side for bindings.

1 Like

That makes sense, but the logical next question from that is why does EP1 have any “out” clusters at all?

Can you confirm which quirk is being applied to this switch? On 2.08 it should be “InovelliVZM31SNv12” as is in the quirk file you linked, that shouldn’t have any out clusters for EP1.

1 Like

Ah, the quirk is out of date! I’ve got v11 listed on my device info page. How do I update it? I’m on home assistant 2022.12.3

1 Like

It’s possible it’s just a matter of the signature being cached since you’ve joined the device. Best way is to remove the switch from HA, reset and rejoin the switch to ZHA and it’ll pull in the signature fresh. That should result in you seeing the v12 quirk being applied, if not, we’ll need to fix the quirk in ZHA and figure out what’s coming through from your switch that’s preventing it from matching.

ok, I’ve got all the lights bound using EP2, clusters 6 and 8, and they seem to work fine.

There are still some unexpected behaviors I observe, though.

The issue with dimming speed not being set when also changing the on/off state remains. I noticed that there’s a separate parameter called “on/off transition time” which I updated from the default (30) to 50, but the lights still fade on/off over about 1 second, not 3 or 5. There was no change when I updated “on/off transition time”

I noticed a new issue, which can be reproduced by

  1. Dim the switch and light to 40%. Wait for them to reach that level.
  2. Press down on the switch. Both the light and light bar fade to zero, although they use different speeds (this is the first bug). Wait for them to both finish.
  3. With the light and switch both off, hold the up paddle. The light bar on the switch starts fading up from zero, but the light bumps to 40% and then starts fading up at the same rate as the light bar on the switch, but a constant offset of 40% higher.
  4. Release the paddle when the light bar gets to around 50 or 60%. The light now quickly bumps back down from where it was (light bar + 40%) to the value of the light bar.

My guess as to what’s happening is that when the bulb gets the turn off command, it turns off, but its “current_level” is still set to whatever it was at when it was on. Then the switch sends a “move” command to increase the level at a certain rate, which it does, starting at its “current_level”.

I think the way to fix this would be to add logic to the switch firmware that, if the switch was off and you hold up on the paddle, before sending a move command, send a move_to_level (level = 0, transition_time = 0) command to bound devices.

1 Like

I did more or less this, and it did the trick. Now I’m on v12.

Specific instructions for future reference:

  1. Go to the device page, hamburger menu in the top left, and press Remove:
    This removes the switch and puts it in pairing mode.
  2. Go back to the zha integration configure screen, press “add device”
  3. When it shows up, give it the same name as before. This should preserve most automations that use it, but perhaps not all.
1 Like

Updating the quirk resolved some of the issues I was having with the “normal” way of doing binding with ZHA, but it didn’t do anything to fix the underlying behavior of the switch.

I think there are two likely firmware bugs here:

  1. Not sending duration values with on/off commands (maybe the issue is sending on/off rather than move_to_level?
  2. Not telling bound bulbs to start the fade at zero when holding up with the switch off

I don’t think my Juno lights are the issue, since I also bound a Philips Hue recessed light, and saw the same behavior.

Can anyone else confirm these, and then we can hopefully get them on the “official” bug list?

1 Like

I’ve reported this to the issues log with the manufacturer.

After digging in deeper to a related issue in another thread, I think the inovelli switch and Juno lights are both following the ZigBee spec, but the ZigBee spec results in undesired/unintuitive behavior. Especially annoying is the fact that the “On” and “Off” commands don’t have parameters for a duration.

Unfortunately, the solution I proposed to that other thread won’t work for generic bound zigbee lights, since we can’t change their behavior, and in truth can only kind of hope they mostly follow the spec. But I’ve got an idea that would bring the observed behavior in line with what I’d expect to happen, inspired by @mamber’s workaround in the hubitat driver.

This is assuming my idea in the other thread is implemented first/at the same time.

When sending commands to a bound zigbee device, use different behavior depending on whether both OnOff and LevelControl are bound, or just OnOff. If only OnOff is bound, just do current behavior.
If both are bound:

  • On receipt of an “on” command which the existing logic decides should be sent to bound devices, instead of sending “on”,
    • First send “move to level” with a level equal to the switch’s CurrentLevel from the LevelControl cluster, and a duration of 0. I’m not sure if “Move to Level” or “Move to Level with On/Off” would be better here. It seems like it would probably be a good idea to set the ExecuteIfOff bit to 1 on the OptionsMask and OptionsOverride fields for this command.
    • Next send a “Move to Level with On/Off” command with the target level and duration set to the value the internal dimmer is moving to, according to the existing logic or what I specified in the other thread.
  • On receipt of an “off” command which the existing logic decides should be sent to bound devices:
    • Send a “Move to level with On/Off” command, with a target level of 0, and a duration set according to the existing logic for the internal dimmer.

I think the “Move to level 0 with On/Off” should be sufficient to leave the CurrentLevel of the bound light(s) at either 0 or 1, which means that no matter how they’re turned on, they’ll start their fade from off.

Well, I think that is the real issue. Its the way the Zigbee Alliance defined it. The firmware is following the spec even though many of us believe this is undesired behavior.

And again, this would not be following the Zigbee standards. Asking the firmware to behave differently than Zigbee standard is an unlikely proposition.

When a device is bound to another device, it essentially just repeats the commands it is given for the bound cluster. If the primary device (usually the switch) receives an ON command, thats what its going to send to the target devices (usually bulbs) If the primary device receives a MOVE_TO_LEVEL command then thats what its going to send to the target devices.

I think the issue is that different devices have different default transition times. And I suspect (but just guessing) the firmware is not sending the optional transition time with the MOVE_TO_LEVEL command and so the target device uses its default transition time which is likely different than the switches default transition time. It is my belief that the primary device should always send its transition time in any bound Set Level Cluster commands. That way, all bound devices would be using the same transition. However, it doesn’t force them to all start at the same level.

1 Like