외거노비
외거노비 일지
외거노비

공지사항

블로그 메뉴

  • 홈
  • 태그
  • 방명록
  • 분류 전체보기 (35)
    • 스파르타 프로젝트 (1)
      • 소개페이지(feat. 팀 외거노비) (1)
      • 프로젝트(미정)(feat. 팀 외래교란종) (0)
    • 스파르타 개발일지 (34)
hELLO · Designed By 정상우.
외거노비

외거노비 일지

스파르타 개발일지

개발일지 20221212 리액트 숙련 강의 1

2022. 12. 12. 21:15

CSS-in-JS

 

styled-components 설치

: 리액트에서 CSS-in-JS 방식으로 component를 꾸밀 수 있게 도와주는 패키지

# git bash에서 yarn 명령어로 설치
yarn add styled-components

 

styled-components plugin 설치

: VScode에서 style 코드를 편하게 작성하기 위해 제공해 주는 플러그인

vscode의 Extensions -> vscode-styled-component 검색 후 라이브러리 install

 

 

styled-component 사용 예시)

// src/App.js

import React from "react";
import styled from "styled-components";

// 1. styled-components
const StBox = styled.div`
  width: 100px;
  height: 100px;
  border: 1px solid ${(props) => props.borderColor};
  			// 4.부모 컴포넌트에서 보낸 props를 받아 사용
  margin: 20px;
`;

const App = () => {
  return (
    <div>
         {/* 2. 위에서 만든 styled-components를 사용 */}
         {/* 3. props를 통해 borderColor라는 값을 전달 */}
      <StBox borderColor="red">빨간 박스</StBox>
      <StBox borderColor="green">초록 박스</StBox>
      <StBox borderColor="blue">파랑 박스</StBox>
    </div>
  );
};

export default App;

styled-component 장점

: style을 작성할 때 if문, switch문, 삼항연산자 등을 구현하기 위해 쓰여 className에 비해 조건부 스타일링을 하기 쉬움

ex) 같은 StBox여도 borderColor를 다르게 설정할 수 있음 (props를 통해 전달해 줌으로써 조건부스타일링 구현)

 

 

map을 이용해 리팩토링!

// src/App.js

import React from "react";
import styled from "styled-components";

// styled-components
const StBox = styled.div`
  width: 100px;
  height: 100px;
  border: 1px solid ${(props) => props.borderColor};
  			// 부모 컴포넌트에서 보낸 props를 받아 사용
  margin: 20px;
`;

const boxList = ["red", "green", "blue"];

// 색을 넣으면 이름을 반환해주는 함수 만들기
const getBoxName = (color) => {
  switch (color) {
    case "red":
      return "빨간 박스";
    case "green":
      return "초록 박스";
    case "blue":
      return "파란 박스";
    default:
      return "검정 박스";
  }
};
const App = () => {
  return (
    <div>
      {boxList.map((box) => (
        <StBox borderColor={box}>{getBoxNam(box)}</StBox>
      ))}
      {/* 각각의 컬러(box)에 대해 */}
      {/* borderColor는 color값 {box}을 주고, 그 컬러에 따른 {boxName(box)}을 호출하는 함수 */}
    </div>
  );
};

export default App;

 

 

React Hook

useState: 가장 기본적인 hook이면서 함수 컴포넌트에서 가변적인 상태를 가지게 해 준다. 즉, 상태관리를 할 수 있게 해 줌. 중요하고 자주 쓰이는 hook

//useState의 기본적인 형태
const [state, setState] = useState(initialState);

useState 함수가 배열을 반환하고, 이것을 구조 분해 문법으로 꺼내놓은 모습!

state를 변수로 사용하고 setState를 이용해서 state 값을 수정할 수 있음

만약 state가 원시 데이터타입이 아닌 객체 데이터 타입인 경우에는 불변성을 유지해줘야 한다

 

 

함수형 업데이트

// 기존에 사용하던 방식
setState(number + 1);

// 함수형 업데이트 
setState(() => {});

setState의 ( ) 안에 수정할 값이 아니라 함수를 넣을 수 있음

그리고 그 함수의 인자에서는 현재의 state을 가져올 수 있고, { } 안에서는 이 값을 변경하는 코드를 작성할 수 있음

// 현재 number의 값을 가져와서 그 값에 +1을 더하여 반환
setState((currentNumber)=>{ return currentNumber + 1 });

 

일반 업데이트 방식 & 함수형 업데이트 방식 차이

 

일반 업데이트 방식: onClick안에서 setNumber(number + 1) 를 3번 호출했는데 number가 1씩 증가

이유: 버튼을 클릭했을 때 첫번째 줄 ~ 세번째 줄의 있는 setNumber가 각각 실행되는 것이 아니라, 배치(batch)로 처리한다. 즉 onClick을 했을 때 setNumber 라는 명령을 세번 내리지만, 리액트는 그 명령을 하나로 모아 최종적으로 한번만 실행

// 일반 업데이트 방식

// src/App.js

import { useState } from "react";

const App = () => {
  const [number, setNumber] = useState(0);
  return (
    <div>
			{/* 버튼을 누르면 1씩 플러스된다. */}
      <div>{number}</div> 
      <button
        onClick={() => {
          setNumber(number + 1); // 첫번째 줄 
          setNumber(number + 1); // 두번쨰 줄
          setNumber(number + 1); // 세번째 줄
        }}
      >
        버튼
      </button>
    </div>
  );
}

export default App;

함수형 업데이트 방식: number가 3씩 증가

이유: 3번을 동시에 명령을 내리면 그 명령을 모아 순차적으로 각각 1번씩 실행

// 함수형 업데이트 방식

// src/App.js

import { useState } from "react";

const App = () => {
  const [number, setNumber] = useState(0);
  return (
    <div>
			{/* 버튼을 누르면 3씩 플러스 된다. */}
      <div>{number}</div>
      <button
        onClick={() => {
          setNumber((previousState) => previousState + 1);
          setNumber((previousState) => previousState + 1);
          setNumber((previousState) => previousState + 1);
        }}
      >
        버튼
      </button>
    </div>
  );
}

export default App;

 

 

useEffect

: react component가 렌더링이 될 때마다 특정 작업을 수행할 수 있게 하는 hook

(component가 화면에 보이거나 사라졌을 때 무언가를 실행하려면 useEffect 사용)

import React, { useEffect } from "react";

import를 해야 사용할 수 있음!

import React, { useEffect } from "react";

const App = () => {
	useEffect(() => {
    // 이 부분이 실행
    console.log("hello useEffect");
    });
    
    return <div>Home</div>;
};

App component가 화면에 렌더링 될 때 실행

// 크롬 콘솔창에 출력
hello useEffect
hello useEffect

hello useEffect 가 두 번 출력되는 이유

: useEffect가 2번 실행된 것이 아니라 strictmode가 적용되어 있기 때문!

 

 

리렌더링(re-rendering)과 리렌더링 문제 해결

리렌더링 예시↓

import React, { useEffect, useState } from "react";

const App = () => {
  const [value, setValue] = useState("");

  useEffect(() => {
    console.log("hello useEffect");
  });

  return (
    <div>
      <input
        type="text"
        value={value}
        onChange={(event) => {
          setValue(event.target.value);
        }}
      />
    </div>
  );
}

export default App;

 

state가 변경되면 리렌더링이 일어남 -> input값을 입력하면 App component가 리렌더링되는데, 리렌더링이 되었기 때문에 useEffect가 또 다시 한 번 진행됨

그래서 브라우저에서 input에 어떤 값을 입력할 때마다 useEffect가 계속 실행되는 것!!!

동영상 서비스가 종료되어 해당 콘텐츠를 재생할 수 없습니다.

 

리렌더링 문제 해결법

: 의존성배열(useEffect를 제어-함수의 실행조건을 제어-할 수 있는 방법)

이 배열에 값을 넣고, 그 값이 바뀔 때만 useEffect를 실행

// useEffect의 두번째 인자가 의존성 배열이 들어가는 곳
useEffect(()=>{
	// 실행하고 싶은 함수
}, [의존성배열])

 

비어있는 의존성배열

: 처음 한 번만 실행이 되고, 그 이후로는 어떤 일도 일어나서는 안 됨

어떤 값이 변할 때마다 바뀌는데(useEffect 실행) 주어진 값이 없기 때문

import React, { useEffect, useState } from "react";

const App = () => {
  const [value, setValue] = useState("");

  useEffect(() => {
    console.log("hello useEffect");
  }, []); // 비어있는 의존성배열
  // '이 배열 안에 값을 넣으면, 그 값이 바뀔 때만 useEffect를 실행하라'는 의미

  return (
    <div>
      <input
        type="text"
        value={value}
        onChange={(event) => {
          setValue(event.target.value);
        }}
      />
    </div>
  );
};

export default App;

input에 어떤 값을 입력하더라도 처음에 실행된 hello useEffect 외에는 더 이상 실행이 되지 않음

동영상 서비스가 종료되어 해당 콘텐츠를 재생할 수 없습니다.

∴ 어떤 함수를 컴포넌트가 렌더링 될 때 단 한번만 실행하고 싶으면 의존성 배열을 [ ] 빈 상태로 넣으면 된다

 

 

의존성배열에 값이 있는 경우

: 최초 렌더링 뿐만 아니라 해당 값이 변할 때마다 useEffect 안에 있는 코드(console.log("hello useEffect");)도 계속 실행이 됨

// src/App.js

import React, { useEffect, useState } from "react";

const App = () => {
  const [value, setValue] = useState("");
  useEffect(() => {
    console.log("hello useEffect");
  }, [value]); // value를 넣음

  return (
    <div>
      <input
        type="text"
        value={value}
        onChange={(event) => {
          setValue(event.target.value);
        }}
      />
    </div>
  );
}

export default App;

동영상 서비스가 종료되어 해당 콘텐츠를 재생할 수 없습니다.

클린업 cleanUp

: component가 사라졌을 때 무언가를 실행하는 과정

// src/App.js

import React, { useEffect } from "react";

const App = () => {
	useEffect(()=>{
		// 화면에 컴포넌트가 나타났을 때(mount) 실행하고자 하는 함수 넣기

		return ()=>{
		// 화면에서 컴포넌트가 사라졌을 때(unmount) 실행하고자 하는 함수 넣기
		// clean up
		}
	}, [])

	return <div>hello react!</div>
};

export default App;

도비 버튼을 누르면 useNavigate에 의해서 /todos로 이동하면서 HouseElf 컴포넌트를 벗어나게 될 것!

-> 화면에서 HouseElf 컴포넌트가 사라지고, useEffect의 return 부분이 실행됨

import React, { useEffect } from "react";
import { useNavigate } from "react-router-dom";

const HouseElf = () => {
  const nav = useNavigate();

  useEffect(() => {
    return () => {
      console.log(
        "도비는 자유예요"
      );
    };
  }, []);

  return (
    <button
      onClick={() => {
        nav("/todos");
      }}
    >
      도비 버튼
    </button>
  );
};

export default HouseElf;

 

 

 

정리)

  • useEffect는 화면에 컴포넌트가 mount 또는 unmount 됐을 때 실행하고자 하는 함수를 제어하게 해주는 훅이다
  • 의존성 배열을 통해 함수의 실행 조건을 제어할 수 있다
  • useEffect 에서 함수를 1번만 실행시키고자 할때는 의존성 배열을 빈 배열로 둔다

 

 

HW

stricmode

react Lifecycle

mount

unmount

추가로 알아보기!!!

'스파르타 개발일지' 카테고리의 다른 글

20221229 리액트 네이티브 시작!  (0) 2022.12.29
개발일지 20221213 리액트 숙련 강의 2  (0) 2022.12.13
개발일지 20221210~11 todo-list 만들기  (0) 2022.12.11
개발일지 20221208 리액트 입문 3 실습  (0) 2022.12.08
개발일지 20221207 리액트 입문 2  (0) 2022.12.07
    '스파르타 개발일지' 카테고리의 다른 글
    • 20221229 리액트 네이티브 시작!
    • 개발일지 20221213 리액트 숙련 강의 2
    • 개발일지 20221210~11 todo-list 만들기
    • 개발일지 20221208 리액트 입문 3 실습

    티스토리툴바