Hi,
I am a newbie to Node Red and loving it. I am trying to achieve a flow for Tuya Dimmers flashed with Tasmota and working with Homeassistant. I am wanting to use another single pushbutton on a seperate Sonoff device also running Tasmota with a switchmode1 0 with a momentary pushbutton to toggle light on/off with a short press and cycle between dim up to 100% and down to about 10% with long press. The flow I have kind of works (it is a mix of several flows i have found online) but I know there must be a more elegant way of deciding if short press (less than x milliseconds)then send toggle, else pass press push and subsequent release of button to process dimming. Any help would be greatly appreciated.
Thanks
[{"id":"6060c8b6.1977e","type":"api-current-state","z":"8fc67949.33607","name":"Office Brightness","server":"f33ae2cd.0fa4","version":1,"outputs":1,"halt_if":"","halt_if_type":"str","halt_if_compare":"is","override_topic":true,"entity_id":"light.office_light","state_type":"str","state_location":"payload","override_payload":"msg","entity_location":"data","override_data":"msg","blockInputOverrides":false,"x":150,"y":500,"wires":[["83302ba.965fdd8"]]},{"id":"69e8c99.022afb8","type":"change","z":"8fc67949.33607","name":"Get Brightness","rules":[{"t":"set","p":"payload","pt":"msg","to":"data.attributes.brightness","tot":"msg"}],"action":"","property":"","from":"","to":"","reg":false,"x":340,"y":560,"wires":[["d4743cd1.548d"]]},{"id":"49cf06fb.b1e638","type":"function","z":"8fc67949.33607","name":"Add Fib","func":"var iCurr = context.flow.get('iCurr') || 2;\nvar iPrev = context.flow.get('iPrev') || 1;\nvar iFib = context.flow.get('iFib') || 2;\n\nmsg.payload = Math.min(100, msg.payload + iFib);\n\niCurr = iFib;\niFib = iFib + iPrev;\niPrev = iCurr;\n\ncontext.flow.set('iCurr',iCurr);\ncontext.flow.set('iPrev',iPrev);\ncontext.flow.set('iFib',iFib);\n\nif (iCurr == 2){\n context.flow.set('dCurr',null);\n context.flow.set('dPrev',null);\n context.flow.set('dFib',null);\n}\n\nreturn msg;","outputs":1,"noerr":0,"x":920,"y":360,"wires":[["58176016.a7ef9","c293ba8f.64b658"]]},{"id":"d2213fcb.659ac8","type":"server-state-changed","z":"8fc67949.33607","name":"Office Switch State","server":"f33ae2cd.0fa4","version":1,"entityidfilter":"binary_sensor.office_switch","entityidfiltertype":"substring","outputinitially":false,"state_type":"str","haltifstate":"","halt_if_type":"str","halt_if_compare":"is","outputs":1,"output_only_on_state_change":false,"x":110,"y":220,"wires":[["fdcd66b3.9e41a","d4de75bd.11a56"]]},{"id":"d4de75bd.11a56","type":"switch","z":"8fc67949.33607","name":"Hold State","property":"payload","propertyType":"msg","rules":[{"t":"eq","v":"on","vt":"str"},{"t":"nnull"}],"checkall":"true","repair":false,"outputs":2,"x":150,"y":300,"wires":[["6060c8b6.1977e"],["b2f3b0b3.cc8f2","b1580762.edfe5"]]},{"id":"c5848476.d0628","type":"function","z":"8fc67949.33607","name":"Subtract Fib","func":"var dCurr = context.flow.get('dCurr') || 2;\nvar dPrev = context.flow.get('dPrev') || 1;\nvar dFib = context.flow.get('dFib') || 2;\n\nmsg.payload = Math.max(10, msg.payload - dFib);\n\ndCurr = dFib;\ndFib = dFib + dPrev;\ndPrev = dCurr;\n\ncontext.flow.set('dCurr',dCurr);\ncontext.flow.set('dPrev',dPrev);\ncontext.flow.set('dFib',dFib);\n\nif (dCurr == 2){\n context.flow.set('iCurr',null);\n context.flow.set('iPrev',null);\n context.flow.set('iFib',null);\n}\n\nreturn msg;","outputs":1,"noerr":0,"x":890,"y":300,"wires":[["3ed7284c.f01ff","c293ba8f.64b658"]]},{"id":"ac48a0d5.87cf1","type":"msg-router","z":"8fc67949.33607","routerType":"roundrobin","topicDependent":false,"counterReset":true,"msgKeyField":"payload","undefinedHash":false,"outputsInfo":[{"active":true,"clone":false,"delay":"0","weight":"0"},{"active":true,"clone":false,"delay":"0","weight":"0"}],"name":"Round Robin Router","delaying":"unrelated","msgControl":false,"outputs":2,"x":740,"y":560,"wires":[["49cf06fb.b1e638"],["c5848476.d0628"]]},{"id":"aa22df38.988778","type":"api-call-service","z":"8fc67949.33607","name":"Office Light","server":"f33ae2cd.0fa4","service_domain":"light","service":"turn_on","data":"{\"entity_id\":\"light.office_light\"}","mergecontext":"","output_location":"payload","output_location_type":"msg","mustacheAltTags":false,"x":1330,"y":360,"wires":[[]],"icon":"node-red/light.png"},{"id":"b2f3b0b3.cc8f2","type":"traffic","z":"8fc67949.33607","name":"Break when Stop","property_allow":"payload","filter_allow":"on","ignore_case_allow":false,"negate_allow":false,"send_allow":false,"property_stop":"payload","filter_stop":"off","ignore_case_stop":false,"negate_stop":false,"send_stop":false,"default_start":true,"differ":false,"x":670,"y":260,"wires":[["c5848476.d0628"]]},{"id":"3ed7284c.f01ff","type":"delay","z":"8fc67949.33607","name":"","pauseType":"delay","timeout":"400","timeoutUnits":"milliseconds","rate":"1","nbRateUnits":"1","rateUnits":"second","randomFirst":"1","randomLast":"5","randomUnits":"seconds","drop":false,"x":670,"y":200,"wires":[["b2f3b0b3.cc8f2"]]},{"id":"b1580762.edfe5","type":"traffic","z":"8fc67949.33607","name":"Break when Stop","property_allow":"payload","filter_allow":"on","ignore_case_allow":false,"negate_allow":false,"send_allow":false,"property_stop":"payload","filter_stop":"off","ignore_case_stop":false,"negate_stop":false,"send_stop":false,"default_start":true,"differ":false,"x":670,"y":360,"wires":[["49cf06fb.b1e638"]]},{"id":"58176016.a7ef9","type":"delay","z":"8fc67949.33607","name":"","pauseType":"delay","timeout":"400","timeoutUnits":"milliseconds","rate":"1","nbRateUnits":"1","rateUnits":"second","randomFirst":"1","randomLast":"5","randomUnits":"seconds","drop":false,"x":650,"y":420,"wires":[["b1580762.edfe5"]]},{"id":"d4743cd1.548d","type":"range","z":"8fc67949.33607","minin":"1","maxin":"255","minout":"1","maxout":"100","action":"clamp","round":true,"property":"payload","name":"Brightness %","x":520,"y":560,"wires":[["ac48a0d5.87cf1"]]},{"id":"83302ba.965fdd8","type":"switch","z":"8fc67949.33607","name":"Light On/Off","property":"payload","propertyType":"msg","rules":[{"t":"eq","v":"on","vt":"str"},{"t":"eq","v":"off","vt":"str"}],"checkall":"true","repair":false,"outputs":2,"x":150,"y":560,"wires":[["69e8c99.022afb8"],["e9b0771a.56668"]]},{"id":"e9b0771a.56668","type":"change","z":"8fc67949.33607","name":"Set Brightness","rules":[{"t":"set","p":"payload","pt":"msg","to":"10","tot":"num"}],"action":"","property":"","from":"","to":"","reg":false,"x":340,"y":640,"wires":[["3f9bbda3.c02cca"]]},{"id":"3f9bbda3.c02cca","type":"function","z":"8fc67949.33607","name":"Reset Context","func":"context.flow.set('iCurr',null);\ncontext.flow.set('iPrev',null);\ncontext.flow.set('iFib',null);\n\nreturn msg;","outputs":1,"noerr":0,"x":520,"y":640,"wires":[["49cf06fb.b1e638","68a8e294.84651c"]]},{"id":"68a8e294.84651c","type":"change","z":"8fc67949.33607","name":"Reset Router","rules":[{"t":"set","p":"reset","pt":"msg","to":"true","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":690,"y":640,"wires":[["ac48a0d5.87cf1"]]},{"id":"c293ba8f.64b658","type":"function","z":"8fc67949.33607","name":"Brightness Data","func":"newmsg = {};\n\nbrightness = msg.payload;\n\nnewmsg.payload = { data: {\"brightness_pct\":brightness, \"transition\":0.1 }};\n\nreturn newmsg;","outputs":1,"noerr":0,"x":1160,"y":360,"wires":[["aa22df38.988778"]]},{"id":"bdecf56c.911b78","type":"comment","z":"8fc67949.33607","name":"Why not events?","info":"You must use state because \"hold\" is\ncommunicated by the switch being \"on\".\n\nWe capture the release by the state being \"off\".\n\nThe events node lets you capture a\n\"long click\", but not a hold.","x":100,"y":180,"wires":[]},{"id":"55b063ca.037e94","type":"comment","z":"8fc67949.33607","name":"What's happening here?","info":"If the light is on then we capture its\nbrightness attribute thanks to the\noverride payload earlier. Now we set payload\nto brightness.\n\nIf it's off then we set payload (brightness)\nto 1.","x":150,"y":460,"wires":[]},{"id":"ce214ee1.0cb6f8","type":"comment","z":"8fc67949.33607","name":"Reset?","info":"In Add Fib we have variables that allow us to\nincrease in fibonacci increments.\n\nThese variables are set in the node context\nwhich only ever go back to null if we redeploy\nor explicitly say so.\n\nLet's say we just brightened the light, then\nturned it off. The variables will still be set.\n(They are reset when you go through the other\ndirection).\nWe want to start brightening our light with\nsmall increments again, so we nullify the\ncontext.\n\nWe also need to reset the router because if we\ndimmed, then turned off light, it will want to\nbrighten next time. But we *are* brightening\nnow (from off)! So we reset it because next time\nit should dim.","x":530,"y":700,"wires":[]},{"id":"eb4abda1.de66b","type":"comment","z":"8fc67949.33607","name":"Router?","info":"Round Robin.\n\nWe brighten.\nWe dim.\nWe brighten.\nWe dim.\netc.","x":730,"y":520,"wires":[]},{"id":"49eff3d2.ae64fc","type":"comment","z":"8fc67949.33607","name":"Loops?","info":"Both loops work the same.\n\nWe receive the payload with brightness % and then\nstart adding/subtracting fibonacci increments.\n\nThe traffic node allows this loop to continue\nas long as the hold state is \"on\". Once the hold\nstate changes to \"off\" the loop is broken.\n\nEvery 500ms a light.turn_on with a brightness\nand transition option is sent to the light\nspecified, hopefully gracefully brightening\nthe light.\n\nThere is a little Math in the functions to\ninsure that we don't go below 0% or over 100%.","x":670,"y":300,"wires":[]},{"id":"c1670d07.441d88","type":"debug","z":"8fc67949.33607","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","x":1510,"y":260,"wires":[]},{"id":"b4dea629.3cf7c","type":"switch","z":"8fc67949.33607","name":"Short toggle","property":"payload","propertyType":"msg","rules":[{"t":"eq","v":"short","vt":"str"}],"checkall":"true","repair":false,"outputs":1,"x":790,"y":80,"wires":[["2870c693.ebfbaa"]]},{"id":"2870c693.ebfbaa","type":"change","z":"8fc67949.33607","name":"Toggle","rules":[{"t":"set","p":"payload","pt":"msg","to":"toggle","tot":"str"}],"action":"","property":"","from":"","to":"","reg":false,"x":930,"y":80,"wires":[["b1a73ca2.6c77a8"]]},{"id":"fdcd66b3.9e41a","type":"change","z":"8fc67949.33607","name":"Add timestamp","rules":[{"t":"set","p":"payload","pt":"msg","to":"{\t 'state': payload,\t 'timestamp': $millis()\t}","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":140,"y":80,"wires":[["74932ec.17155d"]]},{"id":"74932ec.17155d","type":"join","z":"8fc67949.33607","name":"","mode":"custom","build":"object","property":"payload","propertyType":"msg","key":"payload.state","joiner":"\\n","joinerType":"str","accumulate":false,"timeout":"","count":"2","reduceRight":false,"reduceExp":"","reduceInit":"","reduceInitType":"","reduceFixup":"","x":290,"y":80,"wires":[["e596acd1.f23bb"]]},{"id":"e1c5e484.53c948","type":"change","z":"8fc67949.33607","name":"Process delta","rules":[{"t":"set","p":"threshold","pt":"msg","to":"400","tot":"num"},{"t":"set","p":"delta","pt":"msg","to":"$lookup(payload, 'off').timestamp - $lookup(payload, 'on').timestamp","tot":"jsonata"},{"t":"set","p":"payload","pt":"msg","to":"delta < threshold ? 'short' : 'long'","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":620,"y":80,"wires":[["b4dea629.3cf7c"]]},{"id":"e596acd1.f23bb","type":"switch","z":"8fc67949.33607","name":"Filter negative","property":"$lookup(payload, 'off').timestamp - $lookup(payload, 'on').timestamp","propertyType":"jsonata","rules":[{"t":"nnull"}],"checkall":"true","repair":false,"outputs":1,"x":440,"y":80,"wires":[["e1c5e484.53c948"]]},{"id":"8f4d0d9a.3086c","type":"api-call-service","z":"8fc67949.33607","name":"Office Light","server":"f33ae2cd.0fa4","service_domain":"light","service":"toggle","data":"{\"entity_id\":\"light.office_light\"}","mergecontext":"","output_location":"payload","output_location_type":"msg","mustacheAltTags":false,"x":1250,"y":80,"wires":[[]],"icon":"node-red/light.png"},{"id":"b1a73ca2.6c77a8","type":"change","z":"8fc67949.33607","name":"Set Brightness","rules":[{"t":"set","p":"payload","pt":"msg","to":"10","tot":"num"}],"action":"","property":"","from":"","to":"","reg":false,"x":1080,"y":80,"wires":[["8f4d0d9a.3086c"]]},{"id":"f33ae2cd.0fa4","type":"server","z":"","name":"Home Assistant","legacy":false,"hassio":true,"rejectUnauthorizedCerts":true,"ha_boolean":"y|yes|true|on|home|open","connectionDelay":false}]