关键词不能为空

当前您在: 主页 > 英语 >

DOM 事件模型

作者:高考题库网
来源:https://www.bjmy2z.cn/gaokao
2021-02-28 05:39
tags:

-

2021年2月28日发(作者:摆脱)


DOM


事件模型




事件



HTML


元素事件是浏览器内在自动产生的


,


当有事件发生时


html


元素会向外界


(


这里主要指元素


事件的订阅者


)


发出 各种事件


,



click,onmou seover,onmouseout


等等。



DOM


事件流



DOM(


文档对象模型


)


结构是一个 树型结构,当一个


HTML


元素产生一个事件时,该事件会在元


素结点与根结点之间的路径传播,


路径所经过的结点都会收到该 事件,


这个传播过程可称为


DOM


事件 流。



主流浏览器的事件模型



早在


2004


前在


H TML


元素事件的订阅,发送,传播,处理模型上各浏览器实现并不一致,直到


DOM Level3


中规定后,多数主流浏览器才陆陆续续支持


DOM


标准的事件处理模型





捕获型


与冒泡型。


< br>目前除


IE


浏览器外,其它主流的


Firefox, Opera, Safari


都支持标准的


DOM


事件处理模型。


IE



然使用自己的模型,即冒泡型,它模型的一部份被


DOM


采用,这点对于开发者来说也是有好处


的,只使用


D OM


标准,


IE


都共有的事件处理方式 才能有效的跨浏览器。



冒泡型事件


(Bubbling)


< /p>


这是


IE


浏览器对事件模型的实现,也是 最容易理解的,至少笔者觉得比较符合实际的。冒泡,


顾名思义,事件像个水中的气泡一 样一直往上冒,直到顶端。从


DOM


树型结构上理解,就是事< /p>


件由叶子结点沿祖先结点一直向上传递直到根结点;从浏览器界面视图

HTML


元素排列层次上


理解就是事件由具有从属关系的最 确定的目标元素一直传递到最不确定的目标元素


.


捕获型事件


(Capturing)



Netscape Navigator


的实现,它与冒泡型刚 好相反,由


DOM


树最顶层元素一直到最精确的元素,


这个事件模型对于开发者来说(至少是我


..


) 有点费解,因为直观上的理解应该如同冒泡型,事


件传递应该由最确定的元素,即事件产 生元素开始。



但这个模型在某些情况下也是很有用的,接下来会讲解到。




DOM


标准事件模型



因为两个不同的模型都有其优点和解释,


DOM


标准支 持捕获型与冒泡型,可以说是它们两者的


结合体。它可以在一个


DOM


元素上绑定多个事件处理器,并且在处理函数内部,


th is


关键字仍


然指向被绑定的


DOM< /p>


元素,另外处理函数参数列表的第一个位置传递事件


event< /p>


对象。



首先是捕获式传递事件,


接着是冒泡式传递,


所以,


如果一个处理函数 既注册了捕获型事件的监


听,又注册冒泡型事件监听,那么在


D OM


事件模型中它就会被调用两次。




注册与移除事件监听器



注册事件监听 器,


或又称订阅事件,


当元素事件发生时浏览器回调该监听函数 执行事件处理。



前主流浏览器中有两种注册事件的方法,一种 是


IE


浏览器的,另一种是


DOM


标准的。



1.


直 接


JS



HTML

挂载法





onclick


=



>



element.


onclick



=



function


(){


alert


(


this


.


innerHTML


)


;


}



移除时将事件属性设 为


nul


即可,这个也是最常用的方法了,优缺点也是显然的:



?



?



?



?



简单方便,在

HTML


中直接书写处理函数的代码块,在


JS

< p>
中给元素对应事件属性赋值


即可



IE



DOM


标准都支持的一 种方法,


它在


IE


< br>DOM


标准中都是在事件冒泡过程中被调


用的。



可以在处理函数块内直接用


this


引用注册事件的元素



要给元素注册多个监听器,就不能用这方法了



2. IE


下注册多个事件监听器与移除监听器方法



IE


浏览器中


HTML


元素有 个


attachEvent


方法允许外界注册该元素多个事件监 听器


,


例如



element.


attachEvent


(

< br>'onclick'


,


observer


)


;



attachEvent


接受两个参数。第一个参数是事件名称,

< p>
第二个参数


observer


是回调处理函数。< /p>


这里


得说明一下,有个经常会出错的地方,


IE


下利用


attachEvent


注册的处理函数调用时


this


指向不


再是先前注册事件的元素,这时的


this


< br>window


对象了,笔者很奇怪


IE

< br>为什么要这么做,完


全看不出好处所在。



要移除先前注册的事件的监听器


,


调用


element



detachEvent


方法即可,参数相同。



elemen t.


detachEvent


(


'on click'


,


observer


)


;



3. DOM


标准下注册多个事件监听器与移除监听器方法



实现


DOM


标准的浏览器与

IE


浏览器中注册元素事件监听器方式有所不同,它通过元素的

addEventListener


方法注册,该方法既支持注册冒泡型事件处理, 又支持捕获型事件处理。



element.


addEventListener


(


'click '


,


observer


,


useCapture


)


;



addEventListener


方法接受三个参数。第一个参数是事 件名称,值得注意的是,这里事件名称与


IE


的不同,事件名称 是没


’on’


开头的


;


第二个参数


observer


是回调处理函数


;


第三个参数注明该处


理回调函数是在事件传递 过程中的捕获阶段被调用还是冒泡阶段被调用



移除已注册的事 件监听器调用


element



rem oveEventListener


即可,参数不变


.


element.


removeEventListene r


(


'click'


,


observer


,


useCapture


)


;



跨浏览器的注册与移除元素事件监听器方案


< br>弄清楚


DOM


标准与


IE


的注册元素事件监听器之间的异同后,就可以实现一个跨浏览器的注册


与移除元素事件监听器方案


:



//


注册



function


addEventHandler


(


element


,


evtName


,


callback


,


useCapture


)



{



//DOM


标准



if



(


el ement.


addEventListener


)

< p>


{



element.


addEventListener


(


evtName


,


callback


,


useCapture


)


;



}



else



{



//IE


方式


,


忽略


useCapture


参数



element.

< br>attachEvent


(


'on'


+


evtName


,


callback


)


;



}



}




//


移除



//


注册



function


removeEventHandler< /p>


(


element


,

evtName


,


callback


,


useCapture


)



{



//DOM


标准



if



(


el ement.


removeEventListener


)



{



eleme nt.


removeEventListener


(

< p>
evtName


,


callback


,


useCapture


)


;



}



else



{



//IE


方式


,


忽略


useCapture


参数



element.

< br>dettachEvent


(


'on'

< br>


+


evtName


,


callback


)


;



}



}



如何取消浏览器事件的传递与事件传递后浏览器的默认处理


< /p>


先说明取消事件传递与浏览器事件传递后的默认处理是两个不同的概念,

< br>可能很多同学朋友分不


清,或者根本不存在这两个概念。



取消事件传递是指,


停止捕获型事件或冒泡型事件的进一步传递 。


例如上图中的冒泡型事件传递


中,



body


处理停止事件传递后,


位于上 层的


document


的事件监听器就不再收到通知,


不再被


处理。



事件传 递后的默认处理是指,


通常浏览器在事件传递并处理完后会执行与该事件关联的默认动作


(如果存在这样的动作)。例如,如果表单中


input type


属性是



“submit”


,点击后在事件传播完


浏览器就就自动提交表单。又例如,


input


元素的



keydown


事件发生并处理后,浏览器默认会

< p>
将用户键入的字符自动追加到



input


元素的值中。



要取消浏览器的件传递


,IE



DOM


标准又有所不同。




IE



,


通过设置


even t


对象的


cancelBubble



true


即可。




function


someHandle


()



{



window.

< br>event


.


cancelBubble



=



true


;



}



DOM


标 准通过调用


event


对象的


stop Propagation()


方法即可。




function


someHa ndle


(


event


)



{



event.


stopPropagation


()


;



}



因些,跨浏览器的停止事件传递的方法是


:



function


someHa ndle


(


event


)



{



event


=


event


||


window.


event


;



if


(


event.


stopPropagation


)



event.


stopPropagation


()

< p>
;



else


event.


cancelBubble



=



true


;



}



取消事件传递后的默认处理,


IE



DOM


标准 又不所不同。




IE



,


通过设置


event


对象的


returnValue



false


即可。




function


someHandle


()



{



window.

< br>event


.


returnValue

< br>


=



false


;



}



DOM


标 准通过调用


event


对象的


prev entDefault()


方法即可。




function


someHa ndle


(


event


)



{



event.


preventDefault


()


;



}



因些,跨浏览器的取消事件传递后的默认处理方法是:




function


someHa ndle


(


event


)



{



event


=


event


||


window.


event


;



if


(


event.


preventDefault


)



e vent.


preventDefault


()


;



else


event.


returnValue



=



false


;



}



捕获型事件模型与冒泡型事件模型的应用场合



标准事件模型为我们提供了两种方案,


可能很多朋友分不清这两种不同模型有啥 好处,


为什么不


只采取一种模型。


< /p>


这里抛开


IE


浏览器讨论(


IE


只有一种,没法选择)什么情况下适合哪种事件模型。

< br>


1.


捕获型应用场合



捕获型事件传递由最不精确的祖先元素一直到最精确的事件源元素,


传递方式与操作系统中的全


局快捷键与应用程序快捷键相似。


当 一个系统组合键发生时,


如果注册了系统全局快捷键监听器,


该 事件就先被操作系统层捕获,


全局监听器就先于应用程序快捷键监听器得到通知,


也就是全局


的先获得控制权,


它有权阻止事件 的进一步传递。


所以捕获型事件模型适用于作全局范围内的监


听 ,这里的全局是相对的全局,相对于某个顶层结点与该结点所有子孙结点形成的集合范围。



例如你想作全局的点击事件监听,


相对于

< br>document


结点与


document


下所有的子结点,


在某个条


件下要求所有的子结点点 击无效,


这种情况下冒泡模型就解决不了了,


而捕获型却非常适 合,



以在最顶层结点添加捕获型事件监听器,伪码如下


:



function


globalClickListener


(


event


)



{



if


(


canEventPass


==



false


)



{



//


取消 事件进一步向子结点传递和冒泡传递



event.

< p>
stopPropagation


()


;



//


取消浏览器事件后的默认执行


< /p>


event.


preventDefault

()


;



}



}



这样一来,当


canEventPass


条 件为假时,


document


下所有的子结点

< br>click


注册事件都不会被浏览


器处理。



2.


冒泡型的应用场合



可以说我们平时用的都是冒泡事件模型,因为


IE


只支持这模型。这里还是说说,在恰当利用该


模型可以提高脚本性能。在元素 一些频繁触发的事件中,如


onmousemove,


onm ouseover,onmouseout,


如果明确事件处理后没必要进一步传递,那 么就可以大胆的取消它。此


外,


对于子结点事件监听器的处理会 对父层监听器处理造成负面影响的,


也应该在子结点监听器


中禁 止事件进一步向上传递以消除影响。



综合案例分析



最后结合下面


HTML


代码作分析


:




id


=




onclick


=



>





id


=




onclick


=



>





id


=




onclick


=



>





id


=




style


=



re d;



onclick


=



>









HTML


运行后点击红色区域


,


这是最里层的


DIV,


根据上面说明


,


无论 是


DOM


标准还是


IE,


直接写



html


里的监听 处理函数是事件冒泡传递时调用的


,


由最里层一直往上传递


,


所以会先后出现



current is event_source


current is div2


current is div1


current is div0


current is body


添加以下片段


:



var


div2


=


document.


getEle mentById


(


'div2'


)< /p>


;



addEventHandler< /p>


(


div2


,



'click'


,


< br>function


(


event


){



event


=


event


||


window.


event


;



if


(


event.


stopPropagation


)



event.


stopPropagation


()

< p>
;



else


event.


cancelBubble



=



true


;



}


,



fal se


)


;



当 点击红色区域后


,


根据上面说明


,


在泡冒泡处理期间


,


事件传递到

< p>
div2


后被停止传递了


,


所以


div2


上层的元素收不到通知


,


所以会先后出现


:

-


-


-


-


-


-


-


-



本文更新与2021-02-28 05:39,由作者提供,不代表本网站立场,转载请注明出处:https://www.bjmy2z.cn/gaokao/678995.html

DOM 事件模型的相关文章