css, html, php, javascript, jQuery, ajax … – решения, примеры, рецепты
13 Янв
Месяц назад в блоге была опубликована статья «Обработка событий для элементов DOM, загружаемых через ajax» (ее стоит прочитать, чтобы быть в курсе), в комментариях к которой многие поделились своими способами решения проблемы. Среди прочих было упоминание плагина Live Query о котором сегодня и пойдет речь.
Плагин Live Query использует возможности селекторов jQuery для связывания событий или вызова функций-обработчиков для выбранных элементов автоматически, при обновлении дерева DOM.
Подключив плагин к странице
<script type="text/javascript" src="js/jquery-1.2.6.js"></script> <script type="text/javascript" src="js/jquery.livequery.js"></script>
мы можем использовать всю его функциональность. Теперь, чтобы автоматически связывать событие click с любым элементом (пусть для примера это будет параграф p), который есть или появится в будущем в объектной модели документа, достаточно написать такой код:
$("p").livequery("click", function() {
alert($(this).text());
});
Клик по параграфу приведет к тому, что в alert’е будет выведен текст, содержащийся в этом параграфе.
Вот пример, где Вы сможете испытать работу плагина. Попробуйте покликать по параграфам, как по изначально существующим, так и по добавленным с помощью ajax-запроса. Затем попробуйте удалить обработчики события, кликнув по соответствующей кнопке.
Но это не все возможности плагина Live Query. Мы познакомимся с некоторыми методами, которые предлагает плагин и начнем с метода livequery(type, fn), который был использован в примере.
livequery(type, fn) – связывает обработчик события, определенный в параметре fn, с событием, указанным в параметре type. В этом параметре можно указать любое событие jQuery. Функция-обработчик будет вызвана для каждого элемента набора, к которому применен метод livequery. Любой элемент, если он при появлении в DOM будет соответствовать тому селектору jQuery, с помощью которого создавался набор, автоматически будет связан с существующим обработчиком события. Как только элемент перестает соответствовать селектору – он потеряет и обработчик.
expire( ) – этот метод удаляет все события и их обработчики, связанных с элементами набора к которому применен метод.
expire( type ) – позволяет удалить только обработчики для события, определенного в параметре type.
expire( type, fn ) – позволяет удалить обработчики, определенные в параметре fn для события, определенного в параметре type.
Кстати, обнаружил, что первые статьи появились в блоге ровно год назад – так что «С Днем Рождения, блог!».
Отзывов (39) на «Плагин Live Query»
о))) типа по моему коменту сделали? ))) приятно))
в 1.3 сдается мне он будет интегрирован в ядро.
Удобная вещь, но неудобно постоянно подключать плагин и привязывать свой код к его использованию. Хорошо, что v1.3 избавит нас от этого…
Кстати данное решение актуально не только для данных полученных через ajax. Это подходит если вы просто добавили блок кода через $(«xxx»).append();
О, спасибо за информацию. Буду думать, как прикрутить этот плагин к jquery.tooltip, чтоб всплывающие подсказки работали для динамически создаваемых объектов.
При добавлении данного кода
jQuery(«#a[rel*=lightbox]«).livequery(‘click’,
function(event){
jQuery(this).lightBox({
fixedNavigation:true
});
}
);
на страницу в консоли ошибка jQuery(«#a[rel*=lightbox]«).livequery is not a function
В чём может быть проблема?
Антон, а ты плагин прицепил?
Подключил
если интересно,можешь свой пример кинуть…. на досуге гляну… dber-ov@mail.ru
Здравствуйте.
Опыта работы с javascript практически нет, так что вопрос может показаться глупым
Имеется:
в который с помощью:
$(‘#menu’).find(‘a’).click(function(){
var url = $(this).attr(‘href’);
$(‘#content’).empty().load(url);return false;
грузится div для карусели (jcarousel):
…..
к которому в свою очередь «прикручена» функция формирования карусели (находится на главной):
$(‘#faq-carousel ul’).jCarouselFade(
{itemVisible: 3, ….} );
Проблема: в том что она конечно же не отрабатывает. Топчусь второй день на этих граблях.
Не знаю как правильнее спросить. live() связывает событие с обработчиком для нового элемента, а тут функция…Подскажите, может я чего не так понял.
dber спасибо за помощь. Ошибка была в банальном подключении, а именно, сам плагин лежал в другом каталоге
информация очень полезная, большое спасибо, но дизайн страшно неудобный!
хотелось бы, чтобы информационная составляющая занимала бОльшую часть страницы, а не 40%.
за инфу спасибо еще раз.
А не подскажите, как именно работает данный метод live?
а) Вешает обработчик на каждый созданный динамический узел DOM
б) Вешает один глобальный обработчик и в нем уже проверяет, куда пересылать указанное событие
У меня на странице выводятся данные в виде дерева через ajax. Теоретически – пользователь может открыть до 1000 и больше узлов. И, как я понимаю, при навешивании обработчика на каждый узел это будет тормощить систему (хотя, возможно и не сильно). Я сейчас определил обработчик на контейнер и там разгребаю сообщение в зависимости от того, на чем именно нажали.
Но данный метод может сделать мой код более красивым.
Если честно, то в код не смотрел даже. Просто в реальных проектах до сих пор 1.2.6 использую, на 1.3.2 пока мало что делал…
Здраствуйте!
Код начинается с аякс запроса к скрипту который который возвращает результат в виде divov следущего вида.
Название жанра1
del
right
Название жанра1
del
right
затем мне надо скрыть блоки .janr-content.
пишу
$(«.janr-content»).hide();
Ничего не выходит. Тут видимо нужно live query использовать но ума не приложу как по синтаксису правильно. Пробывал
$(«.janr-content»).livequery(hide(););
$(«.janr-content»).livequery(«hide()»);
и как только не пробывал но не могу понять как надо?
События то нет. Скрываться они должны не по клику, и ни при навединии а просто «при рождении».
Заранее признателен за ответ.
Нет, у Вас и синтаксис не совсем верен… Да и зачем тут live() вообще? Просто при создании элемента воспользуйтесь методом css и сделайте что-то типа:
$(‘.janr-content’).css(‘display’,'none’);
Здравствуйте, Геннадий и читатели.
У меня такая проблема, только на вас вся надежда. Есть такой html
Info1
Info1
Info1
Info1
Нужно написать такой код, который бы по щелчку на любой строке добавлял бы сразу после нее еще строку, например такого вида: Kukuku. А при повторном щелчке ее удалял бы.
Начал делать так:
$(document).ready(function() {
$(«.aa»).click(function(){
$(this).after(«Привет чуваки»);
});
});
Так строка добавляется, а вот как ее удалить никак не придумаю…нужно что-то типа такого:
$(document).ready(function() {
$(«.aa»).click(function(){
if(document.getElementById(‘aa2′))
{
$(«#aa2′).remove();
}
else
{
$(this).after(«Привет чуваки»);
}
});
});
А вот как грамотно реализовать это, уму не приложу….Тем более что проверять на существование объекта DOM, который добавляеться динамически совершенно непонятно как… Очень прошу помощи гениев JQuery… заранее очень благодарен..
P.S.
правильные теги подрезались..
там таблица вверху такая:
[table]
[tr class='aa'][td]Info1[/td][/tr]
[tr class='aa'][td]Info1[/td][/tr]
[tr class='aa'][td]Info1[/td][/tr]
[tr class='aa'][td]Info1[/td][/tr]
[/table]
а вставляется строка: [tr class='aa2'][td]Привет чуваки[/td][/tr]
$("tr").toggle(function(){
$(this).after('<tr class="aa"><td>Привет, чуваки!</td></tr>');
},
function(){
$(this).next("tr").remove();
}
);
Спасибо большое, Геннадий. Все оказалось проще чем я думал
Продолжу грызть матчасть) Кстати, купил вашу книгу по ajax – могу сказать, что это первый учебник написанный русскими авторами, который я отношу к must have. )
Кстати маленький вопросик. В вашем примере:
$(this).after(‘
Привет, чуваки!
‘);
Здесь Html в функцию after() вставлен в несколько строк. Но при функция корректно срабатывает только если он вставлен в одну строку. Не могли бы вы уточнить в чем может быть причина?
В синтаксисе JS причина. А у меня просто плагин вордпрессовский постоянно то в коде сожрет чего-нибудь, то перенесет строку где не надо….
Как быть если полученные через AJAX данные должны быть droppable. Мне интересный метод drop()? (UI Droppable)
Спасибо!
Попробуйте загружать код инициализации плагина вместе с загружаемыми данными. Вероятно это самый простой путь.
а как насчет live селекторов?
ну, например:
$(‘a’).css( {color: ‘red’} );
чтобы подгружаемые через ajax элементы принимали нужные свой-ва?
вообще задача, получать инфу/событие измнения DOM.
неужели, без таймера никак не обойтись?
или я зря переживаю, может такой код и не сильно будет нагружать браузер?
var i = setInterval(function()
{
$(‘a’).each(function(){
});
}, 1000);
в дополнение к вышесказанному:
ajax грузит левый скрипт, поэтому success я обработать не могу.
хотя, только если внедриться как-то глобально в XMLHttpRequest
den, походу у Вас небольшая каша в голове ….
Этот плагин очень старый – использовался в версии jQuery до 1.3. Сейчас в составе библиотеки есть соответствующие методы – просто читайте документацию, а если что-то непонятно останется, то технические вопросы лучше задавать на форуме jQuery.
Подскажите пожалуйста!
Есть jquery.corner.js для скругления границ.
Но при загрузке div через ajax скругление для него не применяется (((
Как будет выглядеть $(‘#div_id’).corner(‘tl br’); в таком случае?
Все дело в том, что загруженный с помощью ajax-запроса элемент появляется в DOM уже ПОСЛЕ того, как к элементам была применена функциональность плагина corner. Поэтому у загруженного элемента уголков не появляется.
Вывод – инициализировать плагин, т.е. писать $(‘#div_id’).corner(‘tl br’); в коде, который отрабатывает при успешном выполнении ajax-запроса. В опции success например (для вспомогательной функции $.ajax(options).
А вообще такие вопросы лучше на форуме задавать.
а можно как-нибудь метод each всунуть внутрь live?
Можно… Просто вопрос не совсем понятен. Метод live() используется (грубо говоря) для развешивания обработчиков на несуществующие (пока) элементы DOM. Может быть имелось ввиду, что «всунуть метод each» внутрь обработчика события навешенного с помощью live()? А вообще лучше такие вопросы на форуме задавать – удобнее там.
нужно совершить обход несуществующих пока элементов, и назначить им какие-то обработчики. вобщем, пока я обошелся без этого. непонятно как, но работает как надо.
пс. что касается форума, то там больно много «хамят», не побоюсь этого слова, тем кто не понимает казалось бы очевидных вещей. я поэтому и обрадовался, что увидел, что снова можно оставлять отзывы тут.
Ну, положим там не хамят, а просто не любят тех, кто хочет не вникнуть в суть, а решить свою проблему чужими мозгами.
подскажите, пож-ста, как совершить обход несуществующих пока элементов, всё-таки вариант типа «непонятно как, но работает как надо» меня не устраивает.
Дмитрий, с какой целью-то? Обход элементов обычно совершается с целью применить к каждому элементу какую-то функцию например. Причем зачастую функция эта принимает в качестве аргументов какие-либо параметры текущего элемента.
Как Вы все это себе представляете для «несуществующих элементов»???
Может Вам просто с помощью live() хочется навесить соответствующие обработчики событий на выбранный(ые) (и пока не существующие) элемент(ы) DOM?
Тогда Вы уже это сделали. А непонимание того, как именно это произошло – не от непонимания механизмов самого live(), а скорее от непонимания механизма селекторов в jQuery.
Ну а уж по селекторам материалов в сети просто завались
нет, дело не в селекторах.
я обошелся без метода live вообще, хотя изначального нужного элемента на странице нету ….
это и выглядит очень подозрительно…
>>> это и выглядит очень подозрительно…
чтобы говорить предметно, нужно видеть коды. Без них рассуждать бессмысленно.
Такой разговор возможен, но только тогда на форуме. Если не хотите выносить на всеобщее обсуждение – можете написать мне в личку.
вру. ничего не заработало. работает там, где такие элементы есть. спасибо.
попробую написать вам.
в принципе действительно, можно обойтись и без each. прямо непосредственно назначая обработчик. и незачем обходить их как-то заранее. дурацкая привычка. но проблемы остались. но это уже второй вопрос. спасибо вам!
Оставьте отзыв