检查我的网站是否在另一个标签中打开 [英] Check if my website is open in another tab

查看:148
本文介绍了检查我的网站是否在另一个标签中打开的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果用户已经在浏览器的另一个标签页中打开了我的网站,我想查看 JavaScript

I want to check with JavaScript if the user has already opened my website in another tab in their browser.

好像我不能使用 pagevisibility 来做到这一点......

It seems I cannot do that with pagevisibility...

我看到的唯一方法是使用基于会话cookie的WebSocket,并检查客户端是否有多个套接字。但通过这种方式,从当前选项卡,我必须问我的服务器,如果此用户有一个标签旁边打开他们当前的浏览器选项卡。这有点牵强!

The only way I see is to use WebSocket based on a session cookie, and check if the client has more than one socket. But by this way, from current tab, I have to ask my server if this user has a tab opened right next to their current browser tab. It is a little far-fetched!

可能使用 localstorage

推荐答案

使用本地存储我创建了一个简单的演示,可以完成你想做的事情。基本上,它只是维持当前打开的窗口的计数。当窗口关闭时,卸载事件触发并从窗口总数中移除它。

Using local storage I created a simple demo that should accomplish what your looking to do. Basically, it simply maintains a count of currently opened windows. When the window is closed the unload events fire and remove it from the total window count.

当您第一次看到它时,您可能会认为还有更多是。其中大部分是为了给谁是主窗口添加逻辑的一个琐碎的尝试,当你关闭孩子时,谁应该接替作为主要窗口。 (因此,setTimeout调用重新检查是否应该将其提升到主窗口)在经过一些头部划伤之后,我认为需要花费太多时间来实现,并且超出了这个问题的范围。但是,如果您打开两个窗口(主窗口和子窗口)并关闭主窗口,则该子窗口将被升级为主窗口。

When you first look at it, you may think there's more going on than there really is. Most of it was a shotty attempt to add logic into who was the "main" window, and who should take over as the "main" window as you closed children. (Hence the setTimeout calls to recheck if it should be promoted to a main window) After some head scratching, I decided it would take too much time to implement and was outside the scope of this question. However, if you have two windows open (Main, and Child) and you close the Main, the child will be promoted to a main.

在大多数情况下,您应该能够了解最新情况并将其用于您自己的实施。

For the most part you should be able to get the general idea of whats going on and use it for your own implementation.

请参阅以下所有内容:
http:// jsbin .com / mipanuro / 1 / edit

See it all in action here: http://jsbin.com/mipanuro/1/edit

哦,是的,要真正看到它的行动...打开多个窗口中的链接。 :)

Oh yeah, to actually see it in action... Open the link in multiple windows. :)

我做了必要的修改,让本地存储保持主窗口。当你关闭标签时,子窗口可以被提升为主窗口。有两种方法通过传递给WindowStateManager的构造函数的参数来控制主窗口状态。这个实现比我以前的尝试要好得多。

I've made the necessary changes to have the the local storage maintain the "main" window. As you close tabs child windows can then become promoted to a main window. There are two ways to control the "main" window state through a parameter passed to the constructor of WindowStateManager. This implementation is much nicer than my previous attempt.

JavaScript:

JavaScript:

// noprotect

var statusWindow = document.getElementById('status');

(function (win)
{
    //Private variables
    var _LOCALSTORAGE_KEY = 'WINDOW_VALIDATION';
    var RECHECK_WINDOW_DELAY_MS = 100;
    var _initialized = false;
    var _isMainWindow = false;
    var _unloaded = false;
    var _windowArray;
    var _windowId;
    var _isNewWindowPromotedToMain = false;
    var _onWindowUpdated;


    function WindowStateManager(isNewWindowPromotedToMain, onWindowUpdated)
    {
        //this.resetWindows();
        _onWindowUpdated = onWindowUpdated;
        _isNewWindowPromotedToMain = isNewWindowPromotedToMain;
        _windowId = Date.now().toString();

        bindUnload();

        determineWindowState.call(this);

        _initialized = true;

        _onWindowUpdated.call(this);
    }

    //Determine the state of the window 
    //If its a main or child window
    function determineWindowState()
    {
        var self = this;
        var _previousState = _isMainWindow;

        _windowArray = localStorage.getItem(_LOCALSTORAGE_KEY);

        if (_windowArray === null || _windowArray === "NaN")
        {
            _windowArray = [];
        }
        else
        {
            _windowArray = JSON.parse(_windowArray);
        }

        if (_initialized)
        {
            //Determine if this window should be promoted
            if (_windowArray.length <= 1 ||
               (_isNewWindowPromotedToMain ? _windowArray[_windowArray.length - 1] : _windowArray[0]) === _windowId)
            {
                _isMainWindow = true;
            }
            else
            {
                _isMainWindow = false;
            }
        }
        else
        {
            if (_windowArray.length === 0)
            {
                _isMainWindow = true;
                _windowArray[0] = _windowId;
                localStorage.setItem(_LOCALSTORAGE_KEY, JSON.stringify(_windowArray));
            }
            else
            {
                _isMainWindow = false;
                _windowArray.push(_windowId);
                localStorage.setItem(_LOCALSTORAGE_KEY, JSON.stringify(_windowArray));
            }
        }

        //If the window state has been updated invoke callback
        if (_previousState !== _isMainWindow)
        {
            _onWindowUpdated.call(this);
        }

        //Perform a recheck of the window on a delay
        setTimeout(function()
                   {
                     determineWindowState.call(self);
                   }, RECHECK_WINDOW_DELAY_MS);
    }

    //Remove the window from the global count
    function removeWindow()
    {
        var __windowArray = JSON.parse(localStorage.getItem(_LOCALSTORAGE_KEY));
        for (var i = 0, length = __windowArray.length; i < length; i++)
        {
            if (__windowArray[i] === _windowId)
            {
                __windowArray.splice(i, 1);
                break;
            }
        }
        //Update the local storage with the new array
        localStorage.setItem(_LOCALSTORAGE_KEY, JSON.stringify(__windowArray));
    }

    //Bind unloading events  
    function bindUnload()
    {
        win.addEventListener('beforeunload', function ()
        {
            if (!_unloaded)
            {
                removeWindow();
            }
        });
        win.addEventListener('unload', function ()
        {
            if (!_unloaded)
            {
                removeWindow();
            }
        });
    }

    WindowStateManager.prototype.isMainWindow = function ()
    {
        return _isMainWindow;
    };

    WindowStateManager.prototype.resetWindows = function ()
    {
        localStorage.removeItem(_LOCALSTORAGE_KEY);
    };

    win.WindowStateManager = WindowStateManager;
})(window);

var WindowStateManager = new WindowStateManager(false, windowUpdated);

function windowUpdated()
{
    //"this" is a reference to the WindowStateManager
    statusWindow.className = (this.isMainWindow() ? 'main' : 'child');
}
//Resets the count in case something goes wrong in code
//WindowStateManager.resetWindows()

HTML:

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title>JS Bin</title>
</head>
<body>
  <div id='status'> 
    <span class='mainWindow'>Main Window</span>
    <span class='childWindow'>Child Window</span>
  </div>
</body>
</html>

CSS:

CSS:

#status
{
  display:table;
  width:100%;
  height:500px;
  border:1px solid black;
}
span
{
  vertical-align:middle;
  text-align:center; 
  margin:0 auto;
  font-size:50px;
  font-family:arial;
  color:#ba3fa3;  
  display:none;
}

#status.main .mainWindow,
#status.child .childWindow
{
  display:table-cell;
}

.mainWindow
{
  background-color:#22d86e;
}
.childWindow
{
  background-color:#70aeff;
}

这篇关于检查我的网站是否在另一个标签中打开的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆