JavaScript – Введение в события. Обработчик события

В этой статье вы узнаете: что такое событие, способы задания обработчика (слушателя) событию, методы addEventListener
и removeEventListener
.
Что такое событие?
Событие – это определённый сигнал от браузера. Он сообщает нам о том, что что-то произошло.
Например: щелчок мыши, нажатие клавиши на клавиатуре, изменение размера области просмотра, завершение загрузки документа и т.д.
При этом сигнал всегда связан с объектом. Подавать сигналы могут различные объекты: window
, document
, DOM-элементы и т.д.
Список некоторых событий и их название:
DOMContentLoaded
– завершение загрузки DOM;click
– клик (нажатие левой кнопки мыши, на устройствах с сенсорным управлением возникает при касании);keydown
– нажатие клавиши на клавиатуре;resize
– изменение размеров документа;change
– окончание изменения значения в поле ввода.
Обработчик события
Зачем нам события? Они нам нужны для того, чтобы мы могли реагировать на них, или другими словами выполнять определённые действия, когда они произойдут.
В JavaScript это выполняется посредством привязывания некоторой функции к событию. После этого эта функция будет вызываться всякий раз, когда это событие на указанном элементе будет возникать. Эту функцию в JavaScript принято называть обработчиком события.
Следует отметить, что на странице постоянно возникает огромное количество событий, независимо от того назначили ли мы им обработчик или нет. Наша задача – это заставить наш сайт или приложение реагировать только на те события, которые нам небезразличны.
Способы задания событию обработчика
Назначить обработчик событию можно разными способами:
- через HTML-атрибут
on{событие}
(не является хорошей практикой); - посредством свойства DOM-элемента
on{событие}
; - используя специальный метод
addEventListener
.
Инициализация обработчика через атрибут
Этот способ позволяет прописать обработчик напрямую в разметке. Выполняется это посредством указания JavaScript кода в атрибуте on{событие}
. Вместо {событие}
необходимо написать имя (тип) события (например: click
).
Пример, в котором назначим HTML-элементу button
обработчик события click
, используя атрибут:
<!-- onclick - атрибут, содержащий код, который будет выполняться всякий раз при наступлении события click на этом элементе --> <button type="button" onclick="alert(Date())">Текущая дата</button>
Если код, который нужно поместить в атрибут достаточно большой, то в этом случае его лучше оформить в виде функции, а в атрибут поместить её вызов.
Например:
<script> // функция sum function sum() { const number1 = +document.querySelector('#number1').value; const number2 = +document.querySelector('#number2').value; const sum = number1 + number2; document.querySelector('#answer').textContent = sum; } </script> <input type="text" id="number1"> <input type="text" id="number2"> <div id="answer"></div> <button type="button" onclick="sum()">Посчитать</button>
В этом примере мы указали в качестве обработчика функцию sum
.
При этом задавать обработчик напрямую в разметке не является хорошей практикой, т.к. это приведёт к смешиванию JavaScript и HTML кода.
Добавление обработчика через свойство DOM объекта
Второй способ назначить обработчик - это использовать свойство on{событие}
.
Например, привяжем обработчик события click
к элементу (для этого события свойство будет onclick
):
<!-- HTML код кнопки --> <button type="button" id="my-btn">Нажми на меня</button> <!-- Скрипт на JavaScript --> <script> // получим кнопку и сохраним ссылку на неё в переменную const $btn = document.querySelector('#my-btn'); // добавим к $btn обработчик события click $btn.onclick = function() { alert('Вы кликнули на кнопку!'); } </script>
В приведённом выше примере обработчик представляет собой анонимную функцию, которая будет выполняться всякий раз, когда это событие на указанном элементе будет происходить.
Другой вариант – это назначить уже существующую функцию.
Например:
function changeBgColor() { document.body.style.backgroundColor = `rgb(${Math.round(Math.random()*255)}, ${Math.round(Math.random()*255)}, ${Math.round(Math.random()*255)})`; } document.onclick = changeBgColor;
Внутри обработчика можно обратиться к текущему элементу, т.е. к тому для которого в данный момент был вызван этот обработчик. Осуществляется это с помощью ключевого слова this
.
Например:
<!-- HTML код кнопок --> <button type="button">Кнопка 1</button> <button type="button">Кнопка 2</button> <button type="button">Кнопка 3</button> <!-- Скрипт на JavaScript --> <script> function message() { // this - обращаемся к кнопке для которой вызван обработчик alert(this.textContent); } // получим кнопки и сохраним ссылки на них в переменную $btns const $btns = document.querySelectorAll('button'); // переберём кнопки и добавим к ним обработчик, используя onclick $btns.forEach(function($element) { $element.onclick = message; }); </script>
Кстати, когда обработчик задаётся через атрибут, то браузер самостоятельно при чтении такого HTML создаёт из значения этого атрибута функцию и присваивает её одноименному свойству этого элемента.
Например:
<button id="btn" type="button" onclick="alert('Вы кликнули на кнопку')">Кнопка</button> <script> const $element = document.querySelector('#btn'); // получим значение свойства onclick (как видно браузер туда автоматически записал функцию, которую создал на основании содержимого этого атрибута) console.log($element.onclick); </script>

Т.е., по сути, задание свойства через атрибут – это просто способ инициализации обработчика. Т.к. сам обработчик в этом случае тоже хранится в свойстве DOM-объекта.
Но установка обработчика через свойство имеет недостаток. С помощью него нельзя назначить одному событию несколько обработчиков. Если в коде создадим новый обработчик, то он перезапишет существующий:
<button id="btn" type="button">Кнопка</button> <script> const $element = document.querySelector('#btn'); $element.onclick = function () { alert(`id = ${this.id}`); } // заменит предыдущий обработчик $element.onclick = function () { alert(`text = ${this.textContent}`); } </script>
Кстати, также не получится назначить несколько обработчиков, один через атрибут, а другой через свойство. Последний перепишет предыдущий.
<button id="btn" type="button" onclick="alert(`id = ${this.id}`);">Кнопка</button> <script> const $element = document.querySelector('#btn'); // заменит обработчик, инициализированный с помощью атрибута $element.onclick = function () { alert(`text = ${this.textContent}`); } </script>
Подписка на событие через addEventListener
Ещё один способ назначить событию обработчик — это использовать метод addEventListener
.
Синтаксис addEventListener
:
// $element - объект или DOM-элемент к которому нужно добавить обработчик $element.addEventListener(event, handler[, options]);
Параметры:
event
- имя события (например,click
);handler
- функция, которая будет вызвана при возникновении этого события;;options
(не обязательный) - объект, в котором можно задать дополнительные параметры.
В options
можно задать:
once
- еслиtrue
, то обработчик будет вызван всего один раз;capture
- задаёт фазу, на которой нужно вызвать обработчик события (по умолчанию - на этапе всплытия); если нужно на этапе погружения (перехвата) - то этому ключу следует установить значениеtrue
;passive
- определяет следует ли вызыватьpreventDefault()
; если установитьtrue
- то обработчик никогда не вызовет этот метод.
Кроме этого, options
можно установить true
или false
, в этом случае он будет просто определять фазу (всплытие или погружение).
Пример:
function changeBgColor() { document.body.style.backgroundColor = '#3f51b5'; } document.addEventListener('click', changeBgColor, false);
В этом примере addEventListener
прикреплен к объекту document
. Когда событие click
возникнет на этом элементе, будет вызвана функция changeBgColor
.
Если мы откроем документ, содержащий этот код в браузере, то сначала увидим пустую страницу.

Однако при клике фон страницы изменится с белого на #3f51b5
.

Иногда возникают ситуации, когда нужно удалить обработчик. Это можно выполнить, используя removeEventListener
:
$element.removeEventListener(event, handler[, options]);
Этот метод принимает аргументы тех же типов, что addEventListener
.
При этом для того, чтобы удалить обработчик нам нужно указать точно такие же аргументы, которые мы использовали при его назначении.
function changeBgColor() { document.body.style.backgroundColor = '#3f51b5'; } document.addEventListener('click', changeBgColor, false); document.removeEventListener('click', changeBgColor, false);
Если обработчик - анонимная функция, то её удалить нельзя.
document.addEventListener('click', function() { document.body.style.backgroundColor = '#3f51b5'; }); // удалить обработчик установленный выше с помощью addEventListener не получится, т.к. это разные функции, имеющие одинаковый код document.removeEventListener('click', function() { document.body.style.backgroundColor = '#3f51b5'; });
Как добавить несколько обработчиков к событию?
Метод addEventListener
в отличие от предыдущих способов позволяет назначить одному событию несколько обработчиков:
function handler1() { ... } function handler2() { ... } document.addEventListener('click', handler1); document.addEventListener('click', handler2);
Как правильно прикрепить обработчики к элементам?
Для прикрепления обработчиков к элементам, необходимо чтобы эти элементы на странице были доступны. Определить, когда они будут доступны с момента загрузки документам можно с помощью события DOMContentLoaded
. Данное событие возникает на document
когда DOM полностью построено:
document.addEventListener('DOMContentLoaded', function () { // DOM полностью построен и доступен ... });
Задачи
1. Скрыть элемент по нажатию кнопки с классом spoiler-trigger
Написать JavaScript код, который при нажатии на кнопку spoiler-trigger
будет скрывать элемент, расположенный сразу за ней. При этом на странице таких кнопок может быть несколько.

<style> .hide { display: none; } </style> <button class="spoiler-trigger">Скрыть/показать контент</button> <div>...</div> ... <button class="spoiler-trigger">Скрыть/показать контент</button> <div>...</div>Решение
2. Создать выпадающее меню
Имеется следующая разметка (стили добавлять не нужно, они имеются в примере):
<div class="dropdown"> <button class="dropdown__trigger">Меню</button> <div class="dropdown__content"> <a href="#">Ссылка 1</a> <a href="#">Ссылка 2</a> <a href="#">Ссылка 3</a> </div> </div>

Необходимо написать скрипт, который будет при нажатии на кнопку (.dropdown__trigger
) переключался класс show
у элемента .dropdown
:

Комментарии: