Skip to content
  • Home
  • Aktuell
  • Tags
  • 0 Ungelesen 0
  • Kategorien
  • Unreplied
  • Beliebt
  • GitHub
  • Docu
  • Hilfe
Skins
  • Light
  • Brite
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Standard: (Kein Skin)
  • Kein Skin
Einklappen
ioBroker Logo

Community Forum

donate donate
  1. ioBroker Community Home
  2. Deutsch
  3. Skripten / Logik
  4. Umfassendes Alarmanlagen-Skript

NEWS

  • UPDATE 31.10.: Amazon Alexa - ioBroker Skill lĂ€uft aus ?
    apollon77A
    apollon77
    48
    3
    8.9k

  • MonatsrĂŒckblick – September 2025
    BluefoxB
    Bluefox
    13
    1
    2.3k

  • Neues Video "KI im Smart Home" - ioBroker plus n8n
    BluefoxB
    Bluefox
    16
    1
    3.6k

Umfassendes Alarmanlagen-Skript

Geplant Angeheftet Gesperrt Verschoben Skripten / Logik
javascriptsecurity
145 BeitrÀge 27 Kommentatoren 32.4k Aufrufe 52 Watching
  • Älteste zuerst
  • Neuste zuerst
  • Meiste Stimmen
Antworten
  • In einem neuen Thema antworten
Anmelden zum Antworten
Dieses Thema wurde gelöscht. Nur Nutzer mit entsprechenden Rechten können es sehen.
  • W Offline
    W Offline
    wizard2010
    schrieb am zuletzt editiert von
    #96

    Hi @andreaskos, nice work with this very good initiative.
    I'm trying to get this work with my setup using KNX, but I've facing some issues, I'm doing this configuration:

    // Arrays fĂŒr die Melder
    var detectorsOuterSkin = [
        'knx.0.Corredor.Status.PORTA_ENTRADA_STATUS',
        'knx.0.Cozinha.Status.COZ_DOOR_STATUS',
        'knx.0.Arrumos.Status.LAV_DOOR_STATUS',
        'knx.0.EscritĂłrio.Status.ESC_WINDOW_STATUS',
        'knx.0.Sala_de_Estar.Status.SALA_DOOR_DIR_STATUS',
        'knx.0.Sala_de_Estar.Status.SALA_DOOR_ESQ_STATUS',
        'knx.0.Suite.Status.SUI_DOOR_STATUS',
        'knx.0.Suite.Status.SUI_WC_WINDOW_STATUS'
    ];
    var detectorsIndoor = [];
    var detectorsDelayed = [];
     
    

    But this seems that is not working.
    Can you tell me if I'm doing this in the right way?
    By the way, can you please also tell me where is the latest version of the script and VIS?

    Really good work.
    Thank you.

    1 Antwort Letzte Antwort
    0
    • andreaskosA Offline
      andreaskosA Offline
      andreaskos
      schrieb am zuletzt editiert von andreaskos
      #97

      Hi folks,

      Danke fĂŒr euer Interesse an dem Skript. Ich möchte mich fĂŒr die spĂ€te Reaktion entschuldigen und auf eure Anfragen eingehen:

      @Freaknet
      Die Funktion ĂŒber die einzene Ausnahme von Meldern ist etwas, das man öfter brauchen könnte. Hast du immer noch Bedarf? Ich werde das einbauen, nur widme ich derzeit meine Zeit vorwiegend anderen Dingen. Ich werde hier posten, wenn es soweit ist, aber leider kann ich keine Deadline angeben momentan.

      @LaBamba
      Du muss rausfinden, was das Schloss von sich gibt, bei den unterschiedlichen ZustÀnden. Ich kenne es selbst leider nur aus der Werbung, aber etwa so:
      1 = geschlossen
      2 = offen
      Und dann kannst du mit einem Skript den Zustand ĂŒbersetzen. Möglicherweise geht das noch eleganter mit einem Alias, siehe hier, aber damit kenne ich mich leider nicht so gut aus.

      @wizard2010
      It all seems right. Please check the settings of your KNX adapter. You can define if it uses 1 and 0 or instead true and false for the KNX datapoints. This could be the reason. You should set it to true/false.
      The latest version of the script can be found in the first post if this thread.

      Best regards
      Andreas

      F 1 Antwort Letzte Antwort
      0
      • andreaskosA Offline
        andreaskosA Offline
        andreaskos
        schrieb am zuletzt editiert von andreaskos
        #98

        @wizard2010
        One more thing: did you check, if the states can trigger anything? Often the flags for the corresponding groups are not correctly set after importing the knxproj-file by the KNX adapter. Maybe you should have a look at the read/write/update flags on the objects tab. There you should set them read=true, write=false, update=true.

        1 Antwort Letzte Antwort
        0
        • SchmakusS Offline
          SchmakusS Offline
          Schmakus
          Developer
          schrieb am zuletzt editiert von
          #99

          Hi,
          schönes Script! Ich hĂ€tte jedoch noch einen Vorschlag bezĂŒglich der Scharfstellung bei geöffneten Fenstern.
          GrundsÀtzlich sollten ja alle Fenster geschlossen sein, wenn man das Haus verlÀsst und die Alarmanlage scharf schaltet.
          Jedoch gibt es Fenster im Haus, welche gerne gekippt sind, jedoch fĂŒr einen Einbrecher nahezu nicht erreichbar sind.
          Das wĂ€ren Kellerfenster, welche durch das gesicherte Gitter des Schachts unzugĂ€nglich sind, oder Fenster im OG, welche nur ĂŒber eine Leiter erreichbar sind.

          Der Anwender sollte die Möglichkeit haben, selbst zu entscheiden, welche Fenster "offen" sein dĂŒrfen, wenn die Anlage scharf geschaltet wird.
          Ein Ändern des Zustands von Offen => Zu => Offen wĂŒrde dann zum Auslösen der Anlage fĂŒhren.

          Die ließe sich entweder ĂŒber eine weitere AufzĂ€hlung lösen z.B.: "Alarmanlage_Innenraum_IgnoreOpen" oder fĂŒr jede AufzĂ€hlung wird ein separater Datenpunkt erzeugt, ĂŒber welchen "IgnoreOpen" ein- und ausgeschaltet werden kann. Das mit dem Datenpunkt ist sogar die bessere Alternative, da man darĂŒber mehr Kontrolle hat und ggf. diesen auch ĂŒber andere Scripte steuern könnte.

          Abschließend sollte dies natĂŒrlich auch zurĂŒckgemeldet werden. D.h. wenn die Alarmanlage scharf geschaltet wird, obwohl ein Fenster gewollt offen ist, sollte ein Datenpunkt dies anzeigen. So kann man es in der Visu anzeigen lassen, als unterschiedliche Farbe einer Lampe oder Alexa weißt einen darauf hin.
          Beim Verlassen des Hause bleibt es dann jedem selbst ĂŒberlassen, ob er mit diesem "Sicherheitsrisiko" leben kann, oder nicht.

          GrĂŒĂŸe
          Markus

          Dev of LightControl Adapter, Contributor of HUE and DoorBird Adapter

          1 Antwort Letzte Antwort
          0
          • S Offline
            S Offline
            Straty
            schrieb am zuletzt editiert von
            #100

            Guten Abend zusammen.
            Sehr schönes Script und vielen dank an Andreas, das es soweit auch veröffentlicht wurde.
            Ich habe leider noch ein kleines Problem mit der Alarmierung ĂŒber die beiden Outputs AlarmAccoustical bzw. AlarmOptical.
            Nach auslösen vom Alarm werden beide states auf TRUE gesetzt. Soweit so gut. nach Ablauf der Delaytime werden auch beide auf FALSE zurĂŒck gesetzt, jedoch bei erneutem Wechsel eines Sensors von FALSE auf TRUE gehen beide wieder in den TRUE zustand und durchlaufen wieder die Delaytime. Ist das ganze so gewollt oder eventuell nur bei mir ein Fehler, der nicht da sein sollte.
            Das ganze lÀuft auf einem PI3B+ auf dem nur IoBroker lÀuft.
            mfg Philip

            andreaskosA 1 Antwort Letzte Antwort
            0
            • andreaskosA andreaskos

              Hi folks,

              Danke fĂŒr euer Interesse an dem Skript. Ich möchte mich fĂŒr die spĂ€te Reaktion entschuldigen und auf eure Anfragen eingehen:

              @Freaknet
              Die Funktion ĂŒber die einzene Ausnahme von Meldern ist etwas, das man öfter brauchen könnte. Hast du immer noch Bedarf? Ich werde das einbauen, nur widme ich derzeit meine Zeit vorwiegend anderen Dingen. Ich werde hier posten, wenn es soweit ist, aber leider kann ich keine Deadline angeben momentan.

              @LaBamba
              Du muss rausfinden, was das Schloss von sich gibt, bei den unterschiedlichen ZustÀnden. Ich kenne es selbst leider nur aus der Werbung, aber etwa so:
              1 = geschlossen
              2 = offen
              Und dann kannst du mit einem Skript den Zustand ĂŒbersetzen. Möglicherweise geht das noch eleganter mit einem Alias, siehe hier, aber damit kenne ich mich leider nicht so gut aus.

              @wizard2010
              It all seems right. Please check the settings of your KNX adapter. You can define if it uses 1 and 0 or instead true and false for the KNX datapoints. This could be the reason. You should set it to true/false.
              The latest version of the script can be found in the first post if this thread.

              Best regards
              Andreas

              F Offline
              F Offline
              Freaknet
              schrieb am zuletzt editiert von
              #101

              @andreaskos said in Umfassendes Alarmanlagen-Skript:

              Hi folks,

              Danke fĂŒr euer Interesse an dem Skript. Ich möchte mich fĂŒr die spĂ€te Reaktion entschuldigen und auf eure Anfragen eingehen:

              @Freaknet
              Die Funktion ĂŒber die einzene Ausnahme von Meldern ist etwas, das man öfter brauchen könnte. Hast du immer noch Bedarf? Ich werde das einbauen, nur widme ich derzeit meine Zeit vorwiegend anderen Dingen. Ich werde hier posten, wenn es soweit ist, aber leider kann ich keine Deadline angeben momentan.

              Hey @andreaskos,

              erstmal Danke fĂŒr Deine RĂŒckmeldung :-)
              Bedarf besteht natĂŒrlich noch immer, gerade jetzt dann wo die "warmen" Sommermonate anstehen. :stuck_out_tongue_winking_eye:
              Meld dich einfach falls Du dazu kommst, bin gerne bereit auch als Tester zu fungieren.

              GrĂŒĂŸe
              Freaknet

              1 Antwort Letzte Antwort
              0
              • S Straty

                Guten Abend zusammen.
                Sehr schönes Script und vielen dank an Andreas, das es soweit auch veröffentlicht wurde.
                Ich habe leider noch ein kleines Problem mit der Alarmierung ĂŒber die beiden Outputs AlarmAccoustical bzw. AlarmOptical.
                Nach auslösen vom Alarm werden beide states auf TRUE gesetzt. Soweit so gut. nach Ablauf der Delaytime werden auch beide auf FALSE zurĂŒck gesetzt, jedoch bei erneutem Wechsel eines Sensors von FALSE auf TRUE gehen beide wieder in den TRUE zustand und durchlaufen wieder die Delaytime. Ist das ganze so gewollt oder eventuell nur bei mir ein Fehler, der nicht da sein sollte.
                Das ganze lÀuft auf einem PI3B+ auf dem nur IoBroker lÀuft.
                mfg Philip

                andreaskosA Offline
                andreaskosA Offline
                andreaskos
                schrieb am zuletzt editiert von
                #102

                @straty
                Hi! Ja, das Verhalten wĂ€re so in Ordnung. Solange die Anlage scharf ist, geht der Alarm fĂŒr die eingestellte Dauer los, wenn ein Melder anschlĂ€gt. Auch, wenn der Alarm zu diesem Zeitpunkt zuvor schon einmal durchlaufen wurde.
                LG Andreas

                1 Antwort Letzte Antwort
                0
                • andreaskosA Offline
                  andreaskosA Offline
                  andreaskos
                  schrieb am zuletzt editiert von andreaskos
                  #103

                  Lieber @Freaknet und @Schmakus und alle anderen Leser,

                  ich habe eben die Funktion eingebaut, einzelne Melder aus der AussenhĂŒlle von der Überwachung ausnehmen zu können. Die Funktion ist mehr oder weniger ungetestet und ich wĂŒrde euch bitten hier Feedback zu geben, um das Skript fehlerfrei zu bekommen und auch als neue Version oben im ersten Thread updaten zu können.

                  Neue Datenpunkte
                  Unter "Input" ist nun ein neuer Knoten namens "IgnoreOpen" zu finden. Unterhalb diesem können per Flag die einzelnen Melder inaktiv geschaltet werden.
                  true = wird mitĂŒberwacht
                  false = von der Überwachung ausgenommen

                  Unter "Output" ist ein Text-Datenpunkt, der die Liste der offenen Melder mit gesetztem IgnoreOpen-Flag beinhaltet. Diese Melder kommen nicht in die Liste der ganz regulÀr offenen Melder.
                  Diesen Datenpunkt könnte man verwenden, um sich zu warnen, wenn zum Zeitpunkt des Scharf-Schaltens (oder ein paar Millisekunden spÀter) hier Text enthalten ist.

                  ACHTUNG
                  Die Einstellung der IgnoreOpen-Flags wird (derzeit) nicht automatisch zurĂŒck gesetzt, etwa beim Scharf-Schalten. Das bedeutet, man muss selbst drauf achten, dass ein Melder nicht ewig auf Inaktiv bleibt, weil man vergessen hat das Flag wieder auf true zu stellen.

                  /*
                  ########################################################################################################################
                  # ALARMSYSTEM
                  #
                  # Das Skript bildet eine einfache Alarmanlage nach mit der Schaltmöglichkeit
                  # fĂŒr intern und extern.
                  # Datenpunkte fĂŒr Inputs und Outputs werden angelegt.
                  # NĂ€here Beschreibung siehe im ioBroker-Forum unter
                  # https://forum.iobroker.net/topic/32885/umfassendes-alarmanlagen-skript
                  # Änderungshistorie:
                  # 2020-05-01    Andreas Kos     Erstellt
                  # 2020-05-02    Andreas Kos     Schaltwunsch mit Number-Datenpunkt Input.SwitchNumber (Idee von @Homer.J.)
                  #                               Schaltstatus mit Number-Datenpunkt Output.ActiveNumber (Idee von @Homer.J.)
                  # 2020-05-03    Andreas Kos     Korrekturen, u.a. fĂŒr Melderauswertung (chage: "ne") & AlarmText
                  # 2020-05-04    Andreas Kos     - Melder werden aus den Functions (AufzĂ€hlungen, enums) dafĂŒr geholt. Auch beim Unscharf-
                  #                                 schalten, dadurch ist kein Neustarten des Skripts notwendig bei
                  #                                 Änderungen an diesen AufzĂ€hlungen.
                  #                               - Eine Schaltung von einem scharf-Zustand auf einen anderen
                  #                                 wird verhindert. ZB von scharf intern auf scharf extern.
                  #                                 Es muss immer unscharf dazwischen geschaltet werden.
                  # 2020-05-09    Andreas Kos     ZusĂ€tzliche Objekte mit JSON-Strings fĂŒr:
                  #                               - den auslösenden Melder
                  #                               - alle offenen Melder
                  #                               - alle offenen Melder der Außenhaut
                  #                               - alle offenen Melder des Innenraums
                  #                               Die JSON-String beinhalten das auslösende Objekt, sowie (falls vorhanden)
                  #                               das Parent und das ParentsParent-Objekt mit allen in ioBroker verfĂŒgbaren Eigenschaften.
                  #                               Kleinere Verbesserungen, z.B. bezĂŒglich setzen der AlarmTexte.
                  # 2020-05-12    Andreas Kos     Setzen des Datenpunkts idReady zur Bereitschaftsanzeige neu gemacht.
                  # 2021-06-13    Andreas Kos     Einbau der Funktion zum Ausnehmen einzelner Melder der AussenhĂŒlle
                  #                               von der Melder-Überwachung. Soll zum Kippen von Fenstern dienen u.Ă€.
                  ########################################################################################################################
                  */
                  
                  // EINBRUCHSMELDER
                  // Jeder Melder muss ein State sein, der bei Auslösung true liefert und in Ruhe (geschlossen) false.
                  // Die Melder sind in Arrays zusammengefasst, d.h. sie mĂŒssen jeweils mit Beistrich voneinander getrennt werden.
                  // Die Namen der Melder sollten gut gepflegt sein fĂŒr eine sinnvolle Verwendung (Attribut name bei den Objekten)
                  
                  // Melder der Außenhaut
                  // Dies können Öffnungskontakte sein von Fenster und TĂŒren in den Außenmauern des Objekts.
                  // EINGABE: In der AufzĂ€hlung "alarmanlage_aussenhaut" die States einfĂŒgen.
                  
                  // Melder des Innenraums
                  // Dies können Bewegungsmelder sein aus dem Inneren.
                  // EINGABE: In der AufzĂ€hlung "alarmanlage_innenraum" die States einfĂŒgen.
                  
                  // Verzögerte Melder
                  // Diese kommen in den Gruppen oben auch vor. Sie bewirken eine Aktivierung der Eingangsverzögerung
                  // bei scharf geschalteter Anlage und erlauben wÀhrend der Ausgangsverzögerung nach dem
                  // Scharfschalten das Haus zu verlassen.
                  // EINGABE: In der AufzĂ€hlung "alarmanlage_verzoegert" die States einfĂŒgen.
                  
                  
                  // EINSTELLUNGEN
                  const entryDelay =                30;         // Eingangsverzögerung in Sekunden (sollte maximal 60s sein)
                  const exitDelay =                 30;         // Ausgangsverzögerung in Sekunden (sollte maximal 60s sein)
                  const alarmDurationAccoustical =  180;         // Dauer des akkustischen Alarms in Sekunden (ACHTUNG: in Ö sind maximal 180s erlaubt!)
                  const alarmDurationOptical =      -1;         // Dauer des optischen Alarm in Sekunden, -1 fĂŒr unendlich
                  
                  // TEXTE FÜR SCHALTZUSTAND
                  // Diese Text geben Auskunft ĂŒber den Zustand der Anlage.
                  // Sie werden in den Datenpunkt "javascript.X.Output.StatusText" geschrieben.
                  const textStatusInactive =        "unscharf";
                  const textStatusActiveInternal =  "scharf intern";
                  const textStatusActiveExternal =  "scharf extern";
                  const textActiveExternalDelayed = "scharf extern verzögert";
                  const textEntryDelayActive =      "Eingangsverzögerung aktiv";
                  const textExitDelayActive =       "Ausgangsverzögerung aktiv";
                  
                  // TEXTE FÜR ALARMIERUNG UND FEHLER
                  // Diese Text geben im unscharfen Zustand der Anlage Auskunft ĂŒber die Bereitschaft
                  // zum Scharfschalten (nur möglich, wenn alle Melder geschlossen - in Ruhe - sind) und
                  // Fehler bei der Scharfschaltung bzw. bei scharfer Anlage ĂŒber den Zustand Frieden oder Alarm.
                  // Sie werden in den Datenpunkt "javascript.X.Output.AlarmText" geschrieben.
                  const textAlarmInactive =         "Alles OK";
                  const textAlarmActive =           "Alarm!!";
                  const textReady =                 "Bereit";
                  const textNotReady =              "Nicht bereit";
                  const textError =                 "Fehler bei der Scharfschaltung";
                  
                  // EXPERTEN-EINSTELLUNGEN
                  const pathToCreatedStates = "Alarmanlage";    // Beispiel: States werden erzeugt unter javascript.X.Alarmanlage
                  const seperator = ", ";                       // Trenn-String, der zwischen den Meldernamen verwendet wird, im Datenpunkt "OpenDetectors"
                  const loglevel = 2;                           // 0 bis 3. 0 ist AUS, 3 ist maximales Logging
                                                              // Empfehlung fĂŒr Nachvollziehbarkeit aller Handlungen ist 2 (Ereignisliste)
                  const functionOuterSkin = "alarmanlage_aussenhaut";
                  const functionIndoor = "alarmanlage_innenraum";
                  const functionDelayedDetectors = "alarmanlage_verzoegert";
                  
                  /*
                     ###############################################################################
                                      DO NOT CHANGE ANYTHING BELOW THIS LINE
                                           AB HIER NICHTS MEHR ÄNDERN
                     ###############################################################################
                  */
                  
                  // ===============================================================================
                  // Variablen
                  // ===============================================================================
                  
                  // Arrays fĂŒr die Melder
                  var detectorsOuterSkin = [];
                  var detectorsIndoor = [];
                  var detectorsDelayed = [];
                  
                  // Array fĂŒr die IgnoreOpen-Melder (beinhaltet nur Flags).
                  // Das Array ist inital deckungsgleich mit detectorsOuterSkin, da diese
                  // nur aus dieser Function kommen können.
                  // Dieses Array ist 2-Dimensional: [Melder-ID, IgnoreOpen-Zustands-ID]
                  var detectorsIgnoreOpen = [];
                  
                  // Javascript-Instanz mit der das Alarmanlagen-Skript ausgefĂŒhrt wird
                  var javascriptInstance = instance;
                  
                  // States, die erzeugt werden fĂŒr Status-Ausgaben
                  var idActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Active";
                  var idActiveExternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveExternal";
                  var idActiveInternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveInternal";
                  var idActiveNumber = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveNumber";
                  var idAlarm = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Alarm";
                  var idAlarmAccoustical = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmAccoustical";
                  var idAlarmOptical = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmOptical";
                  var idReady = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Ready";
                  var idEntryDelayActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.EntryDelayActive";
                  var idExitDelayActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ExitDelayActive";
                  var idAlarmingDetector = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmingDetector";
                  var idAlarmingDetectorJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmingDetectorJSON";
                  var idOpenDetectors = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectors";
                  var idOpenDetectorsJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsJSON";
                  var idOpenDetectorsOuterSkinJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsOuterSkinJSON";
                  var idOpenDetectorsIndoorJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsIndoorJSON";
                  var idOpenDetectorsWithIgnoreOpenFlagSet = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsIgnoreOpen";
                  
                  var idStatusText = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.StatusText";
                  var idAlarmText = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmText";
                  var idError = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Error";
                  
                  // States, die erzeugt werden fĂŒr Eingaben
                  var idSwitchExternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchExternal";
                  var idSwitchInternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchInternal";
                  var idSwitchExternalDelayed = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchExternalDelayed";
                  var idSwitchNumber = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchNumber";
                  
                  // Sonstige globale Variablen, die gebraucht werden
                  var timerExitDelay = null;
                  var timerTexts = null;
                  
                  // ===============================================================================
                  // Precode
                  // ===============================================================================
                  
                  // Logging
                  if (loglevel >= 1) log ("Alarmsystem started.");
                  
                  getAllDetectors();
                  
                  // States erzeugen
                  myCreateState(idActive, "boolean", false, "Switch Status Total", false, "info.status");
                  myCreateState(idActiveExternal, "boolean", false, "Switch Status External", false, "info.status");
                  myCreateState(idActiveInternal, "boolean", false, "Switch Status Internal", false, "info.status");
                  myCreateState(idAlarm, "boolean", false, "Alarm Status", false, "sensor.alarm");
                  myCreateState(idAlarmAccoustical, "boolean", false, "Accoustical Alarm Status", false, "sensor.alarm");
                  myCreateState(idAlarmOptical, "boolean", false, "Optical Alarm Status", false, "sensor.alarm");
                  myCreateState(idReady, "boolean", false, "Alarmsystem Ready", false, "info.status");
                  myCreateState(idError, "boolean", false, "Error Switching Active", false, "info.status");
                  myCreateState(idEntryDelayActive, "boolean", false, "Entry Delay Active Status", false, "info.status");
                  myCreateState(idExitDelayActive, "boolean", false, "Exit Delay Active Status", false, "info.status");
                  myCreateState(idAlarmingDetector, "string", "", "Alarming Detector", false, "text");
                  myCreateState(idAlarmingDetectorJSON, "string", "", "Alarming Detector JSON", false, "json");
                  myCreateState(idOpenDetectors, "string", "", "Open Detectors", false, "info.name");
                  myCreateState(idOpenDetectorsJSON, "string", "", "Open Detectors JSON", false, "json");
                  myCreateState(idOpenDetectorsOuterSkinJSON, "string", "", "Open Detectors Outer Skin JSON", false, "json");
                  myCreateState(idOpenDetectorsIndoorJSON, "string", "", "Open Detectors Indoor JSON", false, "json");
                  myCreateState(idOpenDetectorsWithIgnoreOpenFlagSet, "string", "", "Open Detectors with IgnoreOpen-Flag set", false, "text");
                  myCreateState(idStatusText, "string", "", "Status Text", false, "text");
                  myCreateState(idAlarmText, "string", "", "Alarm Text", false, "text");
                  myCreateState(idSwitchExternal, "boolean", false, "Enable Surveillance External", true, "switch");
                  myCreateState(idSwitchInternal, "boolean", false, "Enable Surveillance Internal", true, "switch");
                  myCreateState(idSwitchExternalDelayed, "boolean", false, "Enable Surveillance External Delayed", true, "switch");
                  
                  myCreateMultiState (idActiveNumber, "number", 0, "Switch Status Number", false, 0, 4,"0:"+textStatusInactive+"; 1:"+textStatusActiveInternal+"; 2:"+textStatusActiveExternal+"; 3:"+textExitDelayActive+"; 4:"+textEntryDelayActive);
                  myCreateMultiState (idSwitchNumber, "number", 0, "Switch by Number", true, 0, 3, "0:"+textStatusInactive+"; 1:"+textStatusActiveInternal+" ; 2:"+textStatusActiveExternal+" ; 3:"+textActiveExternalDelayed);
                  
                  // Erzeugen der Datenpunkte fĂŒr die IgnoreOpen-Einstellung
                  myCreateIgnoreOpenDPs();
                  
                  // Melder nach dem Starten checken
                  checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                  
                  // ===============================================================================
                  // ON-Subscribtions
                  // ===============================================================================
                  
                  // Auf Schaltstellen EXTERN verzögert reagieren (schalten EIN/AUS)
                  on ({id: idSwitchExternalDelayed, change: "any"}, function(obj){
                      if (loglevel >= 3) log ("Switching External Delayed, Value: " + getState(obj.id).val);
                      if (getState(obj.id).val) { // Einschalten, scharf extern VERZÖGERT
                          if (loglevel >= 2) log ("Switching required: Delayed External Active");
                              if (getState(idActive).val) {
                                  if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                  setState(idError, true);
                              } else {
                                  setState(idExitDelayActive, true);
                                  if (timerExitDelay) clearTimeout(timerExitDelay);
                                  timerExitDelay = setTimeout(switchActiveExternal, exitDelay * 1000);
                              }
                      }
                      else { // Ausschalten, unscharf SOFORT
                          if (loglevel >= 2) log ("Switching required: Inactive");
                          switchInactive();
                      }
                  });
                  
                  // Auf Schaltstellen EXTERN sofort reagieren (schalten EIN/AUS)
                  on ({id: idSwitchExternal, change: "any"}, function(obj){
                      if (loglevel >= 3) log ("Switching External Immediately, Value: " + getState(obj.id).val);
                      if (getState(obj.id).val) { // Einschalten, scharf extern
                          if (loglevel >= 2) log ("Switching required: External Active");
                          if (getState(idActive).val) {
                              if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                              setState(idError, true);
                          } else {
                              switchActiveExternal();
                          }
                      }
                      else { // Ausschalten, unscharf
                          if (loglevel >= 2) log ("Switching required: Inactive");
                          switchInactive();
                      }
                  });
                  
                  // Auf Schaltstellen INTERN sofort reagieren (schalten EIN/AUS)
                  on ({id: idSwitchInternal, change: "any"}, function(obj){
                      if (loglevel >= 3) log ("Switching Internal, Value: " + getState(obj.id).val);
                      if (getState(obj.id).val) { // Einschalten, scharf intern
                          if (loglevel >= 2) log ("Switching required: Internal Active");
                          if (getState(idActive).val) {
                              if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                              setState(idError, true);
                          } else {
                              switchActiveInternal();
                          }
                      }
                      else { // Ausschalten, unscharf
                          switchInactive();
                          if (loglevel >= 2) log ("Switching required: Inactive");
                      }
                  });
                  
                  // Auf Schaltstelle mit Datenpunkt SwitchNumber reagieren
                  // Folgende Reaktionen:
                  //      0 ... unscharf schalten
                  //      1 ... scharf intern schalten
                  //      2 ... scharf extern schalten
                  //      3 ... verzögert scharf extern schalten
                  on ({id: idSwitchNumber, change: "any"}, function(obj){
                      if (loglevel >= 3) log ("Switching Number, Value: " + obj.state.val);
                      switch (obj.state.val) {
                          case 0:
                              if (loglevel >= 2) log ("Switching required: Inactive");
                              switchInactive();
                              break;
                          case 1:
                              if (loglevel >= 2) log ("Switching required: Internal Active");
                              if (getState(idActive).val) {
                                  if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                  setState(idError, true);
                              } else {
                                  switchActiveInternal();
                              }
                              break;
                          case 2:
                              if (loglevel >= 2) log ("Switching required: External Active");
                              if (getState(idActive).val) {
                                  if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                  setState(idError, true);
                              } else {
                                  switchActiveExternal();
                              }
                              break;
                          case 3:
                              if (loglevel >= 2) log ("Switching required: Delayed External Active");
                              if (getState(idActive).val) {
                                  if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                  setState(idError, true);
                              } else {
                                  setState(idExitDelayActive, true);
                                  if (timerExitDelay) clearTimeout(timerExitDelay);
                                  timerExitDelay = setTimeout(switchActiveExternal, exitDelay * 1000);
                              }
                              break;
                          default:
                              if (loglevel >= 3) log ("idSwitchNumber has unknown number!");
                      }
                  });
                  
                  // Auf Fehler bei der Scharfschaltung reagieren
                  on ({id: idError, val: true, change: "any"}, function(obj){
                      if (loglevel >= 1) log ("Error when switching to active.");
                      setState(idAlarmText, textError);
                  });
                  
                  // Auf Eingangsverzögerung reagieren
                  on({id: idEntryDelayActive, val: true, change: "ne"}, function (obj) {
                      if (loglevel >= 2) log ("Entry Delay is active (" + entryDelay + " seconds)");
                      setState(idStatusText, textEntryDelayActive);
                      setStateDelayed(idAlarmAccoustical, true, entryDelay * 1000);
                      setStateDelayed(idAlarmOptical, true, entryDelay * 1000);
                  });
                  
                  // Auf Ausgangsverzögerung reagieren
                  on({id: idExitDelayActive, val: true, change: "ne"}, function (obj) {
                      if (loglevel >= 2) log ("Exit Delay is active (" + exitDelay + " seconds)");
                      setState(idStatusText, textExitDelayActive);
                  });
                  
                  // Auf Akustischen Alarm reagieren
                  on ({id: idAlarmAccoustical, val: true, change: "ne"}, function(obj){
                      if (loglevel >= 1) log ("ALARM is active!");
                      setState(idEntryDelayActive, false);
                      setState(idAlarmText, textAlarmActive);
                      setState(idAlarm, true);
                      setStateDelayed(idAlarmAccoustical, false, alarmDurationAccoustical * 1000);
                      if (getState(idActiveExternal).val) setState(idStatusText, textStatusActiveExternal);
                      if (getState(idActiveInternal).val) setState(idStatusText, textStatusActiveInternal);
                  });
                  
                  // Auf Optischen Alarm reagieren
                  on ({id: idAlarmOptical, val: true, change: "ne"}, function(obj){
                      if (alarmDurationOptical >= 0)
                          setStateDelayed(idAlarmOptical, false, alarmDurationOptical * 1000);
                  });
                  
                  // Melderauswertung
                  on( {id: detectorsOuterSkin.concat(detectorsIndoor), change: "ne"}, function(obj){
                      detectorSurveillance(obj);
                  });
                  
                  // Status in Active.Number schreiben
                  on ({id: [idActiveInternal, idActiveExternal, idEntryDelayActive, idExitDelayActive], change: "ne"}, function(obj){
                      if (loglevel >= 3) log ("on for writing ActiveNumber, Trigger: " + obj.id);
                      setActiveNumber();
                  });
                  
                  // Texte korrekt setzen
                  on ({id: [idAlarm, idActive, idOpenDetectors], change: "any"}, function (obj) {
                      // Das Timeout ggf. abbrechen
                      if (timerTexts) clearTimeout(timerTexts);  
                      // Nach einem Timeout den Check anfangen
                      timerTexts = setTimeout(setTexts, 200);
                  });
                  
                  
                  
                  // ===============================================================================
                  // Funktionen
                  // ===============================================================================
                  // Funktion     checkIfIgnoreOpenFlagSet
                  // =====================================
                  // Parameter:       PrĂŒft, ob das IgnoreOpen-Flag fĂŒr einen Melder gesetzt ist.
                  // Übergabewert:    Melder-ID
                  // RĂŒckgabewert:    Flag-Zustand
                  function checkIfIgnoreOpenFlagSet(id){
                      var i=0;
                      while (i<detectorsIgnoreOpen.length){
                          if ( detectorsIgnoreOpen[i][0] == id )
                              if (getState(detectorsIgnoreOpen[i][1]).val)
                                  return true;
                          i++;
                      }
                      return false;
                  }
                  
                  // Function setTexts
                  // =================
                  // Parameter:       keiner
                  // Funktion:        AbhÀngig von den ZustÀnden scharf/unscharf und
                  //                  Alarm / Kein Alarm werden Texte fĂŒr
                  //                  den AlarmText richtig gesetzt. Auch der Datenpunkt idReady wird hier gesetzt.
                  // RĂŒckgabewert:    keiner
                  function setTexts(){    
                      var textListOfDetectors = getState(idOpenDetectors).val;
                      if (textListOfDetectors.length > 0) {
                          if (!getState(idActive).val)
                              // Offene Melder gefunden und unscharf
                              setState(idAlarmText, textNotReady);
                              setState(idReady, false);
                          return false;
                      } else {
                          if (getState(idActive).val && !getState(idAlarm).val)
                              // kein offener Melder gefunden und scharf und kein Alarm
                              setState(idAlarmText, textAlarmInactive);
                          else if (!getState(idActive).val)
                              // kein offener Melder gefunden und unscharf
                              setState(idAlarmText, textReady);
                              setState(idReady, true);
                          return true;
                      }
                  }
                  
                  // Function getAllDetectors
                  // ========================
                  // Parameter:       keiner
                  // Funktion:        Über die Funktion getDetectorsFromFunction werden
                  //                  alle Melder von den Functions geholt und in die
                  //                  globalen Variablen dafĂŒr geschrieben.
                  // RĂŒckgabewert:    keiner
                  function getAllDetectors(){
                      var i=0;
                      detectorsOuterSkin = getDetectorsFromFunction(functionOuterSkin);
                      detectorsIgnoreOpen = [];
                      while (i<detectorsOuterSkin.length) {
                          detectorsIgnoreOpen.push([detectorsOuterSkin[i++]]);
                      }
                      detectorsIndoor = getDetectorsFromFunction(functionIndoor);
                      detectorsDelayed = getDetectorsFromFunction(functionDelayedDetectors);
                  }
                  
                  // Function getDetectorsFromFunction
                  // =================================
                  // Parameter:       functionString
                  //                  Name der Function, in der die Melder enthalen sind.
                  // Funktion:        Alle Teilnehmer der ĂŒbergebenen Function werden
                  //                  in ein Array geschrieben.
                  // RĂŒckgabewert:    Array der Melder-IDs
                  function getDetectorsFromFunction( functionString ) {
                      if (loglevel >= 3) log ("Function getDetectorsFromFunction");
                      var detectors = [];
                      $('state(functions='+functionString+')').each(function(id, i) {
                          detectors.push(id);
                          if (loglevel >= 3) log ("This detector was added to surveillance from function "+functionString+": " + id);
                      });
                      return detectors;
                  }
                  
                  // Function detectorSurveillance
                  // =============================
                  // Parameter:       obj
                  //                  Objekt des auslösenden Melders
                  // Funktion:        AbhĂ€ngig vom Schaltzustand werden die Melder ĂŒberprĂŒft.
                  //                  Bei unscharf wird nur die Liste der offenen Melder und die
                  //                  Bereitschaft der Anlage zum Scharfschalten gepfelgt.
                  //                  Bei scharf geschalteter Anlage ist es anders:
                  //                  Es wird geprĂŒft, ob der auslösende Melder in den Außenhaut- oder
                  //                  Innenraum-Meldern enthalten ist und ob dieser ein verzögerter Melder ist.
                  //                  AbhÀngig davon wird entweder sofort oder verzögert Alarm ausgelöst.
                  // RĂŒckgabewert:    keiner
                  function detectorSurveillance (obj) {
                      var active = getState(idActive).val;
                      var activeExternal = getState(idActiveExternal).val;
                      var activeInternal = getState(idActiveInternal).val;
                      var ready;
                      var ignoreOpenSet;
                      
                      if (loglevel >= 2) log ("Surveillance of detectors started, triggering detector: " + obj.common.name);
                  
                      // Alle offenen Melder feststellen
                      ready = checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                  
                      // Auslösenden Melder schreiben
                      setState(idAlarmingDetector, obj.common.name);
                      setState(idAlarmingDetectorJSON, JSON.stringify(  getDetectorObject(obj.id)  ));
                  
                      // PrĂŒfen, wie der der Schaltzustand ist
                      // bei unscharf
                      if (!active) {
                          if (loglevel >= 2) log ("Alarmsystem is Inactive");
                      }
                      // bei scharf intern
                      if (activeInternal) {
                          if (loglevel >= 2) log ("Alarmsystem is Internal Active");
                          if (detectorsOuterSkin.indexOf(obj.id) != -1) {
                              if (loglevel >= 3) log ("Detector is part of Outer Skin");
                              if (detectorsDelayed.indexOf(obj.id) != -1) {
                                  if (loglevel >= 3) log ("Detector is part of Delayed Detectors");
                                  if(!getState(idAlarm).val) setState(idEntryDelayActive, true);
                                  else {
                                      if (loglevel >= 3) log ("EntryDelay was already active, alarming now");
                                      setState(idAlarmAccoustical, true);
                                      setState(idAlarmOptical, true);
                                  }
                              } else {
                                  if (loglevel >= 3) log ("Detector is not delayed");
                                  setState(idAlarmAccoustical, true);
                                  setState(idAlarmOptical, true);
                              }
                          }
                      }
                      // bei scharf extern
                      if (activeExternal) {
                          if (loglevel >= 2) log ("Alarmsystem is External Active");
                          // PrĂŒfen, ob er der Melder das IgnoreOpen-Flag gesetzt hat.
                          ignoreOpenSet = checkIfIgnoreOpenFlagSet(obj.id);
                          if (loglevel >= 2) log ("Detector has IgnoreOpen-Flag set true!");
                          if (ignoreOpenSet)  return;
                          if (detectorsOuterSkin.concat(detectorsIndoor).indexOf(obj.id) != -1) {
                              if (loglevel >= 3) log ("Detector is part of Outer Skin or Indoor");
                              if (detectorsDelayed.indexOf(obj.id) != -1) {
                                  if (loglevel >= 3) log ("Detector is part of Delayed Detectors");
                                  if(!getState(idAlarm).val) setState(idEntryDelayActive, true);
                                  else {
                                      if (loglevel >= 3) log ("EntryDelay was already active, alarming now");
                                      setState(idAlarmAccoustical, true);
                                      setState(idAlarmOptical, true);
                                  }
                              } else {
                                  if (loglevel >= 3) log ("Detector is not delayed");
                                  if (loglevel >= 2) log ("System is ALARMING now!");
                                  setState(idAlarmAccoustical, true);
                                  setState(idAlarmOptical, true);
                              }
                          }
                      }
                  }
                  
                  // Function myCreateState
                  // =======================
                  // Parameter:       id      ... id des neu anzulegenden Datenpunkts
                  //                  typ     ... typ des anzulegenden Datenpunkts ("boolean", "string", "number", etc.)
                  //                  val     ... Wert, den der Datenpunkt nach dem Anlegen haben soll
                  //                  descr   ... Name als String
                  //                  writeaccess Schreibrechte true oder false
                  // Funktion:        Mit der Funktion createState wird der neue Datenpunkt mit den ĂŒbergebenen
                  //                  Parametern angelegt.
                  // RĂŒckgabewert:    keiner
                  function myCreateState(id, typ, val, descr, writeaccess, role) {
                      if (loglevel >= 3) log ("Function myCreateState for " + id);
                      createState(id, val,    {read: !writeaccess, 
                                              write: writeaccess, 
                                              name: descr,
                                              type: typ,
                                              def: val,
                                              role: role ? role : "state"
                      });
                  }
                  
                  // Function myCreateMultiState
                  // ===========================
                  // Parameter:       id      ... id des neu anzulegenden Datenpunkts
                  //                  typ     ... typ des anzulegenden Datenpunkts ("boolean", "string", "number", etc.)
                  //                  val     ... Wert, den der Datenpunkt nach dem Anlegen haben soll
                  //                  descr   ... Name als String
                  //                  min     ... Minimalwert
                  //                  max     ... Maximalwert
                  //                  list    ... Liste mit Werten und Bezeichnern im Format "0:Text0; 1:Text1; 2:Text2"
                  //                  writeaccess Schreibrechte true oder false
                  // Funktion:        Mit der Funktion createState wird der neue Datenpunkt mit den ĂŒbergebenen
                  //                  Parametern angelegt.
                  // RĂŒckgabewert:    keiner
                  function myCreateMultiState(id, typ, val, descr, writeaccess, minimum, maximum, list, role) {
                      if (loglevel >= 3) log ("Function myCreateMultiState for " + id);
                      createState(id, val, {  read: true, 
                                              write: writeaccess, 
                                              name: descr,
                                              type: typ,
                                              def: val,
                                              min: minimum, 
                                              max: maximum, 
                                              states: list,
                                              role: role ? role : "state"
                      });
                  }
                  // Funktion myCreateIgnoreOpenDPs
                  // ==============================
                  // Parameter:       Keine
                  // Funktion:        Erzeugt die Datenpunkte fĂŒr die Ignoge-Open-Melder.
                  //                  DafĂŒr werden die Namen aus dem detectorsOuterSkin-Array geholt.
                  //                  Die IDs der Ignore-Open Datenpunkte fĂŒr jeden Melder werden auch in
                  //                  das Array detectorsIgnoreOpen geschrieben. Dieses wird damit 3-Dimensional.
                  // RĂŒckgabewert:    Keiner.
                  function myCreateIgnoreOpenDPs(){
                      var detectorName;
                      var idBase = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.IgnoreOpen.";
                      var i=0;
                      while (i<detectorsOuterSkin.length) {
                          detectorName = getObject(detectorsOuterSkin[i]).common.name.replace(/\./g,"_");
                          myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                          detectorsIgnoreOpen[i].push(idBase + detectorName);
                          i++;
                      }
                  }
                  
                  // Function switchActiveExternal
                  // =============================
                  // Parameter:       keiner
                  // Funktion:        Nach PrĂŒfung auf Bereitschaft zum externen Scharfschalten, wird 
                  //                  scharf geschaltet oder ein Fehler angezeigt.
                  // RĂŒckgabewert:    keiner
                  function switchActiveExternal () {
                      if (loglevel >= 3) log ("Function switchActiveExternal");
                      setState(idExitDelayActive, false);
                      var ok = checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                      if (ok) {
                          setState(idActiveExternal, true);
                          setState(idActive, true);
                          setState(idStatusText, textStatusActiveExternal);
                          setState(idAlarmText, textAlarmInactive);
                          setState(idAlarmingDetector,"");
                          setState(idError, false);
                          if (loglevel >= 2) log ("Switched to External Active");
                      } else {
                          if (loglevel >= 2) log ("NOT ready to switch to External Active!");
                          setState(idError, true);
                      }
                  }
                  
                  // Function switchActiveInternal
                  // =============================
                  // Parameter:       keiner
                  // Funktion:        Nach PrĂŒfung auf Bereitschaft zum internen Scharfschalten, wird 
                  //                  scharf geschaltet oder ein Fehler angezeigt.
                  // RĂŒckgabewert:    keiner
                  function switchActiveInternal () {
                      if (loglevel >= 3) log ("Function switchActiveInternal");
                      var ok = checkDetectors(detectorsOuterSkin);
                      if (ok) {
                          setState(idActiveInternal, true);
                          setState(idActive, true);
                          setState(idStatusText, textStatusActiveInternal);
                          setState(idAlarmText, textAlarmInactive);
                          setState(idAlarmingDetector,"");
                          setState(idError, false);
                          if (loglevel >= 2) log ("Switched to Internal Active");
                      } else {
                          if (loglevel >= 2) log ("NOT ready to switch to Internal Active!");
                          setState(idError, true);
                      }
                  ;}
                  
                  // Function switchInactive
                  // =============================
                  // Parameter:       keiner
                  // Funktion:        Es wird unscharf geschaltet und die ganze Anlage resetiert.
                  // RĂŒckgabewert:    keiner
                  function switchInactive () {
                      if (loglevel >= 3) log ("Function switchInactive");
                      if (timerExitDelay) clearTimeout(timerExitDelay);
                      setState(idEntryDelayActive, false);
                      setState(idExitDelayActive, false);
                      setState(idActiveExternal, false);
                      setState(idActiveInternal, false);
                      setState(idActive, false);
                      setState(idError, false);
                      clearStateDelayed(idAlarmAccoustical);
                      clearStateDelayed(idAlarmOptical);
                      setState(idAlarmAccoustical, false);
                      setState(idAlarmOptical, false);
                      setState(idAlarm, false);
                      setState(idAlarmText, textAlarmInactive);
                      setState(idStatusText, textStatusInactive);
                      checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                      if (loglevel >= 2) log ("Switched to Inactive");
                      getAllDetectors();
                  }
                  
                  // Function setActiveNumber
                  // =======================
                  // Parameter:       keine
                  // Funktion:        PrĂŒft ob intern scharf, extern scharf oder unscharf ist und
                  //                  ob jeweils Eingangs- oder Ausgangsverzögerung aktiv ist.
                  //                  AbhÀngig davon wird der Datenpunt "Output.ActiveNumber"
                  //                  wie folgt gesetzt:
                  //                    0 ... unscharf
                  //                    1 ... intern scharf
                  //                    2 ... extern scharf
                  //                    3 ... Eingangsverzögerung aktiv
                  //                    4 ... Ausgangsverzögerung aktiv
                  // RĂŒckgabewert:    keiner
                  function setActiveNumber () {
                      if (loglevel >= 3) log ("Function setActiveNumber");
                      var internal = getState(idActiveInternal).val;
                      var external = getState(idActiveExternal).val;
                      var entry = getState(idEntryDelayActive).val;
                      var exit = getState(idExitDelayActive).val;
                      if (!external && !internal) {
                          if (exit)
                              setState(idActiveNumber, 4);
                          else
                              setState(idActiveNumber, 0);
                      }
                      if (internal) setState(idActiveNumber, 1);
                      if (external){
                          if (entry)
                              setState(idActiveNumber, 3);
                          else
                              setState(idActiveNumber, 2);
                      }
                  }
                  
                  // Function checkDetectors
                  // =======================
                  // Parameter:       detectors
                  //                  Array mit Melder-IDs
                  // Funktion:        Alle Melder aus dem Array werden geprĂŒft und alle offenen
                  //                  Melder werden in einen Datenpunkt geschrieben als String.
                  //                  Das Trennzeichen zwischen den Meldernamen ist die globale
                  //                  Variable "seperator".
                  // RĂŒckgabewert:    true, wenn alle Melder in Ruhe sind
                  //                  false, wenn ein oder mehr Melder ausgelöst sind
                  function checkDetectors ( detectors ) {
                      if (loglevel >= 3) log ("Function checkDetectors");
                      var i=0;
                      var textListOfDetectors="";
                      var textListOfDetectorsIgnoreOpen="";
                      var objOpenDetectors = {
                          title: "All open detectors",
                          zone: null,
                          listOfDetectors:    []
                      };
                      var objOpenDetectorsOuterSkin = {
                          title: "Open detectors outer skin",
                          zone: functionOuterSkin,
                          listOfDetectors:    []
                      };
                      var objOpenDetectorsIndoor = {
                          title: "Open detectors indoor",
                          zone: functionIndoor,
                          listOfDetectors:    []
                      };
                      while(i < detectors.length) {
                          if (getState(detectors[i]).val) {
                              if (checkIfIgnoreOpenFlagSet(detectors[i])) {
                                  if (textListOfDetectorsIgnoreOpen.length > 0) textListOfDetectorsIgnoreOpen += seperator;
                                  textListOfDetectorsIgnoreOpen += getObject(detectors[i]).common.name;
                              }
                              else {
                                  if (textListOfDetectors.length > 0) textListOfDetectors += seperator;
                                  textListOfDetectors += getObject(detectors[i]).common.name;
                              }
                              var detObj = getDetectorObject(detectors[i]);
                              objOpenDetectors.listOfDetectors.push(detObj);
                              if (detectorsOuterSkin.indexOf(detectors[i]) != -1) objOpenDetectorsOuterSkin.listOfDetectors.push(detObj);
                              if (detectorsIndoor.indexOf(detectors[i]) != -1) objOpenDetectorsIndoor.listOfDetectors.push(detObj);
                          }
                          i++;
                      }
                      if (loglevel >= 3) log ("Open Detectors found: " + (textListOfDetectors.length ? textListOfDetectors : "none"));
                      
                      // Datenpunkte schreiben
                      setState(idOpenDetectors, textListOfDetectors);
                      setState(idOpenDetectorsWithIgnoreOpenFlagSet, textListOfDetectorsIgnoreOpen);
                      setState(idOpenDetectorsJSON, JSON.stringify(objOpenDetectors));
                      setState(idOpenDetectorsOuterSkinJSON, JSON.stringify(objOpenDetectorsOuterSkin));
                      setState(idOpenDetectorsIndoorJSON, JSON.stringify(objOpenDetectorsIndoor));
                  
                      if (textListOfDetectors.length > 0) {
                          return false;
                      } else {
                          return true;
                      }
                  }
                  
                  // Function getDetectorObject
                  // ==========================
                  // Parameter:       id
                  //                  id eines Melder-States
                  // Funktion:        Vom Melder mit der id wird das Objekt ĂŒber getObjekt(id) geholt,
                  //                  sowie von seinem Parent und ParentsParent.
                  //                  Alle Objekte kommen in ein großes Objekt und werden zurĂŒck gegeben.
                  // RĂŒckgabewert:    Das Objekt des Melders samt Parent und ParentsParent (sofern es welche gibt)
                  function getDetectorObject (id) {
                      if (loglevel >= 3) log ("Function getDetectorObject for id: " + id);
                      // ioBroker Parent-Datenpunkt (z.B. Kanal), kann auch null sein (zB bei KNX)
                      var idParent = id.substr(0, id.lastIndexOf("."));
                      // ioBroker ParentsParent-Datenpunkt (z.B. GerÀt), kann auch null sein (zB bei KNX)
                      var idParentsParent = idParent.substr(0, idParent.lastIndexOf("."));
                  
                      // Objekte dazu holen
                      var obj    = getObject(id);
                      var objParent = getObject(idParent);
                      var objParentsParent = getObject(idParentsParent);
                  
                      // Alle Objekte in ein großes Objekt sammeln
                      var detectorsObj = {
                          id:             id,
                          self:           obj,
                          parent:         objParent,
                          parentsparent:  objParentsParent
                      };
                  
                      // RĂŒckgeben
                      return detectorsObj;
                  }
                  
                  
                  

                  Ich hoffe, es funktioniert einigermaßen. Bitte mal testen.
                  Danke und LG
                  Andreas

                  BBTownB SchmakusS 2 Antworten Letzte Antwort
                  0
                  • andreaskosA andreaskos

                    Lieber @Freaknet und @Schmakus und alle anderen Leser,

                    ich habe eben die Funktion eingebaut, einzelne Melder aus der AussenhĂŒlle von der Überwachung ausnehmen zu können. Die Funktion ist mehr oder weniger ungetestet und ich wĂŒrde euch bitten hier Feedback zu geben, um das Skript fehlerfrei zu bekommen und auch als neue Version oben im ersten Thread updaten zu können.

                    Neue Datenpunkte
                    Unter "Input" ist nun ein neuer Knoten namens "IgnoreOpen" zu finden. Unterhalb diesem können per Flag die einzelnen Melder inaktiv geschaltet werden.
                    true = wird mitĂŒberwacht
                    false = von der Überwachung ausgenommen

                    Unter "Output" ist ein Text-Datenpunkt, der die Liste der offenen Melder mit gesetztem IgnoreOpen-Flag beinhaltet. Diese Melder kommen nicht in die Liste der ganz regulÀr offenen Melder.
                    Diesen Datenpunkt könnte man verwenden, um sich zu warnen, wenn zum Zeitpunkt des Scharf-Schaltens (oder ein paar Millisekunden spÀter) hier Text enthalten ist.

                    ACHTUNG
                    Die Einstellung der IgnoreOpen-Flags wird (derzeit) nicht automatisch zurĂŒck gesetzt, etwa beim Scharf-Schalten. Das bedeutet, man muss selbst drauf achten, dass ein Melder nicht ewig auf Inaktiv bleibt, weil man vergessen hat das Flag wieder auf true zu stellen.

                    /*
                    ########################################################################################################################
                    # ALARMSYSTEM
                    #
                    # Das Skript bildet eine einfache Alarmanlage nach mit der Schaltmöglichkeit
                    # fĂŒr intern und extern.
                    # Datenpunkte fĂŒr Inputs und Outputs werden angelegt.
                    # NĂ€here Beschreibung siehe im ioBroker-Forum unter
                    # https://forum.iobroker.net/topic/32885/umfassendes-alarmanlagen-skript
                    # Änderungshistorie:
                    # 2020-05-01    Andreas Kos     Erstellt
                    # 2020-05-02    Andreas Kos     Schaltwunsch mit Number-Datenpunkt Input.SwitchNumber (Idee von @Homer.J.)
                    #                               Schaltstatus mit Number-Datenpunkt Output.ActiveNumber (Idee von @Homer.J.)
                    # 2020-05-03    Andreas Kos     Korrekturen, u.a. fĂŒr Melderauswertung (chage: "ne") & AlarmText
                    # 2020-05-04    Andreas Kos     - Melder werden aus den Functions (AufzĂ€hlungen, enums) dafĂŒr geholt. Auch beim Unscharf-
                    #                                 schalten, dadurch ist kein Neustarten des Skripts notwendig bei
                    #                                 Änderungen an diesen AufzĂ€hlungen.
                    #                               - Eine Schaltung von einem scharf-Zustand auf einen anderen
                    #                                 wird verhindert. ZB von scharf intern auf scharf extern.
                    #                                 Es muss immer unscharf dazwischen geschaltet werden.
                    # 2020-05-09    Andreas Kos     ZusĂ€tzliche Objekte mit JSON-Strings fĂŒr:
                    #                               - den auslösenden Melder
                    #                               - alle offenen Melder
                    #                               - alle offenen Melder der Außenhaut
                    #                               - alle offenen Melder des Innenraums
                    #                               Die JSON-String beinhalten das auslösende Objekt, sowie (falls vorhanden)
                    #                               das Parent und das ParentsParent-Objekt mit allen in ioBroker verfĂŒgbaren Eigenschaften.
                    #                               Kleinere Verbesserungen, z.B. bezĂŒglich setzen der AlarmTexte.
                    # 2020-05-12    Andreas Kos     Setzen des Datenpunkts idReady zur Bereitschaftsanzeige neu gemacht.
                    # 2021-06-13    Andreas Kos     Einbau der Funktion zum Ausnehmen einzelner Melder der AussenhĂŒlle
                    #                               von der Melder-Überwachung. Soll zum Kippen von Fenstern dienen u.Ă€.
                    ########################################################################################################################
                    */
                    
                    // EINBRUCHSMELDER
                    // Jeder Melder muss ein State sein, der bei Auslösung true liefert und in Ruhe (geschlossen) false.
                    // Die Melder sind in Arrays zusammengefasst, d.h. sie mĂŒssen jeweils mit Beistrich voneinander getrennt werden.
                    // Die Namen der Melder sollten gut gepflegt sein fĂŒr eine sinnvolle Verwendung (Attribut name bei den Objekten)
                    
                    // Melder der Außenhaut
                    // Dies können Öffnungskontakte sein von Fenster und TĂŒren in den Außenmauern des Objekts.
                    // EINGABE: In der AufzĂ€hlung "alarmanlage_aussenhaut" die States einfĂŒgen.
                    
                    // Melder des Innenraums
                    // Dies können Bewegungsmelder sein aus dem Inneren.
                    // EINGABE: In der AufzĂ€hlung "alarmanlage_innenraum" die States einfĂŒgen.
                    
                    // Verzögerte Melder
                    // Diese kommen in den Gruppen oben auch vor. Sie bewirken eine Aktivierung der Eingangsverzögerung
                    // bei scharf geschalteter Anlage und erlauben wÀhrend der Ausgangsverzögerung nach dem
                    // Scharfschalten das Haus zu verlassen.
                    // EINGABE: In der AufzĂ€hlung "alarmanlage_verzoegert" die States einfĂŒgen.
                    
                    
                    // EINSTELLUNGEN
                    const entryDelay =                30;         // Eingangsverzögerung in Sekunden (sollte maximal 60s sein)
                    const exitDelay =                 30;         // Ausgangsverzögerung in Sekunden (sollte maximal 60s sein)
                    const alarmDurationAccoustical =  180;         // Dauer des akkustischen Alarms in Sekunden (ACHTUNG: in Ö sind maximal 180s erlaubt!)
                    const alarmDurationOptical =      -1;         // Dauer des optischen Alarm in Sekunden, -1 fĂŒr unendlich
                    
                    // TEXTE FÜR SCHALTZUSTAND
                    // Diese Text geben Auskunft ĂŒber den Zustand der Anlage.
                    // Sie werden in den Datenpunkt "javascript.X.Output.StatusText" geschrieben.
                    const textStatusInactive =        "unscharf";
                    const textStatusActiveInternal =  "scharf intern";
                    const textStatusActiveExternal =  "scharf extern";
                    const textActiveExternalDelayed = "scharf extern verzögert";
                    const textEntryDelayActive =      "Eingangsverzögerung aktiv";
                    const textExitDelayActive =       "Ausgangsverzögerung aktiv";
                    
                    // TEXTE FÜR ALARMIERUNG UND FEHLER
                    // Diese Text geben im unscharfen Zustand der Anlage Auskunft ĂŒber die Bereitschaft
                    // zum Scharfschalten (nur möglich, wenn alle Melder geschlossen - in Ruhe - sind) und
                    // Fehler bei der Scharfschaltung bzw. bei scharfer Anlage ĂŒber den Zustand Frieden oder Alarm.
                    // Sie werden in den Datenpunkt "javascript.X.Output.AlarmText" geschrieben.
                    const textAlarmInactive =         "Alles OK";
                    const textAlarmActive =           "Alarm!!";
                    const textReady =                 "Bereit";
                    const textNotReady =              "Nicht bereit";
                    const textError =                 "Fehler bei der Scharfschaltung";
                    
                    // EXPERTEN-EINSTELLUNGEN
                    const pathToCreatedStates = "Alarmanlage";    // Beispiel: States werden erzeugt unter javascript.X.Alarmanlage
                    const seperator = ", ";                       // Trenn-String, der zwischen den Meldernamen verwendet wird, im Datenpunkt "OpenDetectors"
                    const loglevel = 2;                           // 0 bis 3. 0 ist AUS, 3 ist maximales Logging
                                                                // Empfehlung fĂŒr Nachvollziehbarkeit aller Handlungen ist 2 (Ereignisliste)
                    const functionOuterSkin = "alarmanlage_aussenhaut";
                    const functionIndoor = "alarmanlage_innenraum";
                    const functionDelayedDetectors = "alarmanlage_verzoegert";
                    
                    /*
                       ###############################################################################
                                        DO NOT CHANGE ANYTHING BELOW THIS LINE
                                             AB HIER NICHTS MEHR ÄNDERN
                       ###############################################################################
                    */
                    
                    // ===============================================================================
                    // Variablen
                    // ===============================================================================
                    
                    // Arrays fĂŒr die Melder
                    var detectorsOuterSkin = [];
                    var detectorsIndoor = [];
                    var detectorsDelayed = [];
                    
                    // Array fĂŒr die IgnoreOpen-Melder (beinhaltet nur Flags).
                    // Das Array ist inital deckungsgleich mit detectorsOuterSkin, da diese
                    // nur aus dieser Function kommen können.
                    // Dieses Array ist 2-Dimensional: [Melder-ID, IgnoreOpen-Zustands-ID]
                    var detectorsIgnoreOpen = [];
                    
                    // Javascript-Instanz mit der das Alarmanlagen-Skript ausgefĂŒhrt wird
                    var javascriptInstance = instance;
                    
                    // States, die erzeugt werden fĂŒr Status-Ausgaben
                    var idActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Active";
                    var idActiveExternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveExternal";
                    var idActiveInternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveInternal";
                    var idActiveNumber = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveNumber";
                    var idAlarm = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Alarm";
                    var idAlarmAccoustical = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmAccoustical";
                    var idAlarmOptical = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmOptical";
                    var idReady = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Ready";
                    var idEntryDelayActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.EntryDelayActive";
                    var idExitDelayActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ExitDelayActive";
                    var idAlarmingDetector = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmingDetector";
                    var idAlarmingDetectorJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmingDetectorJSON";
                    var idOpenDetectors = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectors";
                    var idOpenDetectorsJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsJSON";
                    var idOpenDetectorsOuterSkinJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsOuterSkinJSON";
                    var idOpenDetectorsIndoorJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsIndoorJSON";
                    var idOpenDetectorsWithIgnoreOpenFlagSet = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsIgnoreOpen";
                    
                    var idStatusText = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.StatusText";
                    var idAlarmText = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmText";
                    var idError = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Error";
                    
                    // States, die erzeugt werden fĂŒr Eingaben
                    var idSwitchExternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchExternal";
                    var idSwitchInternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchInternal";
                    var idSwitchExternalDelayed = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchExternalDelayed";
                    var idSwitchNumber = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchNumber";
                    
                    // Sonstige globale Variablen, die gebraucht werden
                    var timerExitDelay = null;
                    var timerTexts = null;
                    
                    // ===============================================================================
                    // Precode
                    // ===============================================================================
                    
                    // Logging
                    if (loglevel >= 1) log ("Alarmsystem started.");
                    
                    getAllDetectors();
                    
                    // States erzeugen
                    myCreateState(idActive, "boolean", false, "Switch Status Total", false, "info.status");
                    myCreateState(idActiveExternal, "boolean", false, "Switch Status External", false, "info.status");
                    myCreateState(idActiveInternal, "boolean", false, "Switch Status Internal", false, "info.status");
                    myCreateState(idAlarm, "boolean", false, "Alarm Status", false, "sensor.alarm");
                    myCreateState(idAlarmAccoustical, "boolean", false, "Accoustical Alarm Status", false, "sensor.alarm");
                    myCreateState(idAlarmOptical, "boolean", false, "Optical Alarm Status", false, "sensor.alarm");
                    myCreateState(idReady, "boolean", false, "Alarmsystem Ready", false, "info.status");
                    myCreateState(idError, "boolean", false, "Error Switching Active", false, "info.status");
                    myCreateState(idEntryDelayActive, "boolean", false, "Entry Delay Active Status", false, "info.status");
                    myCreateState(idExitDelayActive, "boolean", false, "Exit Delay Active Status", false, "info.status");
                    myCreateState(idAlarmingDetector, "string", "", "Alarming Detector", false, "text");
                    myCreateState(idAlarmingDetectorJSON, "string", "", "Alarming Detector JSON", false, "json");
                    myCreateState(idOpenDetectors, "string", "", "Open Detectors", false, "info.name");
                    myCreateState(idOpenDetectorsJSON, "string", "", "Open Detectors JSON", false, "json");
                    myCreateState(idOpenDetectorsOuterSkinJSON, "string", "", "Open Detectors Outer Skin JSON", false, "json");
                    myCreateState(idOpenDetectorsIndoorJSON, "string", "", "Open Detectors Indoor JSON", false, "json");
                    myCreateState(idOpenDetectorsWithIgnoreOpenFlagSet, "string", "", "Open Detectors with IgnoreOpen-Flag set", false, "text");
                    myCreateState(idStatusText, "string", "", "Status Text", false, "text");
                    myCreateState(idAlarmText, "string", "", "Alarm Text", false, "text");
                    myCreateState(idSwitchExternal, "boolean", false, "Enable Surveillance External", true, "switch");
                    myCreateState(idSwitchInternal, "boolean", false, "Enable Surveillance Internal", true, "switch");
                    myCreateState(idSwitchExternalDelayed, "boolean", false, "Enable Surveillance External Delayed", true, "switch");
                    
                    myCreateMultiState (idActiveNumber, "number", 0, "Switch Status Number", false, 0, 4,"0:"+textStatusInactive+"; 1:"+textStatusActiveInternal+"; 2:"+textStatusActiveExternal+"; 3:"+textExitDelayActive+"; 4:"+textEntryDelayActive);
                    myCreateMultiState (idSwitchNumber, "number", 0, "Switch by Number", true, 0, 3, "0:"+textStatusInactive+"; 1:"+textStatusActiveInternal+" ; 2:"+textStatusActiveExternal+" ; 3:"+textActiveExternalDelayed);
                    
                    // Erzeugen der Datenpunkte fĂŒr die IgnoreOpen-Einstellung
                    myCreateIgnoreOpenDPs();
                    
                    // Melder nach dem Starten checken
                    checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                    
                    // ===============================================================================
                    // ON-Subscribtions
                    // ===============================================================================
                    
                    // Auf Schaltstellen EXTERN verzögert reagieren (schalten EIN/AUS)
                    on ({id: idSwitchExternalDelayed, change: "any"}, function(obj){
                        if (loglevel >= 3) log ("Switching External Delayed, Value: " + getState(obj.id).val);
                        if (getState(obj.id).val) { // Einschalten, scharf extern VERZÖGERT
                            if (loglevel >= 2) log ("Switching required: Delayed External Active");
                                if (getState(idActive).val) {
                                    if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                    setState(idError, true);
                                } else {
                                    setState(idExitDelayActive, true);
                                    if (timerExitDelay) clearTimeout(timerExitDelay);
                                    timerExitDelay = setTimeout(switchActiveExternal, exitDelay * 1000);
                                }
                        }
                        else { // Ausschalten, unscharf SOFORT
                            if (loglevel >= 2) log ("Switching required: Inactive");
                            switchInactive();
                        }
                    });
                    
                    // Auf Schaltstellen EXTERN sofort reagieren (schalten EIN/AUS)
                    on ({id: idSwitchExternal, change: "any"}, function(obj){
                        if (loglevel >= 3) log ("Switching External Immediately, Value: " + getState(obj.id).val);
                        if (getState(obj.id).val) { // Einschalten, scharf extern
                            if (loglevel >= 2) log ("Switching required: External Active");
                            if (getState(idActive).val) {
                                if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                setState(idError, true);
                            } else {
                                switchActiveExternal();
                            }
                        }
                        else { // Ausschalten, unscharf
                            if (loglevel >= 2) log ("Switching required: Inactive");
                            switchInactive();
                        }
                    });
                    
                    // Auf Schaltstellen INTERN sofort reagieren (schalten EIN/AUS)
                    on ({id: idSwitchInternal, change: "any"}, function(obj){
                        if (loglevel >= 3) log ("Switching Internal, Value: " + getState(obj.id).val);
                        if (getState(obj.id).val) { // Einschalten, scharf intern
                            if (loglevel >= 2) log ("Switching required: Internal Active");
                            if (getState(idActive).val) {
                                if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                setState(idError, true);
                            } else {
                                switchActiveInternal();
                            }
                        }
                        else { // Ausschalten, unscharf
                            switchInactive();
                            if (loglevel >= 2) log ("Switching required: Inactive");
                        }
                    });
                    
                    // Auf Schaltstelle mit Datenpunkt SwitchNumber reagieren
                    // Folgende Reaktionen:
                    //      0 ... unscharf schalten
                    //      1 ... scharf intern schalten
                    //      2 ... scharf extern schalten
                    //      3 ... verzögert scharf extern schalten
                    on ({id: idSwitchNumber, change: "any"}, function(obj){
                        if (loglevel >= 3) log ("Switching Number, Value: " + obj.state.val);
                        switch (obj.state.val) {
                            case 0:
                                if (loglevel >= 2) log ("Switching required: Inactive");
                                switchInactive();
                                break;
                            case 1:
                                if (loglevel >= 2) log ("Switching required: Internal Active");
                                if (getState(idActive).val) {
                                    if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                    setState(idError, true);
                                } else {
                                    switchActiveInternal();
                                }
                                break;
                            case 2:
                                if (loglevel >= 2) log ("Switching required: External Active");
                                if (getState(idActive).val) {
                                    if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                    setState(idError, true);
                                } else {
                                    switchActiveExternal();
                                }
                                break;
                            case 3:
                                if (loglevel >= 2) log ("Switching required: Delayed External Active");
                                if (getState(idActive).val) {
                                    if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                    setState(idError, true);
                                } else {
                                    setState(idExitDelayActive, true);
                                    if (timerExitDelay) clearTimeout(timerExitDelay);
                                    timerExitDelay = setTimeout(switchActiveExternal, exitDelay * 1000);
                                }
                                break;
                            default:
                                if (loglevel >= 3) log ("idSwitchNumber has unknown number!");
                        }
                    });
                    
                    // Auf Fehler bei der Scharfschaltung reagieren
                    on ({id: idError, val: true, change: "any"}, function(obj){
                        if (loglevel >= 1) log ("Error when switching to active.");
                        setState(idAlarmText, textError);
                    });
                    
                    // Auf Eingangsverzögerung reagieren
                    on({id: idEntryDelayActive, val: true, change: "ne"}, function (obj) {
                        if (loglevel >= 2) log ("Entry Delay is active (" + entryDelay + " seconds)");
                        setState(idStatusText, textEntryDelayActive);
                        setStateDelayed(idAlarmAccoustical, true, entryDelay * 1000);
                        setStateDelayed(idAlarmOptical, true, entryDelay * 1000);
                    });
                    
                    // Auf Ausgangsverzögerung reagieren
                    on({id: idExitDelayActive, val: true, change: "ne"}, function (obj) {
                        if (loglevel >= 2) log ("Exit Delay is active (" + exitDelay + " seconds)");
                        setState(idStatusText, textExitDelayActive);
                    });
                    
                    // Auf Akustischen Alarm reagieren
                    on ({id: idAlarmAccoustical, val: true, change: "ne"}, function(obj){
                        if (loglevel >= 1) log ("ALARM is active!");
                        setState(idEntryDelayActive, false);
                        setState(idAlarmText, textAlarmActive);
                        setState(idAlarm, true);
                        setStateDelayed(idAlarmAccoustical, false, alarmDurationAccoustical * 1000);
                        if (getState(idActiveExternal).val) setState(idStatusText, textStatusActiveExternal);
                        if (getState(idActiveInternal).val) setState(idStatusText, textStatusActiveInternal);
                    });
                    
                    // Auf Optischen Alarm reagieren
                    on ({id: idAlarmOptical, val: true, change: "ne"}, function(obj){
                        if (alarmDurationOptical >= 0)
                            setStateDelayed(idAlarmOptical, false, alarmDurationOptical * 1000);
                    });
                    
                    // Melderauswertung
                    on( {id: detectorsOuterSkin.concat(detectorsIndoor), change: "ne"}, function(obj){
                        detectorSurveillance(obj);
                    });
                    
                    // Status in Active.Number schreiben
                    on ({id: [idActiveInternal, idActiveExternal, idEntryDelayActive, idExitDelayActive], change: "ne"}, function(obj){
                        if (loglevel >= 3) log ("on for writing ActiveNumber, Trigger: " + obj.id);
                        setActiveNumber();
                    });
                    
                    // Texte korrekt setzen
                    on ({id: [idAlarm, idActive, idOpenDetectors], change: "any"}, function (obj) {
                        // Das Timeout ggf. abbrechen
                        if (timerTexts) clearTimeout(timerTexts);  
                        // Nach einem Timeout den Check anfangen
                        timerTexts = setTimeout(setTexts, 200);
                    });
                    
                    
                    
                    // ===============================================================================
                    // Funktionen
                    // ===============================================================================
                    // Funktion     checkIfIgnoreOpenFlagSet
                    // =====================================
                    // Parameter:       PrĂŒft, ob das IgnoreOpen-Flag fĂŒr einen Melder gesetzt ist.
                    // Übergabewert:    Melder-ID
                    // RĂŒckgabewert:    Flag-Zustand
                    function checkIfIgnoreOpenFlagSet(id){
                        var i=0;
                        while (i<detectorsIgnoreOpen.length){
                            if ( detectorsIgnoreOpen[i][0] == id )
                                if (getState(detectorsIgnoreOpen[i][1]).val)
                                    return true;
                            i++;
                        }
                        return false;
                    }
                    
                    // Function setTexts
                    // =================
                    // Parameter:       keiner
                    // Funktion:        AbhÀngig von den ZustÀnden scharf/unscharf und
                    //                  Alarm / Kein Alarm werden Texte fĂŒr
                    //                  den AlarmText richtig gesetzt. Auch der Datenpunkt idReady wird hier gesetzt.
                    // RĂŒckgabewert:    keiner
                    function setTexts(){    
                        var textListOfDetectors = getState(idOpenDetectors).val;
                        if (textListOfDetectors.length > 0) {
                            if (!getState(idActive).val)
                                // Offene Melder gefunden und unscharf
                                setState(idAlarmText, textNotReady);
                                setState(idReady, false);
                            return false;
                        } else {
                            if (getState(idActive).val && !getState(idAlarm).val)
                                // kein offener Melder gefunden und scharf und kein Alarm
                                setState(idAlarmText, textAlarmInactive);
                            else if (!getState(idActive).val)
                                // kein offener Melder gefunden und unscharf
                                setState(idAlarmText, textReady);
                                setState(idReady, true);
                            return true;
                        }
                    }
                    
                    // Function getAllDetectors
                    // ========================
                    // Parameter:       keiner
                    // Funktion:        Über die Funktion getDetectorsFromFunction werden
                    //                  alle Melder von den Functions geholt und in die
                    //                  globalen Variablen dafĂŒr geschrieben.
                    // RĂŒckgabewert:    keiner
                    function getAllDetectors(){
                        var i=0;
                        detectorsOuterSkin = getDetectorsFromFunction(functionOuterSkin);
                        detectorsIgnoreOpen = [];
                        while (i<detectorsOuterSkin.length) {
                            detectorsIgnoreOpen.push([detectorsOuterSkin[i++]]);
                        }
                        detectorsIndoor = getDetectorsFromFunction(functionIndoor);
                        detectorsDelayed = getDetectorsFromFunction(functionDelayedDetectors);
                    }
                    
                    // Function getDetectorsFromFunction
                    // =================================
                    // Parameter:       functionString
                    //                  Name der Function, in der die Melder enthalen sind.
                    // Funktion:        Alle Teilnehmer der ĂŒbergebenen Function werden
                    //                  in ein Array geschrieben.
                    // RĂŒckgabewert:    Array der Melder-IDs
                    function getDetectorsFromFunction( functionString ) {
                        if (loglevel >= 3) log ("Function getDetectorsFromFunction");
                        var detectors = [];
                        $('state(functions='+functionString+')').each(function(id, i) {
                            detectors.push(id);
                            if (loglevel >= 3) log ("This detector was added to surveillance from function "+functionString+": " + id);
                        });
                        return detectors;
                    }
                    
                    // Function detectorSurveillance
                    // =============================
                    // Parameter:       obj
                    //                  Objekt des auslösenden Melders
                    // Funktion:        AbhĂ€ngig vom Schaltzustand werden die Melder ĂŒberprĂŒft.
                    //                  Bei unscharf wird nur die Liste der offenen Melder und die
                    //                  Bereitschaft der Anlage zum Scharfschalten gepfelgt.
                    //                  Bei scharf geschalteter Anlage ist es anders:
                    //                  Es wird geprĂŒft, ob der auslösende Melder in den Außenhaut- oder
                    //                  Innenraum-Meldern enthalten ist und ob dieser ein verzögerter Melder ist.
                    //                  AbhÀngig davon wird entweder sofort oder verzögert Alarm ausgelöst.
                    // RĂŒckgabewert:    keiner
                    function detectorSurveillance (obj) {
                        var active = getState(idActive).val;
                        var activeExternal = getState(idActiveExternal).val;
                        var activeInternal = getState(idActiveInternal).val;
                        var ready;
                        var ignoreOpenSet;
                        
                        if (loglevel >= 2) log ("Surveillance of detectors started, triggering detector: " + obj.common.name);
                    
                        // Alle offenen Melder feststellen
                        ready = checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                    
                        // Auslösenden Melder schreiben
                        setState(idAlarmingDetector, obj.common.name);
                        setState(idAlarmingDetectorJSON, JSON.stringify(  getDetectorObject(obj.id)  ));
                    
                        // PrĂŒfen, wie der der Schaltzustand ist
                        // bei unscharf
                        if (!active) {
                            if (loglevel >= 2) log ("Alarmsystem is Inactive");
                        }
                        // bei scharf intern
                        if (activeInternal) {
                            if (loglevel >= 2) log ("Alarmsystem is Internal Active");
                            if (detectorsOuterSkin.indexOf(obj.id) != -1) {
                                if (loglevel >= 3) log ("Detector is part of Outer Skin");
                                if (detectorsDelayed.indexOf(obj.id) != -1) {
                                    if (loglevel >= 3) log ("Detector is part of Delayed Detectors");
                                    if(!getState(idAlarm).val) setState(idEntryDelayActive, true);
                                    else {
                                        if (loglevel >= 3) log ("EntryDelay was already active, alarming now");
                                        setState(idAlarmAccoustical, true);
                                        setState(idAlarmOptical, true);
                                    }
                                } else {
                                    if (loglevel >= 3) log ("Detector is not delayed");
                                    setState(idAlarmAccoustical, true);
                                    setState(idAlarmOptical, true);
                                }
                            }
                        }
                        // bei scharf extern
                        if (activeExternal) {
                            if (loglevel >= 2) log ("Alarmsystem is External Active");
                            // PrĂŒfen, ob er der Melder das IgnoreOpen-Flag gesetzt hat.
                            ignoreOpenSet = checkIfIgnoreOpenFlagSet(obj.id);
                            if (loglevel >= 2) log ("Detector has IgnoreOpen-Flag set true!");
                            if (ignoreOpenSet)  return;
                            if (detectorsOuterSkin.concat(detectorsIndoor).indexOf(obj.id) != -1) {
                                if (loglevel >= 3) log ("Detector is part of Outer Skin or Indoor");
                                if (detectorsDelayed.indexOf(obj.id) != -1) {
                                    if (loglevel >= 3) log ("Detector is part of Delayed Detectors");
                                    if(!getState(idAlarm).val) setState(idEntryDelayActive, true);
                                    else {
                                        if (loglevel >= 3) log ("EntryDelay was already active, alarming now");
                                        setState(idAlarmAccoustical, true);
                                        setState(idAlarmOptical, true);
                                    }
                                } else {
                                    if (loglevel >= 3) log ("Detector is not delayed");
                                    if (loglevel >= 2) log ("System is ALARMING now!");
                                    setState(idAlarmAccoustical, true);
                                    setState(idAlarmOptical, true);
                                }
                            }
                        }
                    }
                    
                    // Function myCreateState
                    // =======================
                    // Parameter:       id      ... id des neu anzulegenden Datenpunkts
                    //                  typ     ... typ des anzulegenden Datenpunkts ("boolean", "string", "number", etc.)
                    //                  val     ... Wert, den der Datenpunkt nach dem Anlegen haben soll
                    //                  descr   ... Name als String
                    //                  writeaccess Schreibrechte true oder false
                    // Funktion:        Mit der Funktion createState wird der neue Datenpunkt mit den ĂŒbergebenen
                    //                  Parametern angelegt.
                    // RĂŒckgabewert:    keiner
                    function myCreateState(id, typ, val, descr, writeaccess, role) {
                        if (loglevel >= 3) log ("Function myCreateState for " + id);
                        createState(id, val,    {read: !writeaccess, 
                                                write: writeaccess, 
                                                name: descr,
                                                type: typ,
                                                def: val,
                                                role: role ? role : "state"
                        });
                    }
                    
                    // Function myCreateMultiState
                    // ===========================
                    // Parameter:       id      ... id des neu anzulegenden Datenpunkts
                    //                  typ     ... typ des anzulegenden Datenpunkts ("boolean", "string", "number", etc.)
                    //                  val     ... Wert, den der Datenpunkt nach dem Anlegen haben soll
                    //                  descr   ... Name als String
                    //                  min     ... Minimalwert
                    //                  max     ... Maximalwert
                    //                  list    ... Liste mit Werten und Bezeichnern im Format "0:Text0; 1:Text1; 2:Text2"
                    //                  writeaccess Schreibrechte true oder false
                    // Funktion:        Mit der Funktion createState wird der neue Datenpunkt mit den ĂŒbergebenen
                    //                  Parametern angelegt.
                    // RĂŒckgabewert:    keiner
                    function myCreateMultiState(id, typ, val, descr, writeaccess, minimum, maximum, list, role) {
                        if (loglevel >= 3) log ("Function myCreateMultiState for " + id);
                        createState(id, val, {  read: true, 
                                                write: writeaccess, 
                                                name: descr,
                                                type: typ,
                                                def: val,
                                                min: minimum, 
                                                max: maximum, 
                                                states: list,
                                                role: role ? role : "state"
                        });
                    }
                    // Funktion myCreateIgnoreOpenDPs
                    // ==============================
                    // Parameter:       Keine
                    // Funktion:        Erzeugt die Datenpunkte fĂŒr die Ignoge-Open-Melder.
                    //                  DafĂŒr werden die Namen aus dem detectorsOuterSkin-Array geholt.
                    //                  Die IDs der Ignore-Open Datenpunkte fĂŒr jeden Melder werden auch in
                    //                  das Array detectorsIgnoreOpen geschrieben. Dieses wird damit 3-Dimensional.
                    // RĂŒckgabewert:    Keiner.
                    function myCreateIgnoreOpenDPs(){
                        var detectorName;
                        var idBase = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.IgnoreOpen.";
                        var i=0;
                        while (i<detectorsOuterSkin.length) {
                            detectorName = getObject(detectorsOuterSkin[i]).common.name.replace(/\./g,"_");
                            myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                            detectorsIgnoreOpen[i].push(idBase + detectorName);
                            i++;
                        }
                    }
                    
                    // Function switchActiveExternal
                    // =============================
                    // Parameter:       keiner
                    // Funktion:        Nach PrĂŒfung auf Bereitschaft zum externen Scharfschalten, wird 
                    //                  scharf geschaltet oder ein Fehler angezeigt.
                    // RĂŒckgabewert:    keiner
                    function switchActiveExternal () {
                        if (loglevel >= 3) log ("Function switchActiveExternal");
                        setState(idExitDelayActive, false);
                        var ok = checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                        if (ok) {
                            setState(idActiveExternal, true);
                            setState(idActive, true);
                            setState(idStatusText, textStatusActiveExternal);
                            setState(idAlarmText, textAlarmInactive);
                            setState(idAlarmingDetector,"");
                            setState(idError, false);
                            if (loglevel >= 2) log ("Switched to External Active");
                        } else {
                            if (loglevel >= 2) log ("NOT ready to switch to External Active!");
                            setState(idError, true);
                        }
                    }
                    
                    // Function switchActiveInternal
                    // =============================
                    // Parameter:       keiner
                    // Funktion:        Nach PrĂŒfung auf Bereitschaft zum internen Scharfschalten, wird 
                    //                  scharf geschaltet oder ein Fehler angezeigt.
                    // RĂŒckgabewert:    keiner
                    function switchActiveInternal () {
                        if (loglevel >= 3) log ("Function switchActiveInternal");
                        var ok = checkDetectors(detectorsOuterSkin);
                        if (ok) {
                            setState(idActiveInternal, true);
                            setState(idActive, true);
                            setState(idStatusText, textStatusActiveInternal);
                            setState(idAlarmText, textAlarmInactive);
                            setState(idAlarmingDetector,"");
                            setState(idError, false);
                            if (loglevel >= 2) log ("Switched to Internal Active");
                        } else {
                            if (loglevel >= 2) log ("NOT ready to switch to Internal Active!");
                            setState(idError, true);
                        }
                    ;}
                    
                    // Function switchInactive
                    // =============================
                    // Parameter:       keiner
                    // Funktion:        Es wird unscharf geschaltet und die ganze Anlage resetiert.
                    // RĂŒckgabewert:    keiner
                    function switchInactive () {
                        if (loglevel >= 3) log ("Function switchInactive");
                        if (timerExitDelay) clearTimeout(timerExitDelay);
                        setState(idEntryDelayActive, false);
                        setState(idExitDelayActive, false);
                        setState(idActiveExternal, false);
                        setState(idActiveInternal, false);
                        setState(idActive, false);
                        setState(idError, false);
                        clearStateDelayed(idAlarmAccoustical);
                        clearStateDelayed(idAlarmOptical);
                        setState(idAlarmAccoustical, false);
                        setState(idAlarmOptical, false);
                        setState(idAlarm, false);
                        setState(idAlarmText, textAlarmInactive);
                        setState(idStatusText, textStatusInactive);
                        checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                        if (loglevel >= 2) log ("Switched to Inactive");
                        getAllDetectors();
                    }
                    
                    // Function setActiveNumber
                    // =======================
                    // Parameter:       keine
                    // Funktion:        PrĂŒft ob intern scharf, extern scharf oder unscharf ist und
                    //                  ob jeweils Eingangs- oder Ausgangsverzögerung aktiv ist.
                    //                  AbhÀngig davon wird der Datenpunt "Output.ActiveNumber"
                    //                  wie folgt gesetzt:
                    //                    0 ... unscharf
                    //                    1 ... intern scharf
                    //                    2 ... extern scharf
                    //                    3 ... Eingangsverzögerung aktiv
                    //                    4 ... Ausgangsverzögerung aktiv
                    // RĂŒckgabewert:    keiner
                    function setActiveNumber () {
                        if (loglevel >= 3) log ("Function setActiveNumber");
                        var internal = getState(idActiveInternal).val;
                        var external = getState(idActiveExternal).val;
                        var entry = getState(idEntryDelayActive).val;
                        var exit = getState(idExitDelayActive).val;
                        if (!external && !internal) {
                            if (exit)
                                setState(idActiveNumber, 4);
                            else
                                setState(idActiveNumber, 0);
                        }
                        if (internal) setState(idActiveNumber, 1);
                        if (external){
                            if (entry)
                                setState(idActiveNumber, 3);
                            else
                                setState(idActiveNumber, 2);
                        }
                    }
                    
                    // Function checkDetectors
                    // =======================
                    // Parameter:       detectors
                    //                  Array mit Melder-IDs
                    // Funktion:        Alle Melder aus dem Array werden geprĂŒft und alle offenen
                    //                  Melder werden in einen Datenpunkt geschrieben als String.
                    //                  Das Trennzeichen zwischen den Meldernamen ist die globale
                    //                  Variable "seperator".
                    // RĂŒckgabewert:    true, wenn alle Melder in Ruhe sind
                    //                  false, wenn ein oder mehr Melder ausgelöst sind
                    function checkDetectors ( detectors ) {
                        if (loglevel >= 3) log ("Function checkDetectors");
                        var i=0;
                        var textListOfDetectors="";
                        var textListOfDetectorsIgnoreOpen="";
                        var objOpenDetectors = {
                            title: "All open detectors",
                            zone: null,
                            listOfDetectors:    []
                        };
                        var objOpenDetectorsOuterSkin = {
                            title: "Open detectors outer skin",
                            zone: functionOuterSkin,
                            listOfDetectors:    []
                        };
                        var objOpenDetectorsIndoor = {
                            title: "Open detectors indoor",
                            zone: functionIndoor,
                            listOfDetectors:    []
                        };
                        while(i < detectors.length) {
                            if (getState(detectors[i]).val) {
                                if (checkIfIgnoreOpenFlagSet(detectors[i])) {
                                    if (textListOfDetectorsIgnoreOpen.length > 0) textListOfDetectorsIgnoreOpen += seperator;
                                    textListOfDetectorsIgnoreOpen += getObject(detectors[i]).common.name;
                                }
                                else {
                                    if (textListOfDetectors.length > 0) textListOfDetectors += seperator;
                                    textListOfDetectors += getObject(detectors[i]).common.name;
                                }
                                var detObj = getDetectorObject(detectors[i]);
                                objOpenDetectors.listOfDetectors.push(detObj);
                                if (detectorsOuterSkin.indexOf(detectors[i]) != -1) objOpenDetectorsOuterSkin.listOfDetectors.push(detObj);
                                if (detectorsIndoor.indexOf(detectors[i]) != -1) objOpenDetectorsIndoor.listOfDetectors.push(detObj);
                            }
                            i++;
                        }
                        if (loglevel >= 3) log ("Open Detectors found: " + (textListOfDetectors.length ? textListOfDetectors : "none"));
                        
                        // Datenpunkte schreiben
                        setState(idOpenDetectors, textListOfDetectors);
                        setState(idOpenDetectorsWithIgnoreOpenFlagSet, textListOfDetectorsIgnoreOpen);
                        setState(idOpenDetectorsJSON, JSON.stringify(objOpenDetectors));
                        setState(idOpenDetectorsOuterSkinJSON, JSON.stringify(objOpenDetectorsOuterSkin));
                        setState(idOpenDetectorsIndoorJSON, JSON.stringify(objOpenDetectorsIndoor));
                    
                        if (textListOfDetectors.length > 0) {
                            return false;
                        } else {
                            return true;
                        }
                    }
                    
                    // Function getDetectorObject
                    // ==========================
                    // Parameter:       id
                    //                  id eines Melder-States
                    // Funktion:        Vom Melder mit der id wird das Objekt ĂŒber getObjekt(id) geholt,
                    //                  sowie von seinem Parent und ParentsParent.
                    //                  Alle Objekte kommen in ein großes Objekt und werden zurĂŒck gegeben.
                    // RĂŒckgabewert:    Das Objekt des Melders samt Parent und ParentsParent (sofern es welche gibt)
                    function getDetectorObject (id) {
                        if (loglevel >= 3) log ("Function getDetectorObject for id: " + id);
                        // ioBroker Parent-Datenpunkt (z.B. Kanal), kann auch null sein (zB bei KNX)
                        var idParent = id.substr(0, id.lastIndexOf("."));
                        // ioBroker ParentsParent-Datenpunkt (z.B. GerÀt), kann auch null sein (zB bei KNX)
                        var idParentsParent = idParent.substr(0, idParent.lastIndexOf("."));
                    
                        // Objekte dazu holen
                        var obj    = getObject(id);
                        var objParent = getObject(idParent);
                        var objParentsParent = getObject(idParentsParent);
                    
                        // Alle Objekte in ein großes Objekt sammeln
                        var detectorsObj = {
                            id:             id,
                            self:           obj,
                            parent:         objParent,
                            parentsparent:  objParentsParent
                        };
                    
                        // RĂŒckgeben
                        return detectorsObj;
                    }
                    
                    
                    

                    Ich hoffe, es funktioniert einigermaßen. Bitte mal testen.
                    Danke und LG
                    Andreas

                    BBTownB Offline
                    BBTownB Offline
                    BBTown
                    schrieb am zuletzt editiert von
                    #104

                    @andreaskos sagte in Umfassendes Alarmanlagen-Skript:

                    true = wird mitĂŒberwacht
                    false = von der Überwachung ausgenommen

                    mĂŒĂŸte es nicht logisch bei einem "ignoreOpen" genau anders herum sein?

                    ioBroker auf NUC (VM debian v13 (Trixie ), node v22.21.0 npm v10.9.4, js-controller v7.0.7 jsonl/jsonl / HomeMatic CCU-2 (Wired und Funk) / Philips HUE / echo.DOT / Broadlink RM pro / SONOS

                    andreaskosA 1 Antwort Letzte Antwort
                    0
                    • BBTownB BBTown

                      @andreaskos sagte in Umfassendes Alarmanlagen-Skript:

                      true = wird mitĂŒberwacht
                      false = von der Überwachung ausgenommen

                      mĂŒĂŸte es nicht logisch bei einem "ignoreOpen" genau anders herum sein?

                      andreaskosA Offline
                      andreaskosA Offline
                      andreaskos
                      schrieb am zuletzt editiert von
                      #105

                      @bbtown
                      Korrekt - und tatsĂ€chlich ist es das auch! 😂
                      Es war schön spĂ€t...😉

                      1 Antwort Letzte Antwort
                      0
                      • andreaskosA andreaskos

                        Lieber @Freaknet und @Schmakus und alle anderen Leser,

                        ich habe eben die Funktion eingebaut, einzelne Melder aus der AussenhĂŒlle von der Überwachung ausnehmen zu können. Die Funktion ist mehr oder weniger ungetestet und ich wĂŒrde euch bitten hier Feedback zu geben, um das Skript fehlerfrei zu bekommen und auch als neue Version oben im ersten Thread updaten zu können.

                        Neue Datenpunkte
                        Unter "Input" ist nun ein neuer Knoten namens "IgnoreOpen" zu finden. Unterhalb diesem können per Flag die einzelnen Melder inaktiv geschaltet werden.
                        true = wird mitĂŒberwacht
                        false = von der Überwachung ausgenommen

                        Unter "Output" ist ein Text-Datenpunkt, der die Liste der offenen Melder mit gesetztem IgnoreOpen-Flag beinhaltet. Diese Melder kommen nicht in die Liste der ganz regulÀr offenen Melder.
                        Diesen Datenpunkt könnte man verwenden, um sich zu warnen, wenn zum Zeitpunkt des Scharf-Schaltens (oder ein paar Millisekunden spÀter) hier Text enthalten ist.

                        ACHTUNG
                        Die Einstellung der IgnoreOpen-Flags wird (derzeit) nicht automatisch zurĂŒck gesetzt, etwa beim Scharf-Schalten. Das bedeutet, man muss selbst drauf achten, dass ein Melder nicht ewig auf Inaktiv bleibt, weil man vergessen hat das Flag wieder auf true zu stellen.

                        /*
                        ########################################################################################################################
                        # ALARMSYSTEM
                        #
                        # Das Skript bildet eine einfache Alarmanlage nach mit der Schaltmöglichkeit
                        # fĂŒr intern und extern.
                        # Datenpunkte fĂŒr Inputs und Outputs werden angelegt.
                        # NĂ€here Beschreibung siehe im ioBroker-Forum unter
                        # https://forum.iobroker.net/topic/32885/umfassendes-alarmanlagen-skript
                        # Änderungshistorie:
                        # 2020-05-01    Andreas Kos     Erstellt
                        # 2020-05-02    Andreas Kos     Schaltwunsch mit Number-Datenpunkt Input.SwitchNumber (Idee von @Homer.J.)
                        #                               Schaltstatus mit Number-Datenpunkt Output.ActiveNumber (Idee von @Homer.J.)
                        # 2020-05-03    Andreas Kos     Korrekturen, u.a. fĂŒr Melderauswertung (chage: "ne") & AlarmText
                        # 2020-05-04    Andreas Kos     - Melder werden aus den Functions (AufzĂ€hlungen, enums) dafĂŒr geholt. Auch beim Unscharf-
                        #                                 schalten, dadurch ist kein Neustarten des Skripts notwendig bei
                        #                                 Änderungen an diesen AufzĂ€hlungen.
                        #                               - Eine Schaltung von einem scharf-Zustand auf einen anderen
                        #                                 wird verhindert. ZB von scharf intern auf scharf extern.
                        #                                 Es muss immer unscharf dazwischen geschaltet werden.
                        # 2020-05-09    Andreas Kos     ZusĂ€tzliche Objekte mit JSON-Strings fĂŒr:
                        #                               - den auslösenden Melder
                        #                               - alle offenen Melder
                        #                               - alle offenen Melder der Außenhaut
                        #                               - alle offenen Melder des Innenraums
                        #                               Die JSON-String beinhalten das auslösende Objekt, sowie (falls vorhanden)
                        #                               das Parent und das ParentsParent-Objekt mit allen in ioBroker verfĂŒgbaren Eigenschaften.
                        #                               Kleinere Verbesserungen, z.B. bezĂŒglich setzen der AlarmTexte.
                        # 2020-05-12    Andreas Kos     Setzen des Datenpunkts idReady zur Bereitschaftsanzeige neu gemacht.
                        # 2021-06-13    Andreas Kos     Einbau der Funktion zum Ausnehmen einzelner Melder der AussenhĂŒlle
                        #                               von der Melder-Überwachung. Soll zum Kippen von Fenstern dienen u.Ă€.
                        ########################################################################################################################
                        */
                        
                        // EINBRUCHSMELDER
                        // Jeder Melder muss ein State sein, der bei Auslösung true liefert und in Ruhe (geschlossen) false.
                        // Die Melder sind in Arrays zusammengefasst, d.h. sie mĂŒssen jeweils mit Beistrich voneinander getrennt werden.
                        // Die Namen der Melder sollten gut gepflegt sein fĂŒr eine sinnvolle Verwendung (Attribut name bei den Objekten)
                        
                        // Melder der Außenhaut
                        // Dies können Öffnungskontakte sein von Fenster und TĂŒren in den Außenmauern des Objekts.
                        // EINGABE: In der AufzĂ€hlung "alarmanlage_aussenhaut" die States einfĂŒgen.
                        
                        // Melder des Innenraums
                        // Dies können Bewegungsmelder sein aus dem Inneren.
                        // EINGABE: In der AufzĂ€hlung "alarmanlage_innenraum" die States einfĂŒgen.
                        
                        // Verzögerte Melder
                        // Diese kommen in den Gruppen oben auch vor. Sie bewirken eine Aktivierung der Eingangsverzögerung
                        // bei scharf geschalteter Anlage und erlauben wÀhrend der Ausgangsverzögerung nach dem
                        // Scharfschalten das Haus zu verlassen.
                        // EINGABE: In der AufzĂ€hlung "alarmanlage_verzoegert" die States einfĂŒgen.
                        
                        
                        // EINSTELLUNGEN
                        const entryDelay =                30;         // Eingangsverzögerung in Sekunden (sollte maximal 60s sein)
                        const exitDelay =                 30;         // Ausgangsverzögerung in Sekunden (sollte maximal 60s sein)
                        const alarmDurationAccoustical =  180;         // Dauer des akkustischen Alarms in Sekunden (ACHTUNG: in Ö sind maximal 180s erlaubt!)
                        const alarmDurationOptical =      -1;         // Dauer des optischen Alarm in Sekunden, -1 fĂŒr unendlich
                        
                        // TEXTE FÜR SCHALTZUSTAND
                        // Diese Text geben Auskunft ĂŒber den Zustand der Anlage.
                        // Sie werden in den Datenpunkt "javascript.X.Output.StatusText" geschrieben.
                        const textStatusInactive =        "unscharf";
                        const textStatusActiveInternal =  "scharf intern";
                        const textStatusActiveExternal =  "scharf extern";
                        const textActiveExternalDelayed = "scharf extern verzögert";
                        const textEntryDelayActive =      "Eingangsverzögerung aktiv";
                        const textExitDelayActive =       "Ausgangsverzögerung aktiv";
                        
                        // TEXTE FÜR ALARMIERUNG UND FEHLER
                        // Diese Text geben im unscharfen Zustand der Anlage Auskunft ĂŒber die Bereitschaft
                        // zum Scharfschalten (nur möglich, wenn alle Melder geschlossen - in Ruhe - sind) und
                        // Fehler bei der Scharfschaltung bzw. bei scharfer Anlage ĂŒber den Zustand Frieden oder Alarm.
                        // Sie werden in den Datenpunkt "javascript.X.Output.AlarmText" geschrieben.
                        const textAlarmInactive =         "Alles OK";
                        const textAlarmActive =           "Alarm!!";
                        const textReady =                 "Bereit";
                        const textNotReady =              "Nicht bereit";
                        const textError =                 "Fehler bei der Scharfschaltung";
                        
                        // EXPERTEN-EINSTELLUNGEN
                        const pathToCreatedStates = "Alarmanlage";    // Beispiel: States werden erzeugt unter javascript.X.Alarmanlage
                        const seperator = ", ";                       // Trenn-String, der zwischen den Meldernamen verwendet wird, im Datenpunkt "OpenDetectors"
                        const loglevel = 2;                           // 0 bis 3. 0 ist AUS, 3 ist maximales Logging
                                                                    // Empfehlung fĂŒr Nachvollziehbarkeit aller Handlungen ist 2 (Ereignisliste)
                        const functionOuterSkin = "alarmanlage_aussenhaut";
                        const functionIndoor = "alarmanlage_innenraum";
                        const functionDelayedDetectors = "alarmanlage_verzoegert";
                        
                        /*
                           ###############################################################################
                                            DO NOT CHANGE ANYTHING BELOW THIS LINE
                                                 AB HIER NICHTS MEHR ÄNDERN
                           ###############################################################################
                        */
                        
                        // ===============================================================================
                        // Variablen
                        // ===============================================================================
                        
                        // Arrays fĂŒr die Melder
                        var detectorsOuterSkin = [];
                        var detectorsIndoor = [];
                        var detectorsDelayed = [];
                        
                        // Array fĂŒr die IgnoreOpen-Melder (beinhaltet nur Flags).
                        // Das Array ist inital deckungsgleich mit detectorsOuterSkin, da diese
                        // nur aus dieser Function kommen können.
                        // Dieses Array ist 2-Dimensional: [Melder-ID, IgnoreOpen-Zustands-ID]
                        var detectorsIgnoreOpen = [];
                        
                        // Javascript-Instanz mit der das Alarmanlagen-Skript ausgefĂŒhrt wird
                        var javascriptInstance = instance;
                        
                        // States, die erzeugt werden fĂŒr Status-Ausgaben
                        var idActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Active";
                        var idActiveExternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveExternal";
                        var idActiveInternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveInternal";
                        var idActiveNumber = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ActiveNumber";
                        var idAlarm = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Alarm";
                        var idAlarmAccoustical = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmAccoustical";
                        var idAlarmOptical = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmOptical";
                        var idReady = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Ready";
                        var idEntryDelayActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.EntryDelayActive";
                        var idExitDelayActive = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.ExitDelayActive";
                        var idAlarmingDetector = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmingDetector";
                        var idAlarmingDetectorJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmingDetectorJSON";
                        var idOpenDetectors = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectors";
                        var idOpenDetectorsJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsJSON";
                        var idOpenDetectorsOuterSkinJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsOuterSkinJSON";
                        var idOpenDetectorsIndoorJSON = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsIndoorJSON";
                        var idOpenDetectorsWithIgnoreOpenFlagSet = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.OpenDetectorsIgnoreOpen";
                        
                        var idStatusText = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.StatusText";
                        var idAlarmText = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.AlarmText";
                        var idError = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Output.Error";
                        
                        // States, die erzeugt werden fĂŒr Eingaben
                        var idSwitchExternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchExternal";
                        var idSwitchInternal = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchInternal";
                        var idSwitchExternalDelayed = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchExternalDelayed";
                        var idSwitchNumber = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.SwitchNumber";
                        
                        // Sonstige globale Variablen, die gebraucht werden
                        var timerExitDelay = null;
                        var timerTexts = null;
                        
                        // ===============================================================================
                        // Precode
                        // ===============================================================================
                        
                        // Logging
                        if (loglevel >= 1) log ("Alarmsystem started.");
                        
                        getAllDetectors();
                        
                        // States erzeugen
                        myCreateState(idActive, "boolean", false, "Switch Status Total", false, "info.status");
                        myCreateState(idActiveExternal, "boolean", false, "Switch Status External", false, "info.status");
                        myCreateState(idActiveInternal, "boolean", false, "Switch Status Internal", false, "info.status");
                        myCreateState(idAlarm, "boolean", false, "Alarm Status", false, "sensor.alarm");
                        myCreateState(idAlarmAccoustical, "boolean", false, "Accoustical Alarm Status", false, "sensor.alarm");
                        myCreateState(idAlarmOptical, "boolean", false, "Optical Alarm Status", false, "sensor.alarm");
                        myCreateState(idReady, "boolean", false, "Alarmsystem Ready", false, "info.status");
                        myCreateState(idError, "boolean", false, "Error Switching Active", false, "info.status");
                        myCreateState(idEntryDelayActive, "boolean", false, "Entry Delay Active Status", false, "info.status");
                        myCreateState(idExitDelayActive, "boolean", false, "Exit Delay Active Status", false, "info.status");
                        myCreateState(idAlarmingDetector, "string", "", "Alarming Detector", false, "text");
                        myCreateState(idAlarmingDetectorJSON, "string", "", "Alarming Detector JSON", false, "json");
                        myCreateState(idOpenDetectors, "string", "", "Open Detectors", false, "info.name");
                        myCreateState(idOpenDetectorsJSON, "string", "", "Open Detectors JSON", false, "json");
                        myCreateState(idOpenDetectorsOuterSkinJSON, "string", "", "Open Detectors Outer Skin JSON", false, "json");
                        myCreateState(idOpenDetectorsIndoorJSON, "string", "", "Open Detectors Indoor JSON", false, "json");
                        myCreateState(idOpenDetectorsWithIgnoreOpenFlagSet, "string", "", "Open Detectors with IgnoreOpen-Flag set", false, "text");
                        myCreateState(idStatusText, "string", "", "Status Text", false, "text");
                        myCreateState(idAlarmText, "string", "", "Alarm Text", false, "text");
                        myCreateState(idSwitchExternal, "boolean", false, "Enable Surveillance External", true, "switch");
                        myCreateState(idSwitchInternal, "boolean", false, "Enable Surveillance Internal", true, "switch");
                        myCreateState(idSwitchExternalDelayed, "boolean", false, "Enable Surveillance External Delayed", true, "switch");
                        
                        myCreateMultiState (idActiveNumber, "number", 0, "Switch Status Number", false, 0, 4,"0:"+textStatusInactive+"; 1:"+textStatusActiveInternal+"; 2:"+textStatusActiveExternal+"; 3:"+textExitDelayActive+"; 4:"+textEntryDelayActive);
                        myCreateMultiState (idSwitchNumber, "number", 0, "Switch by Number", true, 0, 3, "0:"+textStatusInactive+"; 1:"+textStatusActiveInternal+" ; 2:"+textStatusActiveExternal+" ; 3:"+textActiveExternalDelayed);
                        
                        // Erzeugen der Datenpunkte fĂŒr die IgnoreOpen-Einstellung
                        myCreateIgnoreOpenDPs();
                        
                        // Melder nach dem Starten checken
                        checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                        
                        // ===============================================================================
                        // ON-Subscribtions
                        // ===============================================================================
                        
                        // Auf Schaltstellen EXTERN verzögert reagieren (schalten EIN/AUS)
                        on ({id: idSwitchExternalDelayed, change: "any"}, function(obj){
                            if (loglevel >= 3) log ("Switching External Delayed, Value: " + getState(obj.id).val);
                            if (getState(obj.id).val) { // Einschalten, scharf extern VERZÖGERT
                                if (loglevel >= 2) log ("Switching required: Delayed External Active");
                                    if (getState(idActive).val) {
                                        if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                        setState(idError, true);
                                    } else {
                                        setState(idExitDelayActive, true);
                                        if (timerExitDelay) clearTimeout(timerExitDelay);
                                        timerExitDelay = setTimeout(switchActiveExternal, exitDelay * 1000);
                                    }
                            }
                            else { // Ausschalten, unscharf SOFORT
                                if (loglevel >= 2) log ("Switching required: Inactive");
                                switchInactive();
                            }
                        });
                        
                        // Auf Schaltstellen EXTERN sofort reagieren (schalten EIN/AUS)
                        on ({id: idSwitchExternal, change: "any"}, function(obj){
                            if (loglevel >= 3) log ("Switching External Immediately, Value: " + getState(obj.id).val);
                            if (getState(obj.id).val) { // Einschalten, scharf extern
                                if (loglevel >= 2) log ("Switching required: External Active");
                                if (getState(idActive).val) {
                                    if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                    setState(idError, true);
                                } else {
                                    switchActiveExternal();
                                }
                            }
                            else { // Ausschalten, unscharf
                                if (loglevel >= 2) log ("Switching required: Inactive");
                                switchInactive();
                            }
                        });
                        
                        // Auf Schaltstellen INTERN sofort reagieren (schalten EIN/AUS)
                        on ({id: idSwitchInternal, change: "any"}, function(obj){
                            if (loglevel >= 3) log ("Switching Internal, Value: " + getState(obj.id).val);
                            if (getState(obj.id).val) { // Einschalten, scharf intern
                                if (loglevel >= 2) log ("Switching required: Internal Active");
                                if (getState(idActive).val) {
                                    if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                    setState(idError, true);
                                } else {
                                    switchActiveInternal();
                                }
                            }
                            else { // Ausschalten, unscharf
                                switchInactive();
                                if (loglevel >= 2) log ("Switching required: Inactive");
                            }
                        });
                        
                        // Auf Schaltstelle mit Datenpunkt SwitchNumber reagieren
                        // Folgende Reaktionen:
                        //      0 ... unscharf schalten
                        //      1 ... scharf intern schalten
                        //      2 ... scharf extern schalten
                        //      3 ... verzögert scharf extern schalten
                        on ({id: idSwitchNumber, change: "any"}, function(obj){
                            if (loglevel >= 3) log ("Switching Number, Value: " + obj.state.val);
                            switch (obj.state.val) {
                                case 0:
                                    if (loglevel >= 2) log ("Switching required: Inactive");
                                    switchInactive();
                                    break;
                                case 1:
                                    if (loglevel >= 2) log ("Switching required: Internal Active");
                                    if (getState(idActive).val) {
                                        if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                        setState(idError, true);
                                    } else {
                                        switchActiveInternal();
                                    }
                                    break;
                                case 2:
                                    if (loglevel >= 2) log ("Switching required: External Active");
                                    if (getState(idActive).val) {
                                        if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                        setState(idError, true);
                                    } else {
                                        switchActiveExternal();
                                    }
                                    break;
                                case 3:
                                    if (loglevel >= 2) log ("Switching required: Delayed External Active");
                                    if (getState(idActive).val) {
                                        if (loglevel >= 3) log ("Alarmsystem already active, switch to inactive first!");
                                        setState(idError, true);
                                    } else {
                                        setState(idExitDelayActive, true);
                                        if (timerExitDelay) clearTimeout(timerExitDelay);
                                        timerExitDelay = setTimeout(switchActiveExternal, exitDelay * 1000);
                                    }
                                    break;
                                default:
                                    if (loglevel >= 3) log ("idSwitchNumber has unknown number!");
                            }
                        });
                        
                        // Auf Fehler bei der Scharfschaltung reagieren
                        on ({id: idError, val: true, change: "any"}, function(obj){
                            if (loglevel >= 1) log ("Error when switching to active.");
                            setState(idAlarmText, textError);
                        });
                        
                        // Auf Eingangsverzögerung reagieren
                        on({id: idEntryDelayActive, val: true, change: "ne"}, function (obj) {
                            if (loglevel >= 2) log ("Entry Delay is active (" + entryDelay + " seconds)");
                            setState(idStatusText, textEntryDelayActive);
                            setStateDelayed(idAlarmAccoustical, true, entryDelay * 1000);
                            setStateDelayed(idAlarmOptical, true, entryDelay * 1000);
                        });
                        
                        // Auf Ausgangsverzögerung reagieren
                        on({id: idExitDelayActive, val: true, change: "ne"}, function (obj) {
                            if (loglevel >= 2) log ("Exit Delay is active (" + exitDelay + " seconds)");
                            setState(idStatusText, textExitDelayActive);
                        });
                        
                        // Auf Akustischen Alarm reagieren
                        on ({id: idAlarmAccoustical, val: true, change: "ne"}, function(obj){
                            if (loglevel >= 1) log ("ALARM is active!");
                            setState(idEntryDelayActive, false);
                            setState(idAlarmText, textAlarmActive);
                            setState(idAlarm, true);
                            setStateDelayed(idAlarmAccoustical, false, alarmDurationAccoustical * 1000);
                            if (getState(idActiveExternal).val) setState(idStatusText, textStatusActiveExternal);
                            if (getState(idActiveInternal).val) setState(idStatusText, textStatusActiveInternal);
                        });
                        
                        // Auf Optischen Alarm reagieren
                        on ({id: idAlarmOptical, val: true, change: "ne"}, function(obj){
                            if (alarmDurationOptical >= 0)
                                setStateDelayed(idAlarmOptical, false, alarmDurationOptical * 1000);
                        });
                        
                        // Melderauswertung
                        on( {id: detectorsOuterSkin.concat(detectorsIndoor), change: "ne"}, function(obj){
                            detectorSurveillance(obj);
                        });
                        
                        // Status in Active.Number schreiben
                        on ({id: [idActiveInternal, idActiveExternal, idEntryDelayActive, idExitDelayActive], change: "ne"}, function(obj){
                            if (loglevel >= 3) log ("on for writing ActiveNumber, Trigger: " + obj.id);
                            setActiveNumber();
                        });
                        
                        // Texte korrekt setzen
                        on ({id: [idAlarm, idActive, idOpenDetectors], change: "any"}, function (obj) {
                            // Das Timeout ggf. abbrechen
                            if (timerTexts) clearTimeout(timerTexts);  
                            // Nach einem Timeout den Check anfangen
                            timerTexts = setTimeout(setTexts, 200);
                        });
                        
                        
                        
                        // ===============================================================================
                        // Funktionen
                        // ===============================================================================
                        // Funktion     checkIfIgnoreOpenFlagSet
                        // =====================================
                        // Parameter:       PrĂŒft, ob das IgnoreOpen-Flag fĂŒr einen Melder gesetzt ist.
                        // Übergabewert:    Melder-ID
                        // RĂŒckgabewert:    Flag-Zustand
                        function checkIfIgnoreOpenFlagSet(id){
                            var i=0;
                            while (i<detectorsIgnoreOpen.length){
                                if ( detectorsIgnoreOpen[i][0] == id )
                                    if (getState(detectorsIgnoreOpen[i][1]).val)
                                        return true;
                                i++;
                            }
                            return false;
                        }
                        
                        // Function setTexts
                        // =================
                        // Parameter:       keiner
                        // Funktion:        AbhÀngig von den ZustÀnden scharf/unscharf und
                        //                  Alarm / Kein Alarm werden Texte fĂŒr
                        //                  den AlarmText richtig gesetzt. Auch der Datenpunkt idReady wird hier gesetzt.
                        // RĂŒckgabewert:    keiner
                        function setTexts(){    
                            var textListOfDetectors = getState(idOpenDetectors).val;
                            if (textListOfDetectors.length > 0) {
                                if (!getState(idActive).val)
                                    // Offene Melder gefunden und unscharf
                                    setState(idAlarmText, textNotReady);
                                    setState(idReady, false);
                                return false;
                            } else {
                                if (getState(idActive).val && !getState(idAlarm).val)
                                    // kein offener Melder gefunden und scharf und kein Alarm
                                    setState(idAlarmText, textAlarmInactive);
                                else if (!getState(idActive).val)
                                    // kein offener Melder gefunden und unscharf
                                    setState(idAlarmText, textReady);
                                    setState(idReady, true);
                                return true;
                            }
                        }
                        
                        // Function getAllDetectors
                        // ========================
                        // Parameter:       keiner
                        // Funktion:        Über die Funktion getDetectorsFromFunction werden
                        //                  alle Melder von den Functions geholt und in die
                        //                  globalen Variablen dafĂŒr geschrieben.
                        // RĂŒckgabewert:    keiner
                        function getAllDetectors(){
                            var i=0;
                            detectorsOuterSkin = getDetectorsFromFunction(functionOuterSkin);
                            detectorsIgnoreOpen = [];
                            while (i<detectorsOuterSkin.length) {
                                detectorsIgnoreOpen.push([detectorsOuterSkin[i++]]);
                            }
                            detectorsIndoor = getDetectorsFromFunction(functionIndoor);
                            detectorsDelayed = getDetectorsFromFunction(functionDelayedDetectors);
                        }
                        
                        // Function getDetectorsFromFunction
                        // =================================
                        // Parameter:       functionString
                        //                  Name der Function, in der die Melder enthalen sind.
                        // Funktion:        Alle Teilnehmer der ĂŒbergebenen Function werden
                        //                  in ein Array geschrieben.
                        // RĂŒckgabewert:    Array der Melder-IDs
                        function getDetectorsFromFunction( functionString ) {
                            if (loglevel >= 3) log ("Function getDetectorsFromFunction");
                            var detectors = [];
                            $('state(functions='+functionString+')').each(function(id, i) {
                                detectors.push(id);
                                if (loglevel >= 3) log ("This detector was added to surveillance from function "+functionString+": " + id);
                            });
                            return detectors;
                        }
                        
                        // Function detectorSurveillance
                        // =============================
                        // Parameter:       obj
                        //                  Objekt des auslösenden Melders
                        // Funktion:        AbhĂ€ngig vom Schaltzustand werden die Melder ĂŒberprĂŒft.
                        //                  Bei unscharf wird nur die Liste der offenen Melder und die
                        //                  Bereitschaft der Anlage zum Scharfschalten gepfelgt.
                        //                  Bei scharf geschalteter Anlage ist es anders:
                        //                  Es wird geprĂŒft, ob der auslösende Melder in den Außenhaut- oder
                        //                  Innenraum-Meldern enthalten ist und ob dieser ein verzögerter Melder ist.
                        //                  AbhÀngig davon wird entweder sofort oder verzögert Alarm ausgelöst.
                        // RĂŒckgabewert:    keiner
                        function detectorSurveillance (obj) {
                            var active = getState(idActive).val;
                            var activeExternal = getState(idActiveExternal).val;
                            var activeInternal = getState(idActiveInternal).val;
                            var ready;
                            var ignoreOpenSet;
                            
                            if (loglevel >= 2) log ("Surveillance of detectors started, triggering detector: " + obj.common.name);
                        
                            // Alle offenen Melder feststellen
                            ready = checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                        
                            // Auslösenden Melder schreiben
                            setState(idAlarmingDetector, obj.common.name);
                            setState(idAlarmingDetectorJSON, JSON.stringify(  getDetectorObject(obj.id)  ));
                        
                            // PrĂŒfen, wie der der Schaltzustand ist
                            // bei unscharf
                            if (!active) {
                                if (loglevel >= 2) log ("Alarmsystem is Inactive");
                            }
                            // bei scharf intern
                            if (activeInternal) {
                                if (loglevel >= 2) log ("Alarmsystem is Internal Active");
                                if (detectorsOuterSkin.indexOf(obj.id) != -1) {
                                    if (loglevel >= 3) log ("Detector is part of Outer Skin");
                                    if (detectorsDelayed.indexOf(obj.id) != -1) {
                                        if (loglevel >= 3) log ("Detector is part of Delayed Detectors");
                                        if(!getState(idAlarm).val) setState(idEntryDelayActive, true);
                                        else {
                                            if (loglevel >= 3) log ("EntryDelay was already active, alarming now");
                                            setState(idAlarmAccoustical, true);
                                            setState(idAlarmOptical, true);
                                        }
                                    } else {
                                        if (loglevel >= 3) log ("Detector is not delayed");
                                        setState(idAlarmAccoustical, true);
                                        setState(idAlarmOptical, true);
                                    }
                                }
                            }
                            // bei scharf extern
                            if (activeExternal) {
                                if (loglevel >= 2) log ("Alarmsystem is External Active");
                                // PrĂŒfen, ob er der Melder das IgnoreOpen-Flag gesetzt hat.
                                ignoreOpenSet = checkIfIgnoreOpenFlagSet(obj.id);
                                if (loglevel >= 2) log ("Detector has IgnoreOpen-Flag set true!");
                                if (ignoreOpenSet)  return;
                                if (detectorsOuterSkin.concat(detectorsIndoor).indexOf(obj.id) != -1) {
                                    if (loglevel >= 3) log ("Detector is part of Outer Skin or Indoor");
                                    if (detectorsDelayed.indexOf(obj.id) != -1) {
                                        if (loglevel >= 3) log ("Detector is part of Delayed Detectors");
                                        if(!getState(idAlarm).val) setState(idEntryDelayActive, true);
                                        else {
                                            if (loglevel >= 3) log ("EntryDelay was already active, alarming now");
                                            setState(idAlarmAccoustical, true);
                                            setState(idAlarmOptical, true);
                                        }
                                    } else {
                                        if (loglevel >= 3) log ("Detector is not delayed");
                                        if (loglevel >= 2) log ("System is ALARMING now!");
                                        setState(idAlarmAccoustical, true);
                                        setState(idAlarmOptical, true);
                                    }
                                }
                            }
                        }
                        
                        // Function myCreateState
                        // =======================
                        // Parameter:       id      ... id des neu anzulegenden Datenpunkts
                        //                  typ     ... typ des anzulegenden Datenpunkts ("boolean", "string", "number", etc.)
                        //                  val     ... Wert, den der Datenpunkt nach dem Anlegen haben soll
                        //                  descr   ... Name als String
                        //                  writeaccess Schreibrechte true oder false
                        // Funktion:        Mit der Funktion createState wird der neue Datenpunkt mit den ĂŒbergebenen
                        //                  Parametern angelegt.
                        // RĂŒckgabewert:    keiner
                        function myCreateState(id, typ, val, descr, writeaccess, role) {
                            if (loglevel >= 3) log ("Function myCreateState for " + id);
                            createState(id, val,    {read: !writeaccess, 
                                                    write: writeaccess, 
                                                    name: descr,
                                                    type: typ,
                                                    def: val,
                                                    role: role ? role : "state"
                            });
                        }
                        
                        // Function myCreateMultiState
                        // ===========================
                        // Parameter:       id      ... id des neu anzulegenden Datenpunkts
                        //                  typ     ... typ des anzulegenden Datenpunkts ("boolean", "string", "number", etc.)
                        //                  val     ... Wert, den der Datenpunkt nach dem Anlegen haben soll
                        //                  descr   ... Name als String
                        //                  min     ... Minimalwert
                        //                  max     ... Maximalwert
                        //                  list    ... Liste mit Werten und Bezeichnern im Format "0:Text0; 1:Text1; 2:Text2"
                        //                  writeaccess Schreibrechte true oder false
                        // Funktion:        Mit der Funktion createState wird der neue Datenpunkt mit den ĂŒbergebenen
                        //                  Parametern angelegt.
                        // RĂŒckgabewert:    keiner
                        function myCreateMultiState(id, typ, val, descr, writeaccess, minimum, maximum, list, role) {
                            if (loglevel >= 3) log ("Function myCreateMultiState for " + id);
                            createState(id, val, {  read: true, 
                                                    write: writeaccess, 
                                                    name: descr,
                                                    type: typ,
                                                    def: val,
                                                    min: minimum, 
                                                    max: maximum, 
                                                    states: list,
                                                    role: role ? role : "state"
                            });
                        }
                        // Funktion myCreateIgnoreOpenDPs
                        // ==============================
                        // Parameter:       Keine
                        // Funktion:        Erzeugt die Datenpunkte fĂŒr die Ignoge-Open-Melder.
                        //                  DafĂŒr werden die Namen aus dem detectorsOuterSkin-Array geholt.
                        //                  Die IDs der Ignore-Open Datenpunkte fĂŒr jeden Melder werden auch in
                        //                  das Array detectorsIgnoreOpen geschrieben. Dieses wird damit 3-Dimensional.
                        // RĂŒckgabewert:    Keiner.
                        function myCreateIgnoreOpenDPs(){
                            var detectorName;
                            var idBase = "javascript." + javascriptInstance + "." + pathToCreatedStates + ".Input.IgnoreOpen.";
                            var i=0;
                            while (i<detectorsOuterSkin.length) {
                                detectorName = getObject(detectorsOuterSkin[i]).common.name.replace(/\./g,"_");
                                myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                                detectorsIgnoreOpen[i].push(idBase + detectorName);
                                i++;
                            }
                        }
                        
                        // Function switchActiveExternal
                        // =============================
                        // Parameter:       keiner
                        // Funktion:        Nach PrĂŒfung auf Bereitschaft zum externen Scharfschalten, wird 
                        //                  scharf geschaltet oder ein Fehler angezeigt.
                        // RĂŒckgabewert:    keiner
                        function switchActiveExternal () {
                            if (loglevel >= 3) log ("Function switchActiveExternal");
                            setState(idExitDelayActive, false);
                            var ok = checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                            if (ok) {
                                setState(idActiveExternal, true);
                                setState(idActive, true);
                                setState(idStatusText, textStatusActiveExternal);
                                setState(idAlarmText, textAlarmInactive);
                                setState(idAlarmingDetector,"");
                                setState(idError, false);
                                if (loglevel >= 2) log ("Switched to External Active");
                            } else {
                                if (loglevel >= 2) log ("NOT ready to switch to External Active!");
                                setState(idError, true);
                            }
                        }
                        
                        // Function switchActiveInternal
                        // =============================
                        // Parameter:       keiner
                        // Funktion:        Nach PrĂŒfung auf Bereitschaft zum internen Scharfschalten, wird 
                        //                  scharf geschaltet oder ein Fehler angezeigt.
                        // RĂŒckgabewert:    keiner
                        function switchActiveInternal () {
                            if (loglevel >= 3) log ("Function switchActiveInternal");
                            var ok = checkDetectors(detectorsOuterSkin);
                            if (ok) {
                                setState(idActiveInternal, true);
                                setState(idActive, true);
                                setState(idStatusText, textStatusActiveInternal);
                                setState(idAlarmText, textAlarmInactive);
                                setState(idAlarmingDetector,"");
                                setState(idError, false);
                                if (loglevel >= 2) log ("Switched to Internal Active");
                            } else {
                                if (loglevel >= 2) log ("NOT ready to switch to Internal Active!");
                                setState(idError, true);
                            }
                        ;}
                        
                        // Function switchInactive
                        // =============================
                        // Parameter:       keiner
                        // Funktion:        Es wird unscharf geschaltet und die ganze Anlage resetiert.
                        // RĂŒckgabewert:    keiner
                        function switchInactive () {
                            if (loglevel >= 3) log ("Function switchInactive");
                            if (timerExitDelay) clearTimeout(timerExitDelay);
                            setState(idEntryDelayActive, false);
                            setState(idExitDelayActive, false);
                            setState(idActiveExternal, false);
                            setState(idActiveInternal, false);
                            setState(idActive, false);
                            setState(idError, false);
                            clearStateDelayed(idAlarmAccoustical);
                            clearStateDelayed(idAlarmOptical);
                            setState(idAlarmAccoustical, false);
                            setState(idAlarmOptical, false);
                            setState(idAlarm, false);
                            setState(idAlarmText, textAlarmInactive);
                            setState(idStatusText, textStatusInactive);
                            checkDetectors(detectorsOuterSkin.concat(detectorsIndoor));
                            if (loglevel >= 2) log ("Switched to Inactive");
                            getAllDetectors();
                        }
                        
                        // Function setActiveNumber
                        // =======================
                        // Parameter:       keine
                        // Funktion:        PrĂŒft ob intern scharf, extern scharf oder unscharf ist und
                        //                  ob jeweils Eingangs- oder Ausgangsverzögerung aktiv ist.
                        //                  AbhÀngig davon wird der Datenpunt "Output.ActiveNumber"
                        //                  wie folgt gesetzt:
                        //                    0 ... unscharf
                        //                    1 ... intern scharf
                        //                    2 ... extern scharf
                        //                    3 ... Eingangsverzögerung aktiv
                        //                    4 ... Ausgangsverzögerung aktiv
                        // RĂŒckgabewert:    keiner
                        function setActiveNumber () {
                            if (loglevel >= 3) log ("Function setActiveNumber");
                            var internal = getState(idActiveInternal).val;
                            var external = getState(idActiveExternal).val;
                            var entry = getState(idEntryDelayActive).val;
                            var exit = getState(idExitDelayActive).val;
                            if (!external && !internal) {
                                if (exit)
                                    setState(idActiveNumber, 4);
                                else
                                    setState(idActiveNumber, 0);
                            }
                            if (internal) setState(idActiveNumber, 1);
                            if (external){
                                if (entry)
                                    setState(idActiveNumber, 3);
                                else
                                    setState(idActiveNumber, 2);
                            }
                        }
                        
                        // Function checkDetectors
                        // =======================
                        // Parameter:       detectors
                        //                  Array mit Melder-IDs
                        // Funktion:        Alle Melder aus dem Array werden geprĂŒft und alle offenen
                        //                  Melder werden in einen Datenpunkt geschrieben als String.
                        //                  Das Trennzeichen zwischen den Meldernamen ist die globale
                        //                  Variable "seperator".
                        // RĂŒckgabewert:    true, wenn alle Melder in Ruhe sind
                        //                  false, wenn ein oder mehr Melder ausgelöst sind
                        function checkDetectors ( detectors ) {
                            if (loglevel >= 3) log ("Function checkDetectors");
                            var i=0;
                            var textListOfDetectors="";
                            var textListOfDetectorsIgnoreOpen="";
                            var objOpenDetectors = {
                                title: "All open detectors",
                                zone: null,
                                listOfDetectors:    []
                            };
                            var objOpenDetectorsOuterSkin = {
                                title: "Open detectors outer skin",
                                zone: functionOuterSkin,
                                listOfDetectors:    []
                            };
                            var objOpenDetectorsIndoor = {
                                title: "Open detectors indoor",
                                zone: functionIndoor,
                                listOfDetectors:    []
                            };
                            while(i < detectors.length) {
                                if (getState(detectors[i]).val) {
                                    if (checkIfIgnoreOpenFlagSet(detectors[i])) {
                                        if (textListOfDetectorsIgnoreOpen.length > 0) textListOfDetectorsIgnoreOpen += seperator;
                                        textListOfDetectorsIgnoreOpen += getObject(detectors[i]).common.name;
                                    }
                                    else {
                                        if (textListOfDetectors.length > 0) textListOfDetectors += seperator;
                                        textListOfDetectors += getObject(detectors[i]).common.name;
                                    }
                                    var detObj = getDetectorObject(detectors[i]);
                                    objOpenDetectors.listOfDetectors.push(detObj);
                                    if (detectorsOuterSkin.indexOf(detectors[i]) != -1) objOpenDetectorsOuterSkin.listOfDetectors.push(detObj);
                                    if (detectorsIndoor.indexOf(detectors[i]) != -1) objOpenDetectorsIndoor.listOfDetectors.push(detObj);
                                }
                                i++;
                            }
                            if (loglevel >= 3) log ("Open Detectors found: " + (textListOfDetectors.length ? textListOfDetectors : "none"));
                            
                            // Datenpunkte schreiben
                            setState(idOpenDetectors, textListOfDetectors);
                            setState(idOpenDetectorsWithIgnoreOpenFlagSet, textListOfDetectorsIgnoreOpen);
                            setState(idOpenDetectorsJSON, JSON.stringify(objOpenDetectors));
                            setState(idOpenDetectorsOuterSkinJSON, JSON.stringify(objOpenDetectorsOuterSkin));
                            setState(idOpenDetectorsIndoorJSON, JSON.stringify(objOpenDetectorsIndoor));
                        
                            if (textListOfDetectors.length > 0) {
                                return false;
                            } else {
                                return true;
                            }
                        }
                        
                        // Function getDetectorObject
                        // ==========================
                        // Parameter:       id
                        //                  id eines Melder-States
                        // Funktion:        Vom Melder mit der id wird das Objekt ĂŒber getObjekt(id) geholt,
                        //                  sowie von seinem Parent und ParentsParent.
                        //                  Alle Objekte kommen in ein großes Objekt und werden zurĂŒck gegeben.
                        // RĂŒckgabewert:    Das Objekt des Melders samt Parent und ParentsParent (sofern es welche gibt)
                        function getDetectorObject (id) {
                            if (loglevel >= 3) log ("Function getDetectorObject for id: " + id);
                            // ioBroker Parent-Datenpunkt (z.B. Kanal), kann auch null sein (zB bei KNX)
                            var idParent = id.substr(0, id.lastIndexOf("."));
                            // ioBroker ParentsParent-Datenpunkt (z.B. GerÀt), kann auch null sein (zB bei KNX)
                            var idParentsParent = idParent.substr(0, idParent.lastIndexOf("."));
                        
                            // Objekte dazu holen
                            var obj    = getObject(id);
                            var objParent = getObject(idParent);
                            var objParentsParent = getObject(idParentsParent);
                        
                            // Alle Objekte in ein großes Objekt sammeln
                            var detectorsObj = {
                                id:             id,
                                self:           obj,
                                parent:         objParent,
                                parentsparent:  objParentsParent
                            };
                        
                            // RĂŒckgeben
                            return detectorsObj;
                        }
                        
                        
                        

                        Ich hoffe, es funktioniert einigermaßen. Bitte mal testen.
                        Danke und LG
                        Andreas

                        SchmakusS Offline
                        SchmakusS Offline
                        Schmakus
                        Developer
                        schrieb am zuletzt editiert von
                        #106

                        @andreaskos wird getestet! Danke fĂŒr die Umsetzung

                        Dev of LightControl Adapter, Contributor of HUE and DoorBird Adapter

                        SchmakusS 1 Antwort Letzte Antwort
                        0
                        • SchmakusS Schmakus

                          @andreaskos wird getestet! Danke fĂŒr die Umsetzung

                          SchmakusS Offline
                          SchmakusS Offline
                          Schmakus
                          Developer
                          schrieb am zuletzt editiert von Schmakus
                          #107

                          @andreaskos: Die States "IgnoreOpen" werden alle mit "Write=false" erstellt. Sollte dies nicht "true" sein?

                          myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                          

                          Habe es mal selbst geÀndert.

                          Dev of LightControl Adapter, Contributor of HUE and DoorBird Adapter

                          andreaskosA 1 Antwort Letzte Antwort
                          0
                          • SchmakusS Schmakus

                            @andreaskos: Die States "IgnoreOpen" werden alle mit "Write=false" erstellt. Sollte dies nicht "true" sein?

                            myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                            

                            Habe es mal selbst geÀndert.

                            andreaskosA Offline
                            andreaskosA Offline
                            andreaskos
                            schrieb am zuletzt editiert von andreaskos
                            #108

                            Hi @schmakus

                            nein, mit false passt eh, denn grundsÀtzlich soll ja keiner ignoriert werden.

                            Der Fehler lag oben in meinem Post.
                            true bedeutet, dass es ignoriert wird.

                            Ah - sorry - zu schnell gelesen.
                            Hast absolut recht Danke!

                            1 Antwort Letzte Antwort
                            0
                            • F Offline
                              F Offline
                              Freaknet
                              schrieb am zuletzt editiert von
                              #109

                              @andreaskos und @Schmakus

                              Erstmal Danke fĂŒr die Überarbeitung und die Umsetzung unserer WĂŒnsche :-)
                              Find das Klasse und werde das Script gerne mal austesten die Tage :sunglasses:

                              Bin jetzt leider nur etwas verwirrt mit der von @Schmakus geposteten Zeile:

                              myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                              

                              Passt die so wie Sie da steht oder muss ich das "false" in "true" vorher noch Àndern?
                              Also quasi dann so:

                              myCreateState(idBase + detectorName, "boolean", true, "Ignore Open for " + detectorName, true, "switch");
                              

                              Im Original Script oben steht das ja noch mit "false" drin. Oder ist das Script nochmal angepasst worden @andreaskos?

                              Danke fĂŒrÂŽs kurze Feedback damit ich loslegen kann :+1:

                              Gruß Freaknet

                              andreaskosA 1 Antwort Letzte Antwort
                              0
                              • F Freaknet

                                @andreaskos und @Schmakus

                                Erstmal Danke fĂŒr die Überarbeitung und die Umsetzung unserer WĂŒnsche :-)
                                Find das Klasse und werde das Script gerne mal austesten die Tage :sunglasses:

                                Bin jetzt leider nur etwas verwirrt mit der von @Schmakus geposteten Zeile:

                                myCreateState(idBase + detectorName, "boolean", false, "Ignore Open for " + detectorName, false, "switch");
                                

                                Passt die so wie Sie da steht oder muss ich das "false" in "true" vorher noch Àndern?
                                Also quasi dann so:

                                myCreateState(idBase + detectorName, "boolean", true, "Ignore Open for " + detectorName, true, "switch");
                                

                                Im Original Script oben steht das ja noch mit "false" drin. Oder ist das Script nochmal angepasst worden @andreaskos?

                                Danke fĂŒrÂŽs kurze Feedback damit ich loslegen kann :+1:

                                Gruß Freaknet

                                andreaskosA Offline
                                andreaskosA Offline
                                andreaskos
                                schrieb am zuletzt editiert von
                                #110

                                @freaknet said in Umfassendes Alarmanlagen-Skript:

                                , false,

                                Ich hab noch nichts geĂ€ndert oder upgedatet seit meiner Überarbeitung des Skripts.
                                Du brauchst nur das zweite, hintere false zu einem true machen, dieses steht fĂŒr den Write-Access. Das erste, linke kannst du lassen. Das steht fĂŒr den Default-Wert nach dem ersten Anlegen des Datenpunktes und da passt false grundsĂ€tzlich eh.

                                LG
                                Andreas

                                F 1 Antwort Letzte Antwort
                                1
                                • andreaskosA andreaskos

                                  @freaknet said in Umfassendes Alarmanlagen-Skript:

                                  , false,

                                  Ich hab noch nichts geĂ€ndert oder upgedatet seit meiner Überarbeitung des Skripts.
                                  Du brauchst nur das zweite, hintere false zu einem true machen, dieses steht fĂŒr den Write-Access. Das erste, linke kannst du lassen. Das steht fĂŒr den Default-Wert nach dem ersten Anlegen des Datenpunktes und da passt false grundsĂ€tzlich eh.

                                  LG
                                  Andreas

                                  F Offline
                                  F Offline
                                  Freaknet
                                  schrieb am zuletzt editiert von
                                  #111

                                  @andreaskos

                                  Supi, hatte ich gesehen, dass wenn ich beide auf "true" stelle die Datenpunkte direkt alle beim anlegen auf true angelegt wurden. Hab das dann bereits wieder geĂ€ndert gehabt, bin dann auch ĂŒber die Schreibrechte recht schnell dahintergekommen. War am Anfang etwas verwirrt :blush:

                                  Bisher scheint das Script genau das zu tun was es soll :-)
                                  Jetzt braucht meine Frau Nachts wenn Sie ein Fenster aufmacht bzw. kippt in bestimmten RÀumen keine Angst mehr haben dass Sie versehentlich den Alarm auslöst bzw. kann ich Fenster gekippt lassen falls wir mal unterwegs sind.

                                  Hab nochmal vielen Dank fĂŒr die Umsetzung und falls ich noch was entdecke was "noch" nicht klappt meld ich mich.

                                  Schönen und angenehmen Start in die neue Woche!

                                  Freaknet

                                  andreaskosA 1 Antwort Letzte Antwort
                                  0
                                  • F Freaknet

                                    @andreaskos

                                    Supi, hatte ich gesehen, dass wenn ich beide auf "true" stelle die Datenpunkte direkt alle beim anlegen auf true angelegt wurden. Hab das dann bereits wieder geĂ€ndert gehabt, bin dann auch ĂŒber die Schreibrechte recht schnell dahintergekommen. War am Anfang etwas verwirrt :blush:

                                    Bisher scheint das Script genau das zu tun was es soll :-)
                                    Jetzt braucht meine Frau Nachts wenn Sie ein Fenster aufmacht bzw. kippt in bestimmten RÀumen keine Angst mehr haben dass Sie versehentlich den Alarm auslöst bzw. kann ich Fenster gekippt lassen falls wir mal unterwegs sind.

                                    Hab nochmal vielen Dank fĂŒr die Umsetzung und falls ich noch was entdecke was "noch" nicht klappt meld ich mich.

                                    Schönen und angenehmen Start in die neue Woche!

                                    Freaknet

                                    andreaskosA Offline
                                    andreaskosA Offline
                                    andreaskos
                                    schrieb am zuletzt editiert von
                                    #112

                                    @freaknet
                                    Cool, vielen Dank fĂŒr's Testen! :-)

                                    @Schmakus
                                    Kannst du zufÀllig auch schon ein Feedback geben?

                                    LG
                                    Andreas

                                    andreaskosA H 2 Antworten Letzte Antwort
                                    0
                                    • andreaskosA andreaskos

                                      @freaknet
                                      Cool, vielen Dank fĂŒr's Testen! :-)

                                      @Schmakus
                                      Kannst du zufÀllig auch schon ein Feedback geben?

                                      LG
                                      Andreas

                                      andreaskosA Offline
                                      andreaskosA Offline
                                      andreaskos
                                      schrieb am zuletzt editiert von
                                      #113

                                      Hi zusammen,
                                      wenn also nichts dagegen spricht, dann aktualisiere ich wieder den ersten Post oben mit der aktuellen Version mit der eingearbeiteten Änderung fĂŒr die Ausnahmen.
                                      Ja? Noch irgendein Feedback?

                                      1 Antwort Letzte Antwort
                                      0
                                      • J Offline
                                        J Offline
                                        juggi1962
                                        schrieb am zuletzt editiert von
                                        #114

                                        Hallo an @kosy oder allen Anderen die hier so tolle Arbeit leisten.
                                        Bin neu hier und versuche mich gerade an dem tollen Alarmanlagen Skript.
                                        Dazu hÀtte ich zu der letzten Aktualisierung (IgnoreOpen) eine Frage.
                                        Wie kann man die Sensoren die jetzt in IgnoreOpen drinn stehen aber mit false auf truhe Ă€ndern um sie von der Alarmanlage auszuschließen wenn sie das Fenster offen ist.
                                        Wenn ich zb. auf false klick tut sich gar nichts, kann man das nicht da Àndern?
                                        Sorry wenn meine Frage komisch kling, aber ich bin noch gaaaanz am Anfang.
                                        Sonst lÀuft eh alles.
                                        Bitte um Hilfe Gruß aus Tirol.

                                        andreaskosA 1 Antwort Letzte Antwort
                                        0
                                        • andreaskosA andreaskos

                                          @freaknet
                                          Cool, vielen Dank fĂŒr's Testen! :-)

                                          @Schmakus
                                          Kannst du zufÀllig auch schon ein Feedback geben?

                                          LG
                                          Andreas

                                          H Offline
                                          H Offline
                                          Holger_B76
                                          schrieb am zuletzt editiert von Holger_B76
                                          #115

                                          Funktioniert

                                          andreaskosA 1 Antwort Letzte Antwort
                                          1
                                          Antworten
                                          • In einem neuen Thema antworten
                                          Anmelden zum Antworten
                                          • Älteste zuerst
                                          • Neuste zuerst
                                          • Meiste Stimmen


                                          Support us

                                          ioBroker
                                          Community Adapters
                                          Donate

                                          744

                                          Online

                                          32.5k

                                          Benutzer

                                          81.6k

                                          Themen

                                          1.3m

                                          BeitrÀge
                                          Community
                                          Impressum | Datenschutz-Bestimmungen | Nutzungsbedingungen | Einwilligungseinstellungen
                                          ioBroker Community 2014-2025
                                          logo
                                          • Anmelden

                                          • Du hast noch kein Konto? Registrieren

                                          • Anmelden oder registrieren, um zu suchen
                                          • Erster Beitrag
                                            Letzter Beitrag
                                          0
                                          • Home
                                          • Aktuell
                                          • Tags
                                          • Ungelesen 0
                                          • Kategorien
                                          • Unreplied
                                          • Beliebt
                                          • GitHub
                                          • Docu
                                          • Hilfe