Step by Step

React Study(4) - 리액트를 다루는 기술 5장 본문

React

React Study(4) - 리액트를 다루는 기술 5장

짤진이 2023. 1. 30. 16:27
반응형

#5장 ref:DOM에 이름 달기

요소에 id를 달면 CSS에서 특정 id에 특정 스타일을 적용하거나 자바스크립트에서 해당 id를 가진 요소를 찾아 작업이 쉽다.
HTML에서 id를 사용하여 DOM에 이름을 다는 것처럼 리액트 프로젝트 내부에서 DOM에 이름을 다는 방법이 있다.

const root = ReactDOM.createRoot(dovument.getElementById('root'));

5.1 ref는 어떤 상황에서 사용해야 할까?
'DOM을 꼭 직접적으로 건드려야 할 때'

* 리액트 컴포넌트에서 state 사용
ValidSample 컴포넌트 만들기 => input에 ref 달기 => 버튼을 누를 때마다 input에 포커스 주기

5.1.1 예제 컴포넌트 생성

<App.js>

import { Component } from "react";
import ValidationSample from './ValidationSample';

class App extends Component{
  render() {
    return (
      <ValidationSample/>
    );
  }
}

export default App;


<ValidationSample.js>

import { Component } from "react";
import './ValidationSample.css'

class ValidationSample extends Component{
    state = {
        password:'',
        clicked: false,
        validated: false
    }
    handleChange = (e) => {
        this.setState({
            password: e.target.value
        });
    }
    handleButtonClicked = () => {
    this.setState({
        clicked: true,
        validated: this.state.password === '0000'
        })
    }
    render() {
        return (
            <div>
                <input
                    type="password"
                    value={this.state.password}
                    onChange={this.handleChange}
                    className={this.state.clicked ? (this.state.validated?'success' : 'failure'): ''}>
                </input>
                <button onClick={this.handleButtonClicked}>검증하기</button>
            </div>
        )
    }
}
export default ValidationSample;



* DOM을 꼭 사용해야 하는 상황
state만으로 해결할 수 없는 기능이 있다.
특정 input에 포커스 줄 때
스크롤 박스 조작할 때
Canvas 요소에 그림 그릴 때

5.2 ref 사용
5.2.1 콜백 함수를 통한 ref 설정
ref를 달고자 하는 요소에 ref라는 콜백 함수를 props로 전달해 준다.
콜백 함수는 ref 값을 파라미터로 전달받고 함수 내부에서 파라미터로 받은 ref를 컴포넌트의 멤버 변수로 설정한다.
콜백 함수 사용 예시
<input ref={(ref) => {this.input=ref}}/>

5.2.3.1 input에 ref 달기

<ValidationSample.js>

// input에 ref 달기
import { Component } from "react";
import './ValidationSample.css'

class ValidationSample extends Component{
    state = {
        password:'',
        clicked: false,
        validated: false
    }
    handleChange = (e) => {
        this.setState({
            password: e.target.value
        });
    }
    handleButtonClicked = () => {
    this.setState({
        clicked: true,
        validated: this.state.password === '0000',
        })
        this.input.focus(); // focus 주기
    }
    render() {
        return (
            <div>
                <input
                    ref={(ref)=> this.input=ref} // input에 ref달기
                    type="password"
                    value={this.state.password}
                    onChange={this.handleChange}
                    className={this.state.clicked ? (this.state.validated?'success' : 'failure'): ''}>
                </input>
                <button onClick={this.handleButtonClicked}>검증하기</button>
            </div>
        )
    }
}
export default ValidationSample;

맞는 답일 때는 초록색
틀린 답일때는 적색

 

5.3 컴포넌트에 ref 달기
<MyComponent ref = {(ref)=>{this.MyComponent=ref}}
이렇게 하면 MyComponent 내부의 메서드 및 멤버 변수에도 접근할 수 있습니다. 즉 내부의 ref에도 접근할 수 있습니다.

부모 컴포넌트애서 스크롤바 내리기
ScrollBox 컴포넌트 만들기 => 컴포넌트애 ref달기 => ref를 이용하여 컴포넌트 내부 메서드 호출하기

5.3.2 컴포넌트 초기 설정

<ScrollBox.js>

import { Component } from "react";

class ScrollBox extends Component {

    scrollToBottom =() => {
        const {scrollHeight,clientHeight} = this.box;
        //const scrollHeight = this.box.scrollHeight
        //const clientHeight = this.box.clientHeight
        this.box.scrollTop = scrollHeight - clientHeight;
    }
    render() {
            const style = {
                border: '1px solid black',
                height: '300px',
                width: '300px',
                overflow: 'auto',
                position: 'relative'
            };
            const innerStyle = {
                width: '100%',
                height: '650px',
                background:'linear-gradient(white, black)'
            }
            return (
                <div
                    style={style}
                    ref={(ref)=>{this.box=ref}}>
                    <div style={innerStyle}/>
                </div>
            )
    }
}
export default ScrollBox;

스크롤 박스 없을 때

 

스크롤 박스 있을 때


5.4 정리
컴포넌트 내부에서 DOM에 접근해야할 때는 ref를 사용합니다.

반응형