ReactJS - Refs и DOM
Здравствуйте, будущие разработчики React! Сегодня мы погрузимся в увлекательную тему, которая поможет вам взаимодействовать с элементами DOM в ваших приложениях React. Закрепите ремни,因为我们 собираемся исследовать мир Refs и DOM!
Что такое Refs?
Прежде чем мы углубимся в детали, давайте поймем, что такое Refs. В React "Ref" - это сокращение от "reference" (ссылка). Это как дать конкретному элементу бирку с именем, чтобы вы могли легко найти его позже. Представьте, что вы на большом празднике и хотите следить за своим лучшим другом. Вы можете дать ему specialную шляпу или уникальную бирку. Это essentially то, что делают Refs в React - они помогают вам следить за конкретными элементами.
Почему нам нужны Refs?
Вы можете задаться вопросом: "Почему мы не можем просто использовать обычный JavaScript для выбора элементов?" Ну, в React мы стараемся избегать прямого манипулирования DOM (Document Object Model), потому что React имеет свой эффективный способ обновления интерфейса. Однако бывают случаи, когда нам нужно выйти за пределы декларативной парадигмы React и работать напрямую с элементами DOM. Вот где Refs могут пригодиться!
Создание Refs с помощью createRef()
Давайте начнем с того, как создаем Ref в React. Мы используем метод createRef()
.
Сигнатура метода createRef
Сигнатура createRef()
довольно проста:
React.createRef()
Вот и все! Никаких параметров, никаких сложностей. Он возвращает пустой объект с единственным свойством: current
. Initially, это свойство установлено в null
.
Давайте посмотрим пример:
class MyComponent extends React.Component {
constructor(props) {
super(props);
this.myRef = React.createRef();
}
render() {
return <div ref={this.myRef} />;
}
}
В этом примере мы создаем Ref в конструкторе и присваиваем его this.myRef
. Затем в методе render
мы attach этого Ref к элементу div
с помощью атрибута ref
.
Применение ref
Теперь, когда мы создали наш Ref, давайте посмотрим, как мы можем его использовать. Есть несколько способов применения Ref:
1. Refs на DOM элементах
Самый распространенный случай - применить Ref к DOM элементу:
class AutoFocusInput extends React.Component {
constructor(props) {
super(props);
this.inputRef = React.createRef();
}
componentDidMount() {
this.inputRef.current.focus();
}
render() {
return <input ref={this.inputRef} />;
}
}
В этом примере мы создаем Ref для элемента ввода. После того как компонент монтируется, мы используем Ref для автоматического фокуса на вводе. Свойство current
Ref дает нам доступ к реальному узлу DOM.
2. Refs на классовых компонентах
Вы также можете использовать Refs с классовыми компонентами:
class AutoScrollingList extends React.Component {
constructor(props) {
super(props);
this.listRef = React.createRef();
}
componentDidUpdate() {
const node = this.listRef.current;
node.scrollToItem(0);
}
render() {
return <MyListComponent ref={this.listRef} />;
}
}
В этом случае this.listRef.current
будет указывать на экземпляр класса MyListComponent
.
3. Refs и функциональные компоненты
Функциональные компоненты не могут быть даны Refы напрямую, но вы можете использовать функцию forwardRef
для передачи Refов:
const FancyButton = React.forwardRef((props, ref) => (
<button ref={ref} className="FancyButton">
{props.children}
</button>
));
class MyComponent extends React.Component {
constructor(props) {
super(props);
this.buttonRef = React.createRef();
}
render() {
return <FancyButton ref={this.buttonRef}>Нажми меня!</FancyButton>;
}
}
В этом примере FancyButton
использует forwardRef
для передачи Refа к реальному элементу按钮а.
Сценарии использования createRef
Теперь, когда мы знаем, как создавать и применять Refs, давайте рассмотрим некоторые распространенные сценарии использования:
1. Управление фокусом, текстовым выделением или воспроизведением медиа
class TextInput extends React.Component {
constructor(props) {
super(props);
this.inputRef = React.createRef();
}
focusTextInput = () => {
this.inputRef.current.focus();
}
render() {
return (
<div>
<input type="text" ref={this.inputRef} />
<button onClick={this.focusTextInput}>Фокус на ввод</button>
</div>
);
}
}
Этот компонент позволяет нам программно фокусировать ввод при нажатии на кнопку.
2. Запуск imperативных анимаций
class Animator extends React.Component {
constructor(props) {
super(props);
this.elementRef = React.createRef();
}
animate = () => {
this.elementRef.current.classList.add('animated');
}
render() {
return (
<div>
<div ref={this.elementRef}>Анимируй меня!</div>
<button onClick={this.animate}>Начать анимацию</button>
</div>
);
}
}
Здесь мы используем Ref для добавления CSS класса к элементу, что запускает анимацию.
3. Интеграция с third-party DOM библиотеками
class MapComponent extends React.Component {
constructor(props) {
super(props);
this.mapRef = React.createRef();
}
componentDidMount() {
const mapLibrary = new FancyMapLibrary();
mapLibrary.createMap(this.mapRef.current);
}
render() {
return <div ref={this.mapRef} style={{width: '100%', height: '400px'}} />;
}
}
В этом примере мы используем Ref для предоставления third-party map библиотеке доступа к DOM узлу, где она может отрендерить карту.
Заключение
Refs - это мощный инструмент в React, который позволяет нам выходить за пределы декларативной парадигмы, когда это необходимо. Они предоставляют способ прямого доступа к DOM узлам или React элементам. Однако важно использовать Refs с умом. В большинстве случаев вы можете достичь того, что вам нужно, через декларативные API React. Но когда вам действительно нужно дополнительное управление, Refs всегда под рукой!
Помните, с большой силой приходит большая ответственность. Используйте Refs wisely, и ваши приложения React будут вам благодарны!
Вот quick reference таблица методов, о которых мы говорили:
Метод | Описание | Пример |
---|---|---|
React.createRef() |
Создает ref объект | this.myRef = React.createRef(); |
ref атрибут |
Присоединяет ref к React элементу | <div ref={this.myRef} /> |
forwardRef |
Позволяет функциональным компонентам принимать refs | const FancyButton = React.forwardRef((props, ref) => ...) |
Счастливого кодирования, и пусть ваши Refs всегда будут актуальными!
Credits: Image by storyset