TIL

state, props, event

rachel_13 2022. 7. 18. 22:26

Props

컴포넌트에 내장되어 있는 객체이다. 그 중에서 부모 컴포넌트에서 자식 컴포넌트로 정보를 전달해주는 객체이다.

  1. 넘겨주고 싶은 정보는 부모 영역에 존재한다.
    자식 요소에게 넘겨주고 싶을 때 : 작명 = {변수명}

📌부모 컴포넌트

import React, {Component} from "react";
import Child form "./Child/Child";

class Parent extends Component {
render(){
  const name ="Kim";
  test = () => {
      console.log('테스트입니다')
  }
    return (
    <>
      <div>Parent</div>
      <Child  name={name} testHandler={this.test}/>
    </>
    );
  }
}

export default Parent;

📌자식 컴포넌트

import React, {Component} from "react";

class Child extends Component {
render(){
  console.log(this.props.name);  ///객체 형태로 콘솔에 찍히는 것을 확인할 수 있다.
  console.log(this.props.testHandler); //함수도 props로 넘겨줄 수 있다.

    return (
    <>
      <div>Child</div>
        <div>this.props.name</div>
    </>
    );
  }
}

export default Parent;
  1. 넘겨주는 행위가 아니라, 넘겨주는 자료가 있어야 할 공간을 'props'라고 한다.
    변수, 배열, 객체, 함수 모두 props로 넘겨줄 수 있다.

State

UI를 그리는데 필요한 정보를 담고 있는 객체
props는 부모에서 전달했다면, state는 컴포넌트 자체에서 가지고 있는 상태이다.
리액트에서는 State가 변함에 따라 UI가 바뀐다. 따라서 변하지 않는 값은 state에 들어가면 안된다!

state는 고정적으로 만드는 틀이 있다. 이를 항상 작성해서 만들어줘야 한다.
constructor는 LifeCycle의 한 종류이다.

import React, {Component} from "react";
import Child form "./Child/Child";

class Parent extends Component {
      constructor(){
        super();

          this.state={
            color: 'red',
              arr : [1, 2, 3],
        };
    }
      changeColor = () => {
        //this.state.color='blue' //이렇게 그냥 바꾸면 제대로 적용되지 않는다.
      this.setState({
              color: 'blue', //💡 이렇게 변경함수를 사용해줘야 바뀐다!
      })
    };

      render(){
        const name = 'Kim';
          console.log(this.state) // { color : 'red'} 객체의 형태로 존재함을 확인할 수 있다. 
          return (
            <>
              <div style={{color: this.state.color}}>Parent</div>
              <button onClick={this.changeColor}>색상 변경하기</button>
              < Child name = {name} testHandler={this.test} />
              </>      
        )
    }
}

export default Parent;

💡 state도 객체니까 dot notation으로 바로 바꿀 수 있지 않나?

❌ 직접 바꾸면 UI가 업데이트가 되질 않는다. render()함수가 재랜더링 되어야 태그들이 다시 그려지면서 변경사항이 반영되는 원리를 가지고 있는데, state값만 바꿔놓으면 랜더링이 되지 않아서 업데이트 되지 않는다.
따라서 전용 함수인 setState함수를 사용해서 바꿔줘야 한다.

즉, setState()함수를 호출하게 되면 state값 변경 + render()함수 재실행(재랜더링) 이 된다.

💡 버튼을 누를때마다 색상이 바뀌게 하고 싶으면?

toggle 효과라고도 불리우는데, state값을 Boolean값으로 사용해서 true이면 어떤 색상, false이면 어떤 색상. 이렇게 조건을 걸어두면(삼항조건 연산자) toggle 버튼이 된다.

<div style={{color: this.state.color ? 'red' : 'blue'}}>Parent</div>
  • 위 상단에서 this.state의 color를 true로 변경
  • render()함수 내에 색상이 바뀌어야 할 태그에 조건 삽입 (T - red, F - blue)

Props + State

Parent에서 정해진 값이 아닌, 변하는 값 즉 State도 보내줄 수 있을 것이다.

📌부모 컴포넌트

class Parent extends Component {
      constructor(){
        super();

          this.state={
          //color: true
            color: 'red'
        };
    }
      changeColor = () => {
        //this.state.color='blue' //이렇게 그냥 바꾸면 제대로 적용되지 않는다.
      this.setState({
              color: !this.state.color, //💡 이렇게 변경함수를 사용해줘야 바뀐다!
      })
    };

      render(){
        const name = 'Kim';
          return (
            <>
              <div style={{color: this.state.color ? 'red' : 'blue'}}>Parent</div>
              <button onClick={this.changeColor}>색상 변경하기</button>
              < Child name = {name} color={this.state.color} />
              </>      
        )
    }
}

📌자식 컴포넌트

import React, {Component} from "react";

class Child extends Component {
render(){
  console.log(this.props);  ///{name: 'Kim', color: 'red'}  

    return (
    <>
      <div style={{this.props.color}}>Child</div>
        <div>this.props.name</div>
    </>
    );
  }
}

export default Parent;

👉 하나 이상의 값도 넘겨줄 수 있다. + 변하는 값인 state도 보내줄 수 있음을 확인할 수 있다.

다시 props로 color를 넘겨놓는다고 생각해보자.

      changeColor = () => {
      this.setState({
              color: 'blue', 
      })
    };

      render(){
        const name = 'Kim';
          return (
            <>
              <div style={{color: this.state.color'}}>Parent</div>
              <button onClick={this.changeColor}>색상 변경하기</button>
              < Child name = {name} color={this.state.color} />
              </>      
        )
    }
}

💡 this.state.color의 값을 color라는 이름으로 사용하라고 보내주고 있다.

여기서 this.props로 접근해서 color의 값을 가져다가 사용하고 있는데, 만약 버튼을 눌러서 Parent가 'blue'로 바뀔 때, Child도 동시에 색깔이 바뀔까?

👉 Yes, state의 주체는 부모이지만, props는 부모의 속성을 상속받는다. 따라서 동시에 바뀌는게 맞다!
버튼을 눌렀을 때, setState()함수가 실행되면서 글자 색상이 바뀐다. 이 때 point는 render()함수가 재실행된다.(재랜더링) 재실행될 경우, div/button뿐아니라 Child 컴포넌트도 다시 한번 실행된다. 이 과정에서 this.state.color가 이미 'blue'로 바뀐 상태이므로 이 바뀐 상태를 반영해서 재실행되는 원리이다.
리액트는 항상 setState()함수가 먼저 실행이 된 다음에! 순차적으로 render()함수가 실행된다는 점을 참고하자.

✔ 참고로 data가 많을 경우 {this.state} 이런식으로 통째로 넘겨줄 수 도 있다. (but, 자식 컴포넌트에서 하나라도 사용하지 않을 경우 비효율적일 수 있다)

💡 setState()함수를 자식 컴포넌트에서 사용하고자 할 때?

앞서 props는 함수형도 전달이 가능하다고 했다.
따라서 {this.함수명}으로 부모 컴포넌트에서 선언 후, 자식 컴포넌트에서 {this.props.함수명}으로 불러와서 사용이 가능하다.

데이터의 단방향성

항상 부모에서 → 자식으로 데이터를 넘겨준다.
state를 만드는 위치에 따라 사용하는 범위가 다르다는 점에 유의한다.

'TIL' 카테고리의 다른 글

[git] Please move or remove them before you can merge  (0) 2022.07.20
React 용어 정리  (0) 2022.07.18
HTTP  (0) 2022.07.18
돔(DOM) - 2탄  (0) 2022.07.18
돔(DOM) 1탄  (0) 2022.07.18