Diferencia entre .on ('clic') vs .click ()


526

¿Hay alguna diferencia entre el siguiente código?

$('#whatever').on('click', function() {
     /* your code here */
});

y

$('#whatever').click(function() {
     /* your code here */
});

Respuestas:


762

Creo que la diferencia está en los patrones de uso.

Preferiría .onhacerlo .clickporque el primero puede usar menos memoria y trabajar para elementos agregados dinámicamente.

Considere el siguiente html:

<html>
    <button id="add">Add new</button>
    <div id="container">
        <button class="alert">alert!</button>
    </div>
</html>

donde agregamos nuevos botones a través de

$("button#add").click(function() {
    var html = "<button class='alert'>Alert!</button>";
    $("button.alert:last").parent().append(html);
});

y quiero "¡Alerta!" para mostrar una alerta. Podemos usar "clic" o "encendido" para eso.


Cuando usamos click

$("button.alert").click(function() {
    alert(1);
});

con lo anterior, se crea un controlador separado para cada elemento que coincida con el selector. Eso significa

  1. muchos elementos coincidentes crearían muchos controladores idénticos y, por lo tanto, aumentarían la huella de memoria
  2. los elementos agregados dinámicamente no tendrán el controlador, es decir, en el html anterior, la nueva "¡Alerta!" los botones no funcionarán a menos que vuelva a vincular el controlador.

Cuando usamos .on

$("div#container").on('click', 'button.alert', function() {
    alert(1);
});

con lo anterior, un único controlador para todos los elementos que coinciden con su selector, incluidos los creados dinámicamente.


... otra razón para usar .on

Como Adrien comentó a continuación, otra razón para usar .ones eventos con espacios de nombres.

Si agrega un controlador .on("click", handler)normalmente lo elimina con el .off("click", handler)cual eliminará ese mismo controlador. Obviamente, esto funciona solo si tiene una referencia a la función, entonces, ¿qué sucede si no la tiene? Utiliza espacios de nombres:

$("#element").on("click.someNamespace", function() { console.log("anonymous!"); });

con desvinculación a través de

$("#element").off("click.someNamespace");

2
¿Qué pasa con: $ ('button.alert'). On ('click', function () {alert (1);}); ?
Mateo

8
@andreister: corríjame si me equivoco, pero creo que otra ventaja es el uso de espacios de nombres cuando se usa on('click' ...), consulte stackoverflow.com/a/3973060/759452, es decir. on('click.darkenallothersections' ...)y al mismo tiempo tengo on('click.displaynextstep' ...), entonces puedo desatar solo el que elijo usar.unbind('click.displaynextstep')
Adrien Be

No creo que se cree un controlador separado para cada elemento que coincida con el selector. Creo que se crearía 1 controlador, pero que la sobrecarga proviene de vincular este controlador a múltiples elementos y monitorear todos estos elementos. Al menos, no encontré esto en la documentación.
Seguimiento

77
¿Alguien puede explicar por qué .on puede funcionar para un elemento agregado dinámicamente pero .click no?
MengT

2
on()es la tendencia en jQuery. Tuve que actualizar $(window).load(function() {});a $(window).on("load", function (e) {})cuando actualicé a jQuery 3.
Victor Stoddard

37

¿Hay alguna diferencia entre el siguiente código?

No, no hay diferencia funcional entre los dos ejemplos de código en su pregunta. .click(fn)es un "método de acceso directo" para .on("click", fn). De la documentación para.on() :

Existen métodos abreviados para algunos eventos, como los .click()que se pueden usar para adjuntar o activar controladores de eventos. Para obtener una lista completa de métodos abreviados, consulte la categoría de eventos .

Tenga en cuenta que .on()difiere de .click()que tiene la capacidad de crear controladores de eventos delegados al pasar un selectorparámetro, mientras .click()que no. Cuando .on()se llama sin un selectorparámetro, se comporta exactamente igual que .click(). Si desea delegar eventos, use .on().


44
¿Qué pasa con el problema de rendimiento señaló mi @andreister?
rubo77

@ rubo77 insignificante en el mejor de los casos. Estamos tomando milisegundos de una sola figura.
Rory McCrossan

1
@RoryMcCrossan, eso es un gran problema para mí, estoy buscando esto porque tengo hasta 3000 preguntas en una página que necesita eventos. Un milisegundo cada uno hace que mi página tarde 3 segundos más en ejecutarse. Tu comentario no es útil para grandes listas.
Randy

11
El problema más grande es por qué tienes 3000 preguntas en una página. Si sigue buenos patrones de IU, nunca debería tener tanta información en una página. Examine la paginación o la carga diferida. Incluso usar la delegación de eventos para tener un único controlador de eventos para todos esos elementos sería mejor.
Rory McCrossan

55
@ rubo77: la ganancia de rendimiento solo se ve cuando se usa la delegación de eventos al pasar un selectorparámetro. Si llama .on()sin un selectorparámetro, no hay mejora en el rendimiento sobre el uso .click().
gilly3

23

.on()es la forma recomendada de hacer todo su enlace de eventos a partir de jQuery 1.7. Enrolla toda la funcionalidad de ambos .bind()y .live()en una sola función que altera el comportamiento a medida que le pasa diferentes parámetros.

Como ha escrito su ejemplo, no hay diferencia entre los dos. Ambos vinculan un controlador al clickevento de #whatever. on()ofrece flexibilidad adicional para permitirle delegar eventos disparados por hijos de #whatevera una sola función de controlador, si lo desea.

// Bind to all links inside #whatever, even new ones created later.
$('#whatever').on('click', 'a', function() { ... });

"Enlace a todos los enlaces dentro de # lo que sea, incluso los nuevos creados más tarde". ¿No es eso exactamente lo que .live()hace? Además, esto parece contradecirse con las otras respuestas que dicen que solo tiene la funcionalidad de .click()y, por lo tanto, no se aplica a eventos futuros.
bgcode

3
@babonk: esto no contradice las otras respuestas, porque como Interrobang dijo en el primer párrafo .on()puede hacer lo que .click()hace y hacer qué .bind()y .live()hacer, depende de los parámetros con los que lo llame. (Algunas otras respuestas también mencionaron esto). Tenga en cuenta que "Vincular a todos los enlaces dentro de #whatever" no es lo que .live()hace, es lo que .delegate()hace. .live()se une a todo el interior en documentlugar de permitirle especificar el contenedor. Note también .live()está en desuso desde jQuery 1.7 en adelante.
nnnnnn

+1 para eventos delegados: "Al elegir un elemento que se garantiza que estará presente en el momento en que se adjunta el controlador de eventos delegado, puede usar eventos delegados para evitar la necesidad de adjuntar y eliminar controladores de eventos con frecuencia". api.jquery.com/on
jimasp

19

Como se menciona en las otras respuestas:

$("#whatever").click(function(){ });
// is just a shortcut for
$("#whatever").on("click", function(){ })

Sin embargo, teniendo en cuenta que .on()admite varias otras combinaciones de parámetros que .click()no, lo que le permite manejar la delegación de eventos (supercediendo .delegate()y .live()).

(Y, obviamente, hay otros métodos de acceso directo similares para "keyup", "focus", etc.)

La razón por la que publico una respuesta adicional es para mencionar lo que sucede si llama .click()sin parámetros:

$("#whatever").click();
// is a shortcut for
$("#whatever").trigger("click");

Teniendo en cuenta que si lo usa .trigger()directamente, también puede pasar parámetros adicionales o un objeto de evento jQuery, con el que no puede hacerlo .click().

También quería mencionar que si observa el código fuente de jQuery (en jquery-1.7.1.js) verá que internamente la función .click()(o .keyup(), etc.) realmente llamará a .on()o .trigger(). Obviamente, esto significa que puede estar seguro de que realmente tienen el mismo resultado, pero también significa que el uso .click()tiene un poco más de sobrecarga: no hay nada de qué preocuparse o incluso pensar en la mayoría de las circunstancias, pero en teoría podría importar en circunstancias extraordinarias.

EDITAR: Finalmente, tenga en cuenta que le .on()permite vincular varios eventos a la misma función en una línea, por ejemplo:

$("#whatever").on("click keypress focus", function(){});

¿No están los dos métodos cargados en la memoria para usar? ¿Entonces no importa? ¿Y para facilitar la lectura es quizás más útil?
Vince V.

@VinceV. - Si. Para los controladores de eventos no delegados "estándar", ambos métodos hacen lo mismo y la diferencia de rendimiento es insignificante, por lo que el método que utilice es realmente una cuestión de preferencia personal. (Normalmente elegiría .click().)
nnnnnn

9

No, no hay
El punto on()es sus otras sobrecargas y la capacidad de manejar eventos que no tienen métodos de acceso directo.


1
@arigold: Esas son las otras sobrecargas.
Habla el

9

Parecen ser lo mismo ... Documentación de la función click () :

Este método es un acceso directo para .bind ('clic', controlador)

Documentación de la función on () :

A partir de jQuery 1.7, el método .on () proporciona toda la funcionalidad necesaria para adjuntar controladores de eventos. Para obtener ayuda en la conversión de métodos de eventos jQuery anteriores, consulte .bind (), .delegate () y .live (). Para eliminar eventos vinculados con .on (), vea .off ().


Ambos puntos de vista deben fusionarse. Click () es un atajo para .Bind () y .On () ... Según JQUERY 1.7.0 +, también es un atajo para Trigger ('click'). [ api.jquery.com/click/]
Dhanasekar

Esta es una explicación bastante directa de los documentos, pero la respuesta a continuación tiene un buen ejemplo de por qué uno es mejor que el otro en .clickvs.on
phatskat

@phatskat - Estoy de acuerdo contigo :)
dana

8

.click Los eventos solo funcionan cuando el elemento se procesa y solo se adjuntan a los elementos cargados cuando el DOM está listo.

.on los eventos se adjuntan dinámicamente a elementos DOM, lo que es útil cuando desea adjuntar un evento a elementos DOM que se representan en una solicitud ajax o algo más (después de que el DOM esté listo).


5

Aquí obtendrá una lista de las diferentes formas de aplicar el evento click. Puede seleccionar en consecuencia como suaitable o si su clic no funciona, pruebe con una alternativa.

$('.clickHere').click(function(){ 
     // this is flat click. this event will be attatched 
     //to element if element is available in 
     //dom at the time when JS loaded. 

  // do your stuff
});

$('.clickHere').on('click', function(){ 
    // same as first one

    // do your stuff
})

$(document).on('click', '.clickHere', function(){
          // this is diffrent type 
          //  of click. The click will be registered on document when JS 
          //  loaded and will delegate to the '.clickHere ' element. This is 
          //  called event delegation 
   // do your stuff
});

$('body').on('click', '.clickHere', function(){
   // This is same as 3rd 
   // point. Here we used body instead of document/

   // do your stuff
});

$('.clickHere').off().on('click', function(){ // 
    // deregister event listener if any and register the event again. This 
    // prevents the duplicate event resistration on same element. 
    // do your stuff
})

3

Ahora han desaprobado click (), por lo que es mejor ir con ('click')


Entonces, ¿qué haces si quieres el viejo comportamiento click () ahora?
bgcode el

1

En cuanto a ilearned de internet y algunos amigos .on () se usa cuando agrega elementos dinámicamente. Pero cuando lo usé en una página de inicio de sesión simple donde el evento click debería enviar AJAX a node.js y al regresar agregar nuevos elementos, comenzó a llamar a llamadas multi-AJAX. Cuando lo cambié para hacer clic () todo salió bien. En realidad no me he enfrentado a este problema antes.


0

NUEVOS ELEMENTOS

Como anexo a las respuestas completas anteriores para resaltar puntos críticos si desea que el clic se adjunte a nuevos elementos:

  1. los elementos seleccionados por el primer selector, por ejemplo, $ ("cuerpo") deben existir en el momento en que se realiza la declaración; de lo contrario, no hay nada a lo que apegarse.
  2. debe usar los tres argumentos en la función .on (), incluido el selector válido para sus elementos de destino como segundo argumento.

-1
$('.UPDATE').click(function(){ }); **V/S**    
$(document).on('click','.UPDATE',function(){ });

$(document).on('click','.UPDATE',function(){ });
  1. es más efectivo que $ ('. ACTUALIZACIÓN'). click (function () {});
  2. puede usar menos memoria y trabajar para elementos agregados dinámicamente.
  3. en algún momento, los datos recuperados dinámicos con el botón editar y eliminar no generan el evento JQuery al momento de EDITAR O BORRAR DATOS de los datos de fila en forma, ese tiempo $(document).on('click','.UPDATE',function(){ });funciona efectivamente como los mismos datos recuperados utilizando jquery. el botón no funciona en el momento de la actualización o eliminación:

ingrese la descripción de la imagen aquí


$ (document) .on ('click', '. UPDATE', function () {}); 1) es más efectivo que $ ('. ACTUALIZACIÓN'). Click (function () {}); 2) puede usar menos memoria y trabajar para elementos agregados dinámicamente. 3) en algún momento los datos recuperados dinámicos con el botón editar y eliminar no generan el evento JQuery al momento de EDITAR O BORRAR DATOS de los datos de la fila en el formulario, esa vez $ (documento) .on ('clic', '. ACTUALIZACIÓN', función () {}); es efectivamente trabajo. [como los mismos datos obtenidos usando jquery. botón no funciona en el momento de la actualización o eliminación
Devang Hire
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.