基础知识javascript--事件
群里有一个小伙伴在处理事件监听函数的时候,遇到了一点问题,正好我比较空闲,于是帮他指出了代码中的问题,顺便整理一下,方便以后遇到类似问题的伙伴们有一个参考。
这是一个很简单的问题,对于基础知识比较杂实的同学来说。下边用代码简单展示一下:
var btn = document.querySelector('#btn'); btn.addEventListener('click',function(){ callback(); },false); function callback(){ var event = event.target || event.srcElement; console.log(event) // 为什么event为未定义? }
这显然是未定义的,估计那个小伙伴以为event和window一样,是系统免费送的参数,看来这样用报错,于是他就在群里问起来了。然后我告诉他问题在哪里,很快,他就改好了。
var btn = document.querySelector('#btn'); btn.addEventListener('click',callback,false); function callback(event){ var event = event.target || event.srcElement; console.log(event) }
他开心的告诉我,问题解决了。可是问题又来了,为什么我没有在callback中传入实参,函数运行的时候也可以收到值呢?真是个爱思考的好孩纸。我决定帮他弄清楚这个问题。
于是写这篇博客来详细分析一下。
首先从
btn.addEventListener('click',callback,false);这里看过来,这里其实只是给click事件邦定一个事件处理函数,可以看成是callback函数的一个引用,它的形参是由我们在定义callback的时候决定的。我们打开Chrome浏览器的控制台一看,就明白了:

当我们点击click的时候,系统会把当前的mouseEvent事件做为callback的第一个实参传进去,相当于这样调用callback(MouseEvent)。
function callback(event){}
其实这个地方的形参随便用什么名字都无所谓,只是习惯上用event,可读性强一点,你硬要用arg1之类的名字也可以。或者你想多定义几个形参
function callback(event,arg1,arg2){} ;通过前面的分析可以知道,除了第一个参数外,其它的参数都不会被赋值,因此都为undefined.
但是我们有时候需要在事件邦定的时候,传入几个自己定义的参数怎么办呢?方法主要有以下三种:
第一种:通过bind传入追加的参数
btn.addEventListener('click',callback.bind(btn,['a','b']),false);
不过这时MouseEvent对象的位置被挤到了我们指定的参数的后面去了。所以,在我们处理callback的时候,对应的形参也要进行变化
var btn = document.querySelector('#btn'); btn.addEventListener('click',callback.bind(btn,['a','b']),false); function callback(arg1,event){ var target = event.target || event.srcElement; console.log(arguments,event,this) }
此时的arg1就等于['a','b'],event 等于MouseEvent,这样就达到了追加参数的目的。为什么arg1不是btn呢?这得从bind的工作原理说起,简单说,bind的第一个参数是作为函数运行时的上下文对象用的。这个和我们下面要说的第二个方法是一样的。
方法二:在不支持bind的情况下,也可以使用apply或call之类的方式,我在第一个位置传入btn,是为了保持事件回调函数的上下文为点击的元素,即callback里边的this指向btn,这是一个小技巧。或者,在callback外边再包一层 :
btn.addEventListener('click',function(event){ callback(event,['a','b']); },false);
不过这种方式对御载事件比较麻烦,因为用的是匿名函数,当然,还有更好的解决方法,那就是用 handleEvent 这个属性。不过它通常需要构造一个对象,比如:
var obj = {
handleEvent : function(event){
callback(event,'a','b','....')
},
click : function(){
btn.addEventListener('click',this,false);
}
}
在handleEvent方法里边,给callback传参数就方便很多了,而且this始终是挂在obj下面,这是非常方便的地方。这也是我最喜欢的用法,各种舒爽谁用谁知道。
好了,关于事件的常见用法就分析到这里了,关于事件的知识还有很多,比如冒包,异步什么的,由于不是本篇的重点,就不再分析了。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?