问题
This is related to the following:
Safari 9.1 for El Capitan
Safari 10 for Sierra
Does anyone know what is Safari doing in the JavaScript engine with respect to setTimeout() when the browser or the tab loses focus (mainly, is minimized)?
I have created a simple JavaScript web application that I load in Safari that calls JavaScript setTimeout() that passes another function to be executed after the timeout value. The function prints the date/time to the console, then calls setTimeout() with the same timeout value.
If the Safari tab loses focus or the browser is minimized, after some time it seems Safari stops executing the setTimeout, and the subsequent function to be called, and until focus is returned, no function execution occurs. It's as if the event loop stops processing.
NOTE: No function calls are lost, they are only paused, and restarted when the browser regains focus.
I do not notice this in Firefox, Chrome or IE11.
Main reason this question is being posed is that the problem is mainly observed with a web application I am maintaining that uses CometD for communication back to the server. CometD library is using setTimeout to execute a request back to the server every 30 seconds. If the browser running the application is minimized, it seems CometD stops communicating with the server until the browser is maximized again.
回答1:
You should probably use setInterval instead, since according to this answer, setInterval
still works, even if it is limited to 1 per second.
The setInterval() method of the WindowOrWorkerGlobalScope mixin repeatedly calls a function or executes a code snippet, with a fixed time delay between each call. Returns an intervalID.
Syntax var intervalID = scope.setInterval(func, delay[, param1, param2, ...]); var intervalID = scope.setInterval(code, delay); Parameters
func A function to be executed every delay milliseconds.
code An optional syntax allows you to include a string instead of a function, which is compiled and executed every delay milliseconds. This syntax is not recommended for the same reasons that make using eval() a security risk.
delay The time, in milliseconds (thousandths of a second), the timer should delay in between executions of the specified function or code. If this parameter is less than 10, a value of 10 is used. Note that the actual delay may be longer; see "Reasons for delays longer than specified" in WindowOrWorkerGlobalScope.setTimeout() for examples.
param1, ..., paramN Optional Additional parameters which are passed through to the function specified by func once the timer expires.
Timeouts in inactive tabs clamped to >=1000ms
To reduce the load (and associated battery usage) from background tabs, timeouts are often clamped to firing no more often than once per second (1000 ms) in inactive tabs.
来源:https://stackoverflow.com/questions/41768173/safari-javascript-settimeout-stops-when-minimized