Копирование событий из одного элемента в другой с помощью jquery
У меня DOM выглядит так:
<a href='javascript:void(0)' id='link1'>Element with events bound initially</a>
<a href='javascript:void(0)' id='link2'>Element to which events are bound in future</a>
И этот javascript:
$(function(){
$('#link1').bind('click',function(){alert('do something to make me happy');})
});
Теперь, в будущем, я хочу скопировать все события, связанные с link1 в link2. Я делаю это, как указано ниже, предложите лучший способ, если это возможно или доступно.
var _elmEvents = $(#link1).data('events');
if (_elmEvents) {
$.each(_elmEvents, function (event, handlers) {
$.each(handlers, function (j, handler) {
$('#link2').bind(event, handler);
});
});
}
Ответы
Ответ 1
Если вы хотите скопировать все события из одного объекта в другой без клонирования, вы можете сделать это, напрямую обратившись к данным событий.
Например, если вы это сделали:
$("#the_link").click(function(e){
// do some stuff
return false;
}.mouseover(function(e){
// do some other stuff
});
Вы можете получить доступ к этим ассоциациям событий в данных "событий" элемента
var events = $("#the_link").data('events');
Это будет объект, ключи которого представляют тип события, каждый из которых содержит массив ассоциаций событий. Независимо от того, здесь простой пример, не учитывающий пространства имен.
var events = $("#the_link").data('events');
var $other_link = $("#other_link");
if ( events ) {
for ( var eventType in events ) {
for ( var idx in events[eventType] ) {
// this will essentially do $other_link.click( fn ) for each bound event
$other_link[ eventType ]( events[eventType][idx].handler );
}
}
}
Ответ 2
Принятый ответ не работал у меня, поскольку я использую пространства имен и другие события (например, "вставить" ), которые не являются методом в jQuery.
Это сработало для меня:
function copyEvents(source, destination) {
// Get source events
var events = source.data('events');
// Iterate through all event types
$.each(events, function(eventType, eventArray) {
// Iterate through every bound handler
$.each(eventArray, function(index, event) {
// Take event namespaces into account
var eventToBind = event.namespace.length > 0
? (event.type + '.' + event.namespace)
: (event.type);
// Bind event
destination.bind(eventToBind, event.data, event.handler);
});
});
}
Ответ 3
Отметьте этот ресурс.
Ответ 4
Вы можете clone элемент и управлять новым элементом, но хотите, однако jQuery не обеспечивает простой способ копирования обработчиков событий от одного элемента к другому. Однако код, который будет делать это, будет:
var events = jQuery.data( originalElement, "events" );
for ( var type in events ) {
for ( var handler in events[ type ] ) {
jQuery.event.add( targetElement, type, events[ type ][ handler ], events[ type ][ handler ].data );
}
}
Но поскольку он полагается на внутренние элементы jQuery, я попытался бы сделать решение с помощью clone.
Ответ 5
Это хорошо работало в моем script.
$.each($('#original').data('events'), function() {
// iterate registered handler of original
$.each(this, function() {
$('#target').bind(this.type, this.handler);
});
});
Я нашел его здесь (источник): http://snipplr.com/view/64750/
Ответ 6
Это основано на Brandons, но обновлено для работы со всеми версиями jQuery. Протестировано на 1.6.4
до 2.0.x
.
/**
* Logic for copying events from one jQuery object to another.
*
* @private
* @name jQuery.event.copy
* @param jQuery|String|DOM Element jQuery object to copy events from. Only uses the first matched element.
* @param jQuery|String|DOM Element jQuery object to copy events to. Copies to all matched elements.
* @type undefined
* @cat Plugins/copyEvents
* @author Brandon Aaron ([email protected] || http://brandonaaron.net)
* @author Yannick Albert ([email protected] || http://yckart.com)
*/
jQuery.event.copy = function (from, to) {
from = from.jquery ? from : jQuery(from);
to = to.jquery ? to : jQuery(to);
var events = from[0].events || jQuery.data(from[0], "events") || jQuery._data(from[0], "events");
if (!from.length || !to.length || !events) return;
return to.each(function () {
for (var type in events)
for (var handler in events[type])
jQuery.event.add(this, type, events[type][handler], events[type][handler].data);
});
};