Захват событий в JavaScript


Содержание материала:

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

Клиентские программы на языке JavaScript основаны на модели программирования, когда выполнение программы управляется событиями. При таком стиле программирования веб-браузер генерирует событие, когда с документом или некоторым его элементом что-то происходит. Например, веб-браузер генерирует событие, когда завершает загрузку документа, когда пользователь наводит указатель мыши на гиперссылку или нажимает клавишу на клавиатуре.

Если JavaScript-приложение интересует определенный тип события для определенного элемента документа, оно может зарегистрировать одну или более функций, которая будет вызываться при возникновении этого события. Имейте в виду, что это не является уникальной особенностью веб-программирования: все приложения с графическим интерфейсом пользователя действуют именно таким образом — они постоянно ожидают, пока что-то произойдет (т.е. ждут появления событий), и откликаются на происходящее.

— это строка, определяющая тип действия, вызвавшего событие. Тип «mousemove», например, означает, что пользователь переместил указатель мыши. Тип «keydown» означает, что была нажата клавиша на клавиатуре. А тип «load» означает, что завершилась загрузка документа (или какого-то другого ресурса) из сети. Поскольку тип события — это просто строка, его иногда называют именем события.

— это объект, в котором возникло событие или с которым это событие связано. Когда говорят о событии, обычно упоминают тип и цель события. Например, событие «load» объекта Window или событие «click» элемента . Самыми типичными целями событий в клиентских приложениях на языке JavaScript являются объекты Window, Document и Element, но некоторые типы событий могут происходить и в других типах объектов.

— это функция, которая обрабатывает, или откликается на событие. Приложения должны зарегистрировать свои функции обработчиков событий в веб-браузере, указав тип события и цель. Когда в указанном целевом объекте возникнет событие указанного типа, браузер вызовет обработчик. Когда обработчики событий вызываются для какого-то объекта, мы иногда говорим, что браузер «возбудил» или «сгенерировал» событие.

— это объект, связанный с определенным событием и содержащий информацию об этом событии. Объекты событий передаются функции обработчика события в виде аргумента (кроме IE8 и более ранних версий, где объект события доступен только в виде глобальной переменной event). Все объекты событий имеют свойство type, определяющее тип события, и свойство target, определяющее цель события.

Для каждого типа события в связанном объекте события определяется набор свойств. Например, объект, связанный с событиями от мыши, включает координаты указателя мыши, а объект, связанный с событиями от клавиатуры, содержит информацию о нажатой клавише и о нажатых клавишах-модификаторах. Для многих типов событий определяются только стандартные свойства, такие как type и target, и не передается никакой дополнительной полезной информации. Для таких типов событий важно само наличие происшествия события, и никакая другая информация не имеет значения.

— это процесс, в ходе которого браузер решает, в каких объектах следует вызвать обработчики событий. В случае событий, предназначенных для единственного объекта (таких как событие «load» объекта Window), надобность в их распространении отсутствует. Однако, когда некоторое событие возникает в элементе документа, оно распространяется, или «всплывает», вверх по дереву документа.

Если пользователь щелкнет мышью на гиперссылке, событие «mousemove» сначала будет возбуждено в элементе , определяющем эту ссылку. Затем оно будет доставлено вмещающим элементам: возможно, элементу

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

Регистрация обработчиков событий

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

Дело осложняется тем, что каждый прием имеет две версии. Свойство обработчика события можно установить в программном коде на языке JavaScript или в элементе документа, определив соответствующий атрибут непосредственно в разметке HTML. Регистрация обработчиков вызовом метода может быть выполнена стандартным методом с именем addEventListener(), который поддерживается всеми браузерами, кроме IE версии 8 и ниже, и другим методом, с именем attachEvent(), поддерживаемым всеми версиями IE до IE9.

Установка свойств обработчиков событий

Самый простой способ зарегистрировать обработчик события заключается в том, чтобы присвоить свойству целевого объекта события желаемую функцию обработчика. По соглашению свойства обработчиков событий имеют имена, состоящие из слова «on», за которым следует имя события: onclick, onchange, onload, onmouseover и т.д. Обратите внимание, что эти имена свойств чувствительны к регистру и в них используются только строчные символы, даже когда имя типа события состоит из нескольких слов (например «readystatechange»). Ниже приводятся два примера регистрации обработчиков событий:

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

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

Установка атрибутов обработчиков событий

Свойства обработчиков событий в элементах документа можно также устанавливать, определяя значения атрибутов в соответствующих HTML-тегах. В этом случае значение атрибута должно быть строкой программного кода на языке JavaScript. Этот программный код должен быть не полным объявлением функции обработчика события, а только ее телом. То есть реализация обработчика события в разметке HTML не должна заключаться в фигурные скобки и предваряться ключевым словом function. Например:

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

Некоторые типы событий предназначены для браузера в целом, а не для какого-то конкретного элемента документа. Обработчики таких событий в языке JavaScript регистрируются в объекте Window. В разметке HTML они должны помещаться в тег , но браузер зарегистрирует их в объекте Window. Ниже приводится полный список таких обработчиков событий, определяемых проектом спецификации HTML5:

При разработке клиентских сценариев обычно принято отделять разметку HTML от программного кода на языке JavaScript. Программисты, следующие этому правилу, избегают (или, по крайней мере, стараются избегать) использовать HTML-атрибуты обработчиков событий, чтобы не смешивать программный код на языке JavaScript и разметку HTML.

addEventListener()

В стандартной модели событий, поддерживаемой всеми браузерами, кроме IE версии 8 и ниже, целью события может быть любой объект — включая объекты Window и Document и все объекты Elements элементов документа — определяющий метод с именем addEventListener(), с помощью которого можно регистрировать обработчики событий для этой цели.

Метод addEventListener() принимает три аргумента. Первый — тип события, для которого регистрируется обработчик. Тип (или имя) события должен быть строкой и не должен включать префикс «on», используемый при установке свойств обработчиков событий. Вторым аргументом методу addEventListener() передается функция, которая должна вызываться при возникновении события указанного типа. В последнем аргументе методу addEventListener() передается логическое значение. Обычно в этом аргументе передается значение false. Если передать в нем значение true, функция будет зарегистрирована как перехватывающий обработчик и будет вызываться в другой фазе распространения события.

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

Следующий фрагмент регистрирует два обработчика события «click» в элементе . Обратите внимание на различия двух используемых приемов:

Вызов метода addEventListener() со строкой «click» в первом аргументе никак не влияет на значение свойства onclick. Во фрагменте, приведенном выше, щелчок на кнопке приведет к выводу двух диалоговых окон alert(). Но важнее то, что метод addEventListener() можно вызвать несколько раз и зарегистрировать с его помощью несколько функций-обработчиков для одного и того же типа события в том же самом объекте. При появлении события в объекте будут вызваны все обработчики, зарегистрированные для этого типа события, в порядке их регистрации.

Многократный вызов метода addEventListener() для одного и того же объекта с теми же самыми аргументами не дает никакого эффекта — функция-обработчик регистрируется только один раз и повторные вызовы не влияют на порядок вызова обработчиков.

Парным к методу addEventListener() является метод removeEventListener(), который принимает те же три аргумента, но не добавляет, а удаляет функцию-обработчик из объекта. Это часто бывает удобно, когда необходимо зарегистрировать временный обработчик события, а затем удалить его в какой-то момент.

Internet Explorer версии ниже IE9 не поддерживает методы addEventListener() и removeEventListener(). В версии IE5 и выше определены похожие методы, attachEvent() и detachEvent(). Поскольку модель событий в IE не поддерживает фазу перехвата, методы attachEvent() и detachEvent() принимают только два аргумента: тип события и функцию обработчика, при этом в первом аргументе методам в IE передается имя свойства обработчика с префиксом «on», а не тип события без этого префикса.

Топ-пост этого месяца:  Как мы создали свой frontend фреймворк MarsMan (и зачем)

Вызов обработчиков событий

После регистрации обработчика событий веб-браузер будет вызывать его автоматически, когда в указанном объекте будет возникать событие указанного типа. В этом разделе подробно описывается порядок вызова обработчиков событий, аргументы обработчиков, контекст вызова (значение this) и назначение возвращаемого значения обработчика. К сожалению, некоторые из этих подробностей отличаются между IE версии 8 и ниже и другими браузерами.

Аргумент обработчика событий

При вызове обработчика событий ему обычно (за одним исключением, о котором рассказывается ниже) передается объект события в виде единственного аргумента. Свойства объекта события содержат дополнительную информацию о событии. Свойство type, например, определяет тип возникшего события.

В IE версии 8 и ниже обработчикам событий, зарегистрированным установкой свойства, объект события при вызове не передается. Вместо этого объект события сохраняется в глобальной переменной window.event. Для переносимости обработчики событий можно оформлять, как показано ниже, чтобы они использовали переменную window.event при вызове без аргумента:

Объект события передается обработчикам событий, зарегистрированным с помощью метода attachEvent(), но они также могут использовать переменную window.event.

При регистрации обработчика события посредством HTML-атрибута браузер преобразует строку с программным кодом на языке JavaScript в функцию. Браузеры, отличные от IE, создают функцию с единственным аргументом event. В IE создается функция, не принимающая аргументов. Если в таких функциях использовать идентификатор event, он будет ссылаться на window.event. В любом случае обработчики событий, определяемые в разметке HTML, могут ссылаться на объект события, используя идентификатор event.

Контекст обработчиков событий

Когда обработчик событий регистрируется установкой свойства, это выглядит как определение нового метода элемента документа:

Поэтому нет ничего удивительного, что обработчики событий вызываются (с одним исключением, касающимся IE, которое описывается ниже) как методы объектов, в которых они определены. То есть в теле обработчика событий ключевое слово this ссылается на цель события.

В обработчиках ключевое слово this ссылается на целевой объект, даже когда они были зарегистрированы с помощью метода addEventListener(). Однако, к сожалению, это не относится к методу attachEvent(): обработчики, зарегистрированные с помощью метода attachEvent(), вызываются как функции, и в них ключевое слово this ссылается на глобальный (Window) объект. Эту проблему можно решить следующим способом:

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

Возвращаемые значения обработчиков

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

Например, обработчик onclick кнопки отправки формы может вернуть false, чтобы предотвратить отправку формы браузером. (Это может пригодиться, если ввод пользователя не прошел проверку на стороне клиента.) Аналогично обработчик события onkeypress поля ввода может фильтровать ввод с клавиатуры, возвращая false при вводе недопустимых символов.

Также важно значение, возвращаемое обработчиком onbeforeunload объекта Window. Это событие генерируется, когда браузер выполняет переход на другую страницу. Если этот обработчик вернет строку, она будет выведена в модальном диалоговом окне, предлагающем пользователю подтвердить свое желание покинуть страницу.

Важно понимать, что учитываются значения, возвращаемые обработчиками событий, только если обработчики зарегистрированы посредством установки свойств. Обработчики, зарегистрированные с помощью addEventListener() или attachEvent() вместо этого должны вызывать метод preventDefault() или устанавливать свойство returnValue объекта события.

Отмена событий

Значение, возвращаемое обработчиком события, зарегистрированным как свойство, можно использовать для отмены действий, выполняемых браузером по умолчанию в случае этого события. В браузерах, поддерживающих метод addEventListener(), отменить выполнение действий по умолчанию можно также вызовом метода preventDefault() объекта события. Однако в IE, версии 8 и ниже, тот же эффект достигается установкой свойства returnValue объекта события в значение false.

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

Текущий проект модуля «DOM Events 3» определяет в объекте Event свойство с именем defaultPrevented. Оно пока поддерживается не всеми браузерами, но суть его в том, что при обычных условиях оно имеет значение false и принимает значение true только в случае вызова метода preventDefault().

Отмена действий, по умолчанию связанных с событием, — это лишь одна из разновидностей отмены события. Имеется также возможность остановить распространение события. В браузерах, поддерживающих метод addEventListener(), объект события имеет метод stopPropagation(), вызов которого прерывает дальнейшее распространение события. Если в том же целевом объекте будут зарегистрированы другие обработчики этого события, то остальные обработчики все равно будут вызваны, но никакие другие обработчики событий в других объекта не будут вызваны после вызова метода stopPropagation().

В IE версии 8 и ниже метод stopPropagation() не поддерживается. Вместо этого объект события в IE имеет свойство cancelBubble. Установка этого свойства в значение true предотвращает распространение события.

Текущий проект спецификации «DOM Events 3» определяет в объекте Event еще один метод — метод с именем stopImmediatePropagation(). Подобно методу stopPropagation(), он предотвращает распространение события по любым другим объектам. Но кроме того, он также предотвращает вызов любых других обработчиков событий, зарегистрированных в том же объекте.

Захват всех событий (javascript)

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

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

Проблемы включают в себя: динамически добавленные элементы, события, распространение которых или барботирование предотвращены, и настраиваемые события, которые генерируются динамически. Я предполагаю, что нужно будет прототипирование dispatchEvent или что-то еще, но я не уверен. Возможно ли это?

Некоторые основы событий:

  • События отправляются «on» объект DOM (обычно элемент), который является целью события.
  • События могут сначала распространяться до дочерних элементов в фазе захвата. Эта фаза используется редко, поскольку до недавнего времени она не поддерживалась некоторыми широко используемыми браузерами.
  • События во втором случае могут распространяться до родительских элементов в фазе барботажа. Эта фаза обычно используется.
  • Некоторые события не распространяются, у них нет фазы захвата или пузыря (например, фокуса, размытия и отправки событий). Некоторые события, которые распространяются в некоторых браузерах, не распространяются в других.
  • Элементы DOM, которые реагируют на события, имеют обработчик событий. Он может быть настроен на прослушивание определенных событий и вызов функции прослушивателя, когда это событие достигает элемента, либо во время захвата, либо в виде пузырьков, либо если элемент является целью события.
  • Слушатели могут отменить распространение, например. событие клика на промежутке внутри ссылки может отменить распространение, так что ссылка не получает щелчок

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

Я предполагаю, что нужно будет прототипирование dispatchEvent или что-то

dispatchEvent — это метод экземпляра события, он не указан как конструктор (нет требования, чтобы он имел внутренний [[Construct]] ), поэтому нецелесообразно использовать как таковой. Браузеру не требуется реализовывать наследование прототипов для объектов хоста (хотя большинство из них делают), а детали реализации объектов и методов хоста в значительной степени скрыты, поэтому это не вариант.

Вы можете попробовать расширить API событий, но вы действительно не должны взаимодействовать с объектами хоста.

Кажется, вас беспокоят динамически добавленные элементы. Существует стратегия, называемая «делегирование событий» , где вы определяете события, которые необходимо прослушать, а затем настраивайте слушателей как можно ближе к целевым объектам как вы можете на элементе, который не изменяется (например, элемент таблицы, если вы динамически добавляете и удаляете строки таблицы или div контейнера для других элементов) для конкретных типов событий, на которые вам нужно ответить.

У вас также могут быть функции, которые изменяют пользовательские события отправки DOM, чтобы добавить слушателей или что-то еще.

Если вы действительно хотите это сделать, вы можете переопределить addEventListener , чтобы отслеживать зарегистрированные и запущенные события.

Однако нет никаких оснований не делать этого, не в последнюю очередь из-за того, что вы быстро исчерпаете память при записи тысяч событий, таких как перемещения мыши. Это также не приведет к тому, что прослушиватели событий будут установлены такими способами, как elt.onclick . Разумеется, они не поймают слушателей, настроенных через старый API IE attachEvent . Самое главное, это не поможет вам, что события, которые генерируются и прослушиваются для внутреннего использования, такие как щелчок мыши на флажке. (Полное решение также потребует обработки removeEventListener .)

Вы также можете переопределить createEvent и dispatch аналогичным образом, но опять же, это будет захватывать только события, которые явно созданы или отправлены в JS-коде.

Если вы действительно хотите сделать то, что вам кажется желательным, я думаю, вам нужно разблокировать Chrome.

Управление событиями в javascript

Механизм DOM — события призваны помочь разработчику перехватить и обработать различные действия от пользователей (клики мышкой по элементам, нажатия клавиш и прочее).

Почти все события состоят из двух фаз:

  • capturing (захват, или погружение)
  • bubbling (всплытие)

Разработчик может установить свой обработчик события на любую из фаз.

Когда происходит событие, информация о нем спускается от корневого элементам dom-дерева вниз, до того элементам, на котором произошло событие (например, если кликнули по ссылке, то событие спускается от корня дерева до ссылки). Этот процесс называется фазой захвата (capture).

То есть браузер посылает информацию о событии (event) от корня (html) вниз.


После этого, процесс начинается в обратном порядке. То есть информация о событии поднимается от элемента, на котором произошло событие до корневого элемента dom-дерева. Этот процесс называется фазой всплытия (bubble).

После того, как событие “всплывет” происходит действие по умолчанию. Например для ссылок, действием по умолчанию является переход на сайт, заданный в атрибуте href .

Иногда говорят так:

  • 1 ФАЗА — Погружение
  • 2 ФАЗА — Выполнение обработчиков (выше мы описали 2 фазы)
  • 3 ФАЗА — Всплытие и действие по умолчанию (после всплытия)

Данный механизм нужен для перехвата событий.

Установка обработчиков события через метод addEventListener

  • Добавляем новый обработчик события к EventTarget .
  • handler будет выполняться при каждом событии event происходящем с EventTarget .
  • Если inCapture равен true , то обработчик будет выполняться не на фазе всплытия (bubble), а на фазе захвата/погружения (capture)
Топ-пост этого месяца:  Сайты на Joomla — примеры популярных проектов на Джумле, как узнать и определить движок (CMS)

Удаление обработчиков события через метод removeEventListener

Удаляем у EventTarget обработчик handler события event .

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

Объект с описанием события (event)

Когда браузер выполняет функцию-обработчик, он автоматически передает функции-обработчику первым параметром объект с информацией о событии.

Основные свойства этого объекта:

  • type — имя события
  • target — элемент, для которого изначально было предназначено событие
    или: event.target – самый глубокий элемент, на котором произошло событие.
  • currentTarget — элемент, который перехватил событие в данный момент (элемент, на котором выполняется обработчик в данный момент)
    или: event.currentTarget (= this ) – элемент, на котором в данный момент сработал обработчик (до которого «доплыло» событие)
  • eventPhase — фаза события (захват, выполнение, всплытие)

Действие по умолчанию, а также stopPropagation

Механизм событий позволяет отменить действие по умолчанию при помощи вызова метода preventDefault из объекта с информацией о событии.

event.stopPropagation() остановить дальнейший ход события по дереву

event.stopImmediatePropagation() остановить дальнейший ход события по дереву и игнорировать другие обработчики этого же события на данном элементе

Делегирование

Делегирование — это действие по установке обработчиков событий на более высоких элементов модели DOM, чем представляющие интерес элементы.

Предположим, что у нас есть div , внутри которого располагаются 100 button .

Вешать обработчик события на каждую кнопку нерационально. Практичнее повесить один обработчик на вышестоящий div . Поясню: при клике на кнопку, события об этом сначала погрузится от корня документа до кнопки, по которой произошел клик, пройдя через div , а затем всплывет от кнопки, по которой произошел клик до корня документа, также пройдя через div .

Мы можем повесить обработчик события click для div на любую фазу, и клики по любой кнопке будут так или иначе перехвачены всего лишь одним общим обработчиком. Это и есть делегирование.

Управление обработкой событий

Хорошая практика: каждому обрабатываемому эл-ту присвоить идентификатор (не путать с id ), а затем сохранить все связанные с ним данные в одном объекте.

JavaScript — Всплытие события

На этом уроке мы познакомимся с таким понятием как всплытие события, а также рассмотрим, как его можно прервать. Кроме этого выясним, какие ещё этапы (фазы) проходит событие, перед тем как начать всплывать.

Всплытие события

Если у некоторого элемента возникает событие, то оно начинает «всплывать», т.е. возникает у родителя, потом у прародителя и т.д.

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

Всплытие события (пузырька) продемонстрируем на следующем примере:

Напишем небольшой скрипт, с помощью которого добавим обработчик события » click » для всех элементов страницы, а также для объектов document и window .

Создадим HTML-страницу и вставим в неё вышеприведённый HTML код. Сценарий, написанный на языке JavaScript, вставим перед закрывающим тегом body . После этого откроем только что созданную страницу в веб-браузере, нажмём клавишу F12 и перейдём в консоль. Теперь нажмём левой кнопкой мышкой в области, принадлежащей элементу strong , и посмотрим, как событие будет всплывать.

Как прервать всплытие события

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

Например, изменим наш вышеприведённый пример таким образом, чтобы событие не всплывало выше body :

Бесспорно всплытие — это очень удобно и архитектурно прозрачно. Не прекращайте его без явной нужды.

Получение элемента, который вызвал обработчик

Для того чтобы получить DOM-элемент (объект), который вызвал обработчик события, необходимо использовать ключевое слово this . Данное ключевое слово (this) доступно в обработчике только в том случае, если Вы подписались на событие с помощью JavaScript.

Например, выведем в консоль id элемента, который вызвал обработчик события:

Для получения текущего элемента также можно использовать свойство currentTarget ( event.currentTarget ).

Этапы (фазы) прохода события

Перед тем как события начинает всплывать (этап всплытия), оно предварительно проходит ещё 2 этапа:

  • 1 этап — это этап погружения до элемента, сгенерировавшего событие. Т.е. на данном этапе происходит движение сверху вниз, т.е. от объекта window до элемента. Также данный этап ещё называют этапом перехвата.
  • 2 этап — это этап достижение цели, т.е. элемента (объекта), сгенерировавшего событие.

С учётом всех этапов, которые проходит событие, получается следующая картина:

Изменим сценарий вышеприведённого примера следующим образом:

Третий параметр методов addEventListener и removeEventListener определяет этап, на котором будет поймано событие. Если данный параметр имеет значение true , то событие будет перехватываться на стадии погружения (перехвата) события. А если параметр имеет значение false , то событие будет перехватываться на этапе всплытия. Для обработки события на самой цели, можно использовать метод addEventListener как со значением false , так и со значением true .

Получение элемента, который сгенерировал событие

Для того чтобы получить целевой элемент, т.е. элемент, который сгенерировал событие, необходимо использовать свойство target ( event.target ).

Рассмотрим вышеприведённый пример, в котором изменим содержимое элемента script на следующее:

В этом примере мы добавили обработчик события » click » для элемента body . Данный обработчик будет выводить в консоль элемент, который вызвал обработчик и элемент, который сгенерировал событие.

Продемонстрируем наш пример, кликнув левой кнопкой мыши в области, принадлежащей элементу strong :

События в Javascript

HTML события это такая «вещь», которая временами происходит с HTML элементами.

HTML событие может быть неким действием, которое делает браузер или пользователь.

При использовании на HTML странице скрипта JavaScript он может реагировать на эти события.

Вот несколько примеров HTML событий:

  • HTML страница закончила загружаться
  • Поле ввода было изменено
  • Пользователь нажал на HTML кнопку

Часто, при возникновении HTML события необходимо что-то сделать. JavaScript позволяет при обнаружении нужного события выполнить необходимый код. Для этого у HTML элементов есть специальные атрибуты обработчики событий, в которые и можно добавить JavaScript код:

С одинарными кавычками:

С двойными кавычками:

В следующем примере элементу button добавлен атрибут onclick с JavaScript кодом:

В приведенном примере при нажатии пользователем на кнопку код JavaScript изменит содержимое элемента с и выведет в него текущую дату и время.

В следующем примере JavaScript код изменит содержимое самого элемента (используется команда this.innerHTML):

Однако, очень редко можно увидеть код JavaScript, состоящий из одного выражения. Поэтому обычно в атрибут события записывают вызов JavaScript функции:

Часто используемые HTML события

Ниже приводится список некоторых часто используемых HTML событий:

Событие Описание
onchange HTML элемент был изменен
onclick Пользователь кликнул мышкой на HTML элемент
onmouseover Пользователь навел мышку на HTML элемент
onmouseout Пользователь вывел мышку за пределы HTML элемента
onkeydown Пользователь нажал на клавишу клавиатуры
onload Браузер закончил загружать страницу

Конечно, список событий гораздо длиннее. Смотрите раздел События HTML DOM и HTML атрибуты-события.

Что может делать JavaScript с событиями?

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

  • Выполнять действия повторяющиеся после загрузки страницы
  • Выполнять действия повторяющиеся после закрытия страницы
  • Действия, которые должны выполняться при нажатии пользователем на кнопку
  • Проверка данных, введенных пользователем в поле формы
  • И многое другое .


В JavaScript существует множество способов работать с событиями:

  • HTML атрибуты-события могут напрямую выполнять код JavaScript
  • HTML атрибуты-события могут вызывать функции JavaScript
  • Вы можете установить собственную функцию обработки события
  • Вы можете запретить отправку и обработку события
  • И многое другое .

Всплытие и перехват

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

Это происходит потому, что событие всплывает.

Например, этот обработчик для DIV сработает, если вы кликните по вложенному тегу EM или CODE :

Всплытие

Основной принцип всплытия:

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

Например, есть 3 вложенных блока:

Всплытие гарантирует, что клик по внутреннему div 3 вызовет событие onclick сначала на внутреннем элементе 3, затем на элементе 2 и в конце концов на элементе 1.

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

Текущий элемент, this

Элемент, на котором сработал обработчик, доступен через this.

Например, повесим на клик по каждому DIV функцию highlight , которая подсвечивает текущий элемент:

Также существует свойство объекта события event.currentTarget .

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

IE8- при назначении обработчика через attachEvent не передаёт this . Браузеры IE8- не предоставляют this при назначении через attachEvent . Также в них нет свойства event.currentTarget .

Если вы будете использовать фреймворк для работы с событиями, то это не важно, так как он всё исправит. А при разработке на чистом JS имеет смысл вешать обработчики через onсобытие: это и кросс-браузерно, и this всегда есть.

Целевой элемент, event.target

Самый глубокий элемент, который вызывает событие, называется «целевым» или «исходным» элементом.

В IE event.srcElement , остальные браузеры используют event.target . Кроссбраузерное решение выглядит так:

  • event.target/srcElement — означает исходный элемент, на котором произошло событие.
  • this — текущий элемент, до которого дошло всплытие и который запускает обработчик.

Прекращения всплытия

Всплытие идет прямо наверх. Обычно оно будет всплывать до , а затем до document , вызывая все обработчики на своем пути.

Но любой промежуточный обработчик может решить, что событие полностью обработано, и остановить всплытие.

Сценарий, при котором это может быть нужно:

  1. На странице по правому клику показывается, при помощи JavaScript, специальное контекстное меню;
  2. На странице также есть таблица, которая показывает меню, но другое, своё;
  3. В случае правого клика по таблице её обработчик покажет меню и остановит всплытие, чтобы меню уровня страницы не показалось.

Код для остановки всплытия различается между IE stopPropagation на событие click . А позже, на совсем другом месте страницы понадобилось отследить «клик вне элемента» — скажем, чтобы закрыть пункт меню. Обычно для этого ставят обработчик document.onclick и по event.target проверяют, внутри был клик или нет. Но над областью, где клики убиваются stopPropagation , такой способ будет нерабочим!

Три стадии прохода событий

Во всех браузерах, кроме IE true , то событие будет перехвачено по дороге вниз.

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

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

    Захват событий в JavaScript

    Когда мы нажимаем на какой-либо элемент на станице и генерируется событие нажатия, то это событие может распространяться от элемента к элементу. Например, если мы нажимаем на блок div, то также мы нажимаем и на элемент body, в котором блок div находится. То есть происходит распространение события.

    Есть несколько форм распространения событий:

    Восходящие: событие распространяется вверх по дереву DOM от дочерних узлов к родительским

    Нисходящие: событие распространяется вниз по дереву DOM от родительских узлов к дочерним, пока не достигнет того элемента, на котором это событие и возникло

    Восходящие события

    Рассмотрим восходящие (bubbling) события, которые распространяются в верх по дереву DOM. Допустим, у нас есть следующая веб-страница:

    Если мы нажмем на вложенный div, то событие пойдет к родительскому элементу div и далее к элементу body:

    Надо сказать, что подобное поведение не всегда является желательным. И в этом случае мы можем остановить распространение событие с помощью метода stopPropagation() объекта Event:

    И в результате нажатия событие будет обработано только обработчиком для redRect.

    Нисходящие события

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

    Возьмем ту же веб-станицу, только изменим ее код javascript:

    Теперь события будут распространяться в обратном порядке:

    Обработка событий в JavaScript

    Обработка событий в JavaScript — это, пожалуй, самое «вкусное блюдо», т.к. именно обработка событий выдает ответную реакцию на действия пользователей.

    События в JS разделяются на системные: загрузка (load) и выгрузка (unload) страницы, события мыши (click, mouseover, mousemove и т.д.) и события клавиатуры (keypress, keydown, keyup).

    Сегодня сосредоточимся на событиях мыши.

    События мыши

    К событиям мыши относятся:

    • click — клик;
    • dblclick — двойной клик;
    • mouseover — наведение курсора мыши на элемент;
    • mousemove — перемещение курсора мыши над элементом;
    • mouseout — уведение курсора мыши с элемента;
    • mousedown — нажатие левой кнопки мыши;
    • mouseup — отпускание левой кнопки мыши;
    • contextmenu — нажатие правой кнопки мыши и вывод контекстного меню.

    Для того чтобы написать ответную реакцию на событие, создают обработчик события (event handler), который, как правило, представляет собой функцию.

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

    Рассмотрим все способы.

    Обработчик события как атрибут элемента

    Это самый старый способ назначения обработчиков события и наименее используемый на данный момент. Для того чтобы его добавить, необходимо к имени события добавить приставку «on» и записать примерно такой код:

    Предотвращение всплывания (bubbling) и захвата (capture) событий

    Предотвратить передачу события от одного элемента другому, так называемое «всплывание» события, можно при помощи следующей функции:

    Здесь — oEvent это объект «событие». Если объект oEvent не определен (имеем дело с Internet Explorer), то используем window.event.

    Для тех, кто не знает, что такое передача событий, вкратце объясню его смысл.

    Событие JavaScript выполняется в две фазы — «захват» (capturing) и «всплывание» (bubbling). Эти схемы передачи событий определяют, какие элементы будут обрабатывать данное событие и в каком порядке. Пример передачи события для обоих схем представлен на следующем рисунке:

    Рисунок показывает, в каком порядке вызываются обработчики событий при щелчке на ссылке. Вначале вызывается обработчик для объекта document, затем , затем

    По окончании первой фазы, начинается вторая — «всплывание» события, когда обработчики событий вызываются в обратном порядке: ,
    и так далее до объекта document.

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

    При использовании обычных обработчиков событий выполняется только вторая фаза — всплывание. Если же вместо обработчиков добавляются слушатели событий при помощи функции addEventListener(), то тип передачи событий можно выбирать:

    Последний параметр в функции addEventListener() указывает на тип передачи событий, если false, то используется всплывание, если true, то захват.

    лабы по информатике, егэ

    лабораторные работы и задачи по программированию и информатике, егэ по информатике

    JavaScript урок 8. Часть 2. Объектная модель документа (javaScript DOM) и события


    Типы событий JavaScript

    Рассмотрим наиболее стандартные и часто используемые javaScript события:

    Поддерживающие HTML- элементы и объекты

    a, area, button, input,
    label, select, textarea

    Потеря текущим элементом фокуса. Возникает при
    щелчке мышью вне элемента либо нажатии клавиши табуляции

    Input, select, textarea

    Изменение значений элементов формы. Возникает после потерей элементом фокуса, т.е. после события blur

    Одинарный щелчок (нажата и отпущена кнопка мыши)

    a, area, button, input, label, select, textarea

    Получение элементом фокуса

    Закончена загрузка документа

    Нажата кнопка мыши в пределах текущего элемента

    Курсор мыши выведен за пределы
    текущего элемента

    Курсор мыши наведен на текущий элемент

    Отпущена кнопка мыши в пределах текущего элемента

    Изменение размеров окна

    Выделение текста в текущем элементе

    Отправка данных формы

    Попытка закрытия окна браузера и выгрузки документа

    Событие onLoad. Свойства высоты и ширины объекта в javaScript

    Для выполнения следующего примера нам понадобится новое понятие — событие.

    В нашем случае событие — это реакция программы на действие пользователя (щелчок мышью по кнопке, уменьшение мышкой окна браузера, ввод текста с клавиатуры и т.д.). С помощью программы у нас есть возможность отреагировать на любые действия пользователя.

    Рассмотрим одно из самых распространенных событий — onload — которое происходит при загрузке документа (когда пользователь своими действиями вызвал загрузку веб-страницы).

    Рассмотрим пример использования события javascript onload для изменения ширины и высоты элемента.

  • переменная myImg ассоциирована с тегом img — картинкой, свойство которой width — ширина — меняется в самой функции.
  • Вызов функции происходит по загрузке страницы в событии onload тела документа (тело — body — главный элемент, поэтому загрузка страницы — это событие, относящееся к телу).

    var allImg=document. ; // получаем массив изображений for (var i=0; i Событие onclick javaScript и три способа обработки событий

    Событие onClick происходит во время одинарного щелчка кнопкой мыши. Обычно для события назначается обработчик, то есть функция, которая сработает, как только событие произошло. Обработать событие, т.е. отреагировать на него посредством скрипта, можно тремя способами. Рассмотрим их:

    Через свойство объекта с использованием пользовательской функции:

    Скрипт:

    html-код:

    Через атрибут тега:

    html-код:

    Скрипт:

    document.myForm.myButton.onclick = message; function message()

    В скрипте, который обязательно находится ниже дерева элементов (можно перед закрытием тега body ), находится обращение к кнопке ( document.myForm.myButton ), для которой назначается обработчик события onclick со значением ссылки на функцию. Обращение к кнопке может быть организовано через атрибут id ( document.getElementBy >)

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

    Именно такой способ обработки событий максимально приближен к тому, который происходит, например, в ОС windows.

  • document.write добавляет html во время построения DOM
  • alert блокируют выполнение JS, пока пользователь не нажмёт OK

    alert(‘str’); // показывает окошко

    document.write(‘htmlstr’); // пишет на страницу

    document.innerHTML += ‘htmlstr’; // добавляет на страницу

    console.log(‘str’); // выводит в консоль браузерах

    1. Создайте веб-страницу и расположите в ней тег img с изображением грустного смайлика.
    2. Щелчок на изображении ( onclick ) вызывает заданный метод (пользовательская функция):

    События onMouseOver и onMouseOut

    Событие наступает при наведении ( onMouseOver ) на объект и при выведении ( onMouseOut ) за пределы объекта курсора мыши.

    Назначение обработчика событий осуществляется точно таким же образом, как и в случае с событием onclick.

    Поэтому выполним задание:

    Зеленый
    … seagreen
    … magenta
    … purple
    … navy
    … royalblue

    — Добавьте в код тег img с изображением.
    — Введите обработчики событий onmouseover (по наведению) и onmouseout (при отведении). Сделайте это в виде функций.
    — Присоедините к обработчику событий onmouseover процедуру загрузки в тег img другого изображения.
    — Присоедините к обработчику событий onmouseout процедуру загрузки другого изображения в тег img .

    Несколько обработчиков одного и того же события

  • addEventListener — добавление обработчика
  • removeEventListener — удаление обработчика

    Синтаксис addEventListener:

    У метода три аргумента:

  • event — название события, например, click
  • handler — функция-обработчик
  • phase — необязательный аргумент, «фаза», на которой обработчик должен сработать

    Синтаксис removeEventListener:

    Методу следует передать те же аргументы, что были у addEventListener:

  • event — название события, например, click
  • handler — функция-обработчик
  • phase — необязательный аргумент, «фаза», на которой обработчик должен сработать

    obj.onevent = function(e) // где e — объект события // e.target — элемент, на котором произошло событие

    Задание Js8_4. Что я делаю не так? Вот мой код(не работает)

    var allImg = document.getElementsByTagName(«img»);
    for (var a in allImg )
    <
    allImg[0].style.w > allImg[0].style.height = 50px;
    allImg[0].style.border = 10px;
    >

    admin

    1. Кавычки лучше другие ставить (не русские) или вообще апостроф, как у меня.
    2. px не нужно писать в данном случае
    3. Скрипт должен находиться перед закрытием тега body )

    var allImg = document.getElementsByTagName(‘img’);
    for (var a in allImg )
    <
    allImg[0].style.w > allImg[0].style.height = 50;
    allImg[0].style.border = 100;
    >

    Добрый вечер,
    подскажите, что не так.
    Пытаюсь воспроизвести пример: «Добавить на страницу изображение и при помощи javascript при наступлении события загрузки страницы сделать ширину изображения соответствующей ширине окна браузера», не получается никак. Картинка не растягивается..

    function resizeImgs() <
    var te = document.getElementById(«img1»);
    te.style.w > >;

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

    function resizeImgs() <
    var te = document.getElementById(«img1»);
    te.style.w > >;

    admin

    Здравствуйте! Попробуйте не использовать такие кавычки в коде: «img1», попробуйте одинарные ‘img1’.

    Топ-пост этого месяца:  Рекламная сеть Яндекса (РСЯ) — один из основных способов заработка на сайте (теперь в формате RTB)
  • Добавить комментарий