gpt4 book ai didi

javascript - 从后台切换回Safari时如何在iOS webapp中检测?

转载 作者:IT王子 更新时间:2023-10-29 08:11:22 27 4
gpt4 key购买 nike

我如何构建一个能够监控页面何时获得焦点的网页,尤其是当 Safari 处于后台并且用户将 Safari 切换回前台时。

当在 iPhone 上切换到 Safari 时,下面的代码不会触发事件

<html>
<head>
<script type="text/javascript">
window.onfocus = function() { alert("onfocus"); };
</script>
</head>
<body>

Main text

</body>
</html>

根据http://www.quirksmode.org/dom/events/index.html :当窗口获得焦点时,Safari iPhone 不会触发事件。

所以我的问题仍然是:如何在 Safari for iPhone 的网页上使用 Javascript 来检测窗口获得焦点?

最佳答案

根据您需要支持的内容,您需要多种不同的技术来检测页面何时可见。由于浏览器 vendor 、浏览器版本、操作系统、在 WebView/UIWebView/WKWebView 中运行等原因而发生变化。

您可以使用 this page 查看正在发生的事件。我发现要检测页面何时“唤醒”所有组合,我需要注册以下所有事件:

  • 窗口可见性改变事件
  • 窗口焦点事件
  • 窗口页面展示事件
  • 启动计时器并查看计时器是否花费的时间比应有的时间长得多(计时器在休眠时由 iOS 进入休眠状态)。即使在 iOS9 上,使用 UIWebView 的 App 也不会触发 visibilityChange 事件(WKWebView 可以)。

我过去也使用 webkitRequestAnimationFrame,但我删除了它,因为它可能会导致卡顿(据我所知,渲染引擎会为它阻塞调用主线程)。

要尝试的事情:

  • 转到另一个标签
  • 锁屏,等待,解锁
  • 让另一个应用成为焦点
  • 最小化浏览器

您可以看到正在发生的事件:

  • 实时查看控制台日志(附加调试器)。
  • 在设备上实时使用 http://output.jsbin.com/rinece#http://localhost:80/ 并查看作为 Ajax 调用请求的日志(使用代理,或在 # 后的地址上运行小型服务器并将正文记录到控制台)。
  • 查看屏幕上的日志,并密切注意每个条目的记录时间,看看是否记录了该条目,例如visibilitychange hide 事件可能不会在页面实际隐藏时发生(如果应用程序处于休眠状态),而是排队并在页面重新显示时发生!!!

iOS:如果使用计时器检测 iOS UIWebView 是否已进入休眠状态,请注意,您需要使用 new Date.getNow() 而不是 performance.now( )。这是因为 performance.now() 在页面进入休眠状态时停止计算时间,而且 iOS 执行 performance.now() 的速度很慢...(另外:您可以测量数量通过检测 new Date.getNow()performance.now() 的差异来确定页面休眠的时间。在 test page 上寻找 != ) .

如果您使用的是 UIWebView,则有两种方法可行(如果您支持 iOS7 应用,则必须使用 UIWebView)。 WKWebView 具有 visibilitychange 事件,因此不需要解决方法。

==技术1.

当 applicationWillEnterForeground 事件在应用程序中发生时,调用 UIWebView stringByEvaluatingJavaScriptFromString 以调用您的 JavaScript pageAwakened()。

优点:干净、准确。

缺点:需要 Objective-C 代码。被调用的函数需要可以从全局范围访问。

==技术2.

使用 webkitRequestAnimationFrame 并检测时间延迟。

优点:仅限 JavaScript。适用于 iOS7 上的移动 Safari。

缺点:卡顿的丑陋风险和使用 webkitRequestAnimationFrame 是一个严重的 hack。

// iOS specific workaround to detect if Mobile App comes back to focus. UIWebView and old iOS don't fire any of: window.onvisibilitychange, window.onfocus, window.onpageshow
function iosWakeDetect() {
function requestAnimationFrameCallback() {
webkitRequestAnimationFrame(function() {
// Can't use timestamp from webkitRequestAnimationFrame callback, because timestamp is not incremented while app is in background. Instead use UTC time. Also can't use performance.now() for same reason.
var thisTime = (new Date).getTime();
if (lastTime && (thisTime - lastTime) > 60000) { // one minute
// Very important not to hold up browser within webkitRequestAnimationFrame() or reference any DOM - zero timeout so shoved into event queue
setTimeout(pageAwakened, 0);
}
lastTime = thisTime;
requestAnimationFrameCallback();
});
}
var lastTime;
if (/^iPhone|^iPad|^iPod/.test(navigator.platform) && !window.indexedDB && window.webkitRequestAnimationFrame) { // indexedDB sniff: it is missing in UIWebView
requestAnimationFrameCallback();
}
}

function pageAwakened() {
// add code here to remove duplicate events. Check !document.hidden if supported
};

window.addEventListener('focus', pageAwakened);
window.addEventListener('pageshow', pageAwakened);
window.addEventListener('visibilitychange', function() {
!document.hidden && pageAwakened();
});

关于javascript - 从后台切换回Safari时如何在iOS webapp中检测?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4656387/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com