热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

JavaScript事件委托的详细介绍(附代码)

​本篇文章给大家带来的内容是关于JavaScript事件委托的详细介绍(附代码),有一定的参考价值,有需要的朋友可以参考一下,希望对你有所帮助。
本篇文章给大家带来的内容是关于Javascript事件委托的详细介绍(附代码),有一定的参考价值,有需要的朋友可以参考一下,希望对你有所帮助。

事件委托(又名事件代理),就是利用事件冒泡,只指定一个事件处理程序,就可以管理某一类型的所有事件。

网上有关于事件委托的一个“取快递”例子,十分生动,这里我对它作一些修改和拓展,然后通过程序来说明事件委托的机制。

某公司有三位员工,他们的快递收件地址为公司,每当有快递送达时,快递员拨打其电话进行通知,他们接到电话后去取件。

员工ID员工名称联系方式
A111111
B222222
C333333
对应到页面,就是每个员工是一个标记:
  • 员工甲
  • 员工乙
  • 员工丙

每位员工接电话取快递的行为就是一个个事件,这里我们假设收取快递行为对应着onclick事件:

A.Onclik= function() {
    收取快递;
};
B.Onclick= function() {
    收取快递;
};
C.Onclick= function() {
    收取快递;
};

以上的实现,通常为通过循环遍历每一个员工,为其增加事件:

/*程序1*/
var aUl = document.getElemengtByID("前台工作人员");
var aLi = aUl.getElemengtsByTagName("li");
for (var i = 0; i 

可以看到,为每个员工都设置一个事件,会产生冗余代码,占用内存,同时会进行多次DOM操作(与DOM节点进行交互),影响页面运行性能。

“减少DOM操作是性能优化的主要思想之一”

于是,我们理所当然地想到:为什么不能让前台工作人员帮我们签收快递呢?

  • 员工甲
  • 员工乙
  • 员工丙
/*程序2*/ var tel = document.getElementById("前台工作人员"); tel.Onclick= function() { 收取快递; }

假设此时快递员打电话通知员工甲取件(onclick),但员工甲的DOM节点

  • 并无对应事件(onclick),所以这个事件会“冒泡”到
  • 的父元素
      ,发现
        上有onclick处理事件,于是触发该事件,由前台工作人员收取快递。

        可以看到,这样一来,不仅缩减代码量,同时与DOM节点的交互次数也得到了缩减。

        还有一个优点:当增加新的DOM节点时,自动携带父元素的事件效果。也就是说,当有一个新员工丁来公司后,前台工作人员会直接帮他收取快递,而无需专门为他设置事件。

        例如,当新员工丁来到公司后:

        ...
        
        ...
        
        ...
        /*程序3*/
        var aBtn = document.getElementById("btn");
        aBtn.Onclick= function() {
            var aLi = document.createElement("li");
            oLi.innerHTML = "员工丁";
            aUl.appendChild(aLi);
        }
        ...

        在不使用事件委托的程序中,新增的员工丁是没有事件的,我们需要用一个函数包含住程序1:

        /*程序4*/
        function pro1() {
            var aUl = document.getElemengtByID("前台工作人员");
            var aLi = aUl.getElemengtsByTagName("li");
            for (var i = 0; i 

        然后在新增新员工丁的程序的末尾执行这个函数:

        /*程序5*/
        var aBtn = document.getElementById("btn");
        aBtn.Onclick= function() {
            ...
            pro1();
        }

        这样做的缺点是显而易见的:DOM节点交互次数成倍增加。
        若我们采用事件委托机制来实现,就不会存在这个问题,子元素节点的onclick事件会直接在父元素节点得到执行。

        到这里,我们会想到:对于同一种事件来说,使用事件委托将其放置在父元素节点上固然很方便。但如果对于不同的子元素节点要执行不同的事件呢,还能使用事件委托吗?

        答案是肯定的。

        例如上述三位公司员工,总是使用固定品牌的快递:

        • 员工甲因为便宜,喜欢使用申通快递,申通只送到园区大门;
        • 员工乙是京东会员,总是购买京东自营商品,京东快递送到楼下;
        • 员工丙是顺丰VIP,顺丰快递会送到送到所在楼层大厅。

        他们三位在接到电话后,前台工作人员需要去不同的地方取件,对于不使用事件委托的程序,需要对每个人设置独特的处理事件:

        var A = document.getElementById("A");
        var B = document.getElementById("B");
        var C = document.getElementById("C");
        
        A.Onclick= function() {
            去园区大门取快递;
        }
        B.Onclick= function() {
            去楼下取快递;
        }
        C.Onclick= function() {
            去本层大厅取快递;
        }

        至少需要三次DOM操作,而且为每一个对应节点都设置了事件函数。

        而若采用事件委托:

        var aUl = document.getElemengtByID("前台工作人员");
        aUl.Onclick= function (ev) {
            var target = ev || window.event; /*兼容浏览器*/
            var target = ev.target || ev.srcElement; /*兼容浏览器*/
            if (target.nodeName.toLocaleLowerCase() == "li") {
                switch(target.id) {
                    case "A" :
                        去园区大门取快递;
                        break;
                    case "B" :
                        去楼下取快递;
                        break;
                    case "C" :
                        去本层大厅取快递;
                        break;
                }
            }
        }

        这样一来,DOM操作就只有一次,其他的操作都在JS内进行,可以有效提升网页性能。

        以上便是JS事件委托的基本思想。简而言之,就是利用事件冒泡这一特点,来对事件进行管理,减少冗余代码,减少不必要的创建,减少交互操作以节约内存和提高性能。

        事件冒泡

        事件冒泡是当触发某个DOM元素节点时,若该节点没有对应事件,则检查其父元素是否有对应事件,若有,则执行,若没有,继续向上检查。与其对应的还有事件捕获

        以上就是Javascript事件委托的详细介绍(附代码)的详细内容,更多请关注 第一PHP社区 其它相关文章!


  • 推荐阅读
    • 本文内容为asp.net微信公众平台开发的目录汇总,包括数据库设计、多层架构框架搭建和入口实现、微信消息封装及反射赋值、关注事件、用户记录、回复文本消息、图文消息、服务搭建(接入)、自定义菜单等。同时提供了示例代码和相关的后台管理功能。内容涵盖了多个方面,适合综合运用。 ... [详细]
    • 如何实现织梦DedeCms全站伪静态
      本文介绍了如何通过修改织梦DedeCms源代码来实现全站伪静态,以提高管理和SEO效果。全站伪静态可以避免重复URL的问题,同时通过使用mod_rewrite伪静态模块和.htaccess正则表达式,可以更好地适应搜索引擎的需求。文章还提到了一些相关的技术和工具,如Ubuntu、qt编程、tomcat端口、爬虫、php request根目录等。 ... [详细]
    • Monkey《大话移动——Android与iOS应用测试指南》的预购信息发布啦!
      Monkey《大话移动——Android与iOS应用测试指南》的预购信息已经发布,可以在京东和当当网进行预购。感谢几位大牛给出的书评,并呼吁大家的支持。明天京东的链接也将发布。 ... [详细]
    • 本文介绍了lua语言中闭包的特性及其在模式匹配、日期处理、编译和模块化等方面的应用。lua中的闭包是严格遵循词法定界的第一类值,函数可以作为变量自由传递,也可以作为参数传递给其他函数。这些特性使得lua语言具有极大的灵活性,为程序开发带来了便利。 ... [详细]
    • GetWindowLong函数
      今天在看一个代码里头写了GetWindowLong(hwnd,0),我当时就有点费解,靠,上网搜索函数原型说明,死活找不到第 ... [详细]
    • 本文介绍了在开发Android新闻App时,搭建本地服务器的步骤。通过使用XAMPP软件,可以一键式搭建起开发环境,包括Apache、MySQL、PHP、PERL。在本地服务器上新建数据库和表,并设置相应的属性。最后,给出了创建new表的SQL语句。这个教程适合初学者参考。 ... [详细]
    • 基于layUI的图片上传前预览功能的2种实现方式
      本文介绍了基于layUI的图片上传前预览功能的两种实现方式:一种是使用blob+FileReader,另一种是使用layUI自带的参数。通过选择文件后点击文件名,在页面中间弹窗内预览图片。其中,layUI自带的参数实现了图片预览功能。该功能依赖于layUI的上传模块,并使用了blob和FileReader来读取本地文件并获取图像的base64编码。点击文件名时会执行See()函数。摘要长度为169字。 ... [详细]
    • 本文介绍了使用Java实现大数乘法的分治算法,包括输入数据的处理、普通大数乘法的结果和Karatsuba大数乘法的结果。通过改变long类型可以适应不同范围的大数乘法计算。 ... [详细]
    • HDU 2372 El Dorado(DP)的最长上升子序列长度求解方法
      本文介绍了解决HDU 2372 El Dorado问题的一种动态规划方法,通过循环k的方式求解最长上升子序列的长度。具体实现过程包括初始化dp数组、读取数列、计算最长上升子序列长度等步骤。 ... [详细]
    • 本文讨论了Alink回归预测的不完善问题,指出目前主要针对Python做案例,对其他语言支持不足。同时介绍了pom.xml文件的基本结构和使用方法,以及Maven的相关知识。最后,对Alink回归预测的未来发展提出了期待。 ... [详细]
    • 本文讨论了如何优化解决hdu 1003 java题目的动态规划方法,通过分析加法规则和最大和的性质,提出了一种优化的思路。具体方法是,当从1加到n为负时,即sum(1,n)sum(n,s),可以继续加法计算。同时,还考虑了两种特殊情况:都是负数的情况和有0的情况。最后,通过使用Scanner类来获取输入数据。 ... [详细]
    • Ihavethefollowingonhtml我在html上有以下内容<html><head><scriptsrc..3003_Tes ... [详细]
    • Javascript中带有加号 - 减号(±)的极坐标曲线方程 - Polar curve equation with plus-minus sign (±) in Javascript
      IamtryingtodrawpolarcurvesonHTMLcanvasusingJavascript.WhatshouldIdowhenIwanttoco ... [详细]
    • 前言对于从事技术的人员来说ajax是这好东西,都会使用,而且乐于使用。但对于新手,开发一个ajax实例,还有是难度的,必竟对于他们这是新东西。leo开发一个简单的ajax实例,用的是 ... [详细]
    • Itwasworkingcorrectly,butyesterdayitstartedgiving401.IhavetriedwithGooglecontactsAPI ... [详细]
    author-avatar
    冷漠自逍遥2602897565
    这个家伙很懒,什么也没留下!
    PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
    Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有