下面简单介绍JavaScript事件的基本概念。
JavaScript事件发展历史
最早在IE 3.0和Netscape 2.0浏览器中出现事件。互联网初期网速是非常慢的,为了解决用户漫长的等待,开发人员把服务器端处理的任务部分前移到客户端,让客户端JavaScript脚本代替解决。
例如,对用户输入的表单信息进行验证等,于是就出现各种响应用户行为的事件,如表单提交事件、文本输入时键盘事件、文本框中文本发生变化触发的事件、选择下拉菜单时引发的事件等。因此,早期的事件多集中在表单应用上。
DOM 2规范开始尝试标准化DOM事件,直到2004年发布DOM 3.0时,W3C才完善事件模型。IE9、Fircfox、Opera、Safari和Chrome主流浏览器都已经实现了DOM 2事件模块的核心部分。IE8及其早期版本使用IE私有的事件模型。
JavaScript是以事件驱动实现页面交互,事件驱动的核心:以消息为基础,以事件来驱动。通俗说,事件就是文档或浏览器窗口中发生的一些特定交互行为,如加载、单击、输入、选择等。可以使用侦听器预订事件,即在特定事情上绑定事件监听函数,以便在事件发生时执行相应的代码。当事件发生时,浏览器会自动生成事件对象(event),并沿着DOM节点有序进行传播,直到被脚本捕获。这种观察员模式确保JavaScript与HTML保持松散的耦合。
事件模型
在浏览器发展历史中,出现4种事件处理模型。
- 基本事件模型:也称为DOM 0事件模型,是浏览器初期出现的一种比较简单的事件模型,主要通过事件属性,为指定标签绑定事件监听函数。由于这种模型应用比较广泛,获得了所有浏览器的支持,目前依然比较流行。但是这种模型对于HTML文档标签依赖严重,不利于JavaScript独立开发。
- DOM事件模型:由W3C制订,是目前标准的事件处理模型。所有符合标准的浏览器都支持该模型,IE怪异模式不支持。DOM事件模型包括DOM 2事件模块和DOM 3事件模块,DOM 3事件模块为DOM 2事件模块的升级版,略有完善,主要是新增了一些事情类型,以适应移动设备的开发需要,但大部分规范和用法保持一致。
- IE事件模型: IE 4.0及其以上版本浏览器支持,与DOM事件模型相似,但用法不同。
- Netscape事件模型:由Netscape 4浏览器实现,在Netscape 6中停止支持。
事件传播
当一个事件发生以后,它会在不同的DOM节点之间传播,也称为事件流。这种传播分成三个阶段,具体说明如下。
- 捕获阶段:事件从window对象沿着文档树向下传播到目标节点,如果目标节点的任何一个上级节点注册了相同事件,那么事件在传播的过程中就会首先在最接近顶部的上级节点执行,依次向下传播。
- 目标阶段:注册在目标节点上的事件被执行。
- 冒泡阶段:事件从目标节点向上触发,如果上级节点注册了相同的事件,将会逐级响应,依次向上传播。
事件传播的最上层对象是window,接着依次是document,html(document.documentElement)和body(document.dody)。也就是说,如果<body>元素中有一个<div>元素,点击该元素。事件的传播顺序,在捕获阶段依次为window、document、html、body、div,在冒泡阶段依次为div、body、html、document、window。
事件类型
根据触发对象不同,可以将浏览器中发生的事件分成不同的类型。DOM 0事件定义了以下事件类型:
- 鼠标事件:与鼠标操作相关的各种行为,可以细分为两类:跟踪鼠标当前定位(如mouseover、mouseout)的事件和跟踪鼠标单击(如mouseup、mousedown、click)的事件。
- 键盘事件:与键盘操作相关的各种行为,包括追踪键盘敲击和其上下文,追踪键盘包括3种类型:keyup、keydown和keypress。
- 页面事件:关于页面本身的行为,如当首次载入页面时触发load事件和离开页面时触发unload和beforeunload事件。此外,JavaScript的错误使用错误事件追踪,可以让用户独立处理错误。
- UI事件:追踪用户在页面中的各种行为,如监听用户在表单中输入,可以通过focus(获得焦点)和blur(失去焦点)两个事件,如submit事件用来追踪表单的提交,change事件监听用户在文本框中的输入,而select事件可以监听下拉菜单发生更新等。
在DOM 2事件模型中,事件模块包含4个子模块,每个子模块提供对某类事件的支持。例如,MouseEvent子模块提供了对mousedown、mouseup、mouseover、mouseout和click事件类型的支持。包括IE 9在内的所有主流浏览器都支持DOM 2事件类型。
- HTMLEvents:接口为Event,支持的事件类型包括abort、blur、change、error、focus、load、resize、scroll、select、submit、unload。
- MouseEvents:接口为MouseEvent,支持的事件类型包括click、mousedown、mousemove、mouseout、mouseover、mouseup。
- UIEvents:接口为UIEvent,具体支持事件类型可以请扫码了解。
- MutationEvents:接口为MutationEvent,具体支持事件类型可以请扫码了解。
HTMLEvents和MouseEvents模块定义的事件类型与基础事件模型中的事件类型相似,UIEvents模块定义的事件类型与HTML表单元素的支持的获得焦点、失去焦点和单击事件功能类似,MutationEvents模块定义的事件是在文档改变时生成的,一般不常用。