22.03.17 React-typescript

hongwr·2022년 3월 17일
0

TIL

목록 보기
30/42

React-typescript

초기 설치

npx create-react-app 폴더명 --template typescript

props

함수형 컴포넌트에서 부모한테 props를 받을 때는 React.FC를 넣는다.

여기에서 FC는 functional component를 의미하는 것으로 함수형 컴포넌트에서는 이것을 넣어주어야 한다.

이때 컴포넌트에서는 React.FC를 쓰는 순간 children prop을 이미 IDE가 인식을 하는데, 그렇게 때문에 부모에서 오는 prop과 children prop이 합쳐져야하기 때문에 React.FC 다음에는 무조건 유형을 확실하게 적어줘서 유형 추론을 못하게 하여야 한다.

//부모. 부모에서 컴포넌트로 넘겨주는 것을 컴포넌트에서 쓴 것과 다르면 부모에서 오류가 생긴다.
import Todos from "./component/Todos";

function App() {
  return (
    <div>
      <Todos items={["Learn React", "Learn TypeScript"]} />
    </div>
  );
}

export default App;
//컴포넌트
import React from "react";

//items인 문자열 배열이 올 것이다. items뒤에 ?를 넣으면 선택적 prop이 되지면 return에서 선택하지 않을 때는 어떻게 해야하는지를 처리해야 한다. 
//! 즉 삼항연산자를 사용하여 items가 안 올 때는 어떻게 해야하는지를 처리해야 한다. 
//그렇게 안 하고 이런 식으로 작성하면 부모에서 무조건 items를 string type으로 내려줘야 한다.
const Todos: React.FC<{ items: string[] }> = (props) => {
//FC -> functional component. 함수형 컴포넌트를 의미한다는 뜻. 
  //React.FC에는 이미 이 함수는 부모한테 프롭스를 받는 함수라는 것을 가지고 있다. 
  //그래서 children prop을 항상 가지고 있다. 
  //! 부모에서 오는 props와 children prop이 합쳐져야하기 때문에 React.FC 다음에는 유형을 확실하게 적어줘야 한다. 
  //유형 추론을 사용하지 못하게 해야한다.
   return (
    <ul>
      {props.items.map((item) => (
        <li key={item}>{item}</li>
      ))}
    </ul>
  );
};

export default Todos;

component에서 component로 내려주고 올려줄 때

return (
    <ul>
      {props.items.map((item) => (
        <TodoItem key={item.id} gosu={item.text} />
      ))}
    </ul>
  );
  
  ------// TodoItem------
  
  import React from "react";

const TodoItem: React.FC<{ gosu: string }> = (props) => {//프롭스로 받을 때 함수에서 받는 타입을 정해줄 때, 
//앞에 프롭스에서 내려주는 것과 이름은 똑같이 하여야 한다. 부모에서 gosu로 내려주면 gosu로 받기.
  console.log(props);
  return <li>{props.gosu}</li>;
};

export default TodoItem;

useRef와 사용할 때

import React from "react";
import { useRef } from "react";

const NewTodo = () => {
  const todoTextInputRef = useRef<HTMLInputElement>(null); 
  //input은 inputElement, button은 HTMLButtonElement, paragraph는 HTMLParagraphElement. 
  input,button,paragraph는 각각의 type에 기반한 것이기 때문에 이런 식으로 적어야 한다.

 const submitHandler = (e: React.FormEvent) => {
    //리액트 패키지가 제공하는 특별한 타입. 
    //MoustEvent 등도 사용 가능. 
    //즉, Event에 event type을 넣을 수 있다. 
    //보통 return 부분에 마우스를 올리면 나온다. 
    //여기서는 onSubmit 이벤트는 React.FormEvent이기 때문에 사용
    e.preventDefault();

    const enteredText = todoTextInputRef.current?.value; //?는 아직 사용을 안했기 때문에 타입스크립트에서 무엇이 들어올 지 몰라서 ?를 자동으로 넣어준다. 
    //100% current가 null이 아닐 거라고 확신이 든다면 ?를 !로 바꿀 수 있다.

    if (enteredText?.trim().length === 0) {
      //Throw an error
      return;
    }
  };

  return (
    <form onSubmit={submitHandler}>
      <label htmlFor="text">TodoText</label>
      <input type="text" id="text" ref={todoTextInputRef} />
      <button onClick={submitHandler}>Add Todo</button>
    </form>
  );
};

export default NewTodo;

함수를 주고 받을 때

//App

function App() {
  const todos = [new Todo("Learn React"), new Todo("Learn TypeScript")]; //Todo라는 객체를 만듬.

  const addtodoHandler = (todoText: string) => {
    //NewTodo에서 받고있는 함수의 매개변수가 이런 모양이기 때문에 여기서도 이런 식으로 똑같이 써줘야 함. 
    //매개변수명은 아무렇게나 상관없음. 또한 뒤에서 void로 정의했기 때문에 return을 쓰지 않음.
  };

  return (
    <div>
      <NewTodo onAddTodo={addtodoHandler} />
      <Todos items={todos} />
    </div>
  );
  
 //component
 
 const NewTodo: React.FC<{ onAddTodo: (text: string) => void }> = (props) => {
  //onAddTodo를 프롭스로 받을 것이기 때문에 함수형 컴포넌트라는 React.FC에 onAddTodo를 받을 것이라고 명시. 
  //또한 이것은 함수라는 것을 의미하기위해 화살표함수를 사용하였는데, 리턴을 해버리면 밑에서 변수도 못 넣고 
  //상수도 못 넣을 것이기 때문에 return값을 넣지 않고 그냥 void로 처리. 
  //! 원래는 매개변수를 비워뒀지만, 아래에서 onAddTodo에 매개변수를 넣었기 때문에 위에도 넣어야 한다. 
  //변수명은 아무렇게나 넣어도 되지만 이 또한 type을 정의해주어야 한다.
profile
코딩 일기장

0개의 댓글