事件冒泡、事件捕获和事件委托

浅淡事件冒泡、事件捕获和事件委托

先来说下事件冒泡和事件捕获的机制由来。

事件冒泡和事件捕获分别由微软和网景公司提出,这两个概念都是为了解决页面中事件流(事件发生顺序)的问题,后来由W3C决定这两个事件都存在,事件流触发顺序是先触发事件捕获,然后再决定触发冒泡(再决定的意思的可以阻止事件冒泡),我理解的意思冒泡就是从一个泡泡从水底慢慢到水面的过程,捕获是冒泡的倒叙。

下面用代码来演示下过程分别是grandpa father son 三个层级元素

<style>
        div{ display: flex; justify-content: center; align-items: center; }
        .grandpa{ background: #b15959; width: 200px;  height: 200px; border-radius: 50%;  }
        .father{ background: green; width: 150px; height: 150px; border-radius: 50%; }
        .son{ background: lightgreen; width: 100px; height: 100px; border-radius: 50%; }
</style>
<div class="grandpa">
    <div class="father">
        <div class="son"></div>
    </div>
</div>

 

 

 

1事件冒泡(IE的微软提出来的事件流)

就是当我触发一个事件的时候,事件会从最内层的元素开始发生,一直向上传播,直到document对象。当我们点击了son,触发顺序是son > father > grandpa >document

 <script>
        const son = document.querySelector('.son')
        const father = document.querySelector('.father')
        const grandpa = document.querySelector('.grandpa')
        son.addEventListener('click',clickDeal)
        father.addEventListener('click',clickDeal)
        grandpa.addEventListener('click',clickDeal)
        function clickDeal(e){
            console.log(this)
        }
    </script>

我能通多监听每个div的点击事件这个监听是以事件冒泡进行监听的

 

 

 

点击之后依次出现的是 son > father >grandpa 

element.addEventListener(event, function, useCapture)

 

addEventListener方法用来为一个特定的元素绑定一个事件处理函数,是JavaScript中的常用方法,其传入三个参数,分别是‘没有on的事件类型’,‘事件处理函数’,‘控制事件阶段’,第三个参数是boolean类型,默认是false,表示在事件冒泡的阶段调用事件处理函数,像上图中传入true,就表示在事件捕获的阶段调用事件处理函数。

 

 

2事件捕获(网景提出来的事件流)

与事件冒泡相反,事件会从最外层开始发生,直到最具体的元素。当一个元素触发事件后会先从document开始捕获,只但触发这个事件流的具体元素 document > groundpa >father > son

<script>
        const son = document.querySelector('.son')
        const father = document.querySelector('.father')
        const grandpa = document.querySelector('.grandpa')
        son.addEventListener('click',clickDeal,true)
        father.addEventListener('click',clickDeal,true)
        grandpa.addEventListener('click',clickDeal,true)
        function clickDeal(e){
            console.log(this)
        }
    </script>

 

 修改它事件流为捕获触发顺序即grandpa >father >son

 3事件委托(事件代理)

事件代理(Event Delegation),又称之为事件委托。是JavaScript中常用绑定事件的常用技巧。顾名思义,“事件代理”即是把原本需要绑定在子元素的响应事件(click、keydown......)委托给父元素,让父元素担当事件监听的职务。事件代理的原理是DOM元素的事件冒泡。
实现方式:通过给父节点添加监听

优点:

1.大量减少内存占用,减少事件注册。

2.新增元素实现动态绑定事件

需求给li添加点击事件

没有使用事件代理

<div>
        <ul>
            <li>第一项</li>
            <li>第二项</li>
            <li>第三项</li>
        </ul>
    </div>
    <script>
        const liArray = document.querySelectorAll('li')
        //
        liArray.forEach(item=>{
            item.addEventListener('click',function(){
                console.log(this)},false)
        })

    </script>

需要给每个li添加监听事件,

下面使用事件代理

 <div>
        <ul>
            <li>第一项</li>
            <li>第二项</li>
            <li>第三项</li>
        </ul>
    </div>
    <script>
        const ul = document.querySelector('ul')
        ul.addEventListener('click',function(){
                //获取对应的元素进项操作
                },false)
    </script>

 

posted @ 2020-03-07 15:53  GQiangQ  阅读(421)  评论(0编辑  收藏  举报