it-swarm.com.ru

jQuery .live () и метод .on () для добавления события щелчка после загрузки динамического HTML

Я использую jQuery v.1.7.1, где метод .live () явно устарел.

Проблема у меня заключается в том, что при динамической загрузке HTML в элемент с помощью:

$('#parent').load("http://..."); 

Если я попытаюсь добавить событие click после этого, оно не регистрирует событие одним из следующих способов:

$('#parent').click(function() ...); 

или же

// according to documentation this should be used instead of .live()
$('#child').on('click', function() ...); 

Как правильно достичь этой функциональности? Кажется, он работает только с .live (), но я не должен использовать этот метод. Обратите внимание, что #child является динамически загружаемым элементом.

Благодарю.

203
Sean Thoman

Если вы хотите, чтобы обработчик щелчков работал для элемента, который загружается динамически, то вы устанавливаете обработчик событий для родительского объекта (который не загружается динамически) и назначаете ему селектор, соответствующий вашему динамическому объекту, например:

$('#parent').on("click", "#child", function() {});

Обработчик события будет присоединен к объекту #parent, и каждый раз, когда всплывает событие click, возникшее в #child, он запускает ваш обработчик кликов. Это называется делегированной обработкой событий (обработка событий делегируется родительскому объекту).

Это сделано так, потому что вы можете прикрепить событие к объекту #parent, даже если объект #child еще не существует, но когда он позже существует и щелкается по нему, событие click будет пузыриться до объекта #parent, оно увидит, что оно произошел от #child и есть обработчик событий для клика по #child и запуска вашего события.

585
jfriend00

Попробуй это:

$('#parent').on('click', '#child', function() {
    // Code
});

Из $.on() документации:

Обработчики событий связаны только с выбранными в данный момент элементами; они должны существовать на странице в тот момент, когда ваш код вызывает .on().

Ваш элемент #child не существует, когда вы вызываете для него $.on(), поэтому событие не связано (в отличие от $.live()). Однако #parent существует, поэтому связывание события с этим вполне допустимо.

Второй аргумент в моем коде выше действует как "фильтр", который срабатывает, только если событие всплыло до #parent из #child.

32
Bojangles

$(document).on('click', '#selector', function() { /* do stuff */ });

Правка: Я предоставляю немного больше информации о том, как это работает, потому что ... слова. В этом примере вы размещаете слушателя на весь документ.

Когда вы click на любом элементе (элементах), совпадающих с #selector, событие всплывает до основного документа - при условии, что нет других слушателей, которые вызывают метод event.stopPropagation() - что приведет к нарастанию пузыря события для родительских элементов.

Вместо привязки к определенному элементу или набору элементов вы прослушиваете любые события, поступающие от элементов, которые соответствуют указанному селектору. Это означает, что вы можете создать один прослушиватель, один раз, который будет автоматически сопоставлять существующие в настоящее время элементы, а также любые динамически добавленные элементы.

Это разумно по нескольким причинам, включая производительность и использование памяти (в крупномасштабных приложениях)

20
L422Y

Эквивалент .live () в 1.7 выглядит так:

$(document).on('click', '#child', function() ...); 

По сути, смотрите в документе события кликов и фильтруйте их по #child.

11
Jared

Я знаю, что уже немного поздно для ответа, но я создал polyfill для метода .live (). Я протестировал его в jQuery 1.11, и, похоже, он работает довольно хорошо. Я знаю, что мы должны реализовывать метод .on () везде, где это возможно, но в больших проектах, где невозможно преобразовать все вызовы .live () в эквивалентные вызовы .on () по любой причине, может произойти следующее Работа:

if(jQuery && !jQuery.fn.live) {
    jQuery.fn.live = function(evt, func) {
        $('body').on(evt, this.selector, func);
    }
}

Просто включите его после загрузки jQuery и перед вызовом live ().

9
NSV

.on () для jQuery версии 1.7 и выше. Если у вас более старая версия, используйте это:

$("#SomeId").live("click",function(){
    //do stuff;
});
5
Matt Cashatt

Я использовал "live" в своем проекте, но один из моих друзей предложил мне использовать "on" вместо live. И когда я попытался использовать это, я столкнулся с проблемой, как у вас.

На своих страницах я динамически создаю ряды таблиц кнопок и многое другое. но когда я использую магию исчезла.

Другие решения, такие как использование, как ребенок, просто вызывает ваши функции каждый раз при каждом нажатии. Но я нахожу способ сделать это снова, и вот решение.

Напишите свой код как:

function caller(){
    $('.ObjectYouWntToCall').on("click", function() {...magic...});
}

Вызов вызывающего абонента (); после создания вашего объекта на странице, как это.

$('<dom class="ObjectYouWntToCall">bla... bla...<dom>').appendTo("#whereeveryouwant");
caller();

Таким образом, ваша функция вызывается, когда предполагается, что не каждый клик на странице.

3
Coderx07