You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
<divid="myDiv"><inputtype="button" value="Click Me" id="myBtn"></div><scripttype="text/javascript">varbtn=document.getElementById("myBtn");btn.onclick=function(){//先执行某些操作btn.onclick=null;//移除事件处理程序document.getElementById("myDiv").innerHTML="处理中...";//把按钮替换成文字};</script>
javaScript 与 HTML 之间的交互是通过事件实现的。
事件流
概念
:事件流描述的是从页面中接收事件的顺序。事件冒泡
概念
:即事件开始时由最具体的元素(文档中嵌套层次最深 的那个节点)接收,然后逐级向上传播到较为不具体的节点(文档)。理论及运用
运用
:事件委托 更详细的介绍看这篇文章事件委托原理
:以将事件处理程序附加到更高层的地方负责多个目标的事件处理。大多数 Web 应用在用户交互上大量用到事件处理程序。页面上的事件处理程序的数量和页面响应 用户交互的速度之间有个负相关。为了减轻这种惩罚,最好使用事件代理。
事件委托实例
:场景1:需要在点击列表项的时候响应一个事件。如果给每个列表项一一都绑定一个函数,那对于内存消耗是非常大的,效率上需要消耗很多性能。因此,比较好的方法就是把这个点击事件绑定到他的父层,也就是
ul
上,然后在执行事件的时候再去匹配判断目标元素;场景2:动态添加新的Li元素。在很多时候,我们需要通过 AJAX 或者用户操作动态的增加或者去除列表项元素,那么在每一次改变的时候都需要重新给新增的元素绑定事件,给即将删去的元素解绑事件。如果用了事件委托就没有这种麻烦了,因为事件是绑定在父层的,和目标元素的增减是没有关系的,执行到目标元素是在真正响应执行事件函数的过程中去匹配的;
代码: 代码运行
不是所有的事件都能冒泡。以下事件不冒泡:blur、focus、load、unload。
有些业务场景需要阻止冒泡事件的冒泡,比如在一个HTML结构中,父级包含着子级,当事件在子级发生时(click,mouseenter,mouseleave等),由于事件冒泡就会触发父级的同名事件。示例:
当点击li时,会弹出两个1,可以通过阻止冒泡防止这样的行为,点击li就弹出一个1。
event.stopPropagation()或event.cancelBubble = true 可以阻止事件冒泡。
应用
事件代理,事件冒泡允许多个操作被集中处理(把事件处理器添加到一个父级元素上,避免把事件处理器添加到多个子级元素上),它还可以让你在对象层的不同级别捕获事件
让不同的对象同时捕获同一事件,并调用自己的专属处理程序做自己的事情,就像老板一下命令,各自员工做自己岗位上的工作去了。
事件捕获
概念
:事件捕获的思想 是不太具体的节点应该更早接收到事件,而最具体的节点应该最后接收到事件。事件捕获的用意在于在 事件到达预定目标之前捕获它。DOM事件流
“DOM2级事件”规定的事件流包括三个阶段::事件捕获阶段、处于目标阶段和事件冒泡阶段。
首先发生的是事件捕获,为截获事件提供了机会。然后是实际的目标接收到事件。最后一个阶段是冒泡阶 段,可以在这个阶段对事件做出响应。
在 DOM 事件流中,实际的目标(
冒泡阶段的一部分
。然后,冒泡阶段发生, 事件又传播回文档。事件处理程序
概念
:事件就是用户或浏览器自身执行的某种动作。诸如 click、load 和 mouseover,都是事件的名字。 而响应某个事件的函数就叫做事件处理程序(或事件侦听器)。事件处理程序的名字以"on"开头,onclick等。HTML事件处理程序
概念
:某个元素支持的每种事件,都可以使用一个与相应事件处理程序同名的 HTML 特性来指定。例如,要在按钮被单击时执行一些 JavaScript,可以像下面 这样编写代码:
缺点
:首先,存在一个时差问题。因为用户可能会在 HTML 元素一出现在页面上就触发相应的事件,但当时的事件处理程序有可能尚不具备执行条件。
另一个缺点是,这样扩展事件处理程序的作用域链在不同浏览器中会导致不同结果。
最后一个缺点是 HTML 与 JavaScript 代码紧密耦合。如果要更换事 件处理程序,就要改动两个地方:HTML 代码和 JavaScript 代码。
DOM0 级事件处理程序
简单来说就是取得一 个要操作的对象的引用,然后为它指定了某事件处理程序(如onclick)。使用 DOM0 级方法指定的事件处理程序被认为是元素的方法,以这种方式添加的事件处理程序会在事件流的冒泡阶段被处理。
将事件处理程序设置为 null 之后,再单击按钮将不会有任何动作发生。
DOM2 级事件处理程序
“DOM2 级事件”定义了两个方法,用于处理指定和删除事件处理程序的操作:addEventListener() 和 removeEventListener()。
onclick 事件会被覆盖,addevenlistener 事件先后执行。
所有 DOM 节点中都包含这两个方法,并且它们都接受 3 个参数:要处理的事件名、作为事件处理程序的函数和一个布尔值。最后这个布尔值参数如果是 true,表示在捕获 阶段调用事件处理程序;如果是 false,表示在冒泡阶段调用事件处理程序。没有指定的话,默认为 false。
上面的代码为一个按钮添加了 onclick 事件处理程序,而且该事件会在冒泡阶段被触发(因为最后一个参数是 false,此时和DOM0级的onclick事件差不多)。
使用 DOM2 级方法添加事件处理程序的主要好处是可以添加多个事件处理程序。
这两个事件处理程序会按照添加它们的顺序触发,因此首先会显示元素的 ID,其次会显示"Hello world!"消息。
MDN 对第三个参数的解释是:Boolean,是指在DOM树中,注册了该listener的元素,是否会先于它下方的任何事件目标,接收到该事件。
沿着DOM树向上冒泡的事件不会触发被指定为为true的listener(因为此时为true是比冒泡更早的事件捕获阶段)。
例子:
(引自csdn的一篇文章)点击查看实例效果
大多数情况下,都是将事件处理程序添加到事件流的冒泡阶段,这样可以最大限度地兼容各种浏览器。最好只在需要在事件到达目标之前截获它的时候将事件处理程序添加到捕获阶段。如果不是特别需 要,我们不建议在事件捕获阶段注册事件处理程序。
事件对象
兼容 DOM 的浏览器会将一个 event 对象传入到事件处理程序中。无论指定事件处理程序时使用什 么方法(DOM0 级或 DOM2 级),都会传入 event 对象。
触发的事件类型不一样,可用的属性和方法也不一样。常见的有event.type,event.target 等
事件类型
Web 浏览器中可能发生的事件有很多类型。如前所述,不同的事件类型具有不同的信息,而“DOM3 级事件”规定了以下几类事件。
内存和性能
事件委托
这个前面讲到了 ,这边不重复。
移除事件处理程序
每当将事件处理程序指定给元素时,运行中的浏览器代码与支持页面交互的 JavaScript 代码之间就 会建立一个连接。。这种连接越多,页面执行起来就越慢。如前所述,可以采用事件委托技术,限制建立 的连接数量。另外,在不需要的时候移除事件处理程序,也是解决这个问题的一种方案。内存中留有那 些过时不用的“空事件处理程序”(dangling event handler),也是造成 Web 应用程序内存与性能问题的 主要原因。
在两种情况下,可能会造成上述问题。第一种情况就是从文档中移除带有事件处理程序的元素时。 这可能是通过纯粹的 DOM 操作,例如使用 removeChild()和 replaceChild()方法。但更多地是发 生在使用 innerHTML 替换页面中某一部分的时候。如果带有事件处理程序的元素被 innerHTML 删除 了,那么原来添加到元素中的事件处理程序极有可能无法被当作垃圾回收。
这里,有一个按钮被包含在
第二种情况,就是卸载页面的时候。如果在页面被卸载之前没 有清理干净事件处理程序,那它们就会滞留在内存中。每次加载完页面再卸载页面时(可能是在两个页 面间来回切换,也可以是单击了“刷新”按钮),内存中滞留的对象数目就会增加,因为事件处理程序 占用的内存并没有被释放。一般来说,最好的做法是在页面卸载之前,先通过 onunload 事件处理程序移除所有事件处理程序。 在此,事件委托技术再次表现出它的优势——需要跟踪的事件处理程序越少,移除它们就越容易。对这 种类似撤销的操作,我们可以把它想象成:只要是通过 onload 事件处理程序添加的东西,最后都要通 过 onunload 事件处理程序将它们移除。
模拟事件
概念
:使用 JavaScript 在任意时刻来触发特定的事件,此时的事件就如同浏览器创建的事件一样。模拟鼠标事件
思路
: 1.创建事件对象 2.分发事件ps:红包书介绍的创建事件对象的方法有点过时了,现被MDN不建议使用
实例运用
代码运行这边有两个按钮,按钮1绑定一个鼠标点击事件1,alert出一句话;在按钮2绑定一个鼠标点击事件2,鼠标点击事件2将模拟用户去点击按钮1。所以点按钮2,触发一个模拟鼠标事件去点击按钮1。
模拟键盘事件
这边举一反三,不做解释。
模拟其他事件
自定义 DOM 事件
实例运用
代码运行红宝书的方法有点过时,新实现方法可看这篇文章
The text was updated successfully, but these errors were encountered: