Работает ли jQuery.on() для элементов, которые добавляются после создания обработчика событий?
Все это время у меня было впечатление, что .on()
работал как .live()
в отношении динамически создаваемых элементов (например, я использую $('.foo').on('click', function(){alert('click')});
а затем элемент с классом foo
создается из-за некоторого AJAX, теперь я ожидаю, что щелчок по этому элементу вызовет предупреждение). На практике это были не те результаты, которые я получил. Я мог ошибиться, но кто-нибудь мог бы помочь мне понять новый способ достижения этих результатов после .on()
?
Заранее спасибо.
2 ответа
.on()
работает с динамически созданными элементами, если он используется правильно. JQuery Doc делает довольно хорошую работу по его описанию.
Способ использовать его для динамических элементов - использовать эту форму:
$("static selector").on('click', "dynamic selector", fn);
Статический селектор должен разрешаться для некоторого объекта, который является одновременно предком ваших динамических объектов и является статическим - присутствует при запуске этой строки кода и не будет удален или воссоздан.
Динамический селектор - это селектор, который соответствует вашим динамическим элементам. Они не должны существовать во время первой установки обработчика событий, и они могут приходить и уходить так часто, как вы хотите.
Так что если "#container"
соответствует статическому предку и ".foo"
соответствует вашим динамическим элементам, которые вы хотите обработчики кликов, вы бы использовали это;
$("#container").on("click", ".foo", fn);
Если вы действительно хотите это понять, вот как делегированная обработка событий .on()
работает. Когда вы делаете .on()
вызов выше, он прикрепил обработчик события click к #container
объект. Некоторое время спустя, когда вы нажимаете на .foo
объект, нет обработчика клика на фактическом .foo
объект, так что щелчок пузырьков вверх по цепочке предков. Когда щелчок достигает #container
объект, есть обработчик щелчка, и jQuery смотрит на этот обработчик и видит, что этот обработчик предназначен только для объектов, в которых исходный объект, на который нажали, совпадает с селектором ".foo"
, Он проверяет цель события, чтобы определить, соответствует ли она этому селектору, и если да, то вызывает для нее обработчик события.
(Сейчас не рекомендуется) .live()
Метод работал, прикрепляя все обработчики событий к объекту документа. Так как объект документа является предком каждого объекта в документе, они получили делегированное управление событиями таким образом. Итак, в приведенном выше примере эти два эквивалента:
$(document).on("click", ".foo", fn);
$(".foo").live("click", fn);
Но присоединение всех делегированных обработчиков событий к документу иногда создавало серьезное узкое место в производительности, поэтому jQuery решил, что это плохой способ, и лучше потребовать от разработчика указать статического предка, который, как мы надеемся, ближе к реальному целевому объекту, чем объект документа.
Я думаю, что вы столкнулись с подобной ситуацией, с которой я столкнулся. Это довольно хорошее решение для связывания событий с элементами, сгенерированными позже.
Привязка событий Jquery к элементам, созданным с помощью других событий