• JavaScript中addEventListener/attachEvent 与内联事件


    1.addEventListenerattachEvent

    两者都是为元素注册事件,但是有区别:
            i.addEventLstener符合W3C标准,因而大部分浏览器会支持
              attachEvent是IE专有,在IE9以下浏览器中得使用他,IE9+已经转而支持addEventLstener,放弃了attachEvent
            ii.addEventListener的eventType参数不需要加"on"
              attachEvent的eventType必须包含“on”(如“onclick”)
            iii.addEventListener拥有userCapture参数,当该参数为true时执行事件捕获,若为false执行事件冒泡( 冒泡与捕获具体参考这里
               attachEvent参数只有两个(eventType,function),没有userCapture参数
            iiii:addEventListener的标准书写方式为 element.addEventListener('eventType',function,userCapture);
                attachEvent的标准书写方式为 element.attachEvent('on'+'eventType',function);

            //attachEvent没有userCapture参数,那是否支持捕获,他的触发事件顺序是怎样?笔者暂时没有深刻研究,之后会在此补充

    由于两者的差异,我们就需要一个兼容性写法,可以在任何浏览器下注册事件,写法如下:

    function RegisterEventListener(ele,eventType,func,capture){
        if(ele.addEventListener){
            ele.addEventListener(eventType,func,capture);
        }
        else if(ele.attachEvent){
            ele.attachEvent("on"+eventType,func);
        }
    }
     

    2.removeEventListener与detachEvent

     
    removeEventListener标准写法为element.removeEventListener('eventType',function,userCapture)
    detachEvent标准写法为element.detachEvent('on'+'eventType',function)
     
    两者都去除元素对事件的绑定,差异与上文的addEventLstener与attachEvent一样,他们的兼容写法如下:
    function RemoveEventListener(ele,eventType,func,capture){
        if(ele.addEventListener){
            ele.removeEventListener(eventType,func,capture);
        }
        else if(ele.attachEvent){
            ele.detachEvent("on"+eventType,func);
        }
    }
     

    3.内联事件


    注册事件的写法除了上面两个,还有我们最常用的οnclick=“xxx()”(称之为内联事件),这样注册事件的形式就有3种:
    1.addEventLstener
    2.attachEvent
    3.内联事件写法
    前两种实际上是相同的函数在不同浏览器的写法而已,而内联事件则不同,我们来说说前两者与内联事件的区别,我们书写代码如下,为div_2加上内联事件:
    <html>
    <head>
    <script>
    function init(){
        document.getElementById("div_1").addEventListener("click",function (){alert(this.id);},true);
        document.getElementById("div_2").addEventListener("click",function (){alert(this.id);},true);
        document.getElementById("div_3").addEventListener("click",function (){alert(this.id);},true);
    
    }
    </script>
    </head>
    <body onload="init()">
    <div  id="div_1" style="background-color:#FFF200; 150px;height:150px" >    div_1 <br/>
        <div id="div_2" style="background-color:#EFE4B0; 120px;height:120px; margin-left:15px;" onclick="alert(2);"   >     div_2 <br/>
        <div id="div_3" style="background-color:#B5E61D; 90px;height:90px;  margin-left:15px; "  >        div_3<br/><br/>
              click  me!    
        </div>
        </div>
     </div>
    </body>
    </html>
     

    此时弹框为:div_1=>div_2=>div_3=>2

    这样我们猜测内联写法等同于userCapture=false(事件冒泡时触发)的addeventListener写法。我们继续测试,在上面基础上修改init()函数:

    function init(){
        document.getElementById("div_1").addEventListener("click",function (){alert(this.id);},false);
        document.getElementById("div_2").addEventListener("click",function (){alert(this.id);},false);
        document.getElementById("div_3").addEventListener("click",function (){alert(this.id);},false);
    
    }
     

    此时弹框:div_3=>2=>div_2=>div_1

    我们猜测没错,内联确实与usercapture=false的情况相符。同时有个细节,div_2绑定了两个click事件(一个内联事件,一个addEventListener),但是先执行的内联事件。这是由于页面加载时,在init()执行之前就注册的内联事件。

    因此,这时代码等同于:

     
        document.getElementById("div_2").addEventListener("click",function (){alert(2);},false);
        document.getElementById("div_1").addEventListener("click",function (){alert(this.id);},false);
        document.getElementById("div_2").addEventListener("click",function (){alert(this.id);},false);
        document.getElementById("div_3").addEventListener("click",function (){alert(this.id);},false);
     

    所以结论就是:内联事件是等同于userCapture=false的addEventListener写法,只是他在页面初始化时最先注册,所以执行顺序早于同元素usercapture=false的注册事件。

     

    4.什么时候用addEventListener,什么时候用内联事件

    上面的例子我们不难发现,利用addEventListener可以对一个元素注册多个同类(eventType)事件。(上面的div_2就有两个click事件,所以触发了两次)

    而内联事件的写法很显然只能最多有一个,但是他的写法确实比较简便,也容易理解。因此,当你需要对一个元素注册多个事件,并需要考虑捕捉(usercapture)时,使用addEventListener,否则内联即可。

    老外有较精辟的说法,点击这里



     

    作者:Mr.Jimmy
    出处:https://www.cnblogs.com/JHelius
    联系:yanyangzhihuo@foxmail.com
    如有疑问欢迎讨论,转载请注明出处

  • 相关阅读:
    [Day01] Python基础
    Python数据结构与循环语句
    elementui级联下拉框怎么设置可选择任意一级选项以及设置后前面会出现1个单选按钮去掉单选按钮的方法和选好后下拉面板不自动收起的问题
    解决ElementUI中的Cascader 级联选择器高度过高的问题
    git切换分支提示:you need to resolve your current index first
    提交本地代码到git远程仓库时误操作让git代码覆盖了本地代码,找回本地代码的解决方法
    elementui在表格/下来列表等展示数据的区显示加载中
    vueshop
    elementui表单验证无效的解决方法
    elementui滑块开启和关闭状态动态绑定
  • 原文地址:https://www.cnblogs.com/JHelius/p/14318915.html
Copyright © 2020-2023  润新知