Разница между .on ('click') и .click ()

526

Есть ли разница между следующим кодом?

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

а также

$('#whatever').click(function() {
     /* your code here */
});
bgcode
источник

Ответы:

762

Я думаю, разница в моделях использования.

Я бы предпочел .onболее , .clickпотому что прежний может использовать меньше памяти и работать для динамически добавляемых элементов.

Рассмотрим следующий HTML:

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

где мы добавляем новые кнопки через

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

и хочу "Оповещение!" чтобы показать предупреждение. Для этого мы можем использовать «клик» или «вкл».


Когда мы используем click

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

с вышеупомянутым, отдельный обработчик создается для каждого отдельного элемента, который соответствует селектору. Это значит

  1. много соответствующих элементов создаст много идентичных обработчиков и, следовательно, увеличит объем памяти
  2. динамически добавленные элементы не будут иметь обработчика - то есть, в приведенном выше html недавно добавленное «Alert!» кнопки не будут работать, если вы не перепривязаете обработчик.

Когда мы используем .on

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

с вышеупомянутым, один обработчик для всех элементов, которые соответствуют вашему селектору, включая те, которые созданы динамически.


... еще одна причина для использования .on

Как прокомментировал Adrien ниже, еще одна причина использовать .onэто события в пространстве имен.

Если вы добавляете обработчик вместе с .on("click", handler)вами, обычно удаляйте его, .off("click", handler)и этот обработчик удаляется. Очевидно, это работает, только если у вас есть ссылка на функцию, а что, если у вас ее нет? Вы используете пространства имен:

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

с привязкой через

$("#element").off("click.someNamespace");
andreister
источник
2
Как насчет: $ ('button.alert'). On ('click', function () {alert (1);}); ?
Мэтью
8
@andreister: поправьте меня, если я ошибаюсь, но я считаю, что другим преимуществом является использование пространств имен при использовании on('click' ...), см. stackoverflow.com/a/3973060/759452 т.е. on('click.darkenallothersections' ...)и в то же время иметь on('click.displaynextstep' ...), то я могу отменить привязку только тот, который я выбрал, используя.unbind('click.displaynextstep')
Adrien Be
Я не думаю, что отдельный обработчик создается для каждого элемента, который соответствует селектору. Я думаю, что 1 обработчик будет создан, но что накладные расходы связаны с привязкой этого обработчика к нескольким элементам и мониторингом всех этих элементов. По крайней мере, я не нашел этого в документации.
Трассировка
7
Может кто-нибудь объяснить, почему .on может работать с динамически добавляемым элементом, а .click не может?
MengT
2
on()это тенденция в JQuery. Мне пришлось обновляться $(window).load(function() {});до того $(window).on("load", function (e) {})момента, когда я обновился до jQuery 3.
Виктор Стоддард
37

Есть ли разница между следующим кодом?

Нет, между двумя примерами кода в вашем вопросе нет функциональной разницы. .click(fn)является «методом ярлыка» для .on("click", fn). Из документации для.on() :

Для некоторых событий существуют сокращенные методы, например, .click()которые можно использовать для подключения или запуска обработчиков событий. Полный список сокращенных методов см. В категории событий .

Обратите внимание, что .on()отличается от того, .click()что он имеет возможность создавать делегированные обработчики событий путем передачи selectorпараметра, тогда как .click()нет. Когда .on()вызывается без selectorпараметра, он ведет себя точно так же, как .click(). Если вы хотите делегировать события, используйте .on().

gilly3
источник
4
а как насчет проблемы производительности указал мой @andreister?
rubo77
@ rubo77 в лучшем случае незначительно. Мы берем однозначные миллисекунды.
Рори МакКроссан
1
@RoryMcCrossan для меня это большое дело - я ищу это, потому что у меня есть до 3000 вопросов на странице, требующей событий. Каждый милисек заставляет мою страницу работать на 3 секунды дольше. Ваш комментарий не полезен для больших списков.
Рэнди
11
Большая проблема в том, почему у вас есть 3000 вопросов на странице. Если вы следуете хорошим шаблонам пользовательского интерфейса, у вас никогда не должно быть столько информации на странице. Загляните в пейджинговую или ленивую загрузку. Даже лучше использовать делегирование событий, чтобы иметь один обработчик событий для всех этих элементов.
Рори МакКроссан
5
@ rubo77 - Прирост производительности виден только при использовании делегирования события путем передачи selectorпараметра. Если вы звоните .on()без selectorпараметра, производительность не улучшится по сравнению с использованием .click().
gilly3
23

.on()это рекомендуемый способ сделать все привязки вашего события начиная с jQuery 1.7. Он объединяет все функциональные возможности обоих .bind()и .live()в одну функцию, которая изменяет поведение при передаче различных параметров.

Как вы написали свой пример, между ними нет никакой разницы. Оба связывают обработчик с clickсобытием #whatever. on()предлагает дополнительную гибкость, позволяя вам делегировать события, инициируемые потомками, #whateverв одну функцию-обработчик, если вы выберете.

// Bind to all links inside #whatever, even new ones created later.
$('#whatever').on('click', 'a', function() { ... });
лигатура из вопросительных и восклицательных знаков
источник
«Свяжите все ссылки внутри # что угодно, даже новые, созданные позже». Разве это не то, что .live()делает? Кроме того, это, кажется, противоречит другим ответам, которые говорят, что он имеет только функциональность .click(), и, следовательно, не относится к будущим событиям.
bgcode
3
@babonk - Это не противоречит другим ответам, потому что, как сказал Interrobang в первом абзаце, .on()может делать то, что .click()делает, и делать, .bind()и .live()делать - это зависит от того, с какими параметрами вы его называете. (Некоторые другие ответы тоже упоминали об этом.) Обратите внимание, что «Привязать ко всем ссылкам внутри #whwhat» - это не то .live(), что делает, это то, что .delegate()делает. .live()связывает все внутри, documentа не позволяет вам указать контейнер. Примечание также .live()не рекомендуется с jQuery 1.7 и далее.
nnnnnn
+1 для делегированных событий: «Выбрав элемент, который гарантированно будет присутствовать во время присоединения делегированного обработчика событий, вы можете использовать делегированные события, чтобы избежать необходимости часто присоединять и удалять обработчики событий». api.jquery.com/on
jimasp
19

Как уже упоминалось в других ответах:

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

Однако следует отметить, что он .on()поддерживает несколько других комбинаций параметров, которые .click()не поддерживают его, что позволяет ему обрабатывать делегирование событий (superceding .delegate()и .live()).

(И, очевидно, существуют другие похожие методы ярлыков для «keyup», «focus» и т. Д.)

Причина, по которой я публикую дополнительный ответ, состоит в том, чтобы упомянуть, что происходит, если вы звоните .click()без параметров:

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

Отмечая, что если вы используете .trigger()напрямую, вы также можете передавать дополнительные параметры или объект события jQuery, с которым вы не можете делать .click().

Я также хотел упомянуть, что если вы посмотрите на исходный код jQuery (в jquery-1.7.1.js), вы увидите, что внутренне функция .click()(или .keyup(), и т. Д.) Будет фактически вызывать .on()или .trigger(). Очевидно, это означает, что вы можете быть уверены, что они действительно имеют тот же результат, но это также означает, что использование .click()имеет немного больше накладных расходов - не о чем беспокоиться или даже думать в большинстве случаев, но теоретически это может иметь значение в чрезвычайных обстоятельствах.

РЕДАКТИРОВАТЬ: Наконец, обратите внимание, что .on()позволяет привязать несколько событий к одной и той же функции в одной строке, например:

$("#whatever").on("click keypress focus", function(){});
NNNNNN
источник
Разве методы, загруженные в память, не используются? Так что это не имеет значения? А для удобства чтения это может быть удобнее?
Винс В.
@VinceV. - Да. Для «стандартных» обработчиков событий без делегирования оба метода делают одно и то же, и разница в производительности незначительна, поэтому используемый вами метод действительно зависит от личных предпочтений. (Я обычно выбираю .click().)
nnnnnn
9

Нет, нет
Суть on()его других перегрузок и способности обрабатывать события, которые не имеют ярлыков.

SLaks
источник
1
@arigold: это другие перегрузки.
SLaks
9

Они выглядят одинаково ... Документация от функции click () :

Этот метод является ярлыком для .bind ('click', обработчик)

Документация от функции on () :

Начиная с jQuery 1.7, метод .on () предоставляет все функциональные возможности, необходимые для подключения обработчиков событий. Для получения справки по преобразованию из более старых методов событий jQuery см. .Bind (), .delegate () и .live (). Чтобы удалить события, связанные с .on (), см. .Off ().

Dana
источник
Обе ваши точки зрения должны быть объединены. Click () - это ярлык для .Bind () и .On () ... Согласно JQUERY 1.7.0 +, это также ярлык для Trigger ('click'). [ api.jquery.com/click/]
Dhanasekar
Это довольно простое объяснение из документации, но приведенный ниже ответ имеет хороший пример того, почему один лучше, чем другой в .clickvs.on
phatskat
@phatskat - я согласен с вами :)
Дана
8

.click события работают только когда элемент визуализируется и прикрепляются только к элементам, загруженным, когда DOM готов.

.on события динамически присоединяются к элементам DOM, что полезно, если вы хотите прикрепить событие к элементам DOM, которые отображаются по запросу ajax или как-то еще (после того, как DOM готов).

Рамеш Кумар
источник
5

Здесь вы получите список различных способов применения события click. Вы можете выбрать соответственно как подходящий или, если ваш клик не работает, просто попробуйте альтернативу из них.

$('.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
})
Mustkeem K
источник
3

Теперь они устарели click (), так что лучше всего продолжать с ('click')

tw0shoes
источник
Так что же делать, если вам нужно старое поведение click () сейчас?
bgcode
1

Насколько ilearned из Интернета и некоторых друзей .on () используется, когда вы динамически добавляете элементы. Но когда я использовал его на простой странице входа, где событие click должно отправить AJAX в node.js, а при возврате добавить новые элементы, он начал вызывать вызовы multi-AJAX. Когда я изменил его, чтобы щелкнуть () все прошло правильно. На самом деле я не сталкивался с этой проблемой раньше.

Альпер Билгил
источник
0

НОВЫЕ ЭЛЕМЕНТЫ

В качестве дополнения к подробным ответам выше, чтобы выделить критические точки, если вы хотите, чтобы щелчок прикреплялся к новым элементам:

  1. элементы, выбранные первым селектором, например, $ ("body"), должны существовать во время объявления, иначе нечего присоединять.
  2. Вы должны использовать три аргумента в функции .on (), включая действительный селектор для ваших целевых элементов в качестве второго аргумента.
Астра Медведь
источник
-1
$('.UPDATE').click(function(){ }); **V/S**    
$(document).on('click','.UPDATE',function(){ });

$(document).on('click','.UPDATE',function(){ });
  1. это более эффективно, чем $ ('. UPDATE'). click (function () {});
  2. он может использовать меньше памяти и работать с динамически добавляемыми элементами.
  3. Некоторое время динамически извлекаемые данные с помощью кнопки редактирования и удаления не генерировали событие JQuery во время РЕДАКТИРОВАНИЯ ИЛИ УДАЛЕНИЯ ДАННЫХ строковых данных в форме, это время $(document).on('click','.UPDATE',function(){ });эффективно работает как те же извлекаемые данные с использованием jquery. кнопка не работает во время обновления или удаления:

введите описание изображения здесь

Devang Hire
источник
$ (document) .on ('click', '. UPDATE', function () {}); 1) он более эффективен, чем $ ('. UPDATE'). Click (function () {}); 2) он может использовать меньше памяти и работать с динамически добавляемыми элементами. 3) некоторое время динамически извлекаемые данные с кнопкой редактирования и удаления не генерировали событие JQuery во время РЕДАКТИРОВАНИЯ ИЛИ УДАЛЕНИЯ ДАННЫХ данных строки в форме, в это время $ (document) .on ('click', '. UPDATE', function () {}); эффективно работает. [как те же самые извлеченные данные с использованием jquery. кнопка не работает во время обновления или удаления
Devang Hire