Trong trường hợp xử lý sự kiện được ủy quyền, nơi bạn có thể có một cái gì đó như thế này:
<ul>
<li data-id="1">
<span>Item 1</span>
</li>
<li data-id="2">
<span>Item 2</span>
</li>
<li data-id="3">
<span>Item 3</span>
</li>
<li data-id="4">
<span>Item 4</span>
</li>
<li data-id="5">
<span>Item 5</span>
</li>
</ul>
và mã JS của bạn như vậy:
$(document).ready(function() {
$('ul').on('click li', function(event) {
var $target = $(event.target),
itemId = $target.data('id');
//do something with itemId
});
});
Nhiều khả năng bạn sẽ thấy rằng itemId là undefined
, vì nội dung của LI được gói trong một <span>
, có nghĩa là <span>
có thể sẽ là mục tiêu sự kiện. Bạn có thể khắc phục điều này bằng một tấm séc nhỏ, như vậy:
$(document).ready(function() {
$('ul').on('click li', function(event) {
var $target = $(event.target).is('li') ? $(event.target) : $(event.target).closest('li'),
itemId = $target.data('id');
//do something with itemId
});
});
Hoặc, nếu bạn muốn tối đa hóa khả năng đọc (và cũng tránh lặp lại các cuộc gọi gói jQuery không cần thiết):
$(document).ready(function() {
$('ul').on('click li', function(event) {
var $target = $(event.target),
itemId;
$target = $target.is('li') ? $target : $target.closest('li');
itemId = $target.data('id');
//do something with itemId
});
});
Khi sử dụng phân quyền sự kiện, .is()
phương thức này là vô giá để xác minh rằng mục tiêu sự kiện của bạn (trong số những thứ khác) thực sự là những gì bạn cần. Sử dụng .closest(selector)
để tìm kiếm cây DOM và sử dụng .find(selector)
(thường được kết hợp với .first()
, như trong .find(selector).first()
) để tìm kiếm nó. Bạn không cần sử dụng .first()
khi sử dụng .closest()
, vì nó chỉ trả về phần tử tổ tiên phù hợp đầu tiên, trong khi .find()
trả về tất cả các hậu duệ phù hợp.