JS和JQuery中的事件委托 学习笔记

事件委托其实并不是一个很高级的技巧,比如在一个页面里面,当只存在两个按钮的时候,可能你给按钮添加监听是这样的:(本文不考虑浏览器兼容性,关于事件的兼容性可参考前面的学习笔记)

<div id="container">
    <button id="btn1">按钮1</button>
    <button id="btn2">按钮2</button>
</div>
var btn1 = document.getElementById("btn1");
var btn2 = document.getElementById("btn2");
btn1.addEventListener("click", clickHandler1);
btn2.addEventListener("click", clickHandler2);

当按钮越来越多的时候,甚至到了几十上百的时候,我相信很少有人会选择一个一个的添加事件,首先,其实事件处理函数每个都是对象,都会占用内存,创建的越多,内存开销越大,性能越差;其次,大量“重复”性的代码拥挤在脚本里,非常难以维护,也非常难看;还有,添加大量监听意味着要频繁访问DOM元素,延迟整个页面的访问时间。

事件委托就是解决这个问题的一个方案。我们知道,在DOM节点构成的DOM树中,子节点产生一个事件之后会逐级冒泡到父元素上:

事件委托就利用这一特性,只需给所有的按钮的父元素比如container添加一个事件,这样无论是哪个按钮,只要触发了绑定的事件都会冒泡到container上,我们只需判断是不是你想监听的按钮即可。

var container = document.getElementById("container");
container.addEventListener("click", function(e){
    //获取事件触发对象
    var target = e.target;
    if(target.id == "btn1"){
        alert("btn1");
    }else if(target.id == "btn2"){
        alert("btn2");
    }
});

这个方法还有一个明显的好处是你不必再问以后创建的元素添加监听。比如在上面的判断里添加

else if(target.id == "btn3"){
    alert("btn3");
}

添加这个事件处理程序的时候页面中还并没有btn3,但btn3很可能是由用户动态创建的,但不管用户什么时候创建,你都能在这个条件里捕获它。

JQuery里面的事件委托

其实在JQuery里,因为很容易创建一个JQuery集合,所以处理事件相对简单。

一、click函数、bind函数等:

$("a").click(function(){
    if($(this).hasClass("a1")){
        //...
    }else if(...){
        //...
    }
});

$("a").bind("click", function(){
    if($(this).hasClass("a1")){
        //...
    }else if(...){
        //...
    }
});

其实这个方法同样也是通过遍历所有a标签,给他们添加事件函数,但比原生js代码量要少很多。

二、live()

live和上面讲的原生js类似,不指定父元素的时候,将事件绑定在了document上,比如:

$(".link").live("click", function(){
    //...
});

当有事件冒泡到document上时,将检查事件是否为click事件,元素是否带有link的className,满足这两个条件则将触发事件处理函数。

除了默认绑定在document上,也可以绑定在指定父元素上:

$(".link", $("#container")).live("click", function(){
    //...
});

三、delegate

其实不管是live还是bind,他们的写法都很奇怪,我们讨论的事件委托都是给父元素添加的事件监听,但一直到现在都好像是在子元素上调用的方法,不过还好JQuery里面还有一个函数:delegate。

同样是绑定事件到.link筛选条件上,使用delegate方法如下:

$("#container").delegate(".link", "click", function(){
    //...
});

可以看到,我们在需要绑定的父元素(id名为container的元素)上调用的delegate方法,并传递三个参数:监听元素筛选条件、监听事件名、事件处理函数。

通过链式调用更加舒服:

$("#container").delegate(".link", "click", function(){
    //...
}).delegate(".btn", "click", function(){
    //...
}).delegate(".whatever", "click", function(){
    //...
});

注意

bind是不能为后面动态生成的元素绑定事件的(因为调用bind时遍历的是当时页面里的所有元素)。

live和delegate是可以为动态生成的元素触发事件处理函数的,因为绑定在父元素上的只是一个筛选条件。

最后需要注意的是同样是绑定在document元素上的click事件:

$(".btn").live("click", function(){
    //...
});

$("document").delegate(".btn", "click", function(){
    //...
});

最好使用delegate方法,因为虽然live同样是绑定在document上,但$(“.btn”)这句代码还是会遍历所有的.btn元素并给其创建JQuery对象,相比于直接使用document,性能上会有所不如。

当然,就拿写法来说,我们也更应该喜欢delegate方法。

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-10-06 14:17:36

JS和JQuery中的事件委托 学习笔记的相关文章

js和jquery中的事件委托

[转+自己的修改] 概念: 什么是事件委托:通俗的讲,事件就是onclick,onmouseover,onmouseout,等就是事件,委托呢,就是让别人来做,这个事件本来是加在某些元素上的,然而你却加到别人身上来做,完成这个事件. 举个列子:有三个同事预计会在周一收到快递.为签收快递,有两种办法:一是三个人在公司门口等快递:二是委托给前台MM代为签收.现实当中,我们大都采用委托的方案(公司也不会容忍那么多员工站在门口就为了等快递).前台MM收到快递后,她会判断收件人是谁,然后按照收件人的要求签

JavaScript事件委托原理及Jquery中的事件委托

概念 事件委托,通俗来说就是将元素的事件委托给它的父级或者更外级元素处理. 事件流 事件流描述的是从页面中接收事件的顺序. 事件冒泡:事件开始由最具体的元素接收,然后逐级向上传播到较为不具体的节点(或文档). 事件捕获:事件开始由不太具体的节点接收,然后逐级向下传播到最具体的节点.它与事件冒泡是个相反的过程. DOM2级事件规定的事件流包括三个阶段: 事件捕获 目标阶段 事件冒泡 原理 事件委托就是利用事件冒泡机制实现的. 假设有一个列表,要求点击列表项弹出对应字段. <ul id="my

JQuery中的事件委托机制:delegate和undelegate

考虑下面这种场景:如果1个div下面有3个button,点击每个按钮的时候,需要打印出当前按钮的ID. <div id="parent"> <input type="button" id="a" value="1"></input> <input type="button" id="b" value="2"></i

JavaScript和JQuery中的事件\委托链\事件冒泡\事件捕获,兼容所有浏览器

有做过北大青鸟培训讲师经验的我,如今在一家公司做技术部经理的职位,发现有很多程序员的基本功相当糟糕,在组织企业内部培训时讲解了一些案例,总结了一些经典代码,希望对自己和有需要的人提供一些帮助吧: JavaScript版本: DOM0事件不支持委托链 1 <!DOCTYPE html> 2 <html xmlns="http://www.w3.org/1999/xhtml"> 3 <head> 4 <meta http-equiv="C

JS和jQuery中的事件总结(一)

学而时习之,小白现在天天写页面,基础知识还是要恶补的. 进入正题,什么是事件(此处单独对jQuery.JS)?就是JS和Html之间的交互时呢,用户和浏览器操作页面时的动作(其实是为引发的效果的执行操作),此处注明,这是楼主自己的理解哈. 1.页面加载事件 JS提供了一个 window.onload 它的执行时机呢,是页面完全加载完毕后,包括页面上的文件.图片等完全加载到浏览器后才开始执行: 另外,此方法仅能保存对一个函数的引用,会自动的用后面的覆盖前面的.看个例子: function A(){

zepto.1.1.6.js源码中的each方法学习笔记

each方法接受要遍历的对象和对应的回调函数作为参数,它的作用是: 1.如果要遍历的对象是类似数组的形式(以该对象的length属性值的类型是否为number类型来判断),那么就把以要遍历的对象为执行环境,将回调函数放到该执行环境中去循环执行length次: 2.如果要遍历的对象不类似数组,那么用for key in obj 的方法循环执行回调函数key次,同样以要遍历的对象为执行环境,将回调函数放到该执行环境中去循环执行. function each(elements, callback){

【学习笔记】jquery中的事件和动画

---恢复内容开始--- jquery中的事件 jquery用$(document).ready()方法来代替传统JavaScript的window.onload方法. window.onload方法在网页中所有的元素(包括元素的所有关联文件)完全加载到浏览器后执行,通过 $(document).ready()方法注册的事件处理程序的DOM完全就绪时就可以被调用.此时,网页中的所有元素对jquery都是可以访问的. load()方法会在元素的onload事件中绑定一个处理函数,若绑定给windo

jQuery中绑定事件的几种方法

以click事件为例,jQuery中绑定事件有三种方法: (1)target.click(function(){}); (2)target.bind("click",function(){}); (3)target.live("click",function(){}); 第一种方法很好理解,其实就和普通JS的用法差不多,只是少了一个on而已 第二.三种方法都是绑定事件,但是二者又有很大的不同,下面着重讲解一下,因为这个如果用到Jquery的框架的话是用的挺多的,尤其

在Unity中使用事件/委托机制(event/delegate)进行GameObject之

欢迎来到unity学习.unity培训.unity企业培训教育专区,这里有很多U3D资源.U3D培训视频.U3D教程.U3D常见问题.U3D项目源码,[狗刨学习网]unity极致学院,致力于打造业内unity3d培训.学习第一品牌. 一对多的观察者模式机制有什么缺点? 如果你对如何在Unity中使用事件/委托机制还不太了解,建议您查看我的前一篇文章:[Unity3D技巧]在Unity中使用事件/委托机制(event/delegate)进行GameObject之间的通信 在前一篇博客里面,我们写到