IE 中,DOM2 不支持 addEventListener 而只能使用 attachEvenListener ,这使用我们需要进行能力判断去做跨浏览器兼容,那么既然这么麻烦,为什么不直接使用 DOM0 的 elem.onclick 呢?DOM2 有什么比 DOM0 好的地方?
IE 中,DOM2 不支持 addEventListener 而只能使用 attachEvenListener ,这使用我们需要进行能力判断去做跨浏览器兼容,那么既然这么麻烦,为什么不直接使用 DOM0 的 elem.onclick 呢?DOM2 有什么比 DOM0 好的地方?
DOM Level 2 Event Handler更加flexible。 比如,
绑定多个同一类型的事件。前者不能, 我觉得是前者最大的缺点。
通过第3个parameter控制事件是bubbling还是capture。前者不能。
.preventDeault()
可以取消default behavior; .stopPropagation()
可以取消事件的传播。而, 前者只能通过return false
来同时取消propagation和default behavior。
cross-browser。需要花费一点力气写成function,但可以从中学习兼容知识。
不能写在HTML里。
Live in the future
27 回答14.8k 阅读
8 回答3.8k 阅读✓ 已解决
6 回答1.7k 阅读✓ 已解决
5 回答5.5k 阅读✓ 已解决
4 回答1.8k 阅读✓ 已解决
3 回答1.9k 阅读
4 回答2.4k 阅读✓ 已解决
感谢 @王子亭 提供的链接,我觉得挺不错,并且翻译成中文,分享给大家!
问题: addEventListener 和 onclick 有什么不同?
问题描述
代码同时保存在一个分离的 .js 文件里面,而且它们都能完美地运行。
最佳答案
它们都是正确的,它们之间没有哪个是“最好的”,而且开发者有可能同时使用这两个方法。
事件监听器(Event Listeners,包括 addEventListener 以及 IE 的 attacheEvent)
旧版本的 IE 在执行 Javascript 时与几乎所有其它浏览器不同,在 IE 9 之前的版本中,你需要使用
attachEvent
模块,就像这样:在大部分其它浏览器(包括 IE 9 以及更新的版本)中,你可以使用
addEventListener
,就像这样:使用这些方法(DOM2 事件),理论上你可以向某个元素加入无数的事件。但实际上,这会受限于客户端的内存容量以及其它的性能问题,而这对于每一个浏览器都是不同的。
上面的例子使用的都是匿名函数,你也可以将一个函数表达式或者一个闭包添加到事件监听器上:
addEventListener
还有一个特点就是最后的参数,它会控制监听器在事件冒泡阶段时就作出反应。有大约 95% 的可能会像我在例子中那样使用false
。这个参数在attachEvent
中或在使用内联事件(inline Events) 时没有等效的参数。内联事件 (Inline Events, 即 HTML 中的 onclick="" 属性 和 element.onclick)
在所有支持 Javascript 的浏览器中,你可以将一个事件监听器内联,也就是像下面的 HTML 代码那样:
虽然它的确是可以完成任务的,而且简单直接,但绝大部分有经验的开发者都会尽量避开使用这样的方法。同时,你不能在这里使用闭包或者匿名函数(虽然处理程序本身就是一个匿名函数),而且你的控制范围是有限的。
另一个方法是这样的(也就是你提到的):
实际上这等价于内联 Javascript (也就是上面那种在 HTML 标签属性中添加的方法),不过这样可以拥有更大的控制范围,同时可以使用匿名函数、函数表达式或闭包。
内联事件有个重大的缺点就是,不像上面提到的事件监斩器那样,你只可以指定一个内联事件。内联事件会转化元元素的属性,那意味着当指定多个的内联事件时,它之前所指定的内联事件会被覆盖掉。
使用上面 HTML 代码中的
<a>
标签来举个例子:当你点击这个元素后,你只可以看到 "Did stuff #2",原因是第二个值覆盖了第一个指定的
onclick
属性,同时,会把 HTML 中onclick
属性也覆盖掉。点击这里可以试试:http://jsfiddle.net/jpgah/二者谁更好呢?
主要的问题是浏览器兼容性和必要性。你目前是否需要添加一个以上的事件到一个元素上?未来是否需要?大部分时候,你是需要的。所以,使用
attachEvent
和addEventListener
是非常有必要的,不然用内联事件就好了。JQuery 以及很多其它的 Javascript 框架都为不同的浏览器封装了通用的处理 DOM2 事件的通用模型(Models),这样你可以在做跨浏览器兼容时不需要为 IE 的历史遗留问题而烦恼了。同样的代码在 jQuery 中做跨浏览器兼容,只需要这样:
当然了,不要因为这么一件事而使用一个框架。你可以很容易地写出一个小工具来兼容旧版本的浏览器:
点击可以试试:http://jsfiddle.net/bmArj/
综上,除非你看的这段脚本用其他方法处理了不同浏览器之间的差异 ,使用
addEventListener
的部分不会在 IE 9 以下的 IE 工作。文档及相关阅读
原问题链接:http://stackoverflow.com/questions/6348494/addeventlistener-vs-onclick