Обработчики событий

Событие - это определённое действие пользователя или самого браузера. К ним относятся движение мыши, нажатия на кнопки мыши и клавиатуры и т.д. События являются основным инструментом создания динамических страниц. Все события объединены в отдельный интерфейс событий.

Для реакции на определённые события (действия пользователя) назначаются обработчики событий.

Обработчик события - это функция, которая выполняется в тот момент, когда происходит событие.

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

  • keydown - при нажатии на кнопку.
  • keypress - при нажатии на кнопку.
  • keyup - при отпускании кнопки.

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

Назначить обработчик события можно несколькими способами, описанными ниже.

Атрибуты событий

Самый простой способ задания обработчика - это использование атрибутов событий прямо в HTML-коде.

Значением атрибутов событий указывается код JavaScript или название готовой функции. Если указывается просто код JavaScript, то браузер автоматически создаёт анонимную функцию, телом которой является исходный код.

<html>
<head>
  <title>События</title>
</head>
<body>
  <p onmouseover="this.style.background = 'red';" onmouseout="this.style.background = 'transparent';">Наведите курсор</p>
</body>
</html>

Наведите курсор

В данном примере браузер при создании DOM-дерева параграфу <p> присваивает два свойства onmouseover и onmouseout в виде анонимных функций.

<html>
<head>
  <title>События</title>
</head>
<body>
  <p onmouseover="alert('Ok');">Наведите курсор</p>
</body>
</html>

<script>
  var par = document.body.firstElementChild;
  alert(par.onmouseover); /* 'function ...' (в свойстве записана функция) */
</script>

При использовании HTML-атрибутов для задания обработчика события разработчик ограничен стандартом HTML (список событий приводится здесь). Например, спецификация CSS тоже предлагает набор событий, но для них нет атрибутов. Если использовать нестандартный атрибут, то код не пройдёт валидацию. Использование же DOM-интерфейса расширяет возможности по созданию динамических страниц, позволяя устанавливать обработчики на любые события.

DOM-свойства событий

Ещё один способ установки обработчика события - это прямое использование DOM свойств, то есть сразу записывать обработчик в свойство элемента.

Имя свойства должно быть в нижнем регистре. В отличие от HTML-атрибутов DOM-свойства регистрозависимы.

Значением свойства обязательно должна быть функция.

<html>
<head>
  <title>События</title>
</head>
<body>
  <p>Наведите курсор</p>
</body>
</html>

<script>
  var par = document.body.firstElementChild;
  par.onmouseover = function () {
    this.style.background = 'green';
  };
  par.onmouseout = function () {
    this.style.background = 'transparent';
  };
</script>

Наведите курсор

Использование HTML-атрибутов или DOM-свойств позволяет устанавливать только по одному обработчику на каждое событие.

Специальные методы

Для установки и удаления любого количества обработчиков на одно событие используются методы addEventListener() и removeEventListener().

addEventListener()

Метод addEventListener() добавляет обработчик события.

element.addEventListener(имя_события, обработчик[, стадия])
имя_события
Название события в кавычках.
обработчик
Функция-обработчик события (можно указать анонимную функцию или ссылку на готовую).
стадия
Необязательный аргумент. Он содержит информацию, на какой стадии сработает обработчик:
  • true - на стадии перехвата.
  • false (используется по умолчанию) - на стадии всплытия.
<html>
<head>
  <title>События</title>
</head>
<body>
  <input type="button" value="Кнопка">
</body>
</html>

<script>
  var button = document.body.firstElementChild;
  button.addEventListener('click', function() {alert('Обработчик 1');});
  button.addEventListener('click', function() {alert('Обработчик 2');});
</script>

При нажатии на кнопку сработают оба обработчика.

removeEventListener()

Метод removeEventListener() используется для удаления обработчика события, назначенного с помощью метода addEventListener(). Обязательно должны быть указаны те значения, которые использовались при назначении обработчика.

element.removeEventListener(имя_события, обработчик[, стадия])
имя_события
Название события в кавычках.
обработчик
Функция-обработчик события. Должна указываться именно ссылка, чтобы браузер понимал, какой обработчик нужно удалить. Соответственно, если обработчик был назначен напрямую (анонимной функцией), то его удалить не удастся.
стадия
Необязательный аргумент. Указывается, если использовался при назначении обработчика.
<html>
<head>
  <title>События</title>
</head>
<body>
  <input type="button" value="Кнопка">
</body>
</html>

<script>
  function handler() {alert('Обработчик 1');}
  var button = document.body.firstElementChild;
  /* добавление обработчиков */
  button.addEventListener('click', handler);
  button.addEventListener('click', function() {alert('Обработчик 2');});
  /* удаление обработчиков */
  button.removeEventListener('click', handler);
  button.removeEventListener('click', function() {alert('Обработчик 2');});
</script>

Второй обработчик остался, так как он назначен анонимной функцией.

Действия браузера по умолчанию

Помимо выполнения назначенных обработчиков, события могут вызывать действия браузера по умолчанию. Эти действия как бы подразумеваются сами собой в зависимости от элемента страницы. Например:

Событие Действие браузера
click Клик по ссылке вызывает переход на новую страницу.
click Клик по неактивному полю для ввода текста делает его активным.
contextmenu Клик правой кнопкой мыши открывает контекстное меню.
dblclick Двойной клик на тексте выделяет его.
mousedown Нажатие левой кнопки мыши и удержание её над текстом начинает его выделение.
mousewheel Движение колёсика мыши вызывает прокрутку страницы.
keydown Нажатия на кнопки клавиатуры внутри текстового поля приводят к набору текста.
keydown Нажатие на кнопку Enter в активном поле вызывает отправку формы на сервер.

Обычно, если на конкретное событие устанавливается обработчик, то действия браузера по умолчанию не нужны. Тогда их просто можно отменить. Если обработчик установлен с помощью HTML-атрибута или DOM-свойства, тогда после выполнения всех своих действий обработчику необходимо вернуть значение false.

<html>
<head>
  <title>События</title>
</head>
<body>
  <label>Попробуйте поставить галочку <input type="checkbox" onclick="return false;"></label>
</body>
</html>

При помощи мыши поставить галочку не получится.

Если обработчик события установлен с помощью метода addEventListener(), тогда для отмены действий браузера по умолчанию необходимо использовать метод event.preventDefault().