Problem with stopping setTimeout

Hello,

I’m trying to run first Javascript rules with my OpenHab. I am running version 2.5.

Below are my two rules used for controlling lighting by presence detectors. I already know how to turn light on/off with presence detector but I am struggling with script which will turn the light OFF only when presence in the room will be OFF for “X” minutes. I have created setTimeout function and it turns light OFF with delay but I do not know how to exit this setTimeout function when the presence will again change to ON while counting already started.

Below is my script, any hints for beginner?

(Java.type(“java.lang.System”).getenv(“OPENHAB_CONF”)+’/automation/lib/javascript/core/rules.js’);

var me = “HTTPRequestExamples.js”;
logInfo("################# “+me+” ##################");

JSRule({
name: “F_LgtPscJadalnia_ON”,
description: “LgtTurnOn”,
triggers: [
ItemStateChangeTrigger(“PscJadalnia”, “OFF”, “ON”, “ZmianaStanu”)

],
execute: function(){
  
  var LGT = getItem("Lgt_TV")

    sendCommand(LGT, "ON");
    }
}

);

JSRule({
name: “F_LgtPscJadalnia_OFF”,
description: “Testowa funkcja sterowania oświetleniem”,
triggers: [
ItemStateChangeTrigger(“PscJadalnia”, “ON”, “OFF”, “ZmianaStanu”)

],

execute: function( module, input){

  var LGT = getItem("Lgt_TV")
  var PSC = getItem("PscJadalnia")
  
  
  logInfo( "Oświetlenie wyłączy się za 5 sekund");
  var t = setTimeout(function(){
  	sendCommand(LGT, "OFF");
  	if (PSC == "ON") function (){
  		clearTimeout(t);
  	}
  }, 5000);

}

});

Use Jython?! :stuck_out_tongue_winking_eye:

I would use core.actions.js to import ScriptExecution, and then use ScriptExecution.createTimer. You may want to look at the JS Timer example. As a basic rule, whenever possible, use Java or OH classes, interfaces and methods rather than what is available natively in your preferred scripting language.

1 Like

Hi Robert,

it’s from my mobil and I hope it’s not to much typos.
This should solve your task.

JSRule({
name: “F_LgtPscJadalnia_ON/OFF”,
description: “LgtTurnOnAndOff”,
triggers: [
  ItemStateChangeTrigger(“PscJadalnia”)
], 
execute: function( module, input){
  var LGT = getItem("Lgt_TV");
  var PSC = getItem("PscJadalnia");
  var t = null;

  var lightOFF_delayed = function() {
    if (PSC.state == "ON") sendCommand(LGT, "OFF");
    t = null;
  } 
  
  
  logInfo( "Oświetlenie wyłączy się za 5 sekund");
  if (PSC.state == ON) {
    if (LGT.state == OFF) sendCommand(LGT, "ON");
    if (t != null) {
      t.cancel()
      t = null;
    }

    if (PSC.state == OFF) {
      t = setTimeout(lightOFF_delayed, 5000);
    }
}

});

Hi,

Great, thanks for help. Indeed there were some typos but I managed to clean them and finally function is working in way that I expect.

Below I attach full code for such function, maybe it will be useful for some another beginners :slight_smile:

I’ve modified it to work with 0-100% dimmer instead of ON/OFF.

JSRule({
name: “F_LgtPscJadalnia_ON/OFF”,
description: “LgtTurnOnAndOff by presence”,
triggers: [
ItemStateChangeTrigger(“PscJadalnia”)
],
execute: function( module, input){
var LGT = getItem(“AktorDimJadalnia_Dimmer1”);
var PSC = getItem(“PscJadalnia”);
var t = null;

var lightOFF_delayed = function() {
if (PSC.state == “OFF”) sendCommand(LGT, “0”);

t = null;

}

if (PSC.state == “ON”) {
if (LGT.state == “0”) sendCommand(LGT, “10”);
if (t != null) {
t.cancel()
t = null;
}}

if (PSC.state == “OFF”) {
t = setTimeout(lightOFF_delayed, 1000000);
}

}
});