feat(android): setInterval closer to web spec (#9044)

This commit is contained in:
Eduardo Speroni
2020-11-19 18:07:51 -03:00
committed by GitHub
parent 539fd1eb29
commit 1769de9033
2 changed files with 40 additions and 2 deletions

View File

@ -171,6 +171,40 @@ export function test_setInterval_callbackCalledWithExtraArgs(done) {
); );
} }
export function test_setInterval_callbackNotDelayedByBusyWork() {
let calls = 0;
let firstCall = true;
const id = timer.setInterval(() => {
calls++;
if (firstCall) {
firstCall = false;
TKUnit.wait(0.025);
}
}, 50);
TKUnit.wait(0.11);
timer.clearInterval(id);
TKUnit.assertEqual(calls, 2, 'Callback should be called multiple times with busy wait');
}
export function test_setInterval_callbackSkippedByBusyWork() {
let calls = 0;
let firstCall = true;
const id = timer.setInterval(() => {
calls++;
if (firstCall) {
firstCall = false;
TKUnit.wait(0.051);
}
}, 50);
TKUnit.wait(0.16);
timer.clearInterval(id);
TKUnit.assertEqual(calls, 2, 'Callback should be called skipped when it takes too long to process');
}
export function test_setInterval_callbackShouldBeCleared(done) { export function test_setInterval_callbackShouldBeCleared(done) {
const start = TKUnit.time(); const start = TKUnit.time();
// >> timer-set-interval // >> timer-set-interval

View File

@ -58,12 +58,16 @@ export function setInterval(callback: Function, milliseconds = 0, ...args): numb
const handler = timeoutHandler; const handler = timeoutHandler;
const invoke = () => callback(...args); const invoke = () => callback(...args);
const zoneBound = zonedCallback(invoke); const zoneBound = zonedCallback(invoke);
const startOffset = milliseconds > 0 ? Date.now() % milliseconds : 0;
function nextCallMs() {
return milliseconds > 0 ? milliseconds - ((Date.now() - startOffset) % milliseconds) : milliseconds;
}
const runnable = new java.lang.Runnable({ const runnable = new java.lang.Runnable({
run: () => { run: () => {
zoneBound(); zoneBound();
if (timeoutCallbacks[id]) { if (timeoutCallbacks[id]) {
handler.postDelayed(runnable, long(milliseconds)); handler.postDelayed(runnable, long(nextCallMs()));
} }
}, },
}); });
@ -72,7 +76,7 @@ export function setInterval(callback: Function, milliseconds = 0, ...args): numb
timeoutCallbacks[id] = runnable; timeoutCallbacks[id] = runnable;
} }
timeoutHandler.postDelayed(runnable, long(milliseconds)); timeoutHandler.postDelayed(runnable, long(nextCallMs()));
return id; return id;
} }