Tuya-Szenenschalter: Klick- und Sequenz­erkennung über Countdown-Trick

- Veröffentlicht unter Makerspace von

Hinweis: Der Beitrag wurde von KI entworfen und manuell nachbearbeitet. Er basiert auf einem real eingesetzten System; Gerätebezeichnungen wurden anonymisiert.

🛒 = Affiliate-Link (Werbung). Wenn du über diesen Link etwas kaufst, erhalte ich eine kleine Provision – für dich bleibt der Preis gleich.


Projektziel

Ein Tuya-Szenenschalter (zum Beispiel von MOES🛒)soll in Home Assistant nicht nur Szenen umschalten, sondern jede einzelne Betätigung (kurz, doppelt, lang) erfassen – auch wenn die Szene sich nicht ändert. Da localtuya keine Events für gleichbleibende Szenen sendet, wird eine Tuya-Steckdose mit Countdown-Funktion als Event-Proxy verwendet.


Funktionsprinzip

Die Smart-Life-App löst für jeden Klicktyp eine Automation aus, die den Countdown der Steckdose auf einen eindeutigen, hohen Wert setzt (z. B. 70 000 – 80 000 Sekunden). Die Steckdose bleibt dabei aus, sendet aber über localtuya eine Statusänderung an Home Assistant. Diese Countdown-Änderung dient als Signal, das in HA ausgewertet wird.

Damit aus den Events verwertbare Befehle werden, kommen vier Automationen zum Einsatz:

  • Klicks erfassen und in einem Textpuffer speichern
  • Pausen zwischen Klicks erkennen
  • Den Verlauf bei Inaktivität zurücksetzen
  • Muster interpretieren und Aktionen auslösen

Automation 1 – Klicks erfassen

Wandelt Countdownwerte in Klickzeichen (S / D / L) um und speichert sie im input_text-Puffer. Der Countdown wird anschließend auf 0 gesetzt, damit die Steckdose bereit für das nächste Event bleibt (und sich nicht doch irgendwann ausschaltet, falls sie gerade an ist).

alias: Szenenschalter Klicks erfassen
description: Erfasst Klicks (S/D/L) über Countdownwerte und speichert sie im Klickverlauf.
triggers:
  - entity_id: number.schalter_countdown
    above: 0
    trigger: numeric_state
actions:
  - variables:
      val: "{{ states('number.schalter_countdown') | int(0) }}"
      klick: >
        {% if val > 80000 %}S{% elif val > 75000 %}D{% elif val > 70000 %}L{% else %}{% endif %}
  - target:
      entity_id: input_text.klickverlauf
    data:
      value: "{{ states('input_text.klickverlauf') + klick }}"
    action: input_text.set_value
  - target:
      entity_id: number.schalter_countdown
    data:
      value: 0
    action: number.set_value
mode: single

Automation 2 – Pausen markieren

Nach 6 Sekunden ohne neue Klicks wird ein Bindestrich („-“) an den Verlauf angehängt, um Sequenzen voneinander zu trennen.

alias: Szenenschalter Klickpause markieren
description: Fügt nach einer kurzen Pause einen '-' als Trenner ein.
triggers:
  - entity_id: input_text.klickverlauf
    for: "00:00:06"
    trigger: state
conditions:
  - condition: template
    value_template: >
      {% set v = states('input_text.klickverlauf') %}
      {{ v not in ['', 'unknown', 'unavailable'] and not (v | regex_search('-$')) }}
actions:
  - variables:
      alt: "{{ states('input_text.klickverlauf') }}"
      neu: "{{ alt ~ '-' }}"
  - target:
      entity_id: input_text.klickverlauf
    data:
      value: "{{ neu }}"
    action: input_text.set_value
mode: restart

Automation 3 – Verlauf zurücksetzen

Wird 15 Sekunden lang keine Eingabe erkannt und der Verlauf endet bereits auf „-“, wird er gelöscht.

alias: Szenenschalter Klickverlauf Reset
description: Setzt Klickverlauf zurück, wenn sich 15 s lang nichts geändert hat.
triggers:
  - entity_id: input_text.klickverlauf
    for: "00:00:15"
    trigger: state
conditions:
  - condition: template
    value_template: >
      {% set v = states('input_text.klickverlauf') %}
      {{ v | regex_search('-$') }}
actions:
  - target:
      entity_id: input_text.klickverlauf
    data:
      value: ""
    action: input_text.set_value
mode: single

Automation 4 – Klickmuster auswerten

Diese Automation interpretiert bekannte Klickfolgen und löst passende Aktionen aus.

alias: Szenenschalter Klickmuster auswerten
description: Erkennt verschiedene Klickmuster (S/D/L) und führt zugehörige Aktionen aus.
triggers:
  - entity_id: input_text.klickverlauf
    trigger: state
conditions:
  - condition: template
    value_template: "{{ verlauf != '' }}"
actions:
  - choose:
      - conditions:
          - condition: template
            value_template: "{{ verlauf == 'S' }}"
        sequence:
          - action: light.toggle
            target:
              entity_id: light.geraet_1
          - action: input_text.set_value
            target:
              entity_id: input_text.klickverlauf
            data:
              value: ""
      - conditions:
          - condition: template
            value_template: "{{ verlauf == 'DD' }}"
        sequence:
          - action: scene.turn_on
            target:
              entity_id: scene.aktion_1
          - action: input_text.set_value
            target:
              entity_id: input_text.klickverlauf
            data:
              value: ""
      - conditions:
          - condition: template
            value_template: "{{ verlauf == 'L-' }}"
        sequence:
          - choose:
              - conditions:
                  - condition: template
                    value_template: >
                      {{ expand(geraete) | selectattr('state','eq','on') | list | count > 0 }}
                sequence:
                  - action: light.turn_off
                    target:
                      entity_id: "{{ geraete }}"
              - conditions:
                  - condition: template
                    value_template: >
                      {{ expand(geraete) | selectattr('state','eq','off') | list | count == geraete | count }}
                sequence:
                  - action: light.turn_on
                    target:
                      entity_id: "{{ geraete }}"
          - action: input_text.set_value
            target:
              entity_id: input_text.klickverlauf
            data:
              value: ""
  - condition: template
    value_template: "{{ '-' in verlauf }}"
  - action: input_text.set_value
    target:
      entity_id: input_text.klickverlauf
    data:
      value: ""
mode: single
variables:
  verlauf: "{{ trigger.to_state.state | default('') }}"
  geraete:
    - light.geraet_1
    - light.geraet_2
    - light.geraet_3

Hinweise & Erweiterungen

  • Countdownwerte sollten weit auseinanderliegen (z. B. 70 000 / 75 000 / 80 000 Sekunden).
  • Die Steckdose darf nicht automatisch einschalten, wenn ein Countdown gesetzt wird – und auch nicht ausschalten, wenn der Countdown wieder gelöscht oder auf 0 gesetzt wird. Wichtig ist nur, dass sie den Countdownwert an HA meldet, ohne den Schaltzustand zu ändern.
  • Das input_text lässt sich im Dashboard anzeigen, um aktuelle Sequenzen zu sehen.
  • Statt Buchstaben S/D/L können auch andere Kürzel oder Symbole verwendet werden.

Fazit

Mit diesem Trick wird ein gewöhnlicher Tuya-Szenenschalter zu einem vollwertigen Multi-Klick-Controller. Durch die Kombination aus Countdown-Event, Textpuffer und Musterlogik kann Home Assistant selbst komplexe Tastensequenzen erkennen und verarbeiten.