最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

使用JavaScript實現(xiàn)檢測網(wǎng)頁是否為空閑狀態(tài)

 更新時間:2024年03月28日 11:14:40   作者:求知若饑  
最近開發(fā)項目時,常碰到“用戶在一定時間內(nèi)無任何操作時,跳轉(zhuǎn)到某個頁面”的需求,所以本文就來使用JavaScript實現(xiàn)這一要求,需要的可以參考下

1. 背景

最近開發(fā)項目時,常碰到“用戶在一定時間內(nèi)無任何操作時,跳轉(zhuǎn)到某個頁面”的需求。

網(wǎng)上沖浪后,也沒有找到一個比較好的js封裝去解決這個問題,從而決定自己實現(xiàn)。

2. 如何判斷頁面是否空閑(用戶長時間無操作)

首先,我們要知道什么是空閑?用戶一定時間內(nèi),沒有對網(wǎng)頁進行任何操作,則當(dāng)前網(wǎng)頁為空閑狀態(tài)。

用戶操作網(wǎng)頁,無非就是通過鼠標(biāo)、鍵盤兩個輸入設(shè)備(暫不考慮手柄等設(shè)備)。因而我們可以監(jiān)聽相應(yīng)的輸入事件,來判斷網(wǎng)頁是否空閑(用戶是否操作網(wǎng)頁)。

  • 監(jiān)聽鼠標(biāo)移動事件mousemove;
  • 監(jiān)聽鍵盤按下事件mousedown
  • 在用戶進入網(wǎng)頁后,設(shè)置延時跳轉(zhuǎn),如果觸發(fā)以上事件,則移除延時器,并重新開始。

3. 網(wǎng)頁空閑檢測實現(xiàn)

3.1 簡易實現(xiàn)

以下代碼,簡易實現(xiàn)了一個判斷網(wǎng)頁空閑的方法。

const onIdleDetection = (callback, timeout = 15, immediate = false) => {
  let pageTimer;
  
  const onClearTimer = () => {
    pageTimer && clearTimeout(pageTimer);
    pageTimer = undefined;
  };
  const onStartTimer = () => {
    onClearTimer();
    pageTimer = setTimeout(() => {
      callback();
    }, timeout * 1000);
  };

  const startDetection = () => {
    onStartTimer();
    document.addEventListener('mousedown', onStartTimer);
    document.addEventListener('mousemove', onStartTimer);
  };
  const stopDetection = () => {
    onClearTimer();
    document.removeEventListener('mousedown', onStartTimer);
    document.removeEventListener('mousemove', onStartTimer);
  };
  const restartDetection = () => {
      onClearTimer();
      onStartTimer();
  };

  if (immediate) {
    startDetection();
  }

  return {
    startDetection,
    stopDetection,
    restartDetection
  };
};

也許你注意到了,我并沒有針對onStartTimer事件進行防抖,那這是不是會對性能有影響呢?

是的,肯定有那么點影響,那我為啥不添加防抖呢?

這是因為添加防抖后,形成了setTimeout嵌套,嵌套setTimeout會有精度問題(參考)。

或許你還會說,非活動標(biāo)簽頁(網(wǎng)頁被隱藏)的setTimeout的執(zhí)行和精度會有問題(參考非活動標(biāo)簽的超時)。

確實存在以上問題,接下來我們就來一一解決吧!

3.2 處理頻繁觸發(fā)問題

我們可以通過添加一個變量記錄開始執(zhí)行時間,當(dāng)下一次執(zhí)行與當(dāng)前的時間間隔小于某個值時直接退出函數(shù),從而解決這個問題(節(jié)流思想應(yīng)用)。

const onIdleDetection = (callback, timeout = 15, immediate = false) => {
  let pageTimer;
  // 記錄開始時間
  let beginTime = 0;
  const onStartTimer = () => {
    // 觸發(fā)間隔小于100ms時,直接返回
    const currentTime = Date.now();
    if (pageTimer && currentTime - beginTime < 100) {
      return;
    }

    onClearTimer();
    // 更新開始時間
    beginTime = currentTime;
    pageTimer = setTimeout(() => {
      callback();
    }, timeout * 1000);
  };
  const onClearTimer = () => {
    pageTimer && clearTimeout(pageTimer);
    pageTimer = undefined;
  };
  
  const startDetection = () => {
    onStartTimer();
    document.addEventListener('mousedown', onStartTimer);
    document.addEventListener('mousemove', onStartTimer);
  };
  const stopDetection = () => {
    onClearTimer();
    document.removeEventListener('mousedown', onStartTimer);
    document.removeEventListener('mousemove', onStartTimer);
  };
  const restartDetection = () => {
      onClearTimer();
      onStartTimer();
  };
  
  if (immediate) {
    startDetection();
  }

  return {
    startDetection,
    stopDetection,
    restartDetection
  };
};

3.3 處理頁面被隱藏的情況(完整實現(xiàn))

我們可以監(jiān)聽visibilitychange事件,在頁面隱藏時移除延時器,然后頁面顯示時繼續(xù)計時,從而解決這個問題。

/**
 * 網(wǎng)頁空閑檢測
 * @param {() => void} callback 空閑時執(zhí)行,即一定時長無操作時觸發(fā)
 * @param {number} [timeout=15] 時長,默認(rèn)15s,單位:秒
 * @param {boolean} [immediate=false] 是否立即開始,默認(rèn) false
 * @returns
 */
const onIdleDetection = (callback, timeout = 15, immediate = false) => {
  let pageTimer;
  let beginTime = 0;
  const onClearTimer = () => {
    pageTimer && clearTimeout(pageTimer);
    pageTimer = undefined;
  };
  const onStartTimer = () => {
    const currentTime = Date.now();
    if (pageTimer && currentTime - beginTime < 100) {
      return;
    }

    onClearTimer();
    beginTime = currentTime;
    pageTimer = setTimeout(() => {
      callback();
    }, timeout * 1000);
  };

  const onPageVisibility = () => {
     // 頁面顯示狀態(tài)改變時,移除延時器
     onClearTimer();

     if (document.visibilityState === 'visible') {
       const currentTime = Date.now();
       // 頁面顯示時,計算時間,如果超出限制時間則直接執(zhí)行回調(diào)函數(shù)
       if (currentTime - beginTime >= timeout * 1000) {
         callback();
         return;
       }
       // 繼續(xù)計時
       pageTimer = setTimeout(() => {
         callback();
       }, timeout * 1000 - (currentTime - beginTime));
     }
  };

  const startDetection = () => {
    onStartTimer();
    document.addEventListener('mousedown', onStartTimer);
    document.addEventListener('mousemove', onStartTimer);
    document.addEventListener('visibilitychange', onPageVisibility);
  };

  const stopDetection = () => {
    onClearTimer();
    document.removeEventListener('mousedown', onStartTimer);
    document.removeEventListener('mousemove', onStartTimer);
    document.removeEventListener('visibilitychange', onPageVisibility);
  };
  
  const restartDetection = () => {
      onClearTimer();
      onStartTimer();
  };

  if (immediate) {
    startDetection();
  }

  return {
    startDetection,
    stopDetection,
    restartDetection
  };
};

通過以上代碼,我們就完整地實現(xiàn)了一個網(wǎng)頁空閑狀態(tài)檢測的方法。

4. 擴展

chrome瀏覽器其實提供了一個Idle DetectionAPI,來實現(xiàn)網(wǎng)頁空閑狀態(tài)的檢測,但是這個API還是一個實驗性特性,并且Firefox與Safari不支持。API參考

到此這篇關(guān)于使用JavaScript實現(xiàn)檢測網(wǎng)頁是否為空閑狀態(tài)的文章就介紹到這了,更多相關(guān)JavaScript檢測網(wǎng)頁內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • JavaScript作用域全面總結(jié)(附詳細代碼)

    JavaScript作用域全面總結(jié)(附詳細代碼)

    JavaScript的作用域一直以來是前端開發(fā)中比較難以理解的知識點,下面這篇文章主要介紹了JavaScript作用域全面總結(jié)的相關(guān)資料,文中通過代碼介紹的非常詳細,需要的朋友可以參考下
    2025-11-11
  • 前端bug調(diào)試的方法技巧及常見錯誤

    前端bug調(diào)試的方法技巧及常見錯誤

    這篇文章主要介紹了編程中常見的報錯和Bug,以及調(diào)試的重要性,調(diào)試的基本流程是通過縮小范圍來定位問題,并給出了推測法、刪除代碼法、console調(diào)試和debugger調(diào)試等方法,文中通過圖文介紹的非常詳細,需要的朋友可以參考下
    2025-03-03
  • Javascript異步表單提交,圖片上傳,兼容異步模擬ajax技術(shù)

    Javascript異步表單提交,圖片上傳,兼容異步模擬ajax技術(shù)

    使用Javascript異步表單提交,圖片上傳,兼容異步模擬ajax技術(shù),需要的朋友可以參考下。
    2010-05-05
  • 詳解如何在JavaScript中使用裝飾器

    詳解如何在JavaScript中使用裝飾器

    Decorator裝飾器是ES7的時候提案的特性,目前處于Stage?3候選階段(2022年10月)。裝飾器簡單來說就是修改類和類方法的語法糖,很多面向?qū)ο笳Z言都有裝飾器這一特性。本文就來說說如何在JavaScript中使用裝飾器,需要的可以參考一下
    2022-10-10
  • SOSO地圖API使用(一)在地圖上畫圓實現(xiàn)思路與代碼

    SOSO地圖API使用(一)在地圖上畫圓實現(xiàn)思路與代碼

    最近在做SOSO地圖相關(guān)開發(fā),遇到相關(guān)畫圓知識,特此簡單記錄下來,接下來講解如何在在地圖上畫圓,感興趣的朋友可以了解下
    2013-01-01
  • 深入理解js A*尋路算法原理與具體實現(xiàn)過程

    深入理解js A*尋路算法原理與具體實現(xiàn)過程

    這篇文章主要介紹了js A*尋路算法原理與具體實現(xiàn)過程,結(jié)合實例形式詳細分析了A*尋路算法的具體概念、原理、實現(xiàn)方法與相關(guān)操作技巧,需要的朋友可以參考下
    2018-12-12
  • Javascript writable特性介紹

    Javascript writable特性介紹

    這篇文章主要介紹了Javascript writable特性介紹,本文用淺顯易懂的語言講解了writable的特性,需要的朋友可以參考下
    2015-02-02
  • JavaScript繼承模式粗探

    JavaScript繼承模式粗探

    之前提到了JS中比較簡單的設(shè)計模式,在各種設(shè)計模式中被最常使用的工具之一就是原型鏈的繼承。作為OOP的特質(zhì)之一——繼承,今天主要談?wù)凧S中比較簡單的繼承方法
    2016-01-01
  • 使用JavaScript italics方法實現(xiàn)文本變斜體教程示例

    使用JavaScript italics方法實現(xiàn)文本變斜體教程示例

    這篇文章主要為大家介紹了JavaScript italics實現(xiàn)文本變斜體教程示例,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-12-12
  • JavaScript實現(xiàn)獲取兩個排序數(shù)組的中位數(shù)算法示例

    JavaScript實現(xiàn)獲取兩個排序數(shù)組的中位數(shù)算法示例

    這篇文章主要介紹了JavaScript實現(xiàn)獲取兩個排序數(shù)組的中位數(shù)算法,涉及javascript數(shù)組遍歷及數(shù)值計算相關(guān)操作技巧,需要的朋友可以參考下
    2019-02-02

最新評論

长兴县| 惠东县| 鄯善县| 苍溪县| 赞皇县| 开封市| 渝中区| 丹凤县| 舞阳县| 商城县| 池州市| 洞头县| 襄垣县| 巴彦淖尔市| 林口县| 蓝山县| 保康县| 牡丹江市| 乳山市| 上高县| 克什克腾旗| 万源市| 高安市| 北宁市| 乌鲁木齐市| 六枝特区| 广汉市| 翼城县| 旺苍县| 巢湖市| 正蓝旗| 台山市| 安庆市| 西丰县| 黔江区| 维西| 龙口市| 克山县| 阳新县| 双江| 井冈山市|