Реакт по своей природе изолирует нас от прямой работы с DOM на 100%. Но нередко при интеграции сторонних не-Реакт компонентов возникает задача по прямому доступу к DOM. Также подобный механизм нужен для выделения текста, фокусов и проигрывания медиа.

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

Рассмотрим задачу по фокусировке на поле ввода:

See the Pen js_react_refs_focus by Hexlet (@hexlet) on CodePen.

ref — это свойство компонента, значением которого должна быть функция. Она будет вызвана сразу после того, как Реакт вставит элемент в реальный DOM. Единственный параметр функции — реальный DOM элемент.

Дальше можно установить элемент в свойство и использовать его либо в componentDidMount, либо в componentDidUpdate.

Ниже приведен пример создания компонента обертки над популярным JQuery плагином Chosen.

See the Pen js_react_refs_dom by Hexlet (@hexlet) on CodePen.

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

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

const CustomTextInput = (props) => {
  // textInput must be declared here so the ref callback can refer to it
  let textInput = null;

  handleClick = () => textInput.focus();

  return (
    <div>
      <input
        type="text"
        ref={(input) => { textInput = input; }} />
      <input
        type="button"
        value="Focus the text input"
        onClick={handleClick}
      />
    </div>
  );
}