본문 바로가기
FrontEnd/React

React Devtools

by oncerun 2020. 7. 19.
반응형

리액트의 렌더링은 hooks 기준으로 setState만 호출 됐을 때 실질적인 state가 변경되지 않았을 경우에도 렌더링 되는 것을 확인할 수 있다. 

 

따라서 그러한 것을 막기위해 shouldComponentUpdate에서 지정해줄 필요가 있다.

   shouldComponentUpdate(nextProps, nextState, nextContext){
        if(this.state.counter !== nextState.counter){
            return true;

        }
        return false;
    }

 

이렇게 하지 않고 간단하게 PureComponent를 사용하는 방법이 있다.

import React, {PureComponent} from 'react'

class Try extends PureCompnent {}

 

hooks기준이라면 memo를 사용한다.

 

import React, {memo} from 'react';


// class Try extends PureComponent {

//     render(){
//         const {tryInfo} = this.props;
        
//         return(
            
//             <li>
//             <div>{tryInfo.try}</div>
//             <div>{tryInfo.result}</div>
//             </li>
            
//         );
//     }

// }

const  Try = memo( ({tryInfo})   => {


    return(
            
        <li>
        <div>{tryInfo.try}</div>
        <div>{tryInfo.result}</div>
        </li>
    );
});



export default Try;

 

class에서 hooks처럼 ref 사용하는 방법

 

import {createRef} from 'react'; 

inputRef = createRef();

input ref={inputRef}

사용 시 this.inputRef.current.focus(); 가능

 

props와 state 연결하기

자식이 props를 변경하게 되면 부모의 props도 변경해야 한다. 자식이 부모를 바뀐다는 것은 문제가 되기 때문에 꼭 바꿔야 하는 경우 자식이 물려받은 props를 state로 만든다.

const  Try = memo( ({ tryInfo }) => {
    // tryInfo.try = 'gell' 안된다 props는 부모가 변경해야한다. 바꿔야할경우 state에 넣어준다. 좋은구조는아니지만 
    const {result, setResult} = useState(tryInfo.result);

    const onClick = () => {

        setResult('1');

    }

    return(
        <>  
        <li>
        <div>{tryInfo.try}</div>
        <div onClick={onclick}>{tryInfo.result}</div>
        </li>
        </>
    );
});

 

props의 자세한 설정이나, 이전 state를 받아 조정을 해 야하거나 , 즉 미세한 컨트롤을 위해 함수를 사용할 수 있다.

 

 

context : a -> b -> c ->d 컴포넌트가 존재할 경우 a에서 c로 보내고 싶을 경우 a ->b ->c로 넘겨야 한다.

즉 context를 응용한 것을 redux이다.

 

false , undefined, null은 jsx에서 태그 없음을 의미합니다.

 

import React, {Component} from 'react';


class ResponseCheck extends Component {

    state = {
        state : 'waiting',
        message : '클릭해서 시작하세요',
    }


    render(){

        return(
            <>
            <div
                id="screen"
                className={this.state.state}
                onClick={this.onClickScreen} 
            >
            {this.state.message}
            </div>
            {this.state.result.length === 0 ? null
             : 
            <div>
                평균시간 : {this.state.result.reduce( (a,c) => a + b ) / this.state.result.length}
            </div>
            }
            </>
        );
    }
}

export default ResponseCheck;

 

함수로 빼줄 수도 있다.

 

import React, {Component} from 'react';


class ResponseCheck extends Component {

    state = {
        state : 'waiting',
        message : '클릭해서 시작하세요',
        result : [],
    }

    renderAverage = () => {
        const {result} =this.state;

        return  result.length === 0 ? null :<div>평균시간 : {this.state.result.reduce( (a,c) => a + b ) / this.state.result.length}</div>
        
    };

    render(){
        
        const {state , message} =this.state;

        return(
            <>
            <div
                id="screen"
                className={state}
                onClick={this.onClickScreen} 
            >
                {message}
            </div>
                 {this.renderAverage()}
            </>
        );
    }
}

export default ResponseCheck;

 

이렇게 함수로 빼는 것도 좋지만 새로운 컴포넌트로 넘겨주어도 됩니다.

 

함수 컴포넌트는 렌더링 될 경우 전체가 실행되기 때문에 반복적인 함수 호출이 일어날 수 있습니다. useMemo나 , useCallback을 사용해야 합니다. 그전에 useeffect를 먼저 배워야 합니다.

 

class -> hooks전환

const ResponseCheck = () => {

    const [state , setState] = useState('waiting');
    const [message , setMessage] = useState('클릭해서 시작하세요');
    const [result , setResult] = useState([]);

    const timeReset =useRef(null);
    const startTime =useRef();
    const endTime =useRef();

 

    const onClickScreen = () => {

        if (state === 'waiting') {
            
            setState('ready');
            setMessage('초록색이 되면 클릭하세요');

          

         timeReset.current =  setTimeout( () => {
            setState('now');
            setMessage('지금클릭하세요');

            }, Math.floor(Math.random() * 1000) +2000);
            startTime.current = new Date();
        }else if (state === 'ready'){

            clearTimeout(timeReset.current);
            setState('now');
            setMessage('너무 성급하시군요 초록색일때클릭해!');
           

        }else if (state ==='now'){
            endTime.current = new Date();

            setState('waiting');
            setMessage('클릭해서 시작하세요!');
            setResult( (prevResult) => {

                return 
                    [...prevResult, endTime.current - startTime.current]
                

            });

        }
    };
    const onReset = () => {

        setResult([]);

    };
 
    const renderAverage = () => {

        return  result.length === 0 ? null :
        <>
        <div>평균시간 : {result.reduce( (a,c) => a + c ) / result.length}ms</div>
        <button onClick={onReset}>리셋</button>
        </>
    };

    return(
        <>
            <div
                id="screen"
                className={state}
                onClick={onClickScreen} 
            >
                {message}
            </div>
                 {renderAverage()}
            </>
    );

};

 

class에서는 ref를 통해 dom에 접근할 때만 사용했지만 hooks에서는  this. 속성을 ref로 표현합니다.

 

useRef는 업데이트 시 렌더링이 되지 않는다.

화면을 바꾸고 싶지 않는데 값이 변하는 것들을  ref에 사용합니다.

 

반응형

'FrontEnd > React' 카테고리의 다른 글

useMemo 와 useCallback  (0) 2020.07.22
리액트 라이프사이클  (0) 2020.07.22
반복문  (0) 2020.07.18
require, import  (0) 2020.07.18
babel preset env , plugins  (0) 2020.07.16

댓글