Javascript 重写jQuery';s.on(';mouseenter';)转换为纯JS变体
我有一个包含其他div元素的容器div:Javascript 重写jQuery';s.on(';mouseenter';)转换为纯JS变体,javascript,jquery,Javascript,Jquery,我有一个包含其他div元素的容器div: <div id="container"> <div class="child"></div> <div class="child"></div> <div class="child"></div> </div> 也就是说,我如何才能监听鼠标悬停在哪个子鼠标上以应用于它myFunction?我尝试了以下方法,但这仅适用于容器div的myFuncti
<div id="container">
<div class="child"></div>
<div class="child"></div>
<div class="child"></div>
</div>
也就是说,我如何才能监听鼠标悬停在哪个子鼠标上以应用于它myFunction
?我尝试了以下方法,但这仅适用于容器div的myFunction
:
container.addEventListener('mouseenter',函数(事件){
让hoveredElement=event.target;
if(hoveredElement.tagName==='DIV'){
myFunction(hoveredElement);
}
});代码>
#容器{宽度:200px;}
#容器>div{高度:100px;背景色:红色;}
您需要从e.target
开始,遍历祖先,调用找到的每个div
上的处理程序。当到达绑定元素时,停止遍历祖先
同时将事件类型更改为mouseover
,因为mouseenter
不会冒泡,因此事件。target
始终是绑定元素
const container=document.querySelector(“容器”);
container.addEventListener('mouseover',函数(事件){
设el=event.target;
做{
如果(el.tagName==='DIV'){
myFunction.call(el,event);
}
}而((el=el.parentNode)!==this);
});
函数myFunction(事件){
console.log(this.id);
}
将鼠标悬停以调用该函数
这一个不能调用
我在Chrome上调试了jQuery,而jQuerymouseenter
事件实际上在引擎盖下使用了一个mouseover
事件。
在jQuery源代码第4095行中,有一行在每次触发事件时运行:
jQuery.event.dispatch.apply(元素、参数)代码>
如果您在那里暂停并检查参数
,您会发现它是一个类型为mouseover
的MouseEvent
这是有意义的,因为您正在使用jQuery的委托事件处理程序语法,而且jQuery非常聪明,可以用mouseover
替换mouseenter
因此,您的解决方案本质上就是要做jQuery正在做的事情——使用mouseover
:
container.addEventListener('mouseover',函数(事件){
log(“鼠标越过目标”,event.target);
log(“mouseover currentTarget”,event.currentTarget);
});
container.addEventListener('mouseenter',函数(事件){
log(“mouseenter目标”,event.target);
log(“mouseenter currentTarget”,event.currentTarget);
});
$('#container').on('mouseenter','.child',函数(事件){
log('jquery mouseenter target',event.target);
log('jquery mouseenter currentTarget',event.currentTarget);
log('jquery mouseenter delegateTarget',event.delegateTarget);
});代码>
.child{
边框:1px实心#007;
高度:50px;
}
您尝试的是一种称为事件委派的实践。考虑到目前JavaScript的状态,这很容易做到。为了复制您习惯的JavaScript语法,我创建了一个可返回的对象来使用
使用$get(query)
获取要对其执行委派的元素。在那里,您可以使用on
方法和参数(事件、子元素查询、函数)
当您为
方法上的编写函数时,通常会向它传递事件
参数,但下一个参数将是元素的索引,在本例中,鼠标悬停
参数没有安全防护措施,因为这不是问题的一部分,只需一点润滑脂即可轻松解决:)
let$get=(查询)=>{
if(document.querySelector(查询)){
设returnableObj={
元素:document.querySelector(查询),
名单(q){
返回数组.from(this.ele.queryselectoral(q))
},
获取索引(ele){
返回函数(q){
让我们创建索引;
returnableObj.list(q.filter)(itm,ind)=>{
设bool=ele.isSameNode(itm);
如果(bool)foundIndex=ind;
返回布尔;
});
返回foundIndex>=0?foundIndex:false;
}
}
}
returnableObj.on=函数(evt、childquery、fn){
此.ele.addEventListener(evt,函数(e){
if(e.target.matches(childquery)){
让myIndex=returnableObj.getIndex(e.target)(childquery);
fn(e,myIndex);
}
});
}
返回可返回的OBJ;
}else警报(“无效查询”);
}
设ele=$get(“#mydiv”);
ele.on(“mouseover”,“.child”,函数(e,ind){
警报(‘花生酱!孩子’+(ind+1));
})
h1、h2、h3{
宽度:200px;
}
你好
我想要一些糖果吗?
孩子2我选择你,神龙
儿童3,记分牌
@KevinB你说得对。这不是复制粘贴错误,而是书写错误。div有一个id=“container”
它可以工作!但老实说,我不明白我的函数中的this
如何知道引用子div
,而不将this
作为输入。@Liliane:我使用.call()
调用了myFunction
,可以手动设置this
的值。因此我将el
作为第一个参数传递给.call()
,在myFunction
中将其设置为this
,并将event
作为第二个参数传递给.call()
,并将其作为myFunction
中的第一个参数传递,如果我将mouseenter
更改为mouseover
,则我的初始解决方案有效。然后,不需要do/while和.call()
@Liliane:是的,如果您想在mouseenter
上模拟jQuery的委托,您确实需要循环。在里面
$('#container').on('mouseenter', 'div', myFunction)
let $get = (query) => {
if (document.querySelector(query)) {
let returnableObj = {
ele: document.querySelector(query),
list(q) {
return Array.from(this.ele.querySelectorAll(q))
},
getIndex(ele) {
return function(q) {
let foundIndex;
returnableObj.list(q).filter((itm, ind) => {
let bool = ele.isSameNode(itm);
if (bool) foundIndex = ind;
return bool;
});
return foundIndex >= 0 ? foundIndex : false;
}
}
}
returnableObj.on = function(evt, childquery, fn) {
this.ele.addEventListener(evt, function(e) {
if (e.target.matches(childquery)) {
let myIndex = returnableObj.getIndex(e.target)(childquery);
fn(e, myIndex);
}
});
}
return returnableObj;
} else alert('invalid query');
}