NEWS
Blockly - warten auf Freigabewert
-
Hallo,
ich lasse mir verschiedene Ansagen auf meinem Google Home Assistant ausgeben.
Dazu schreibt das jeweilige Ansagescript den text in ein String-Objekt. Sobald dieses String-Objekt sich verändert, wird dessen Inhalt angesagt.
Wenn nun aber mehrere Ansagen kurz nacheinander in dieses Objekt geschrieben werden, gibt es Überschneidungen. Im Endeffekt werden laufende Ansagen durch neue unterbrochen.
Meine Lösung ist, einen zusätzlichen Datenpunkt "Idle" einzubauen. Der wird false, solange eine Ansage läuft. Erst wenn der true ist, darf ein Script wieder einen neuen Text einschreiben.
Dazu muss ich aber in den Scripten, die die Texte einschreiben, warten, bis der Idle-Datenpunkt wieder true ist.
Das versuche ich so zu lösen:
Abgesehen davon, dass ich mir absolut nicht sicher bin, ob das der richtige Weg ist, traue ich mich nicht, das Script scharfzuschalten und zu testen, da man hier im Forum wiederholt vor Script-Endlosschleifen warnt.Fragen also:
Ist der obige Weg zur zusätzlichen Abfrage vor Fortsetzung des Scriptes der richtige oder gibt es elegantere Lösungen?
Falls ja, besteht die Gefahr einer Blockierung der JS-Engine?
-
Schleifen sind immer slecht die blockieren nämlich die CPU.
Wen du mehrere Scripte hast welche Ansagen machen wird diese Lösung auch nicht helfen, Beispiel :
-
Ansage 1 läuft und idle ist aktiviert
-
Ansage 2,3 und 4 warten
-
ändert sich der Status idle schießen al diese 3 gleichzeitig durch
Sind den alle Ansagen notwendig oder könnte man sie auch komplett Wecklassen wen was läuft ?
Alternatief müsste man sonst ne Warteschleife bauen…
Sent from my iPhone using Tapatalk
-
-
Ist der obige Weg zur zusätzlichen Abfrage vor Fortsetzung des Scriptes der richtige oder gibt es elegantere Lösungen?
Falls ja, besteht die Gefahr einer Blockierung der JS-Engine? `
Hallo hmanfredSchleifen ohne "Notausgang" sind immer gefährlich
Habe mal ein Konstrukt versucht.
Ich benutze den SayIt Adapter. Dort gibt es einen Datenpunkt "Is now speaking". Dieser bleibt bei mir immer auf "false".
Deine Situation konnte ich also nicht richtig nachstellen. Keine Ahnung welchen Adapter Du benutzt.
Ich habe wie wild meine FunkSteckdose ein und aus geschaltet. Alle Meldungen kamen sauber durch. Mein TimeOut wurde NIE aktiviert.
Vielleicht kann Du das mal mit Deinem Adapter testen.
Export:
! ````
<xml xmlns="http://www.w3.org/1999/xhtml"><block type="procedures_defnoreturn" id="=,2(9rUOo(mXl[FNXw!4" x="213" y="13"><mutation><arg name="Schaltwert"></arg></mutation>
<field name="NAME">Sprachausgabe</field>
<comment pinned="false" h="80" w="160">Beschreibe diese Funktion …</comment>
<statement name="STACK"><block type="controls_if" id="ZTB}g=/SB~ZhsEgG%P@-"><mutation else="1"></mutation>
<value name="IF0"><block type="logic_compare" id="7PTvWWv*!|/Jw-|G51MZ"><field name="OP">EQ</field>
<value name="A"><block type="get_value" id="Vkq3_XcL+Ii}^;-9:^_"><field name="ATTR">val</field>
<field name="OID">sayit.0.tts.playing</field></block></value>
<value name="B"><block type="logic_boolean" id="JBx=KORofn2|ayU4-eHD"><field name="BOOL">FALSE</field></block></value></block></value>
<statement name="DO0"><block type="controls_if" id="D8mp.eLh3m7GBWS=Ik!|"><mutation else="1"></mutation>
<value name="IF0"><block type="logic_compare" id="i3k`Ml4|cwkqr!hMVCM,"><field name="OP">EQ</field>
<value name="A"><block type="variables_get" id="IKZGj?{Gi+P~!{JXnS|."><field name="VAR">Schaltwert</field></block></value>
<value name="B"><block type="logic_boolean" id="!LXeZ_GB73%[^pM3Jf{"><field name="BOOL">TRUE</field></block></value></block></value>
<statement name="DO0"><block type="sayit" id="M8JsYt0l[d@S4{iH*;%K"><field name="INSTANCE">.0</field><value name="VOLUME"><block type="math_number" id="S){2:9E9DJIGhtN#baa@"><field name="NUM">100</field></block></value> <value name="MESSAGE"><shadow type="text" id="pdqvq:~HXIx)LLU@QBk2"><field name="TEXT">Steckdose an</field></shadow></value></block></statement> <statement name="ELSE"><block type="sayit" id="8JQMy^=2HeZ;c4yv98-d"><field name="INSTANCE">.0</field> <value name="VOLUME"><block type="math_number" id="+a`!.K|xZ:[Z/u;)c7Xm"><field name="NUM">100</field></block></value> <value name="MESSAGE"><shadow type="text" id="KZE%044=-D`cZp)Zn97-"><field name="TEXT">Steckdose aus</field></shadow></value></block></statement></block></statement> <statement name="ELSE"><block type="comment" id="V:uY]_pt-;ahC;Um1bes"><field name="COMMENT">ungetestet weil NIE aufgerufen</field> <next><block type="debug" id="t6iRKPPj(.WtL5Q=gy?H"><field name="Severity">log</field> <value name="TEXT"><shadow type="text" id="zoAt_nD1gO6v!Lg2T/X5"><field name="TEXT">*******test</field></shadow></value> <next><block type="variables_set" id="Ib9B0G,2qGLIX;OF/k~J"><field name="VAR">tempVar</field> <value name="VALUE"><block type="variables_get" id="e.^B}n.V)o_yq~_U/SQA"><field name="VAR">Schaltwert</field></block></value> <next><block type="timeouts_cleartimeout" id="X(L7g!Na9r]^B7B6b(Q0"><field name="NAME">timeout</field> <next><block type="timeouts_settimeout" id="LeaB@?Z#Fqt3t`7ZiM~R"><field name="NAME">timeout</field> <field name="DELAY">2</field> <field name="UNIT">sec</field> <statement name="STATEMENT"><block type="procedures_callnoreturn" id="096cWOZsc#OCPskReJ{h"><mutation name="Sprachausgabe"><arg name="Schaltwert"></arg></mutation> <value name="ARG0"><block type="variables_get" id="d8PTv61a@I`-115olMf#"><field name="VAR">tempVar</field></block></value></block></statement></block></next></block></next></block></next></block></next></block></statement></block></statement></block>
<block type="on_ext" id="[Wcl0zp88{h=f,-33alu" x="-237" y="113"><mutation items="1"></mutation>
<field name="CONDITION">ne</field><value name="OID0"><shadow type="field_oid" id="gv!UMz+V#77N%L}iMXHk"><field name="oid">hm-rpc.0.KEQ0967984.1.STATE</field></shadow></value> <statement name="STATEMENT"><block type="controls_if" id="3SfI}~2.7DVTzmUC_CxR"><value name="IF0"><block type="logic_compare" id="~zu=^,KNaZO3?=+k)dc."><field name="OP">NEQ</field> <value name="A"><block type="on_source" id="#@EYe*{PknO_(!vm:X]/"><field name="ATTR">state.val</field></block></value> <value name="B"><block type="on_source" id="5FO[Ay6tw#6CrNkGO8aV"><field name="ATTR">oldState.val</field></block></value></block></value> <statement name="DO0"><block type="procedures_callnoreturn" id=")NMwbBXu6YSZXik-SZ@A"><mutation name="Sprachausgabe"><arg name="Schaltwert"></arg></mutation> <value name="ARG0"><block type="on_source" id=",E:@457*DFLaM5P7Ma,R"><field name="ATTR">state.val</field></block></value></block></statement></block></statement></block></xml>
! ````
Grüße -
in deinem beispiel wird aber niemals die andere ansage abgegeben sobalt sayit frei ist, mit anderen worten : scripte die eine sprachausgabe getriggerd haben waerend eine laeuft fallen komplett weck
-
in deinem beispiel wird aber niemals die andere ansage abgegeben sobalt sayit frei ist, mit anderen worten : scripte die eine sprachausgabe getriggerd haben waerend eine laeuft fallen komplett weck `
Ich verstehe nicht was Du meinst. -
dein beispiel hat eine IF welche ueberprueft ob eine ansage laeuft, wen ja wird 2 sekunden gewartet beforh die naeste ansage kommt.
Wen script das jetzt z.b. 3 mal hintereinander triggeren ist die erste OK und die 2te + dritte kommt stop einen der timeouts wodurch die ansage verloren geht.
-
Schleifen sind immer slecht die blockieren nämlich die CPU. `
Okay, aber ungeachtet deiner weiteren Bemerkung - wie könnte ich in diesem Beispiel trotz Warten auf Idle=true das Blockieren der CPU verhindern? -
…
Ich benutze den SayIt Adapter. Dort gibt es einen Datenpunkt "Is now speaking". Dieser bleibt bei mir immer auf "false".
...
Vielleicht kann Du das mal mit Deinem Adapter testen. `
Ich nutze auch den SayIt Adapter. Auch bei mir ändert sich der Datenpunkt "Is now speaking" nie.Beim Lautsprecher selbst - Google Home Assistant - gibt es einen Datenpunkt IDLE, der sich auch während der Durchsage auf PLAYING ändert. Nur steht der leider auch auf PLAYING, wenn Musik gespielt wird. :x
-
Schleifen sind immer slecht die blockieren nämlich die CPU.
Okay, aber ungeachtet deiner weiteren Bemerkung - wie könnte ich in diesem Beispiel trotz Warten auf Idle=true das Blockieren der CPU verhindern?
Wieviele scripte/ansagen hast du laufen welche durcheinander kommen koennten ?
-
dein beispiel hat eine IF welche ueberprueft ob eine ansage laeuft, wen ja wird 2 sekunden gewartet beforh die naeste ansage kommt.
Wen script das jetzt z.b. 3 mal hintereinander triggeren ist die erste OK und die 2te + dritte kommt stop einen der timeouts wodurch die ansage verloren geht. `
Das ist in diesem Beispiel auch so gewollt.Ein "alter" Status der Steckdose würde mich nicht interessieren.
Aber wie schon gesagt. Der Timeout ist NIE aktiv geworden, weil egal wie schnell ich den Status geändert habe, die Meldungen alle angesagt wurden.
Zur Not hätte ich noch eine "Timer-Aktiv" abfrage eingebaut.
-
Wieviele scripte/ansagen hast du laufen welche durcheinander kommen koennten ? `
Wenn ich es auf die reduziere, die sehr häufig durcheinander kommen, vier bis sechs.
Ich werde mal folgenden Lösungsansatz probieren:
-
Ich lege für jede Ansage ein Objekt an
-
Das jeweilige Script schreibt den Text ins Objekt
-
Ein separates Script arbeitet, mit kurzen Pausen dazwischen, alle diese Objekte nacheinander ab und leert jeweils das abgearbeitete.
-