Как создавать живые пользовательские события в jQuery

jQuery имеет очень удобный механизм связывания событий под названием live(), который будет добавлять события к элементам DOM на лету (даже для элементов, которые будут добавлены в DOM позже). Проблема в том, что он работает только с определенными событиями (перечислены здесь в документации).

Я действительно хочу иметь живые события для фокусировки, размытия и изменения, которые сейчас не поддерживаются в прямом эфире. Кроме того, если я смогу создавать пользовательские события в прямом эфире, это сильно изменит правила игры для моего приложения. Большая часть кода, который у меня есть сейчас, посвящена повторной привязке старых событий (изменения, фокуса и пользовательских событий для создания элементов, перетаскиваемых или изменяющих размер) к новым элементам dom, которые были добавлены через ajax.

Есть идеи? Я думаю, делегирование событий — это то, что нужно, но сейчас я усложню код. Может быть, плагин, который обрабатывает делегирование событий... не уверен. Помогите мне найти решение.


person Allen Bargi    schedule 02.05.2009    source источник


Ответы (5)


Эта функция теперь доступна в jQuery 1.4. live() теперь поддерживает все события JavaScript (включая пользовательские события), а события focusin и focusout были представлены как всплывающие версии focus и blur.

Из документации jQuery 1.4 по .live():

Начиная с jQuery 1.4, метод .live() поддерживает пользовательские события, а также все события JavaScript. Два исключения: поскольку фокус и размытие на самом деле не являются всплывающими событиями, вместо этого нам нужно использовать focusin и focusout.

person PCheese    schedule 19.01.2010

Если это не в jQuery, скорее всего, причина. Ошибки браузера и т. д., которые делают его ненадежным. Я бы подождал, пока они его реализуют, или попытался бы использовать оригинальный подключаемый модуль, который стал активным http://docs.jquery.com/Plugins/livequery

Редактировать:

Хорошие минусы, ребята. Есть причина, по которой этого нет в jQuery, и я очень сомневаюсь, что они ленивы. На самом деле я потратил время на чтение источника и поиск того, почему в live() реализованы только определенные события, и я не могу понять, почему. Так что если кто знает... просветите пожалуйста.

person Chad Grant    schedule 02.05.2009
comment
livequery звучит как решение. спасибо, что упомянули об этом. Я проверю это, чтобы увидеть, может ли это решить мои проблемы. - person Allen Bargi; 03.05.2009
comment
Информативный источник о различиях между .live() и плагином livequery. Видимо, они используют разные технологии. groups.google.com/group/jquery-en/browse_thread/thread/ - person Allen Bargi; 03.05.2009

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

Если бы я не использовал jQuery и по-прежнему хотел использовать преимущества live(), я бы использовал захват событий в браузерах, которые его поддерживают (большинство браузеров, отличных от IE), а в IE я бы использовал их onFocusIn< /strong>/onFocusOut события (эти события, в отличие от focus/blur, всплывают).

Вот пример:

function onFocus(el, fn) {
    var outerFn = function(e) {
        e = e || window.event;
        if ((e.target || e.srcElement) === el) {
            fn.call(el);
        }
    };
    if (document.body.addEventListener) {
        // This is event capturing:
        document.body.addEventListener('focus', outerFn, true);
    } else {
        // This is event delegation:
        document.body.attachEvent('onfocusin', outerFn);
    }
    return outerFn;
}

Используй это:

onFocus(document.getElementById('myInputField'), function(){
    log('FOCUSED!!!');
});

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

Подробнее о порядке событий (захвате/пузырьке) читайте здесь: http://www.quirksmode.org/js/events_order.html


Также стоит отметить, что liveQuery, подключаемый модуль jQuery, работает, поскольку повторно привязывает событие к новым элементам; он работает только с методами манипулирования DOM jQuery, такими как «append», «insertBefore» и т. д. Поэтому, если бы вы добавили новый элемент без использования jQuery, это не сработало бы.

person James    schedule 03.05.2009
comment
Я только что посмотрел выступление PPK на Yahoo, в котором он подробно рассказал о событиях javascript, а также упомянул все эти проблемы, связанные с всплывающими событиями и их различиями в разных браузерах. Довольно ценно... Очень рекомендую. yuiblog.com/blog/2009/04/27/video-ppk -jsevents - person Allen Bargi; 03.05.2009

Вы можете проверить плагин jQuery.Listen от Ariel Flesley. Он похож на события live() и плагин livequery(), но поддерживает события focus() и blur().

http://flesler.blogspot.com/2007/10/jquerylisten.html

person Kevin Leary    schedule 04.10.2009

Я успешно использовал плагин livequery в качестве дополнения к функции .live() в jQuery. Он не только может связывать такие события, как фокус, размытие и изменение (которые live() еще не поддерживает, начиная с 1.3.2), но также предоставляет вам механизм для привязки пользовательских событий к элементам DOM на лету. Например, я использовал его для привязки draggable и droppables к некоторым элементам DOM, которые будут добавлены через Ajax. Это делает мой код намного проще для чтения и обслуживания.

person Allen Bargi    schedule 03.05.2009
comment
тогда вам, вероятно, следует принять ответ, предлагающий livequery. - person orip; 04.05.2009