deconz-rest-plugin icon indicating copy to clipboard operation
deconz-rest-plugin copied to clipboard

Add support for Tuya (Abalon, Zemismart, ...) Curtain Motor

Open thertweck opened this issue 1 year ago • 9 comments

Is there already an existing issue for this?

  • [X] I have searched the existing issues and there is none for my device

Product name

Abalon Motorized Curtains, Zemismart Smart Curtain

Manufacturer

_TZE200_rmymn92d

Model identifier

TS0601

Device type to add

Other

Node info

node_info

Endpoints and clusters

clusters

Basic

basic

Further relevant clusters

Tuya Specific (EF00)

Does not show any attributes.

thertweck avatar Jan 23 '24 22:01 thertweck

@Smanar is anything missing?

Mimiix avatar Jan 24 '24 10:01 Mimiix

Yep a support for tuya covering using DDF ^^. For the moment not possible using DDF for covering, siren or other device using the tuya cluster and need other command than state/on or state/bri.

Smanar avatar Jan 24 '24 15:01 Smanar

I see, thank you for the swift feedback! There seems to be some preliminary support though, right? E.g. here, here and here. In particular the YS-MT750 device also looks very similar to the ones I got. I'd be happy to work on this if it's in scope currently. Would appreciate any pointers on where to start though.

thertweck avatar Jan 24 '24 16:01 thertweck

Hi there @thertweck : I'm also looking at Tuya Cluster using blinds (AM43, see current bugs) and would be happy help out as well.

The DDF can be used to recognise and bind the device, but IIRC there is a missing property that associates between the open/close condition of the resource, and sending commands to the Tuya cluster to achieve it. There's an On/Off hack, but it's very unsatisfactory.

The current legacy Tuya code for window coverings is somewhat hit/miss in terms of actually getting the bindings to work, so a longer term transition to DDF for them would be amazing! (If it's technically possible....)

ebeasant-arm avatar Jan 24 '24 17:01 ebeasant-arm

The support using the legacy code is possible but

  • you need to compile the code yourself, but I can give te code.
  • The solution will be only for you, never official because for futur device we need to use the DDF core, the support using legacy core is stopped.

It's possible to using a "hacky DDF" but unoffocial too, using state/on for open and state/bri for lift.

Smanar avatar Jan 24 '24 18:01 Smanar

@ebeasant-arm Thank you for the pointer, I'll have a look! IIUC bindings are for direct device to device communication, circumventing the gateway? For me that would be secondary, since I'm using iobroker anyway to "bind" devices also apart from the Zigbee network.

@Smanar That sounds great, it would be amazing to have a temporary hacky solution - no problem compiling deconz. Also if it's easier, a hacky DDF would be ok for me too. Would the idea be to use "state/on" / "state/bri" together with fn: "tuya" to map it to the correct dpids?

thertweck avatar Jan 25 '24 10:01 thertweck

Here you have a post where we make a "hacky DDF" for a covering https://github.com/dresden-elektronik/deconz-rest-plugin/issues/5960#issuecomment-1616634196

The procedure is explained.

I can help you to find dpid if needed. Or I can make you a c++ branch to support your device, but it meen a every new deconz version you need to re complile the code again.

What do you prefering ?

Smanar avatar Jan 25 '24 19:01 Smanar

As there has not been any response in 21 days, this issue has been automatically marked as stale. At OP: Please either close this issue or keep it active It will be closed in 7 days if no further activity occurs.

github-actions[bot] avatar Feb 16 '24 01:02 github-actions[bot]

@thertweck did you find a solution to control your device without applying the "light"-hack? i have an identical device and can only control open/close via REST API but not "stop" as lights only have a boolean on/off value. any advice/hint would be appreciated!

nabossha avatar Feb 23 '24 00:02 nabossha

Just got to work on this again as I now have one of the tracks properly installed.

@Smanar I followed the thread you mentioned with some success. I couldn't get the "on" attribute to work properly though. I think the reason is that after moving in one direction, the curtain will move a slight bit in the opposite direction again (e.g. when closing the curtain, it will reach the end position and then open again just a little bit). I assume (but I have to double check) that in this situation the curtain would report "close" while closing, "stop" when reaching the end position and then report "open" for a fraction of a second while moving back. I think this also explains what @patrusco observed in the other thread.

The "bri" attribute (with dpid 2 on the curtain) however does work well and that is absolutely sufficient for me, since I'm using this through iobroker / yahka and Alexa anyway.

I tried faking the "on" attribute based on dpid 2 - was thinking to do something like:

"write": {
    "dpid": 2,
    "dt": "0x2b",
    "eval": "Item.val == 1 ? 100 : 0;",
    "fn": "tuya"
},
"parse": {
     "dpid": 2,
     "eval": "Item.val = Attr.val > 0;",
     "fn": "tuya"
}

But that didn't work, maybe two attributes cannot use the same dpid? Now I'm just using a static value for on, which makes the deconz adapter in iobroker happy.

What's a little odd though is that the motor doesn't report position updates when using the curtain's remote or when moving the curtain manually. Even though the curtain is closing and position would go to 0 in reality, the value available in deconz is e.g. still 255 (fully open).

Not sure whether the refresh.interval is a solution to this - I tried, but it didn't make a difference.

The curtain reporting its real position is however very useful for UIs like Homekit, where one always has a "current" position and a "target" position. That allows to visualize the direction in which movement happens as well as detecting when the requested movement is finished (when current == target). I'm currently faking this too in iobroker, by estimating the time it would take for a movement to finish and am setting current = target after this time. That works well so far, since the curtain motors move fairly deterministically.

@nabossha I don't have a solution for the "on" attribute, but for me percentage control is sufficient. Instead of requesting "open" and then "stop" at the position I want, I can just directly have the curtain move to a certain position.

thertweck avatar Mar 11 '24 08:03 thertweck

The "bri" field is a numeric value in percent. It's the "lift" value on classic covering. Can use like in previous post


        {
          "name": "state/bri",
          "parse": {"fn": "tuya", "dpid": 2, "eval": "Item.val = (Attr.val / 100.0) * 254.0;"},
          "write": {"fn": "tuya", "dpid": 2, "dt": "0x2b", "eval": "(Item.val / 254.0) * 100.0;"},
          "read": {"fn": "none"}
        }

refresh.interval is useless, the tuya cluster don't use it.

Smanar avatar Mar 11 '24 16:03 Smanar

Right, I'm currently doing exactly that and it's working great so far. Thank you for all the pointers. Only problem is, that the curtain motor doesn't report its position when a movement is triggered from outside of deconz (via the remote or manual operation). But that's not a big issue for me at the moment, I'd use Homekit or Alexa for interacting with the curtain most of the time anyway.

But is it true that two attributes cannot use the same dpid? Because what I was trying to say above was that I'd like to use dpid 2 for the "bri" state as you mentioned above but also for the "on" state with the write and parse fns from the previous post (mapping it to a boolean value). This could be used to work around the issue with dpid 1 being unreliable on that motor.

Just curious: Is there a reason you're using 254 as the maximum value in the eval? I was assuming this is a byte, with maximum value 255. But not sure what this might cause under the hood. Is 255 treated in a special way somewhere else?

thertweck avatar Mar 11 '24 17:03 thertweck

Only problem is, that the curtain motor doesn't report its position when a movement is triggered from outside of deconz (via the remote or manual operation). But that's not a big issue for me at the moment, I'd use Homekit or Alexa for interacting with the curtain most of the time anyway

With deconz log enabled "info+info_l2" you will see all request made by the device, so can take a look if the device don't make one or if we miss it.

But is it true that two attributes cannot use the same dpid?

No, it's not a problem, there is lot of DDF that are using the same dpid or attribute for different field.

Is there a reason you're using 254 as the maximum value in the eval?

Yes, probably ^^, good question (I will ask to other devs by curiosity) it's same in native code for classic covering https://github.com/dresden-elektronik/deconz-rest-plugin/blob/master/window_covering.cpp#L200 But honneslty I don't see the utility for tuya covering.

Smanar avatar Mar 12 '24 16:03 Smanar

@thertweck I have the answer from Ebaauw

Because the max value for Current Level is 254, as defined in the Level Control cluster

Smanar avatar Mar 12 '24 18:03 Smanar

As there has not been any response in 21 days, this issue has been automatically marked as stale. At OP: Please either close this issue or keep it active It will be closed in 7 days if no further activity occurs.

github-actions[bot] avatar Apr 03 '24 01:04 github-actions[bot]

As there has not been any response in 28 days, this issue will be closed. @ OP: If this issue is solved post what fixed it for you. If it is not solved, request to get this opened again.

github-actions[bot] avatar Apr 10 '24 01:04 github-actions[bot]