我遇到的问题非常类似于:"Jquery 'click' not firing when icon is on button"但是该帖子的解决方案并没有为我提供解决方案,所以我认为可能会发生一些不同的事情。
基本问题是我有一个带有图标的按钮。当我点击按钮(例如文本)时,事件目标是按钮元素;但是当我点击图标时,事件目标就是图标对象。不幸的是,这非常烦人,因为我将数据值存储在我想要访问的按钮上。
这是HTML:
<button class="btn btn-success vote-button" id="btnUpVote" type="button" data-vote="1">
<i class="fa fa-thumbs-up"></i>
Up Vote!
</button>
<button class="btn btn-danger vote-button" id="btnDownVote" type="button" data-vote="-1">
<i class="fa fa-thumbs-down"></i>
Down Vote!
</button>
这是Javascript:
function sendVote(event) {
var $btn = $(event.target);
console.log(parseInt($btn.data('vote'));
console.log($btn.prop('tagName'));
}
$('body').on('click', 'button.vote-button', sendVote);
点击文字(&#34; Up Vote!&#34;或&#34; Down Vote!&#34;)会产生以下控制台输出:
1
BUTTON
-1
BUTTON
单击图标(等)会产生以下控制台输出:
NaN
I
NaN
I
即使我已经使用选择器&#34; button.vote-button&#34;注册了元素上的句柄。有谁知道为什么会这样?我讨厌必须为图标提供数据属性。
答案 0 :(得分:38)
使用event.currentTarget
,它始终是侦听事件的对象; event.target
是接收事件的实际目标,在这种情况下不是您想要的,因为它可能是图标。
如果用户点击图标,则event.currentTarget
会将事件冒泡到对象侦听器,即您案例中的按钮。如果用户单击该按钮,它仍然可以工作,因为对象监听器再次是您的按钮。
答案 1 :(得分:5)
它是由事件传播引起的。单击按钮内的图标,以便click
事件通过DOM从图标向上传播到按钮,一直向上传播到文档。这会导致您的click
事件处理程序代码被执行。
如果问题是每次代码运行时你只想要按钮的引用,但是当你点击图标而不是文本时仍然希望它被触发,你只需要使用this
而不是event.target
:
var $btn = $(this);
...
jQuery将确保this
始终引用该按钮,即使实际的event.target
元素是其中的元素。
答案 2 :(得分:1)
更新此内容是因为$(event.target)
并非始终为button
,因此您必须按建议使用三元运算符,或将$(event.target)
替换为始终为$(this)
的{{1}}在选择器的上下文中:
button
或function sendVote(event) {
event.stopPropagation();
var $btn = $(event.target).is('button') ? $(event.target) : $(event.target).parent();
console.log(parseInt($btn.data('vote')));
console.log($btn.prop('tagName'));
}
$(function () {
$('body').on('click','button.vote-button', sendVote);
});
始终为$(this)
,因为事件已绑定到它,如果您点击它的任何子项,那么button
将冒泡到dom树和事件绑定按钮执行:
event
答案 3 :(得分:0)
如果标记名是I,那么只需检查函数内部,如果是,则将父项作为$ btn。 http://jsfiddle.net/jFIT/qZgYU/3/
$('body').on('click', 'button.vote-button', function() {
var $btn = $(this).prop('tagName').toLowerCase() == "i" ? $(this).parent() : $(this);
console.log(parseInt($btn.data('vote')));
console.log($btn.prop('tagName'));
});
答案 4 :(得分:0)
简单的CSS解决方案:
button > * {
pointer-events: none;
}