浏览器渲染机制和crp优化(2)

145 阅读1分钟

1、改变元素样式

<!DOCTYPE html>
<html>

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title></title>
</head>

<body>
    <div id="box"></div>
</body>

</html>
<style>
    #box {
        width: 30px;
        height: 30px;
        background: red;
    }
</style>
<script>
    setTimeout(() => {
        let box = document.querySelector('#box');
        box.style.width = '100px';
        box.style.height = '100px';
    }, 1000);
</script>

2、集中改变元素样式 (1)box.style.cssText

   <script>
    setTimeout(() => {
        let box = document.querySelector('#box');
        box.style.cssText = "width:100px;height:100px;";
    }, 1000);
  </script>

(2)box.className = 'big';

   <style>
    #box {
        width: 30px;
        height: 30px;
        background: red;
    }
    .big{
        width: 100px !important;
        height: 100px !important;
    }
   </style>
    <script>
        setTimeout(() => {
            let box = document.querySelector('#box');
            box.className="big"
        }, 1000);
    </script>
  

3、新版本浏览器机制:渲染队列机制

let box = document.querySelector('#box');
box.style.width = '100px';
console.log(box.style.width); //获取样式:style.xxx/getComputedStyle/getBoundingClientRect/clientWidth.../offsetWidth.../scrollWidth...  刷新浏览器渲染队列
box.style.height = '100px'; //这里执行完,下面没有修改样式的代码了 ,也会触发刷新渲染队列

4、读写分离

(1)我们尽量把设置样式和获取样式分开

box.style.width = '100px';
box.style.height = '100px';
console.log(box.style.width);

(2) 我们要在原来的基础上改变样式

 + 非读写分离方式 
  box.style.width = parseFloat(window.getComputedStyle(box)['width']) + 100 + 'px';
  box.style.height = parseFloat(window.getComputedStyle(box)['height']) + 100 + 'px';
  
  
 + 读写分离方式
let prevW = parseFloat(window.getComputedStyle(box)['width']),
    prevH = parseFloat(window.getComputedStyle(box)['height']);
  box.style.width = prevW + 100 + 'px';
  box.style.height = prevH + 100 + 'px';
  

5、轮播图

(1)本来我们设想的是这样去实现(但是运行发现实现不了因为浏览器的渲染队列机制)

<!DOCTYPE html>
<html>

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title></title>
</head>

<body>
    <div class="container">
        <div class="wrapper">
            <div class="slide">
                <img src="images/1.jpg" alt="">
            </div>
            <div class="slide">
                <img src="images/2.webp" alt="">
            </div>
            <div class="slide">
                <img src="images/3.webp" alt="">
            </div>
            <div class="slide">
                <img src="images/4.webp" alt="">
            </div>
            <!-- 克隆 -->
            <div class="slide">
                <img src="images/1.jpg" alt="">
            </div>
        </div>
    </div>
</body>

</html>
<style>
    * {
        margin: 0;
        padding: 0;
    }

    .container {
        position: relative;
        width: 800px;
        height: 300px;
        margin: 20px auto;
        overflow: hidden;
    }

    .container .wrapper {
        position: absolute;
        top: 0;
        left: 0;
        z-index: 10;
        width: 4000px;
        height: 300px;
        display: flex;
        justify-content: flex-start;
        align-items: center;
        /* 动画 */
        transition: left .3s linear 0s;
    }

    .container .wrapper .slide {
        width: 800px;
        height: 300px;
    }

    .container .wrapper .slide img {
        display: block;
        width: 800px;
        height: 300px;
    }
</style>
<script>

    let wrapper = document.querySelector('.wrapper')
    step = 0,
        timer = null

    timer = setInterval(function () {
        step++
        if (step >= 5) {
            wrapper.style.transition = 'left 0s';
            wrapper.style.left = 0
            step = 1
        }
        wrapper.style.transition = `left .3s`
        wrapper.style.left = `-${step * 800}px`
    }, 2000)



</script>

(2)修改使其实现

 <script>

    let wrapper = document.querySelector('.wrapper')
    step = 0,
        timer = null

    timer = setInterval(function () {
        step++
        if (step >= 5) {
            wrapper.style.transition = 'left 0s';
            wrapper.style.left = 0
            wrapper.offsetLeft  //加上这个会触发dom的回流
            step = 1
        }
        wrapper.style.transition = `left .3s`
        wrapper.style.left = `-${step * 800}px`
    }, 2000)



</script>

6、文档碎片 (1)这种方式创建会触发10次dom的回流

<style>
    #box {
        height: 30px;
        display: flex;
    }

    #box span {
        width: 30px;
        height: 30px;
    }

    #box span:nth-child(even) {
        background: red;
    }
</style>
<script>
    setTimeout(() => {
        let box = document.getElementById('box')
        for (var i = 0;i < 10;i++) {
            var span = document.createElement('span')
            span.innerHTML = i
            box.appendChild(span)
        }
    }, 1000);
</script>

(2)字符串拼接方式

 <script>
    let box = document.getElementById('box')
    let str = ``
    for (var i = 0;i < 10;i++) {
        str += `<span>${i + 1}</span>`
        box.innerHTML = str
    }
</script>

(3)文档碎片

<script>
    let box = document.getElementById('box')
    let frag = document.createDocumentFragment()
    let str = ``
    for (var i = 0;i < 10;i++) {
        var span = document.createElement('span')
        span.innerHTML = i + 1
        frag.appendChild(span)
    }
    box.appendChild(frag)
</script>