2012-05-07 15 views
5

Estoy escribiendo un script en el que me gustaría manejar eventos de mouse solo si no han sido manejados por ningún otro elemento anteriormente.Manejo de eventos de Javascript no manejados por otros elementos

Puedo adjuntar un detector de eventos al objeto del documento, pero recibirá todos los eventos independientemente de si ya se han procesado.

No tengo control sobre los elementos en la página HTML así que no puedo detener manualmente Propagación() cuando se maneja el evento.

¿Alguna idea?

+1

¿Cómo están vinculados los eventos de clic que no controla? –

+0

Realmente no puedo saberlo, ya que esto es parte de una biblioteca que se puede usar con diferentes tipos de páginas. Podría ser addEventListener o onXXX. – Grodriguez

+1

Sí, 'addEventListener' lo hace más difícil. Para los tipos de [evento], puede tenerlo para que su controlador vinculado al documento comience con el 'e.target', y lo pruebe y sus antepasados ​​para ver cuál tenía el controlador, luego envuélvalo con una función que llame 'stopPropagation'. Pero 'addEventListener' no te permitirá hacer eso. –

Respuesta

1

De este artículo here.

Parece que todavía no es posible hacer esto.

¿Qué controladores de eventos están registrados?

Un problema de la implementación actual del registro de eventos del W3C modelo es que no se puede averiguar si alguno de los controladores de eventos ya están registrados en un elemento. En el modelo tradicional que podría hacer:

alert(element.onclick)

y nos vemos la función que está registrada a , o indefinido si no hay nada registrado. Sólo en sus muy reciente DOM Nivel 3 Eventos W3C añade un

eventListenerList

para almacenar una lista de eventos manipuladores que están registrados actualmente en un elemento. Esta funcionalidad aún no es compatible con ningún navegador, es demasiado nuevo. Sin embargo, el problema ha sido abordado.

Afortunadamente

removeEventListener() 

no da ningún error si el detector de eventos que desea eliminar no se ha agregado al elemento, por lo que cuando de duda siempre se puede utilizar removeEventListener ()

+0

OK ... (aunque realmente no necesito una lista de oyentes). Veamos si puedo encontrar otra forma. – Grodriguez

1

Por lo tanto, puede lograr algo como lo desea en un determinado conjunto de circunstancias. En concreto, si

  • Puede cargar su propia JavaScript personalizado antes de que el original de
  • Usted sabe cuáles son los elementos que está escuchando para que otros tiran eventos en

Efectivamente, lo que hace es reemplazar el original El método addEventListener en el elemento de destino con uno personalizado que intercepta la llamada, realiza algún procesamiento especial y luego lo deja continuar de manera normal. Este 'procesamiento especial' es una nueva función que envuelve la devolución de llamada original y marca los argumentos del evento con algún estado para hacerle saber que alguien más ya manejó el evento. Aquí está una prueba de concepto (con un jsFiddle)

Objetivo HTML:

<div id='asdf'>asdf</div>​ 

JavaScript:

var target = document.getElementById('asdf'); 
var original = target.addEventListener; 

var updated = function(){ 
    // Grab the original callback, so we can use it in our wrapper 
    var originalFunc = arguments[1]; 

    // Create new function for the callback, that lets us set a state letting us know it has been handled by someone 
    // Finish the callback by executing the original callback 
    var newFunc = function(e){ 
     console.log('haha, intercepted you'); 
     e.intercepted = true; 
     originalFunc.call(this, e); 
    }; 

    // Set the new function in place in the original arguments 'array' 
    arguments[1] = newFunc; 

    // Perform the standard addEventListener logic with our new wrapper function 
    original.apply(this, arguments); 
}; 

// Set the addEventListener on our target to our modified version 
target.addEventListener = updated; 

// Standard event handling 
target.addEventListener('click', function(e){ 
    console.log('original click'); 
    console.log('intercepted?', e.intercepted); 
}) 
+0

Esta es una idea interesante. Puedo asegurarme de que mi JS se ejecutará antes que el original. Sin embargo, no tengo forma de saber qué elementos agregarán un detector de eventos. ¿Hay alguna manera de hacer esto pero de una manera global? (es decir, reemplazando globalmente el código addEventListener con una versión modificada) – Grodriguez

Cuestiones relacionadas