При выполнении .replaceWith () в jQuery привязки событий не сохраняются - PullRequest
7 голосов
/ 14 февраля 2012

Вот сокращенный пример.

Имейте в виду, что классу .chat-reply привязан обработчик события click.

HTML (кнопка ответа):

<div class="container">
    <a href="#" class="btn small chat-reply">Reply</a>
</div>

Эта функция jQuery вызывается, когда кто-то нажимает другую кнопку , которая отправляет сообщение на сервер для сохранения в базе данных. Это делается с помощью ajax и выполняется успешно. В вышеупомянутом обратном вызове .ajax () success () эта функция вызывается:

$.ajax({
      type      :  'GET',
      url       :  '/some_controller/some_method',
      success   :  function(data) {

      $('.container').replaceWith(data);
    }
});

«Данные» в обратном вызове успеха заменят весь .container div, включая дочернюю кнопку .chat-reply. После этого replaceWith () событие click больше не привязано к кнопке.

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

Ответы [ 4 ]

3 голосов
/ 14 февраля 2012

Захватите jquery 1.7, который теперь использует 'on' для привязки: http://blog.jquery.com/2011/09/28/jquery-1-7-beta-1-released/

Или, если <1.7, используйте 'live' вместо 'bind', так как он будет искать изменения DOM и повторно применять событияизмененного контента.Если нет, вы можете повторно применить событие к вашему обратному вызову. </p>

Старый API для замены для привязки с обработчиками событий живого типа после изменений DOM.

this $ (селектор) .live (события, fn)

становится этим $ (документом) .on (события, селектор, fn)

Или в коде

Это

$(".container a.chat-reply").live("click", function(){
 // do it live!
});

Получается в 1.7

$(".container").on("click", "a.chat-reply", function(event){
 // do it live!
});

С различными вариантами выбора нужного объекта.

2 голосов
/ 14 февраля 2012

В вашем обработчике кликов используйте .on () в качестве делегата вместо

$("div.container").on("click", "a.chat-reply", function(even){
  //click handler here
});

событие будет «пузыриться» до контейнера, и если оно соответствует a.chat-replay, оно сработает.

1 голос
/ 14 февраля 2012

Принято решение о не очень изящном решении, частично благодаря этому сообщению: События не регистрируются после replaceWith

Я создал функцию wireUpChatReply (), которая связывает событие нажатия с кнопкой .chat-reply.

Затем после replaceWith () я вызываю wireUpChatReply () для повторной привязки событий. Я делаю такой же вызов wireUpChatReply для document.ready.

Это не красиво, но работает.

0 голосов
/ 11 января 2018

Два ответа относительно живых событий не решают проблему, потому что сам контейнер заменен, и привязка события исчезла.

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

$(".container").parent().on("click", ".container a.chat-reply", function(){
  // do something
});

или, если есть несколько контейнеров:

$(document.body).on("click", ".container a.chat-reply", function(){
  // do something
});
...