Moin,
ich mache gerade die ersten Schritte mit FHEM und HTML. Mit viel lesen hier und im WIKI konnte ich mir ein kleines System aufbauen
aus 2 RGB Lampen, 1 Umweltsensor, Wetter, Uhr und Müllabfuhr. Alles läuft prima.
Nur bei einem Gerät habe ich ein Verständnisproblem. Es geht um das ESPEasy Modul mit RGBW Stripe:
Nach der Einrichtung desselben meldet und konfiguriert es sich bei FHEM ja selbst.
Danach hatte ich ein RGBW steuerbares Licht. Man kann Ein / Aus, RGB, pct und toggeln.
Hier mal die Daten ausgelesen:
defmod ESP_RGB ESPEasy 192.168.19.43 80 espBridge ESP_Easy_ESP_RGB
attr ESP_RGB IODev espBridge
attr ESP_RGB Interval 300
attr ESP_RGB colorpicker HSVp
attr ESP_RGB devStateIcon { ESPEasy_devStateIcon($name) }
attr ESP_RGB group ESPEasy Device
attr ESP_RGB mapLightCmds lights
attr ESP_RGB parseCmdResponse lights
attr ESP_RGB presenceCheck 1
attr ESP_RGB readingSwitchText 1
attr ESP_RGB room ESPEasy
attr ESP_RGB setState 3
attr ESP_RGB webCmd ct:pct:rgb:rgb ff0000:rgb 00ff00:rgb 0000ff:toggle:on:off
setstate ESP_RGB col: ct ct: 3000 onO: on pct: 0 rgb: 7f7f7f
setstate ESP_RGB 2021-01-20 12:01:36 colormode ct
setstate ESP_RGB 2021-01-20 12:01:36 ct 3000
setstate ESP_RGB 2021-01-20 12:01:36 onOff on
setstate ESP_RGB 2021-01-20 12:01:36 pct 0
setstate ESP_RGB 2021-01-20 12:01:34 presence present
setstate ESP_RGB 2021-01-20 12:01:36 rgb 7f7f7f
setstate ESP_RGB 2021-01-20 12:01:36 state col: ct ct: 3000 onO: on pct: 0 rgb: 7f7f7f
Readings
colormode ct 2021-01-20 12:01:36
ct 3000 2021-01-20 12:01:36
onOff on 2021-01-20 12:01:36
pct 0 2021-01-20 12:01:36
presence present 2021-01-20 12:12:09
rgb 7f7f7f 2021-01-20 12:01:36
state col: ct ct: 2500 onO: on pct: 0 rgb: 7f7f7f 2021-01-20 12:12:09
Das kleine Problem ist, wie man sieht, dass wenn pct = 0 ist, der Status von "onOff "trotzdem "on" bleibt.
Heißt, Wenn ich im ausgeschaltetem Zustand pct von 0 auf irgendwas verstelle, dann geht "onOff" automatisch auf "on". Das wäre richtig.
Schiebe ich den Regler wieder auf "pct 0" , dann bleibt "onOff" aber auf on. Das ist das Problem.
Ich muss dann immer nochmal auf "off" klicken um das Ding auszuschalten.
Wie ändert man das am einfachsten? Mir fehlt es da noch an allen Ecken und Kanten.
Vielleicht erbarmt sich jemand, mich auf das richtige Gleis zu schieben.
Danke!
Eine _mögliche_ Variante: ein userReadings "onOff", das aber _nur_ getriggert wird, wenn pct 0 ist und dann "off" zurückgibt.
Wäre schön, du könntest da erst mal selbst mit den Stichworten tüfteln, bei Bedarf dann aber gerne auch die vollst. Lösung.
Genau so war das gedacht, keine Fertiglösung, ich will ja was lernen...
Ok ein userReading. Dann beschäftige ich mich damit näher. Danke sehr!
So mein erster Versuch lag darin, erstmal ein userReading zu erstellen und zu prüfen. Das ist gelungen.
Mit der Variante:
PCTON { ReadingsVal("ESP_RGB","pct",0) ? ReadingsVal("ESP_RGB","pct",""):"off"}
habe ich ein Reading "PCTON" was mir bei größer "0" den Wert von "pct" anzeigt und bei "pct=0" das Wort "off".
Nun muss ich statt aller anderen Werte das Wort "on" reinbekommen. Ich und Perl, oGott.... noch nie gesehen, wird ja Zeit!
Der 2. Versuch liefert nun "on" und "off"
PCTON {ReadingsVal($name,"pct",0) eq "0"?"off":"on"}
Jetzt muss ich das mit dem normalen "state" verknüpfen...
Zitat von: Beta-User am 20 Januar 2021, 12:23:31
Eine _mögliche_ Variante: ein userReadings "onOff", das aber _nur_ getriggert wird, wenn pct 0 ist und dann "off" zurückgibt.
Fyi:
Beide genannten Elemente waren 100% ernst gemeint: sowohl der Name des userReadings, wie auch das mit dem sehr spezifischen TRIGGER!
V.a. letzteren vermisse ich in deinem Nachtrag immer noch!
Die ersten Sachen waren nur Tests, wie ich das Ergebnis sehen kann, um Errors zu erkennen.
Danach versuchte ich das Problem zu bewältigen. Ich bin kein Programmierer und habe PERL noch nie gesehen.
Daher dürft Ihr ruhig lachen!
Versuch1: läuft nicht.. war ja klar
PCTON:pct.* {if(ReadingsVal($name,"onOff","") eq "on") and(ReadingsVal($name,"pct",0) eq "0")}; fhem("set ESP_RGB off")
Was ich denke verstanden zu haben:
Das Reading "PCTON" wird eingelesen wenn sich "pct" ändert. Im WIKI steht, dass man .* jetzt ranhängen muss.
Das "set" am Ende läuft soweit, das sollte stimmen
eq bedeutet äquivalent
in geschweiften Klammer ist der PERL Code
Was unklar ist:
Darf ich "if" und "and" so verwenden?
was bedeutet bei "ReadingsVal" ,0 und "" ? Das fand ich noch nicht erklärt
Wahrscheinlich stimmt meine Logik auch nicht:
Wenn "pct" = 0 und "onOff" = on dann soll das Device "ESP_RGB" abgeschaltet werden mit dem Befehl "off".
Das aber nur, wenn sich "pct" ändert.
Den Fall ohne Trigger hatte ich schon: Ergebnis: 53 000 Zeilen "set ESP_RGB off" im Logfile, super!
Ich muss noch viel lernen, aber allein ist das doch zu viel. Deshalb freue ich mich über die Hilfe hier.
EDIT: Habe endlich die PERL Referenz gefunden: https://fhem.de/commandref_DE.html#perl
OK, dann also jetzt mal "meine Version(en)":
onOff:pct.0 {"off")
onOff:pct:.0 {"off")
Zur Erläuterung: Das Ding soll wirklich nur auf pct.0/pct:.0 reagieren (Synatx an der Stelle: so wie es auch für ein notify erforderlich wäre, vermutlich brauchst du daher die Doppelpunkt-Fassung). Dann (und nur dann) wird direkt das "eigentliche Reading" verändert, und das war doch das eigentliche Ziel, oder?
Ansonsten ist dein Code etwas "speziell". Wenn du (m.E.) gute Beispiele für alles mögliche suchst, kannst du ja mal in https://svn.fhem.de/trac/browser/trunk/fhem/FHEM/lib/AttrTemplate/mqtt2.template (https://svn.fhem.de/trac/browser/trunk/fhem/FHEM/lib/AttrTemplate/mqtt2.template) schauen, mit der Suche dadrin nach userReadings sollte das eine oder andere kommen.
Grundsätzlich kann man schon auch if etc. verwenden, aber du wirfst an der Stelle die Klammern etwas willkürlich hin und auch der fhem-Befehl außerhalb der geschweifen Klammern dürfte ein Problem sein.
Du hast das richtig erkannt, Syntax ist mein Hauptproblem:
Warum hast Du in dem Beispiel 2 verschiedene Klammern?
Ich werde mich erstmal mit Syntax und Formatierung beschäftigen und einfachsten Beispielen.
Dann erst kommt das kosmetische Problem hier.
Ich ahne mal, dass "onOff" ein Reading direkt vom Device ist und nicht überschrieben werden kann. Wurde ja automatisch erstellt.
Es ist ja die "Antwort" auf "set Device on / off" .
UPS, typo, ja. Geschweifte wäre hinten richtig....
Nun hab ichs laufen.
Das "onOff" Reading lässt sich nicht direkt überschreiben wie es scheint. Alle Versuche änderten den Wert nicht.
Also habe ich mich wieder auf das "Ausschalten" des Devices konzentriert. (fhem "set ESP_RGB off")
Meine Idee mit "if" (wortwörtlich) im userReading ging überhaupt nicht. Immer nur "Syntax Error" sobald das vorn steht.
Da war ich auf dem Holzweg.
Aber so
PCTON:pct.* {ReadingsVal($name,"onOff",0) eq "on" && ReadingsVal($name,"pct",0) eq "0"?[fhem "set ESP_RGB off"]:"on"}
geht das wie es soll. sobald "pct=0" ist und "onOff=on"ist, schaltet sich das Device ab.
Im Event Monitor ist aber eine Meldung: ESPEasy ESP_RGB PCTON: ARRAY(0x30ed5f8) vorhanden. Die war vorher nicht.
Da bekommt mein userReading "PCTON" ganz kurz (sekundenbruchteile) diesen Wert?
Das ist der" fhem set...." Befehl, solange er gültig ist?
Die Zahl in der Klammer ändert sich auch jedes Mal, wenn abgeschaltet wird.
Schade, ich dachte mein "Laiencode" wird hier von den Profis zerrrissen und ich lerne dabei was?
Wir sind uns ja einig, das zwischen dem Code von "Beta-User" und meinem riesen Unterschiede bestehen.
Meiner ist viel zu kompliziert und verschachtelt. Ich denke eben noch nicht "digital"...
Also:
Was kann ich da noch verbessern?
Mich stört auch, dass ich hier eine Variable befülle (PCTON) die ich gar nicht nutze. Geht das nicht auch anders?
Ich würde mich sehr freuen, wenn noch jemand Zeit opfern kann und mir weiter hilft.
Kannst du mal die Events liefern (siehe Wiki zum Event-Monitor). Irgendwie will ich noch nicht recht glauben, dass das hier nicht klappt:
onOff:pct:.0 {"off"}
Zumindest mit meinem CUL_HM-Rollladen klappt folgendes, wenn ich auf "pct 100" fahre:
attr Rollladen_WZ_SSW userReadings state:pct:.100 {"OFF"}
setstate Rollladen_WZ_SSW OFF
(Schon klar, dass das inhaltlich Unsinn ist, geht um die Funktionalität...)
Ja gern, klar:
userReadings habe ich so:
attr ESP_RGB userReadings onOff:pct:.0 {"off"} fhem("setstate onOff off")
umgesetzt?
Event Monitor sagt bei regeln von "pct" hoch und wieder auf 0 das:
2021.01.24 12:01:04 3 : ESPEasy ESP_RGB: set ESP_RGB pct 26
2021-01-24 12:01:04 ESPEasy ESP_RGB pct 26
2021-01-24 12:01:04 ESPEasy ESP_RGB rgb: 0000ff
2021-01-24 12:01:04 ESPEasy ESP_RGB onOff: on
2021-01-24 12:01:04 ESPEasy ESP_RGB colormode: ct
2021-01-24 12:01:04 ESPEasy ESP_RGB pct: 26
2021-01-24 12:01:04 ESPEasy ESP_RGB ct: 2500
2021-01-24 12:01:04 ESPEasy ESP_RGB col: ct ct: 2500 onO: on pct: 26 rgb: 0000ff
2021.01.24 12:01:05 3 : ESPEasy ESP_RGB: set ESP_RGB pct 0
2021-01-24 12:01:05 ESPEasy ESP_RGB pct 0
2021-01-24 12:01:05 ESPEasy ESP_RGB rgb: 0000ff
2021-01-24 12:01:05 ESPEasy ESP_RGB pct: 0
2021-01-24 12:01:05 ESPEasy ESP_RGB ct: 2500
2021-01-24 12:01:05 ESPEasy ESP_RGB colormode: ct
2021-01-24 12:01:05 ESPEasy ESP_RGB onOff: on
2021-01-24 12:01:05 ESPEasy ESP_RGB col: ct ct: 2500 onO: on pct: 0 rgb: 0000ff
Wie gesagt, das "onOff" ist eine Rückmeldung vom ESPEasy Modul.
Schau mal ins log.
Und mach' das fhem.... hinten weg, das stört!
attr ESP_RGB userReadings onOff:pct:.0 {"off"} setstate onOff off
2021.01.24 12:12:32 3: ESPEasy ESP_RGB: set ESP_RGB pct 43
2021.01.24 12:12:32 3: ESPEasy ESP_RGB: set ESP_RGB pct 0
2021.01.24 12:12:34 3: ESPEasy ESP_RGB: set ESP_RGB off
2021.01.24 12:12:34 3: ESPEasy ESP_RGB: set ESP_RGB on
2021.01.24 12:16:10 3: ESPEasy ESP_RGB: set ESP_RGB pct 52
2021.01.24 12:16:11 3: ESPEasy ESP_RGB: set ESP_RGB pct 0
Gebe ich in der Eingabezeile setstate onOff off ein kommt der Error : Please define onOff first
Nein, alles muss hinten weg:
attr ESP_RGB userReadings onOff:pct:.0 {"off"}
Das hatte ich so schon vorgestern und gestern probiert. Keine Reaktion.
2021.01.24 12:36:14 3 : ESPEasy ESP_RGB: set ESP_RGB pct 73
2021-01-24 12:36:14 ESPEasy ESP_RGB pct 73
2021-01-24 12:36:14 ESPEasy ESP_RGB ct: 2500
2021-01-24 12:36:14 ESPEasy ESP_RGB pct: 73
2021-01-24 12:36:14 ESPEasy ESP_RGB colormode: ct
2021-01-24 12:36:14 ESPEasy ESP_RGB onOff: on
2021-01-24 12:36:14 ESPEasy ESP_RGB rgb: 0000ff
2021-01-24 12:36:14 ESPEasy ESP_RGB col: ct ct: 2500 onO: on pct: 73 rgb: 0000ff
2021.01.24 12:36:15 3 : ESPEasy ESP_RGB: set ESP_RGB pct 0
2021-01-24 12:36:15 ESPEasy ESP_RGB pct 0
2021-01-24 12:36:15 ESPEasy ESP_RGB rgb: 0000ff
2021-01-24 12:36:15 ESPEasy ESP_RGB ct: 2500
2021-01-24 12:36:15 ESPEasy ESP_RGB pct: 0
2021-01-24 12:36:15 ESPEasy ESP_RGB onOff: on
2021-01-24 12:36:15 ESPEasy ESP_RGB colormode: ct
2021-01-24 12:36:15 ESPEasy ESP_RGB col: ct ct: 2500 onO: on pct: 0 rgb: 0000ff
Setze ich statt "onOff" mein selbst erstelltes Reading "PCTON" ein, dann bekomme ich mit dem Code "PCTON=off".
Das geht. Nur das "onOff" Device Reading will sich nicht beeinflussen lassen.
2021-01-24 12:44:38 ESPEasy ESP_RGB onOff: on
2021-01-24 12:44:38 ESPEasy ESP_RGB ct: 2500
2021-01-24 12:44:38 ESPEasy ESP_RGB pct: 0
2021-01-24 12:44:38 ESPEasy ESP_RGB PCTON: off
2021-01-24 12:44:38 ESPEasy ESP_RGB col: ct ct: 2500 onO: on pct: 0 rgb: 0000ff
Hmmm, OK...
Könnte man wohl mit einem sleep+setreading _innerhalb_ des Perl-Codes lösen, aber man. ist das Verhalten hier nicht OK und mal sollte den Maintainer fragen, ob das geändert werden kann (ohne userReadings).
Wenn Du meinst, dass meine (funktionierende) Lösung ok ist?
Ich war mir sicher, dass ich das als Anfänger viel zu kompliziert gemacht habe.
Ich sollte weiter lernen, dann finde ich das später selbst raus...
Vielen Dank nochmal für die schnelle Hilfe!
Ich glaube nicht, dass die OK ist, schau ins fhem-log...
Und informiere den maintainer.
Da es um das "_P_123_Lights" Plugin für ESPEasy geht, habe ich den Developer des Moduls schon
vor Tagen angeschrieben. Das ist User "dev0" hier aus dem Forum.
Das Plugin ist für die aktuelle Version von ESPEASY zu alt und müsste angepasst werden.
Leider bekam ich keine Antwort.
Ich kann das leider nicht. Ich könnte höchstens einen Raspberry PI3 aus Einzelteilen zusammenlöten...
Na ja, wenn es um "Rückportierungen" geht, kann ich verstehen, dass du da wenig support bekommst; in der Regel sollte man eher weiterentwickeln...
Wie dem auch sei:
In userReadings MUSS der perl-Code von geschweiften Klammern umgeben sein, irgendwas außerhalb zu notieren sollte zu Fehlermeldungen im Log führen. Es kann schon sein, dass fhem.pl verhindert, dass dasselbe Reading manipuliert wird, das (auch) Teil des Readings-update ist.
Aus diesem Dillema führen afaik mind. zwei Wege raus:
1. readingsChange:
Das ist ein Spezialfall eines notify, leider habe ich selbst die Syntax noch nicht zu 100% durchschaut. Vorteil: das klinkt sich sehr früh in die Event-Verarbeitung ein und erzeugt daher (so mein möglicherweise falsches Verständnis) kein weiteres Event.
Weitere Info: https://fhem.de/commandref_modular.html#readingsChange (und hoffentlich jemand freundliches, der erklären kann, wie man es hier nutzbar macht.
2. Das bereits genannte "fhem-sleep" innerhalb des userReadings-Perl-Codes. Dazu habe ich mal hier ein Beispiel gefunden:
https://forum.fhem.de/index.php/topic,115904.msg1101829.html#msg1101829
Der Code ist allerdings vermutich auch nicht ganz optimal, aber daraus bastle ich mal folgendes:
attr ESP_RGB userReadings ONOFF:pct:.0 {fhem("sleep 0.1; setreading $name onOff off");return undef}
Erklärungen:
- ONOFF brauchen wir wohl als anderen Reading-Namen, damit fhem.pl zufrieden ist;
- eine echte Wertzuweisung für das Reading brauchen wir nicht, daher geben wir am Ende ausdrücklich das (unschöne!) undef zurück;
- die eigentliche Musik spielt in dem kurzen fhem-sleep. Das entkoppelt das setreading von der Eventverarbeitung, damit wird es dann ein zulässiger Befehl, was innerhalb der Event-Verarbeitung nicht der Fall ist... Damit ist auch klar, was der Nachteil ist: Wir erhalten 2 Events, nämlich erst das (falsche) "on" und dann später erst das "off".
- und damit das ganze noch funktioniert, wenn man das Device umbenennt, machen wir den Namen noch dynamisch, $name müßte eigentlich in userReadings passend aufgelöst werden (sonst min $NAME testen).
Nein, das geht so leider auch nicht.
Aber nochmal zum Verständnis, nicht das ich missverstanden wurde:
Ziel des Ganzen ist, das Device abzuschalten, wenn der Wert "pct" =0 ist.
Das Problem war, das wenn man den pct- Regler bewegte, das Device immer eingeschaltet wurde.
Auch, wenn der Regler auf "0" geschoben wurde. Im TabletUI wird das Gerät damit als "eingeschaltet" angezeigt,
obwohl es dunkel ist. Das führte immer zu Verwirrungen. Ist das Licht nun aus oder an???
(Bei Tasmota funktioniert das richtig, pct0 = Device off)
Das Reading des ESP Easy Devices (Plugin Lights) "onOff" ist, so sieht es für mich aus, eine reine Statusmeldung des Devices.
Damit sagt das Gerät dem FHEM, ob es an oder aus ist.
Wenn wird diese Meldung"heimlich" zeitversetzt ändern, bleibt das Device doch eigentlich trotzdem an, oder?
Wir haben dann ja nur seine Meldung "gefälscht".
Ich bin als Anfänger ja auch nur darauf bedacht was zu lernen. Und wenn, dann auch "richtig".
Deshalb meine Frage, ob mein userReading so akzeptierbar ist, oder ob da noch dicke Fehler drin sind, die zwar die Funktion nicht beeinträchtigen,
aber mir später Probleme bereiten, weil ich falsche Schlüsse gezogen habe oder etwas überhaupt nicht verstanden habe.
Syntaxfehler und Formatierung eingeschlossen.
Ich will hier auch niemandem die Zeit stehlen.
Na ja, steht denn bei deiner userReadings-Fassung was im Log?
Wenn nein, kann es ja bleiben, wenn doch, kannst du statt setreading auch (in meinen "mini"-sleep-Vorschlag) ein "set ... off" reinbasteln, wenn man wirklich (!) was schalten muss. Einen firmware-Bug hatte ich eigentlich nicht vermutet, an sich sollte das schon ausgeschaltet werden, wenn man auf 0 stellt...