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

JavaScript判斷元素是否在可視區(qū)域的三種方法

 更新時間:2023年12月07日 09:58:27   作者:WebGirl  
這這篇文章給大家總結(jié)了JavaScript判斷元素是否在可視區(qū)域的三種方法,getBoundingClientRect,IntersectionObserver和offsetTop、scrollTop這三種方法,文中通過代碼示例給大家介紹的非常詳細(xì),需要的朋友可以參考下

方法1:getBoundingClientRect

用法

let domRect = dom.getBoundingClientRect();

DOMRect:{
  x/left:視圖原點(左上角)距離dom左邊框距離,
  y/top:視圖原點(左上角)距離dom上邊框距離,
    right:視圖原點(左上角)距離dom右邊框距離,
    bottom:視圖原點(左上角)距離dom底邊框距離,
    width:dom的寬度,標(biāo)準(zhǔn)盒模型,width = 寬度+padding+border;怪異盒模型,width = 設(shè)置的寬度,
    height:dom的高度,
}

所以我們可以根據(jù)DOMRect的中的各個屬性來判斷dom是否在可視區(qū)域內(nèi)。

eg:

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>getBoundingClientRect可視區(qū)域</title>
  <style>
    * {
      margin: 0
    }
    .circle-wrap {
      position: fixed;
      top: 50px;
      right: 50px;
      padding: 10px;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      width: 140px;
      background: #fff;
    }

    .circle-wrap .circle {
      display: inline-block;
      width: 20px;
      height: 20px;
      border-radius: 50%;
      background: red;
    }

    .card-wrap {
      height: 2000px;
      width: 3000px;
      margin-top: 100px;
    }

    .card-wrap .card {
      width: 200px;
      height: 200px;
      padding: 20px;
      box-sizing: border-box;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      margin-top: 500px;
      margin-left: 500px;
    }
  </style>
</head>

<body>
  <div class="circle-wrap">
    <span>當(dāng)下方的卡片在可視區(qū)域內(nèi),我的圈圈是綠色,否則是紅色</span>
    <span class="circle"></span>
  </div>
  <div class="card-wrap">
    <div class="card">我是一個卡片</div>
  </div>
  <script src="https://cdn.bootcdn.net/ajax/libs/lodash.js/4.17.20/lodash.js"></script>
  <script>
    const card = document.querySelector(".card");
    const circle = document.querySelector(".circle");
    const getBoundingClientRectJudge = () => {
      let domRect = card.getBoundingClientRect();
      console.log(domRect)
      let ch = document.documentElement.clientHeight;
      let cw = document.documentElement.clientWidth;
      let isInsert = true;
      if (domRect.bottom < 0 || domRect.top > ch || domRect.right < 0 || domRect.left > cw) {
        isInsert = false;
      }
      let background = null
      if (isInsert) {
        background = "green"
      } else {
        background = "red"
      }
      circle.style.background = background
    }
    window.addEventListener("scroll", _.throttle(getBoundingClientRectJudge, 500))
    getBoundingClientRectJudge()
  </script>
</body>

</html>

效果圖:

問題

getBoundingClientRect并不能滿足所有情況,甚至說,它只能滿足一種情況的判斷,那就是需要判斷的那個dom節(jié)點,它只身處在一個滾動條的情況下。什么意思呢,就是它所有的祖先節(jié)點,加起來的滾動條只有1個,如果它父節(jié)點有滾動條,父父節(jié)點也有滾動條,那這種方法就不好用了,請看示例:

下面展示的結(jié)果是錯誤的,圈圈應(yīng)該是紅色才對。

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>getBoundingClientRect可視區(qū)域</title>
  <style>
    * {
      margin: 0
    }

    body {
      height: 2000px;
      width: 3000px;
    }

    .circle-wrap {
      position: fixed;
      top: 50px;
      right: 50px;
      padding: 10px;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      width: 140px;
      background: #fff;
    }

    .circle-wrap .circle {
      display: inline-block;
      width: 20px;
      height: 20px;
      border-radius: 50%;
      background: red;
    }

    .card-wrap {
      height: 400px;
      width: 600px;
      margin-top: 100px;
      margin-left: 100px;
      border: 1px solid green;
      overflow: auto;
    }

    .card-wrap .card {
      width: 200px;
      height: 200px;
      padding: 20px;
      box-sizing: border-box;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      margin-top: 500px;
      margin-left: 500px;
    }

    .head {
      width: 100%;
      height: 100px;
      background: pink;
      /* position: fixed; */
      top: 0;
      left: 0;
    }
  </style>
</head>

<body>
  <!-- <div class="head"></div> -->
  <div class="circle-wrap">
    <span>當(dāng)下方的卡片在可視區(qū)域內(nèi),我的圈圈是綠色,否則是紅色</span>
    <span class="circle"></span>
  </div>
  <div class="card-wrap">
    <div class="card">我是一個卡片</div>
  </div>
  <script src="https://cdn.bootcdn.net/ajax/libs/lodash.js/4.17.20/lodash.js"></script>
  <script>
    const card = document.querySelector(".card");
    const circle = document.querySelector(".circle");
    const getBoundingClientRectJudge = () => {
      let domRect = card.getBoundingClientRect();
      let ch = document.documentElement.clientHeight;
      let cw = document.documentElement.clientWidth;
      let isInsert = true;
      if (domRect.bottom < 0 || domRect.top > ch || domRect.right < 0 || domRect.left > cw) {
        isInsert = false;
      }
      let background = null
      if (isInsert) {
        background = "green"
      } else {
        background = "red"
      }
      circle.style.background = background
    }
    window.addEventListener("scroll", _.throttle(getBoundingClientRectJudge, 500))
    getBoundingClientRectJudge()
  </script>
</body>

</html>

由此,我們引出第二種方法,IntersectionObserver。

方法2:IntersectionObserver

用法

eg:

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>getBoundingClientRect可視區(qū)域</title>
  <style>
    * {
      margin: 0
    }

    body {
      height: 2000px;
      width: 3000px;
    }

    .circle-wrap {
      position: fixed;
      top: 50px;
      right: 50px;
      padding: 10px;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      width: 140px;
      background: #fff;
    }

    .circle-wrap .circle {
      display: inline-block;
      width: 20px;
      height: 20px;
      border-radius: 50%;
      background: red;
    }

    .card-wrap {
      height: 400px;
      width: 600px;
      margin-top: 100px;
      margin-left: 100px;
      border: 1px solid green;
      overflow: auto;
    }

    .card-wrap .card {
      width: 200px;
      height: 200px;
      padding: 20px;
      box-sizing: border-box;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      margin-top: 500px;
      margin-left: 500px;
    }
    .head{
      width: 100%;
      height: 100px;
      background: pink;
      /* position: fixed; */
      top:0;
      left: 0;
    }
  </style>
</head>

<body>
  <!-- <div class="head"></div> -->
  <div class="circle-wrap">
    <span>當(dāng)下方的卡片在可視區(qū)域內(nèi),我的圈圈是綠色,否則是紅色</span>
    <span class="circle"></span>
  </div>
  <div class="card-wrap">
    <div class="card">我是一個卡片</div>
  </div>
  <script src="https://cdn.bootcdn.net/ajax/libs/lodash.js/4.17.20/lodash.js"></script>
  <script>
    const card = document.querySelector(".card");
    const circle = document.querySelector(".circle");
    const observer = new IntersectionObserver((changes) => {
      // changes是數(shù)組
      changes.forEach(one => {
        console.log(one)
        let isIntersecting = one.isIntersecting
        let background = null
        if (isIntersecting) {
          background = "green"
        } else {
          background = "red"
        }
        circle.style.background = background
      })
    })
    observer.observe(card)
    // console.log(observer)
    /* 取消觀察特定的元素:observer.unobserve(dom) */
    /* 對象停止監(jiān)聽目標(biāo) observer.disconnect() */
  </script>
</body>

</html>

補充說明

IntersectionObserver可以傳root,進一步判斷dom是相對于哪個節(jié)點,來判斷是否在可視區(qū)域內(nèi),默認(rèn)rootdocument。

const observer = new IntersectionObserver((changes) => {
      console.log(changes)
      changes.forEach(one => {
        console.log(one)
        let isIntersecting = one.isIntersecting
        let background = null
        if (isIntersecting) {
          background = "green"
        } else {
          background = "red"
        }
        circle.style.background = background
      })
    },{root:document.querySelector(".card-wrap")})

方法3:offsetTop、scrollTop

說明

  • offsetTop:元素的上外邊框至包含元素的上內(nèi)邊框之間的像素距離,其他方向相同
  • offsetWidth:元素兩端算上外邊框的寬度,其他方向相同
  • scrollLeftscrollTop:既可以確定當(dāng)前元素的滾動狀態(tài),也可以設(shè)置元素的滾動位置
  • scrollWidthscrollHeight:確定元素內(nèi)容的實際大小
  • clientWidth:元素內(nèi)容區(qū)寬度加上左右內(nèi)邊距寬度,即clientWidth = content + padding
  • clientHeight:元素內(nèi)容區(qū)高度加上上下內(nèi)邊距高度,即clientHeight = content + padding

使用

公式:

0 <= el.offsetTop - document.documentElement.scrollTop <= viewPortHeight

寫法:

function isInViePortOfOne(el){
    const viewPortHeight = window.innerHeight || document.documentElement.clientHeight||document.body.clientHeight
    const offsetTop = el.offsetTop;
    const scollTop = document.documentElement.scrollTop
    const top = offsetTop - scollTop;
    return top <= viewPortHeight && top >= 0
}

以上就是JavaScript判斷元素是否在可視區(qū)域的三種方法的詳細(xì)內(nèi)容,更多關(guān)于JavaScript判斷元素是否在可視區(qū)域的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • 開發(fā)跨瀏覽器的JavaScript方法說明

    開發(fā)跨瀏覽器的JavaScript方法說明

    IE是當(dāng)前瀏覽器的一個異類,不過解決方法倒也相當(dāng)簡單,使用Firefox和Safari 之 類的瀏覽時,可以使用元素的setArribute方法來設(shè)置元素的class屬性
    2008-08-08
  • postcss-pxtorem實現(xiàn)頁面自適應(yīng)的原理解析

    postcss-pxtorem實現(xiàn)頁面自適應(yīng)的原理解析

    postcss-pxtorem是一個PostCSS插件,用于將CSS中的像素值轉(zhuǎn)換為rem單位,以實現(xiàn)響應(yīng)式布局和適配不同屏幕尺寸的需求,本文給大家介紹postcss-pxtorem實現(xiàn)頁面自適應(yīng)的原理解析,感興趣的朋友一起看看吧
    2023-12-12
  • JavaScript中Object和Function的關(guān)系小結(jié)

    JavaScript中Object和Function的關(guān)系小結(jié)

    JavaScript 中 Object 和 Function 的關(guān)系是微妙的,他們互為對方的一個實例。
    2009-09-09
  • Javascript this 的一些學(xué)習(xí)總結(jié)

    Javascript this 的一些學(xué)習(xí)總結(jié)

    相信有C++、C#或Java等編程經(jīng)驗的各位,對于this關(guān)鍵字再熟悉不過了。由于Javascript是一種面向?qū)ο蟮木幊陶Z言,它和C++、C#或Java一樣都包含this關(guān)鍵字,接下來我們將向大家介紹Javascript中的this關(guān)鍵字
    2012-08-08
  • javascript動態(tài)創(chuàng)建表格及添加數(shù)據(jù)實例詳解

    javascript動態(tài)創(chuàng)建表格及添加數(shù)據(jù)實例詳解

    這篇文章主要介紹了javascript動態(tài)創(chuàng)建表格及添加數(shù)據(jù),以實例形式分析了javascript動態(tài)創(chuàng)建表格的常用方法,包括不兼容IE6與兼容IE6的實現(xiàn)方法,非常具有實用價值,需要的朋友可以參考下
    2015-05-05
  • css與javascript跨瀏覽器兼容性總結(jié)

    css與javascript跨瀏覽器兼容性總結(jié)

    這篇文章主要介紹了css與javascript跨瀏覽器兼容性,包括常見的css兼容性問題與javascript兼容性問題,以及IE與Firefox等常用瀏覽器的兼容性分析,需要的朋友可以參考下
    2014-09-09
  • js實現(xiàn)操作cookie的常見方法總結(jié)【創(chuàng)建、讀取、刪除】

    js實現(xiàn)操作cookie的常見方法總結(jié)【創(chuàng)建、讀取、刪除】

    這篇文章主要介紹了js實現(xiàn)操作cookie的常見方法,結(jié)合實例形式分析了js操作cookie創(chuàng)建、讀取、刪除相關(guān)實現(xiàn)技巧與注意事項,需要的朋友可以參考下
    2020-03-03
  • JavaScript初學(xué)者需要了解10個小技巧

    JavaScript初學(xué)者需要了解10個小技巧

    在之前的編程語言排行榜中,我們曾介紹過轉(zhuǎn)正在即的JavaScript語言,正如文章中闡明的那樣,JavaScript不僅是最具活力的腳本語言,還是是最有用的編程語言之一。
    2010-08-08
  • 學(xué)前端,css與javascript重難點淺析

    學(xué)前端,css與javascript重難點淺析

    JavaScript是一種屬于網(wǎng)絡(luò)的腳本語言,已經(jīng)被廣泛用于Web應(yīng)用開發(fā),CSS(Cascading Style Sheet)層疊樣式表單,今天給大家分享css與javascript重難點,感興趣的朋友一起看看吧
    2020-06-06
  • js如何引入wasm文件

    js如何引入wasm文件

    這篇文章主要介紹了js如何引入wasm文件問題,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-04-04

最新評論

奉节县| 北票市| 昔阳县| 凭祥市| 景宁| 乌拉特中旗| 峨眉山市| 介休市| 庆城县| 南皮县| 邹城市| 定结县| 土默特左旗| 平果县| 南澳县| 德江县| 米易县| 宁安市| 济南市| 新龙县| 临高县| 仪征市| 辽宁省| 青川县| 托克逊县| 蒙自县| 五大连池市| 平定县| 岫岩| 玛纳斯县| 沾化县| 通河县| 嵩明县| 辽宁省| 南召县| 延边| 鹤岗市| 茌平县| 铅山县| 新郑市| 泌阳县|