Js一些冷门的高级方法(持续更新)

文章目录

  • getBoundingClientRect()
  • createNodeIterator()
  • requestAnimationFrame()

getBoundingClientRect()

getBoundingClientRect() 是一个用于获取元素位置和尺寸信息的方法。它返回一个 DOMRect对象,其提供了元素的大小及其相对于视口的位置,其中包含了以下属性:

  • x:元素左边界相对于视口的 x 坐标。
  • y:元素上边界相对于视口的 y 坐标。
  • width:元素的宽度。 height:元素的高
  • top:元素上边界相对于视口顶部的距
  • right:元素右边界相对于视口左侧的距离。
  • bottom:元素下边界相对于视口顶部的距离。
  • left:元素左边界相对于视口左侧的距离。
const box = document.getElementById('box');
const rect = box.getBoundingClientRect();

console.log(rect.x);        // 元素左边界相对于视口的 x 坐标
console.log(rect.y);        // 元素上边界相对于视口的 y 坐标
console.log(rect.width);    // 元素的宽度
console.log(rect.height);   // 元素的高度
console.log(rect.top);      // 元素上边界相对于视口顶部的距离
console.log(rect.right);    // 元素右边界相对于视口左侧的距离
console.log(rect.bottom);   // 元素下边界相对于视口顶部的距离
console.log(rect.left);     // 元素左边界相对于视口左侧的距离

对应属性看下图:
Js一些冷门的高级方法(持续更新)_第1张图片
场景:
这个方法通常用于需要获取元素在视口中的位置和尺寸信息的场景,比如实现拖拽、定位或响应式布局等,兼容性很好,一般用滚动事件比较多。
特殊场景会用上,比如你登录了淘宝的网页,当你下拉滑块的时候,下面的图片不会立即加载出来,有一个懒加载的效果。当上面一张图片没在可视区内时,就开始加载下面的图片。
下面代码就是判断一个容器是否出现在可视窗口内:

 
 const box = document.getElementById('box')
 window.onscroll = function () {//window.addEventListener('scroll',()=>{})
  console.log(checkInView(box));
 }

function checkInView(dom) {
const { top, left, bottom, right } = dom.getBoundingClientRect();
 return top > 0 &&
        left > 0 &&
        bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
       right <= (window.innerWidth || 
       document.documentElement.clientWidth)
        }

当容器在可视区域内就输出true,否则就是false。

createNodeIterator()

createNodeIterator() 方法是 DOM API 中的一个方法,用于创建一个 NodeIterator 对象,可以用于遍历文档树中的一组 DOM 节点。

通俗一点来讲就是它可以遍历 DOM 结构,把 DOM 变成可遍历的。
比较偏的面试考点
这种方法算是一个比较偏的面试考点,面试官问你怎样实现遍历 DOM 结构?其实就可以用到这个方法。但是大多数程序员答不上来这个问题,因为我们在日常开发中这个方法用得极少。这个方法常在框架源码中体现。

// An highlighted block
var foo = 'bar';

应用

<body>
    <div id="app">
        <p>hello</p>
        <div class="title">标题</div>
        <div>
            <div class="content">内容</div>
        </div>
    </div>

    <script>
        const body = document.getElementsByTagName('body')[0]
        const item = document.createNodeIterator(body)//让body变成可遍历的
        let root = item.nextNode() // 下一层

        while (root) {
            console.log(root);
            if (root.nodeType !== 3) {
                root.setAttribute('data-index', 123)//给每个节点添加一个属性
            }
            root = item.nextNode()
        }
    </script>
</body>

上面代码成功遍历到了各个 DOM 结构:
Js一些冷门的高级方法(持续更新)_第2张图片

并且在每个 DOM 节点上都添加了data-index = “123”。

requestAnimationFrame()

requestAnimationFrame方法相对使用较多。requestAnimationFrame() 是一个用于在下一次浏览器重绘之前调用指定函数的方法,它是 HTML5 提供的 API。
与setInterval和setTimeout
requestAnimationFrame的调用频率通常为每秒60次。这意味着我们可以在每次重绘之前更新动画的状态,并确保动画流畅运行,而不会对浏览器的性能造成影响。
setInterval与setTimeout它可以让我们在指定的时间间隔内重复执行一个操作,不会考虑浏览器的重绘,而是按照指定的时间间隔执行回调函数,可能会被延迟执行,从而影响动画的流畅度。

设置了两个容器,分别用requestAnimationFrame()方法和setTimeout方法进行平移效果,Js 代码如下所示:

   let distance = 0
        let box = document.getElementById('box')
        let box2 = document.getElementById('box2')

        window.addEventListener('click', function () {

         requestAnimationFrame(function move() {
         box.style.transform = `translateX(${distance++}px)`
         requestAnimationFrame(move)//递归
          })

        setTimeout(function change() {
         box2.style.transform = `translateX(${distance++}px)`
         setTimeout(change, 17)
            }, 17)

        })

自己跑一下代码,仔细能看出确实下面的图形平移没有上面图形流畅,用setTimeout会有卡顿现象。

你可能感兴趣的:(javascript,前端,开发语言)