$(this) 和 event.target 之间的区别?
Posted
技术标签:
【中文标题】$(this) 和 event.target 之间的区别?【英文标题】:Difference between $(this) and event.target? 【发布时间】:2012-08-18 03:44:49 【问题描述】:我是 jQuery 新手,正在制作标签式面板,按照 JavaScript 和 jQuery : The Missing Manual 中的教程,作者这样做时第一行:
var target = $(this);
但我试图这样做
var target = evt.target;
我得到了那个错误:
未捕获的类型错误:对象 http://localhost/tabbedPanels/#panel1 没有方法“attr”
当我将 evt.target
改回 $(this)
时,它就像一个魅力。
我想知道$(this)
和evt.target
有什么区别?
这是我的代码,以防你需要它:
index.html:
<!DOCTYPE html>
<html>
<head>
<title>Tabbed Panel</title>
<style>
body
width : 100%;
height: 100%;
#wrapper
margin : auto;
width : 800px;
#tabsContainer
overflow: hidden;
#tabs
padding:0;
margin:0;
#tabs li
float : left;
list-style:none;
#tabs a
text-decoration:none;
padding : 3px 5px;
display : block;
#tabs a.active
background-color : grey;
#panelsContainer
clear: left;
#panel1
color : blue;
#panel2
color : yellow;
#panel3
color: green;
#panel4
color : black;
</style>
<script type="text/javascript" src="jquery-1.8.0.min.js"></script>
<script type="text/javascript" src="script.js"></script>
</head>
<body>
<div id="wrapper">
<div id="tabsContainer">
<ul id="tabs">
<li><a href="#panel1">Panel1</a></li>
<li><a href="#panel2">Panel2</a></li>
<li><a href="#panel3">Panel3</a></li>
<li><a href="#panel4">Panel4</a></li>
</ul>
</div>
<div id="panelsContainer">
<div id="panel1" class="panel">
this is panel1
</div>
<div id="panel2" class="panel">
this is panel2
</div>
<div id="panel3" class="panel">
this is panel3
</div>
<div id="panel4" class="panel">
this is panel4
</div>
</div>
</div>
</body>
</html>
script.js:
$(function()
$("#tabs a").click(function(evt)
var target = evt.target,
targetPanel = target.attr("href");
$(".panel").hide();
$("#tabs a.active").removeClass("active");
target.addClass("active").blur();
$(targetPanel).fadeIn(300);
evt.preventDefault();
);
$("#tabs a:first").click();
)
【问题讨论】:
this
是对 JavaScript DOM 元素的引用。 $()
是 jQuery 提供的将 DOM 元素转换为 jQuery 对象的格式。使用 evt.target
时,您引用的是一个元素,而使用 $(this)
时,您引用的是带有我们可以访问的参数的对象。
你可以做 $(evt.target)
并且(在这种情况下)最终也会得到相同的结果。 .attr()
方法由 jQuery 对象提供,而不是元素本身
【参考方案1】:
'this' 指的是事件侦听器已附加到的 DOM 对象。 'event.target' 指的是触发事件侦听器的 DOM 对象。 一个自然的问题是,为什么事件侦听器会触发其他 DOM 对象。 这是因为事件侦听器附加了父对象的子对象触发器。
【讨论】:
【参考方案2】:$(this)
和event.target
之间存在差异,而且差异很大。虽然this
(或event.currentTarget
,见下文)始终指代侦听器附加到的DOM 元素,但event.target
是被单击的实际DOM 元素。请记住,由于事件冒泡,如果您有
<div class="outer">
<div class="inner"></div>
</div>
并将点击监听器附加到外部 div
$('.outer').click( handler );
然后,当您在外部 div 和内部 div 内部单击时,将调用 handler
(除非您有其他代码处理内部 div 上的事件并停止传播)。
在本例中,当您在内部 div 内部单击时,然后在 handler
中:
this
指的是 .outer
DOM 元素(因为这是处理程序附加到的对象)
event.currentTarget
还指代 .outer
元素(因为这是处理事件的 当前目标 元素)
event.target
指的是 .inner
元素(这为您提供了事件起源的元素)
jQuery 包装器$(this)
仅将 DOM 元素包装在 jQuery 对象中,因此您可以在其上调用 jQuery 函数。您可以对 $(event.target)
执行相同操作。
另外请注意,如果您重新绑定 this
的上下文(例如,如果您使用 Backbone,它会自动完成),它将指向其他内容。您始终可以从 event.currentTarget
获取实际的 DOM 元素。
【讨论】:
【参考方案3】:在事件处理函数或对象方法中,访问“包含元素”属性的一种方法是使用特殊的 this 关键字。 this 关键字表示当前正在处理的函数或方法的所有者。所以:
对于全局函数,这表示窗口。
对于对象方法,this 表示对象实例。
在事件处理程序中,这表示接收事件的元素。
例如:
<!DOCTYPE html>
<html>
<head>
<script>
function mouseDown()
alert(this);
</script>
</head>
<body>
<p onmouseup="mouseDown();alert(this);">Hi</p>
</body>
</html>
这个html渲染后的alert窗口内容分别是:
object Window
object HTMLParagraphElement
一个事件对象与所有事件相关联。它具有提供“有关事件”信息的属性,例如网页中鼠标单击的位置。
例如:
<!DOCTYPE html>
<html>
<head>
<script>
function mouseDown(event)
var theEvent = event ? event : window.event;
var locString = "X = " + theEvent.screenX + " Y = " + theEvent.screenY;
alert(event);
alert(locString);
</script>
</head>
<body>
<p onmouseup="mouseDown(event);">Hi</p>
</body>
</html>
这个html渲染后的alert窗口内容分别是:
object MouseEvent
X = 982 Y = 329
【讨论】:
【参考方案4】:http://api.jquery.com/on/ 状态:
当 jQuery 调用处理程序时,
this
关键字是对 事件被传递的元素;对于直接绑定的事件this
是附加事件并用于委托的元素 eventsthis
是一个元素匹配选择器。 (请注意,this
可能不会 如果事件从后代冒泡,则等于event.target
元素。)从元素创建一个 jQuery 对象,以便它可以 与 jQuery 方法一起使用,使用 $( this )。
如果我们有
<input type="button" class="btn" value ="btn1">
<input type="button" class="btn" value ="btn2">
<input type="button" class="btn" value ="btn3">
<div id="outer">
<input type="button" value ="OuterB" id ="OuterB">
<div id="inner">
<input type="button" class="btn" value ="InnerB" id ="InnerB">
</div>
</div>
检查以下输出:
<script>
$(function()
$(".btn").on("click",function(event)
console.log($(this));
console.log($(event.currentTarget));
console.log($(event.target));
);
$("#outer").on("click",function(event)
console.log($(this));
console.log($(event.currentTarget));
console.log($(event.target));
)
)
</script>
请注意,我使用$
来包装 dom 元素以创建一个 jQuery 对象,这是我们一贯的做法。
您会发现对于第一种情况,this
,event.currentTarget
,event.target
都引用了同一个元素。
而在第二种情况下,当某个包装元素的事件委托被触发时,event.target
将被引用到被触发的元素,而this
和 event.currentTarget
被引用到事件被传递的位置。
对于this
和event.currentTarget
,根据http://api.jquery.com/event.currenttarget/,它们完全一样
【讨论】:
"对于this和event.currentTarget,根据"..其实不是一回事.. $("外层DOM元素").on('click',"内部 DOM 元素",function() $(this) // 指的是“内部 DOM 元素” ) 在这种情况下 currentTarget 指的是“外部 DOM 元素”而 $(this) 指的是“内部 DOM 元素”跨度> 【参考方案5】:jQuery 使用“on”方法处理 this 变量的方式有很大不同
$("outer DOM element").on('click',"inner DOM element",function()
$(this) // refers to the "inner DOM element"
)
如果您将其与以下内容进行比较:-
$("outer DOM element").click(function()
$(this) // refers to the "outer DOM element"
)
【讨论】:
【参考方案6】:this
是对正在处理事件的 DOM 元素(当前目标)的引用。 event.target
指的是启动事件的元素。在这种情况下,它们是相同的,而且通常可以,但不一定总是如此。
您可以通过查看jQuery event docs 来很好地了解这一点,但总结一下:
event.currentTarget
事件冒泡中的当前DOM元素 阶段。
event.delegateTarget
当前调用jQuery所在的元素 事件处理程序已附加。
event.relatedTarget
事件中涉及的其他 DOM 元素,如果有的话。
event.target
发起事件的 DOM 元素。
要使用 jQuery 获得所需的功能,您必须使用以下任一方法将其包装在 jQuery 对象中:$(this)
或 $(evt.target)
。
.attr()
方法仅适用于 jQuery 对象,不适用于 DOM 元素。 $(evt.target).attr('href')
或简单的 evt.target.href
会给你你想要的。
【讨论】:
它们不一定都引用同一个元素。请参阅彼得的答案。 确实如此,感谢您指出这一点。重新阅读我的旧答案总是很有趣......【参考方案7】:这里存在跨浏览器问题。
一个典型的非 jQuery 事件处理程序是这样的:
function doSomething(evt)
evt = evt || window.event;
var target = evt.target || evt.srcElement;
if (target.nodeType == 3) // defeat Safari bug
target = target.parentNode;
//do stuff here
jQuery 规范化 evt
并使目标在事件处理程序中作为 this
可用,因此典型的 jQuery 事件处理程序将是这样的:
function doSomething(evt)
var $target = $(this);
//do stuff here
使用 jQuery 的规范化 evt
和 POJS 目标的混合事件处理程序将是这样的:
function doSomething(evt)
var target = evt.target || evt.srcElement;
if (target.nodeType == 3) // defeat Safari bug
target = target.parentNode;
//do stuff here
【讨论】:
以上是关于$(this) 和 event.target 之间的区别?的主要内容,如果未能解决你的问题,请参考以下文章