Preventdefault react что это
Handling Events
Handling events with React elements is very similar to handling events on DOM elements. There are some syntax differences:
For example, the HTML:
is slightly different in React:
Another difference is that you cannot return false to prevent default behavior in React. You must call preventDefault explicitly. For example, with plain HTML, to prevent the default form behavior of submitting, you can write:
In React, this could instead be:
Here, e is a synthetic event. React defines these synthetic events according to the W3C spec, so you don’t need to worry about cross-browser compatibility. React events do not work exactly the same as native events. See the SyntheticEvent reference guide to learn more.
When using React, you generally don’t need to call addEventListener to add listeners to a DOM element after it is created. Instead, just provide a listener when the element is initially rendered.
When you define a component using an ES6 class, a common pattern is for an event handler to be a method on the class. For example, this Toggle component renders a button that lets the user toggle between “ON” and “OFF” states:
This is not React-specific behavior; it is a part of how functions work in JavaScript. Generally, if you refer to a method without () after it, such as onClick=
If calling bind annoys you, there are two ways you can get around this. If you are using the experimental public class fields syntax, you can use class fields to correctly bind callbacks:
This syntax is enabled by default in Create React App.
If you aren’t using class fields syntax, you can use an arrow function in the callback:
The problem with this syntax is that a different callback is created each time the LoggingButton renders. In most cases, this is fine. However, if this callback is passed as a prop to lower components, those components might do an extra re-rendering. We generally recommend binding in the constructor or using the class fields syntax, to avoid this sort of performance problem.
Passing Arguments to Event Handlers
Inside a loop, it is common to want to pass an extra parameter to an event handler. For example, if id is the row ID, either of the following would work:
The above two lines are equivalent, and use arrow functions and Function.prototype.bind respectively.
In both cases, the e argument representing the React event will be passed as a second argument after the ID. With an arrow function, we have to pass it explicitly, but with bind any further arguments are automatically forwarded.
Обработка событий
Обработка событий React-элементов очень похожа на обработку событий на элементах DOM. Существуют синтаксические различия:
немного отличается по сравнению с React:
В React это могло бы быть так:
Здесь e — синтетическое событие. React определяет эти синтетические события в соответствии со спецификацией W3C, поэтому вам не нужно беспокоиться о совместимости между браузерами. Посмотрите справочное руководство SyntheticEvent для получения дополнительной информации.
Когда вы определяете компонент, используя класс ES6, распространённой практикой является объявлять обработчик события как метод класса. Например, данный компонент Toggle отображает кнопку, которая позволяет пользователю переключаться между состояниями «ON» и «OFF»:
Это не связано с конкретным поведением React; это часть того, как работают функции в JavaScript. Как правило, если вы ссылаетесь на метод без () после него, например onClick =
Если вызов bind раздражает вас, есть два способа обойти это. Если вы используете экспериментальный [синтаксис полей общедоступных классов] (https://babeljs.io/docs/plugins/transform-class-properties/), вы можете использовать поля классов для правильной привязки колбэков:
Этот синтаксис включён по умолчанию в Create React App.
Если вы не используете синтаксис полей, то вместо него можно воспользоваться стрелочной функцией в колбэке:
Проблема с этим синтаксисом заключается в том, что при каждой отрисовке LoggingButton создаётся новый колбэк. В большинстве случаев это не создае проблем. Однако, если этот колбэк передаётся в качестве свойства нижестоящим компонентам, то эти компоненты могут выполнять дополнительную повторную отрисовку. Как правило, мы рекомендуем привязывать обработчики в конструкторе или использовать синтаксис полей классов, чтобы избежать такого рода проблем с производительностью.
Передача аргментов в обработчики событий
Внутри цикла обычно требуется передать дополнительный параметр обработчику событий. Например, если id — это идентификатор строки, рабочим будет один из следующих вариантов:
Вышеуказанные две строки эквикаленты и используют стрелочные функции и Function.prototype.bind соответственно.
Обработка событий¶
Обработка событий в React-элементах очень похожа на обработку событий в DOM-элементах. Но есть несколько синтаксических отличий:
В React немного иначе:
В React это будет выглядеть так:
В приведённом выше коде e — это синтетическое событие. React определяет синтетические события в соответствии со спецификацией W3C, поэтому не волнуйтесь о кроссбраузерности.
В компоненте, определённом с помощью ES6-класса, в качестве обработчика события обычно выступает один из методов класса. Например, этот компонент Toggle рендерит кнопку, которая позволяет пользователю переключать состояния между «Включено» и «Выключено»:
Дело не в работе React, это часть того, как работают функции в JavaScript. Обычно, если ссылаться на метод без () после него, например, onClick=
Такой синтаксис доступен в Create React App по умолчанию.
Если вы не пользуетесь синтаксисом полей, можете попробовать стрелочные функции в колбэке:
Проблема этого синтаксиса в том, что при каждом рендере LoggingButton создаётся новый колбэк. Чаще всего это не страшно. Однако, если этот колбэк попадает как проп в дочерние компоненты, эти компоненты могут быть отрендерены снова. Мы рекомендуем делать привязку в конструкторе или использовать синтаксис полей классов, чтобы избежать проблем с производительностью.
Передача аргументов в обработчики событий¶
Внутри цикла часто нужно передать дополнительный аргумент в обработчик события. Например, если id — это идентификатор строки, можно использовать следующие варианты:
Две строки выше — эквивалентны, и используют стрелочные функции и Function.prototype.bind соответственно.
Обработчики событий в React
Как определить, какое действие будет предпринято при каждом событии
Работа c обработчиком событий React очень похожа на работу с событиями в элементах DOM. Хотя есть несколько отличий.
Аргумент события:
Привязки обработчиков событий
Прежде чем обсуждать привязки, давайте немного рассмотрим ключевое слово this. Ключевое слово this не определено по умолчанию в компонентах класса.
Теперь вернемся к привязкам. У нас есть три способа привязки обработчиков событий.
1. Динамическое связывание:
Этот подход будет работать, однако проблема с этим подходом состоит в том, что любые изменения в this.state.name приведут к повторной визуализации компонента.
Если на странице всего несколько кнопок, это еще допустимо, однако это плохая практика.
2. Связывание с конструктором:
В этом нет ничего особенного, это один из старых способов ведения дел, и он лучше, чем первый.
3. Использование стрелочных функций
ИМХО, такой подход, честно говоря, является лучшим способом ведения дел.
В приведенном выше коде buttonClicked является функцией, которая эквивалентна: constructor() < this.buttonClicked = () =><…>; >
Следовательно, после инициализации компонента this.buttonClicked больше никогда не изменится. Таким образом, мы можем гарантировать, что повторное отображение не произойдет.
Передача аргументов
В любом React приложении мы будем постоянно создавать обработчики событий для компонентов, чтобы обновлять состояние. Во многих из этих случаев нам нужно передать аргументы или параметр этому обработчику событий.
Мы можем сделать это двумя способами:
Использование анонимной стрелочной функции
Привязка обработчика событий к ‘this’:
Вывод
Мы можем использовать аналогичный подход при работе с событиями для элементов React, как при обработке событий на обычных элементах DOM. Есть несколько различий между ними, что, я думаю, мы можем легко иметь в виду.
Что касается привязок, всегда полезно использовать «Связывание стрелочных функций», когда это возможно.
Действия браузера по умолчанию
Многие события автоматически влекут за собой действие браузера.
Если мы обрабатываем событие в JavaScript, то зачастую такое действие браузера нам не нужно. К счастью, его можно отменить.
Отмена действия браузера
Есть два способа отменить действие браузера:
В следующем примере при клике по ссылке переход не произойдёт:
Обычно значение, которое возвращает обработчик события, игнорируется.
В других случаях return не нужен, он никак не обрабатывается.
Пример: меню
Рассмотрим меню для сайта, например:
Данный пример при помощи CSS может выглядеть так:
Кстати, использование здесь делегирования событий делает наше меню очень гибким. Мы можем добавить вложенные списки и стилизовать их с помощью CSS – обработчик не потребует изменений.
Некоторые события естественным образом вытекают друг из друга. Если мы отменим первое событие, то последующие не возникнут.
Опция «passive» для обработчика
Почему это может быть полезно?
Есть некоторые события, как touchmove на мобильных устройствах (когда пользователь перемещает палец по экрану), которое по умолчанию начинает прокрутку, но мы можем отменить это действие, используя preventDefault() в обработчике.
Поэтому, когда браузер обнаружит такое событие, он должен для начала запустить все обработчики и после, если preventDefault не вызывается нигде, он может начать прокрутку. Это может вызвать ненужные задержки в пользовательском интерфейсе.
Опция passive: true сообщает браузеру, что обработчик не собирается отменять прокрутку. Тогда браузер начинает её немедленно, обеспечивая максимально плавный интерфейс, параллельно обрабатывая событие.
event.defaultPrevented
Рассмотрим практическое применение этого свойства для улучшения архитектуры.
Помните, в главе Всплытие и погружение мы говорили о event.stopPropagation() и упоминали, что останавливать «всплытие» – плохо?
Давайте посмотрим практический пример.
По умолчанию браузер при событии contextmenu (клик правой кнопкой мыши) показывает контекстное меню со стандартными опциями. Мы можем отменить событие по умолчанию и показать своё меню, как здесь:
Теперь в дополнение к этому контекстному меню реализуем контекстное меню для всего документа.
При правом клике должно показываться ближайшее контекстное меню.
Как это поправить? Одно из решений – это подумать: «Когда мы обрабатываем правый клик в обработчике на кнопке, остановим всплытие», и вызвать event.stopPropagation() :
Теперь контекстное меню для кнопки работает как задумано. Но цена слишком высока. Мы навсегда запретили доступ к информации о правых кликах для любого внешнего кода, включая счётчики, которые могли бы собирать статистику, и т.п. Это слегка неразумно.
Как мы можем видеть, event.stopPropagation() и event.preventDefault() (также известный как return false ) – это две разные функции. Они никак не связаны друг с другом.
Есть также несколько альтернативных путей, чтобы реализовать вложенные контекстные меню. Одним из них является единый глобальный объект с обработчиком document.oncontextmenu и методами, позволяющими хранить в нём другие обработчики.
Объект будет перехватывать любой клик правой кнопкой мыши, просматривать сохранённые обработчики и запускать соответствующий.
Итого
Действий браузера по умолчанию достаточно много:
Все эти действия можно отменить, если мы хотим обработать событие исключительно при помощи JavaScript.
Технически, отменяя действия браузера по умолчанию и добавляя JavaScript, мы можем настроить поведение любого элемента. Например, мы можем заставить ссылку работать как кнопку, а кнопку вести себя как ссылка (перенаправлять на другой URL).
Но нам следует сохранять семантическое значение HTML элементов. Например, не кнопки, а тег должен применяться для переходов по ссылкам.
Помимо того, что это «хорошо», это делает ваш HTML лучше с точки зрения доступности для людей с ограниченными возможностями и с особых устройств.