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

Связывание обработчиков событий в конструкторе.

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

class Switcher extends React.Component {
  render() {
    return (
      <button onClick={ this._handleButtonClick }>
        click me
      </button>
    );
  }
  _handleButtonClick() {
    console.log('Button is clicked');
  }
}

Все отлично, потому что_handleButtonClick - это функция, и мы действительно передаем функцию атрибуту onClick. Проблема в том, что этот код не сохраняет контекст. Итак, если мы захотим использовать this внутри _handleButtonClick, то получим ошибку.

class Switcher extends React.Component {
  constructor(props) {
    super(props);
    this.state = { name: 'React in patterns' };
  }
  render() {
    return (
      <button onClick={ this._handleButtonClick }>
        click me
      </button>
    );
  }
  _handleButtonClick() {
    console.log(`Button is clicked inside ${ this.state.name }`);
    // Приводит к
    // Uncaught TypeError: Cannot read property 'state' of null
  }
}

Обычно мы используем bind:

<button onClick={ this._handleButtonClick.bind(this) }>
  click me
</button>

Однако это означает, что функция bind вызывается снова и снова, потому что мы можем отображать кнопку много раз. Лучшим подходом была бы передача bind в конструкторе компонента:

class Switcher extends React.Component {
  constructor(props) {
    super(props);
    this.state = { name: 'React in patterns' };
    this._buttonClick = this._handleButtonClick.bind(this);
  }
  render() {
    return (
      <button onClick={ this._buttonClick }>
        click me
      </button>
    );
  }
  _handleButtonClick() {
    console.log(`Button is clicked inside ${ this.state.name }`);
  }
}

Другой альтернативой является использование стрелочный функций для onClick. Стрелочные функции не влияют на контекст во время вызова ( значение this используется в окружении).

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

Короткий пример с использованием стрелочных функций:

class Switcher extends React.Component {
  state = { name: 'React in patterns' };

  render() {
    return (
      <button onClick={ this._handleButtonClick }>
        click me
      </button>
    );
  }
  _handleButtonClick = () => {
    console.log(`Button is clicked inside ${ this.state.name }`);
  }
}

results matching ""

    No results matching ""