欢迎来到知了汇智!
联系电话:知了汇智-电话号码 028-62016472 / 13228113191

浅谈JavaScript事件冒泡和事件捕获-知了汇智

浅谈JavaScript事件冒泡和事件捕获

  首先咱们先聊聊事件冒泡:

  什么是事件冒泡

  事件冒泡:如果一个元素的事件被触发,那么他的所有父级元素的同名事件也会被依次触发
  元素->父元素->body->html->document->window
  事件冒泡一直存在,只不过以前我们没有给父级元素加同名事件

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title></title>
    <style>
        #box{
            width: 300px;
            height: 300px;
            background-color: hotpink;
            position: relative;
        }

        #son{
            width: 100px;
            height: 100px;
            position: absolute;

            left: 350px;
            top: 350px;

            background-color: yellowgreen;
        }
    </style>
</head>
<body>

<div id="box">
    <input type="button" value="点我" id="btn"/>

    <div id="son"></div>
</div>

</body>
</html>

<script>

    window.onclick = function () {

        alert("window被点击了");
    }

    document.onclick = function () {

        alert("文档被点击了");
    }

    document.documentElement.onclick = function () {

        alert("html被点击了");
    }

    document.body.onclick = function () {

        alert("body被点击了");
    }

    document.getElementById("box").onclick = function () {

        alert("我是骚粉的大盒子");
    };

    document.getElementById("btn").onclick = function () {

        alert("我是小按钮");
    };

    document.getElementById("son").onclick = function () {

        alert("我是又黄又绿的小盒子");
    };
</script>
 

  事件冒泡的好处

  事件冒泡好处:如果想给父元素的多个子元素添加事件,我们可以只需要给父元素添加事件即可,然后
  通过获取事件源(e.target)就可以得知是哪一个子元素触发了这个事件

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title></title>
</head>
<body>

<ul id="ul1">
    <li>隔壁老王1</li>
    <li>隔壁老王2</li>
    <li>隔壁老王3</li>
    <li>隔壁老王4</li>
    <li>隔壁老王5</li>
</ul>

</body>
</html>

<script>

    var ul = document.getElementById("ul1");

    //1.如果想给ul中的每一个li标签添加点击事件,以前的做法需要遍历ul的li标签逐个添加
    //    for (var i = 0; i < ul.children.length; i++) {
    //
    //        ul.children[i].onclick = function () {
    //
    //            alert(this.innerHTML);
    //        }
    //    }

    //2.使用时间冒泡:只需要给父元素添加点击事件即可
    ul.onclick = function (e) {

        e = e || window.event;

        var target = e.target || e.srcElement;

        console.log(target.innerHTML);

        //target:事件源:触发本次事件的源头
        alert(e.target.innerHTML);
    }

</script>


  事件冒泡的影响

  事件冒泡会导致需求冲突:例如我想要添加一个功能,弹出登录窗之后点击body空白区域让登陆窗消失
  此时a标签弹出登录窗的点击事件会触发body的点击事件,导致登陆窗一出来就消失
  阻止事件冒泡
  阻止事件冒泡:让同名事件不要在父元素中冒泡(触发)
  
* 说人话:点击一个元素只会触发当前元素的事件,不会触发父元素的同名事件
  语法: 事件对象.stopPropagation() IE8及之前不支持
  事件对象.cancelBubble = true IE8之前支持
  注意:如果想要阻止事件冒泡,一定要在触发事件的函数中接收事件对象

浅谈JavaScript事件冒泡和事件捕获

  事件捕获

  1.事件冒泡:从触发事件元素,一级一级往上找父元素触发同名事件,如果有就触发
  2.事件捕获:从最顶级的父元素一级一级往下找子元素触发同名事件,直到触发事件的元素为止
  事件捕获与事件冒泡触发事件的顺序完全相反
  3.事件捕获,只能通过addEventListener并且参数写true才是事件捕获
  其他都是冒泡(不是通过addEventListener添加、addEventListener参数为false)
  4.事件对象.stopPropagation() 除了可以阻止冒泡还可以阻止捕获
  5.IE8及以前没有捕获!

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title></title>
    <style>
        #box {
            width: 300px;
            height: 300px;
            background-color: hotpink;
            position: relative;
        }

        #son {
            width: 100px;
            height: 100px;
            position: absolute;

            left: 350px;
            top: 350px;

            background-color: yellowgreen;
        }
    </style>
</head>
<body>

<div id="box">

    <div id="son"></div>
</div>


</body>
</html>

<script>


    var box = document.getElementById("box");
    var son = document.getElementById("son");



    window.addEventListener("click", function () {
        alert("这是window");
    },true)


    document.addEventListener("click", function () {
        alert("这是document");
    },true)

    document.documentElement.addEventListener("click", function (e) {
        e = e || window.event;
        alert("这是html");
        e.stopPropagation();//阻止事件冒泡和事件捕获

    },true)

    document.body.addEventListener("click", function () {

        alert("这是body");

    },true)

    //参数3:默认是false,代表是支持事件冒泡
    box.addEventListener("click", function () {

        alert("这是box");
    },true)

    son.addEventListener("click", function () {

        alert("这是son");
    },true)

</script>
 

  事件的三个阶段

  1.事件一共有三个阶段:事件的执行顺序
  1--捕获阶段 :
  2--目标阶段 :
  3--冒泡阶段 :
  2.事件对象.eventPhase 可以获得触发这个事件时,到底是哪个阶段
  3.先从最顶级往下一级一级捕获,然后到目标的捕获,目标的冒泡,再一级一级往上冒泡
<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title>标题</title>
    <style>
        .one {
            width: 200px;
            height: 200px;
            background-color: pink;
        }
        .son {
            width: 100px;
            height: 100px;
            background-color: green;
            position: absolute;
            left: 250px;
            top: 250px;
        }
    </style>
</head>
<body>
<div class="one" id="box">
    <input type="button" value="按钮" id="btn"/>
    <div class="son" id="son"></div>
</div>

<script>
   
    var box = document.getElementById("box");
    var btn = document.getElementById("btn");
    var son = document.getElementById("son");

    document.addEventListener("click",function (e) {
        alert("document"+ e.eventPhase);
    },true) ;//true表示事件捕获,所以是阶段1,并且优先执行

    document.body.addEventListener("click", function (e) {
        alert("哈哈,我是body"+ e.eventPhase);
    },false);


    box.addEventListener("click",function (e) {
        alert("哈哈哈,我是粉色的盒子box..."+ e.eventPhase);
    },false);



    btn.addEventListener("click",function (e) {
        alert("哈哈哈,我是按钮btn..."+ e.eventPhase);
    },false);



    son.addEventListener("click",function (e) {
        alert("嘻嘻嘻,我是绿色的盒子son"+ e.eventPhase);

    },false);

</script>
</body>
</html>


       版权声明:本文来源于网络,由知了堂搜集整理,仅供大家学习前端时使用

132 2811 3191
预约免费试学
点击咨询
预约试学