如何判断浏览器/选项卡是不是处于活动状态[重复]

Posted

技术标签:

【中文标题】如何判断浏览器/选项卡是不是处于活动状态[重复]【英文标题】:How to tell if browser/tab is active [duplicate]如何判断浏览器/选项卡是否处于活动状态[重复] 【发布时间】:2010-12-18 03:08:03 【问题描述】:

可能重复:Is there a way to detect if a browser window is not currently active?

我有一个每秒调用一次的函数,我只想在当前页面位于前台时运行它,即用户没有最小化浏览器或切换到另一个选项卡。如果用户不看它并可能占用大量 CPU 资源,它就毫无用处,所以我不想只是在后台浪费周期。

有人知道如何在 javascript 中说明这一点吗?

注意:我使用 jQuery,所以如果你的答案使用它,那很好:)。

【问题讨论】:

+1 想知道答案。我关心的不是 CPU 密集型,而是带宽和服务器密集型。 如果你想要一个 Jquery 插件.. github.com/keithhackbarth/jquery-window-active 更新:截至 2013 年,所有主流浏览器都支持所谓的visiblity API。有关示例,请参见此处:***.com/a/19519701/603003 我认为最好的示例是在daniemon.com/tech/webapps/page-visibility 戴上耳机并播放,您会看到(在您开始播放视频后)实施非常到位。 使用document.addEventListener("visibilitychange", onchange); 见***.com/a/1060034/1066234 和w3.org/TR/page-visibility 【参考方案1】:

除了Richard Simões回答你还可以使用Page Visibility API。

if (!document.hidden) 
    // do what you need

本规范为网站开发人员定义了一种方法 以编程方式确定页面的当前可见性状态 为了开发功率和 CPU 高效的 Web 应用程序。

了解详情(2019 年更新)

All modern browsers are supportingdocument.hidden http://davidwalsh.name/page-visibility https://developers.google.com/chrome/whitepapers/pagevisibility 在隐藏窗口/选项卡时暂停视频的示例https://web.archive.org/web/20170609212707/http://www.samdutton.com/pageVisibility/

【讨论】:

+1 用于给出不依赖 jQuery 的答案。从长远来看,这似乎也是最好的答案,因为浏览器正朝着支持 W3C 标准的方向发展。 David Walsh 的示例适用于 Chrome 和 Firefox,但不适用于 Safari。 可见性和焦点是完全不同的东西。 页面可见性 API 检测浏览器是否可见,例如没有最小化或完全被另一个窗口覆盖。它不会检测窗口可见但另一个窗口处于活动状态的情况。 仅供参考:caniuse.com/#search=Page%20Visibility @ckknight 你介意将接受的答案更改为这个吗?这个更新的答案是我们应该在 2019 年使用的答案【参考方案2】:

您将使用窗口的focusblur 事件:

var interval_id;
$(window).focus(function() 
    if (!interval_id)
        interval_id = setInterval(hard_work, 1000);
);

$(window).blur(function() 
    clearInterval(interval_id);
    interval_id = 0;
);

回答“双火”的评论问题并保持 jQuery 易用性:

$(window).on("blur focus", function(e) 
    var prevType = $(this).data("prevType");

    if (prevType != e.type)    //  reduce double fire issues
        switch (e.type) 
            case "blur":
                // do work
                break;
            case "focus":
                // do work
                break;
        
    

    $(this).data("prevType", e.type);
)

点击查看Example Code Showing it working (JSFiddle)

【讨论】:

这行得通吗?测试?就这么简单? 这个答案不是最优的,因为focusblur 事件通常会在浏览器中针对用户采取的每个概念性焦点或模糊操作触发多次,在这种情况下,客户端将开始在多个时间间隔内进行hard_work,基本上是同时进行。 我在别处读到onmousemove 可以替代focus @MichaelRobinson 也许用于最大化/全屏选项卡式浏览器。它可能仍会在 Internet Explorer (bit-tech.net/news/bits/2012/12/13/ie-bug-cursor/1) 中触发,尽管重点是其他一些应用程序。 但是如果用户在页面加载时切换选项卡,在调用$(window)focus/blur 之前呢?根据您的用例,这可能会弄乱回调状态以及任何后台作业? (例如,如果您在页面加载时启动后台作业 - 但 blur 从未发生过,因为用户在注册 $(window).blur 之前切换了选项卡?)【参考方案3】:

我会尝试在 window.onfocuswindow.onblur 事件上设置标志。

以下sn-p已在Firefox、Safari和Chrome上测试过,打开控制台并在标签之间来回移动:

var isTabActive;

window.onfocus = function ()  
  isTabActive = true; 
; 

window.onblur = function ()  
  isTabActive = false; 
; 

// test
setInterval(function ()  
  console.log(window.isTabActive ? 'active' : 'inactive'); 
, 1000);

试试here。

【讨论】:

示例很棒。对 IE 有什么想法吗? 我可以确认它在 IE7 中运行良好,除此之外还没有测试过,这是最好的答案,也是所有功能相同的答案中的第一个答案,投票赞成! 我也喜欢这个简单的例子。我修正了一个小错字并添加了页面反馈 + jquery 以查看在没有控制台的情况下会发生什么。 jsbin.com/ulize3/80 由于某种原因 isActive 在 Chrome 上总是错误的? 实际上,在 Chrome 上它总是为 false 的原因是因为 console.log 使用 window.isActive。删除 window. 部分或将其添加到任何地方。我也认为 isActive 应该初始化为 true 以获得更好的结果。【参考方案4】:

使用 jQuery:

$(function() 
    window.isActive = true;
    $(window).focus(function()  this.isActive = true; );
    $(window).blur(function()  this.isActive = false; );
    showIsActive();
);

function showIsActive()

    console.log(window.isActive)
    window.setTimeout("showIsActive()", 2000);


function doWork()

    if (window.isActive)  /* do CPU-intensive stuff */

【讨论】:

【参考方案5】:

这里的所有示例(rockacola 的除外)都要求用户实际单击窗口来定义焦点。这并不理想,所以.hover() 是更好的选择:

$(window).hover(function(event) 
    if (event.fromElement) 
        console.log("inactive");
     else 
        console.log("active");
    
);

这会告诉你用户何时将鼠标放在屏幕上,但它仍然不会告诉你它是否在前台而用户的鼠标在其他地方。

【讨论】:

善于跳出框框思考;但是,如果您试图弄清楚用户在页面上停留了多长时间,它就不会很好地工作。此外,hover 不是移动浏览器的有效选项。不过公平地说,我不知道focusblur 事件绑定是否适用于移动设备。 另外,悬停取决于鼠标移动。如果选项卡是使用键盘快捷键输入的,则可能不会触发悬停。【参考方案6】:

如果您在 Chrome 中打开时尝试执行类似于 Google 搜索页面的操作(当您“聚焦”页面时会触发某些事件),那么 hover() 事件可能会有所帮助。

$(window).hover(function() 
  // code here...
);

【讨论】:

以上是关于如何判断浏览器/选项卡是不是处于活动状态[重复]的主要内容,如果未能解决你的问题,请参考以下文章

确定浏览器选项卡是不是处于活动状态? - IE?

当用户/选项卡/浏览器处于非活动状态时 JavaScript 播放声音

Vuejs:当特定选项卡处于活动状态时是不是会发出事件(bootstrap-vue)

如何关闭所有选项卡但在 Qt4(QTabWidget)中处于活动状态

如何在回发 ASP.Net Core 后保持选项卡处于活动状态

页面重新加载后,如何使用 twitter bootstrap 保持当前选项卡处于活动状态?