Skip to content

Commit 4ec13c9

Browse files
committed
setWatch now reports lastTime - time of last state change espruino#238
1 parent 50cc51a commit 4ec13c9

4 files changed

Lines changed: 19 additions & 5 deletions

File tree

ChangeLog

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
Fix charCodeAt being signed (should be unsigned)
3636
When casting Strings to booleans, so s.length!=0
3737
Guess initial values for average SysTick time - means that getTime is more accurate for the first 1-2 seconds after startup
38+
setWatch now reports lastTime - time of last state change #238
3839

3940
1v50 : Fix broken Web IDE caused by change to printing JSON for console.log (part of #206)
4041
Fix bug when trying to stringify {5:5}

scripts/build_docs.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ def html(s): htmlFile.write(s+"\n");
3737

3838
def htmlify(d):
3939
d = re.sub(r'```([^`]+)```', r'<code>\1</code>', d) # code tags
40+
d = re.sub(r'`([^`]+)`', r'<code>\1</code>', d) # code tags
4041
d = re.sub(r'(http://[^ ]+)', r'<a href="\1">\1</a>', d) # links tags
4142
return d
4243

src/jsinteractive.c

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1322,7 +1322,7 @@ void jsiIdle() {
13221322
bool pinIsHigh = (event.flags&EV_EXTI_IS_HIGH)!=0;
13231323

13241324
JsVarInt debounce = jsvGetIntegerAndUnLock(jsvObjectGetChild(watchPtr, "debounce", 0));
1325-
if (debounce>0) {
1325+
if (debounce>0) { // Debouncing - use timeouts to ensure we only fire at the right time
13261326
JsVar *timeout = jsvObjectGetChild(watchPtr, "timeout", 0);
13271327
if (timeout) { // if we had a timeout, update the callback time
13281328
JsVar *timerTime = jsvObjectGetChild(timeout, "time", JSV_INTEGER);
@@ -1334,6 +1334,7 @@ void jsiIdle() {
13341334
jsvObjectSetChild(timeout, "watch", watchPtr); // no unlock
13351335
jsvUnLock(jsvObjectSetChild(timeout, "time", jsvNewFromInteger(event.data.time+debounce)));
13361336
jsvUnLock(jsvObjectSetChild(timeout, "callback", jsvObjectGetChild(watchPtr, "callback", 0)));
1337+
jsvUnLock(jsvObjectSetChild(timeout, "lastTime", jsvObjectGetChild(watchPtr, "lastTime", 0)));
13371338
// Add to timer array
13381339
jsiTimerAdd(timeout);
13391340
// Add to our watch
@@ -1344,12 +1345,15 @@ void jsiIdle() {
13441345
// store the current state here
13451346
jsvUnLock(jsvObjectSetChild(watchPtr, "state", jsvNewFromBool(pinIsHigh)));
13461347
} else { // Not debouncing - just execute normally
1348+
JsVar *timePtr = jsvNewFromFloat(jshGetMillisecondsFromTime(event.data.time)/1000);
13471349
if (jsiShouldExecuteWatch(watchPtr, pinIsHigh)) { // edge triggering
13481350
JsVar *watchCallback = jsvObjectGetChild(watchPtr, "callback", 0);
13491351
bool watchRecurring = jsvGetBoolAndUnLock(jsvObjectGetChild(watchPtr, "recur", 0));
13501352
JsVar *data = jsvNewWithFlags(JSV_OBJECT);
13511353
if (data) {
1352-
jsvUnLock(jsvObjectSetChild(data, "time", jsvNewFromFloat(jshGetMillisecondsFromTime(event.data.time)/1000)));
1354+
jsvUnLock(jsvObjectSetChild(data, "lastTime", jsvObjectGetChild(watchPtr, "lastTime", 0)));
1355+
// set both data.time, and watch.lastTime in one go
1356+
jsvObjectSetChild(data, "time", timePtr); // no unlock
13531357
jsvUnLock(jsvObjectSetChild(data, "state", jsvNewFromBool(pinIsHigh)));
13541358
}
13551359
jsiExecuteEventCallback(watchCallback, data, 0);
@@ -1360,6 +1364,7 @@ void jsiIdle() {
13601364
}
13611365
jsvUnLock(watchCallback);
13621366
}
1367+
jsvUnLock(jsvObjectSetChild(watchPtr, "lastTime", timePtr));
13631368
}
13641369
}
13651370

@@ -1401,12 +1406,17 @@ void jsiIdle() {
14011406
bool exec = true;
14021407
JsVar *data = jsvNewWithFlags(JSV_OBJECT);
14031408
if (data) {
1404-
jsvUnLock(jsvObjectSetChild(data, "time", jsvNewFromFloat(jshGetMillisecondsFromTime(jsvGetInteger(timerTime))/1000)));
1409+
JsVar *timePtr = jsvNewFromFloat(jshGetMillisecondsFromTime(jsvGetInteger(timerTime))/1000);
14051410
// if it was a watch, set the last state up
14061411
if (watchPtr) {
14071412
bool state = jsvGetBoolAndUnLock(jsvObjectSetChild(data, "state", jsvObjectGetChild(watchPtr, "state", 0)));
14081413
exec = jsiShouldExecuteWatch(watchPtr, state);
1414+
// set up the lastTime variable of data to what was in the watch
1415+
jsvObjectSetChild(data, "lastTime", jsvObjectGetChild(watchPtr, "lastTime", 0));
1416+
// set up the watches lastTime to this one
1417+
jsvObjectSetChild(watchPtr, "lastTime", timePtr); // don't unlock
14091418
}
1419+
jsvUnLock(jsvObjectSetChild(data, "time", timePtr));
14101420
}
14111421
if (exec) jsiExecuteEventCallback(timerCallback, data, 0);
14121422
jsvUnLock(data);

src/jswrap_io.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -247,8 +247,10 @@ JsVar *jswrap_interface_setTimeout(JsVar *func, JsVarFloat timeout) {
247247

248248
/*JSON{ "type":"function", "name" : "setWatch",
249249
"description" : ["Call the function specified when the pin changes",
250-
"The function may also take an argument, which is an object containing a field called 'time', which is the time in seconds at which the pin changed state, and 'state', which is the current state of the pin",
251-
" This can also be removed using clearWatch" ],
250+
"The function may also take an argument, which is an object of type `{time:float, lastTime:float, state:bool}`.",
251+
"`time` is the time in seconds at which the pin changed state, `lastTime` is the time in seconds at which the pin last changed state, and `state` is the current state of the pin.",
252+
"For instance, if you want to measure the length of a positive pusle you could use: ```setWatch(function(e) { console.log(e.time-e.lastTime); }, BTN, { repeat:true, edge:'falling' });```",
253+
"This can also be removed using clearWatch" ],
252254
"generate" : "jswrap_interface_setWatch",
253255
"params" : [ [ "function", "JsVarName", "A Function or String to be executed"],
254256
[ "pin", "pin", "The pin to watch" ],

0 commit comments

Comments
 (0)