JavaScript >> Javascript 文檔 >  >> JavaScript

使用 JavaScript 和 YUI 3 檢測用戶是否空閒

自 Ajax 爆發以來,Web 開發人員一直對用戶是否處於空閒狀態感興趣。隨著更動態、高度交互的 Web 界面的引入,人們渴望知道用戶在任何時間點是否真的在做任何事情。於是,確定用戶是否空閒的探索就開始了。

這個問題已經解決了,雖然我會不雅地爭論,在很多 Web 應用程序中:Facebook、WordPress 和 Gmail 都試圖找出用戶何時停止與頁面交互以執行某些操作。通常的 JavaScript 解決方案包括監控 mousemove 事件,如果在特定時間段內沒有鼠標移動,則表明用戶處於空閒狀態。這種方法有一個主要缺陷,那就是依賴鼠標事件來指示用戶是活動還是空閒。這是有問題的,因為當然,有兩個主要輸入設備(鍵盤和鼠標)連接到計算機,所以你會丟失 50% 的圖片。如果用戶正在輸入長電子郵件或博客文章,這是否意味著他們只是因為沒有移動鼠標而處於空閒狀態?當然不是。那些因殘疾而無法使用鼠標的用戶,他們總是閒著嗎?再一次,答案是否定的。

考慮到這一背景,我開始在 JavaScript 中創建一個空閒計時器,以適應可能想要使用它的複雜 Web 應用程序。我在 YUI 3 之上構建了這個實現,因為它在短時間內成為了我最喜歡的 JavaScript 庫。我想實現的功能是:

  1. 允許啟動和停止空閒計時器以正確清理資源。
  2. 當用戶空閒時觸發一個事件。
  3. 當用戶在空閒後變為活動狀態時觸發一個事件。
  4. 提供一個函數,以便我可以隨時確定用戶是否處於空閒狀態。

這些功能讓我有了一個基本界面:

Y.IdleTimer = {

    isRunning: function(){
    },

    isIdle: function(){
    },

    start: function(newTimeout){
    },

    stop: function(){
    }

};

我決定使用 YUI 3 Event 實用程序為此實現提供自定義事件支持。這是通過增加 Y.IdleTimer Y.Event.Target 的對象 :

//inherit event functionality
Y.augment(Y.IdleTimer, Y.Event.Target);

這一行添加了基本的事件方法,例如 fire() , subscribe() , 和 unsubscribe() .使用 Y.Event.Target ,自定義事件對象的創建和管理為您完成,讓您可以專注於實現細節。

接下來,我創建了幾個標誌:idle ,表示用戶是否空閒,enabled ,表示計時器是否正在運行。這些在內部用於管理計時器的狀態,並在 isIdle() 中返回 和 isRunning() , 分別。我還創建了 tId ,這是使用setTimeout()時存放定時器ID的地方 和 timeout ,表示在聲明用戶空閒之前等待的默認時間量(最初設置為 30,000 毫秒,這可以通過將值傳遞給 start() 來覆蓋 )。

要管理用戶的空閒狀態,您需要為兩個 mousemove 附加一個事件處理程序 和 keydown .由於這兩種方法都冒泡,我可以在文檔級別附加處理程序來管理整個頁面(當然,這假設沒有人在到達文檔級別之前停止冒泡)。兩個事件的事件處理程序應該是相同的,因此沒有重複的代碼,並且處理程序必須管理超時過程。為此,我最終創建了兩個函數:

//event handler
function handleUserEvent(){

    //clear any existing timeout
    clearTimeout(tId);

    //if the idle timer is enabled
    if (enabled){

        //if it's idle, that means the user is no longer idle
        if (idle){
            toggleIdleState();
        } 

        //set a new timeout
        tId = setTimeout(toggleIdleState, timeout);
    }
}

//helper to fire events
function toggleIdleState(){

    //toggle the state
    idle = !idle;

    //fire appropriate event
    Y.IdleTimer.fire(idle ? "idle" : "active");
}

第一個函數handleUserEvent() 被指定為 mousemove 的事件處理程序 和 keydown .它實際上並沒有使用 event 任何東西的對象,所以我沒有費心將它定義為參數。每當用戶做某事時,最後一個計時器應該被清除,然後應該採取適當的行動。如果計時器停止,則什麼也不會發生;如果它正在運行,則根據用戶當前的 idle 確定操作 狀態。如果用戶空閒,則 toggleIdleState() 立即調用 state 以指示用戶未處於活動狀態。然後,使用定時器來延遲調用toggleIdleState() 因為下一次切換會回到空閒狀態。

toggleIdleState() 函數只是切換 idle 標誌,然後觸發適當的事件。如果用戶在切換後處於空閒狀態,則觸發“idle”,否則觸發“active”。當用戶的空閒狀態發生變化時,這些事件最終會被觸發,並且只會觸發一次,直到狀態再次發生變化。

為了完成實現,我只是填寫了現有的接口骨架來使用這些功能:

Y.IdleTimer = {
    isRunning: function(){
        return enabled;
    },

    isIdle: function(){
        return idle;
    },

    start: function(newTimeout){

        //set to enabled
        enabled = true;

        //set idle to false to begin with
        idle = false;

        //assign a new timeout if necessary
        if (typeof newTimeout == "number"){
            timeout = newTimeout;
        }

        //assign appropriate event handlers
        Y.on("mousemove", handleUserEvent, document);
        Y.on("keydown", handleUserEvent, document);

        //set a timeout to toggle state
        tId = setTimeout(toggleIdleState, timeout);
    },

    stop: function(){

        //set to disabled
        enabled = false;

        //clear any pending timeouts
        clearTimeout(tId);

        //detach the event handlers
        Y.detach("mousemove", handleUserEvent, document);
        Y.detach("keydown", handleUserEvent, document);
    }

};

//inherit event functionality
Y.augment(Y.IdleTimer, Y.Event.Target);

空閒定時器的基本用法如下:

Y.IdleTimer.subscribe("idle", function(){
    //handle when the user becomes idle
});

Y.IdleTimer.subscribe("active", function(){
     //handle when the user becomes active
});

//start the timer with a default timeout of 30s
Y.IdleTimer.start();

由於 YUI 3 的強大功能,這種空閒計時器的實現體積非常小,而且使用起來非常簡單。你可以在 GitHub 上獲取完整的源代碼,還有一個例子可以玩。

更新(2009 年 6 月 6 日): 根據 Paul 的反饋更新了邏輯。

更新(2009 年 6 月 21 日): YUI 2 和通用版本的空閒計時器現在可以在我的 GitHub 項目中獲得。

更新(2009 年 10 月 28 日): YUI 3 IdleTimer 現在是 YUI Gallery 的一部分(更多信息)。


Tutorial JavaScript 教程
  1. [EN-US] 從 Next.js 開始

  2. 輸入jQuery在onchange之前獲取舊值並在onchange之後獲取值

  3. 2020 年面向 Web 開發人員的 20 多個有用的 jQuery 代碼片段

  4. 遷移到 Typescript:保持流暢和穩定

  5. 概念:帶 Promise 的高性能 Web 服務器

  6. Pajama SSG - 使用 Node.js 的簡單靜態站點生成器

  7. 帶有 Typescript 和 React 的 Elixir Phoenix – 2019 年 12 月版

  1. discordjs v13 - 減去變量

  2. 線性搜索算法

  3. 2021 年 Web 工作者的狀態

  4. JavaScript 中鍊錶的完整指南

  5. 在 JavaScript 中設計 API 方法

  6. 異步/等待:錯誤處理

  7. 你應該支持 Internet Explorer 嗎?

  1. 按日期排序對像數組 JavaScript |示例代碼

  2. 從 create-react-app 遷移到 Gatsby.js

  3. 獲取 Array 方法的不可變版本

  4. 製作世界上最快的網站,以及其他錯誤