Javascript 事件&冒泡机制(上)

Javascript 事件

导读

JS事件可以借助WPF路由事件来理解,因为早期浏览器是IE的天下,微软有很多关于渲染和js相关的专利,而WPF是微软推出的,很明显的使用了浏览器内核的编程设计。
与路由事件相同,JS事件也是一种用于元素树的事件。
文章地址:WPF路由事件
https://blog.csdn.net/qinzheng_chen/article/details/103056425

JS事件流

事件流的三个阶段
三个阶段的流程图
在这里插入图片描述

在这里插入图片描述

捕获阶段

捕获阶段处于事件流的第一阶段,该阶段的主要作用是捕获截取事件。在DOM中,该阶段始于Document,结束于body(当然,在现在的很多高版本浏览器中,该过程结束于目标元素,只不过不执行目标元素而已,这也体现了目标元素具有双重范围)。

目标阶段

目标阶段处于事件流的第二阶段,该阶段的主要作用是执行绑定事件。一般地,该阶段具有双重范围,即捕获阶段的结束,冒泡阶段的开始。

冒泡阶段

冒泡阶段处于事件流的第三阶段,该阶段的主要作用是将目标元素绑定事件执行的结果返回给浏览器,处理不同浏览器之间的差异,主要在该阶段完成。

事件冒泡

什么是事件冒泡

在一个对象上触发某类事件(比如单击onclick事件),如果此对象定义了此事件的处理程序,那么此事件就会调用这个处理程序,如果没有定义此事 件处理程序或者事件返回true,那么这个事件会向这个对象的父级对象传播,从里到外,直至它被处理(父级对象所有同类事件都将被激活),或者它到达了对 象层次的最顶层,即document对象(有些浏览器是window)。

打个比方说:你在地方法院要上诉一件案子,如果地方没有处理此类案件的法院,地方相关部门会帮你继续往上级法院上诉,比如从市级到省级,直至到中央法院,最终使你的案件得以处理。

事件冒泡有什么作用

(1)事件冒泡允许多个操作被集中处理(把事件处理器添加到一个父级元素上,避免把事件处理器添加到多个子级元素上),它还可以让你在对象层的不同级别捕获事件。
(2)让不同的对象同时捕获同一事件,并调用自己的专属处理程序做自己的事情,就像老板一下命令,各自员工做自己岗位上的工作去了。

Example

<body>
    <div class="father">
        <div class="son"></div>
    </div>
    <script>
        var fatherEle = document.querySelector('.father');
        var sonEle = document.querySelector('.son');
        var fHandler = function () {
            alert('father click');
        }
        var sHandler = function () {
            alert('son click');
        }
        //捕获阶段
        fatherEle.addEventListener('click', fHandler, true);
        sonEle.addEventListener('click', sHandler, true);

        //冒泡阶段
        fatherEle.addEventListener('click', fHandler, false);
        sonEle.addEventListener('click', sHandler, false);
    </script>
</body>

事件对象

事件对象通常写作event 或者e,event 对象代表事件的状态,比如键盘的按键状态,鼠标的位置,鼠标按钮的状态。事件发生后,跟事件相关的一系列信息数据的集合都放到这个对象里面

function fTest(e) {
            alert('other way');
            e = e || window.event;//为了兼容ie8以前的版本
            console.log(e);
        }

        //冒泡阶段
        fatherEle.addEventListener('click', fTest, false);
        sonEle.addEventListener('click', sHandler, false);

event

事件对象的常用属性

event常用的属性

阻止默认事件(链接不实现跳转或者按钮不提交)

<script>
        var aEle = document.querySelector('a');
        aEle.addEventListener('click',function(e){
            e.preventDefault();//dom 标准写法
            e.returnValue();// 低版本ie
            return false;//return false 可以阻止默认行为,但是return 后面的代码不执行了,而且仅仅限于传统的注册方式

        },false);
    </script>

阻止冒泡

e.target 、e.currentTarget 和this的区别

事件对象有一些非常关键的属性我们经常要用到,重点讲述一下其中的区别
Demo

<body>
    <div>
        <ul>
            <li>1</li>
            <li>2</li>
            <li>3</li>
        </ul>
    </div>
    <script>
        var ulEle = document.querySelector('ul');
        function showEventArg(e) {
            console.log(e.target);
            console.log(this);
            console.log(e.currentTarget);
        }
        ulEle.addEventListener('click', showEventArg, false);
    </script>
</body>
  • e.target 返回的是触发事件的对象
  • this 返回的是绑定事件的对象
  • e.target 是点击了那个元素就返回那个元素,this是那个元素绑定了点击事件就返回那个元素
  • currentTarget 等同于this
  • 如果没有冒泡机制 this 和target一定相同,因为事件无法传递出去,绑定的元素就是触发事件的元素
    返回结果

this 的指向的对象

没有学过后端语言的开发人员对对象的理解可能不是特别深刻,这里插入我的理解供参考。
this 官方解释是当前对象

  • case1:在全局作用域下,或者全局作用域函数中 this 指向window
    理解:我们知道全局变量都会变成window 对象的属性,所以,所有的全局变量和全局函数实际写法都是window.xx 因此,这种情况下,this 指向window
    需要特别注意定时器(window.setTimeout等)this 也指向window

  • case2: 对象的方法中 谁调用this 就指向谁

        var o = {
            sayHi:function (){
                console.log(this);
            }
        }
        o.sayHi();
  • case3 构造函数中的this 指向构造函数返回的实例。类的构造函数都是为了创建类的对象,this 就是指向这个新创建的对象的

总结&注意

Javascript 事件&冒泡机制(下)
https://blog.csdn.net/qinzheng_chen/article/details/115865561 ,下一篇重点说明事件处理程序和事件委托

  • onclick 和 attachEvent 只能支持冒泡阶段
  • addEventListener第三个参数如果是true ,表示在事件捕获阶段调用;如果是false(默认值是false),表示是冒泡阶段
  • 在实际开发中,我们很少使用事件捕获,我们更关注事件冒泡
  • 有些事件没有冒泡,比如onblur,onfocus,onmouseenter,onmouseleave
  • 8
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值