리스트 데이터 추가하기

조뮁·2022년 10월 19일

React

목록 보기
12/34

리액트는 단방향으로만 데이터 전송이 가능함

즉, 같은 레벨의 형제 요소끼리는 데이터를 주고받을 수 없다.

  • 위 이미지처럼 동일한 레벨의 DiaryEditor 컴포넌트에서 DiaryList로는 일기 아이템 데이터를 주고받을 수 없다.

이러한 경우, state를 DiaryEditor와 DiaryList의 공통부모요소(App)로 끌어올려서 사용해야함.

  • App컴포넌트가 일기 데이터를 배열형식의 state로 가지고 있고, data state의 값을 DiaryList 컴포넌트로 전달
  • App컴포넌트가 setData(setState func) 함수를 DiaryEditor컴포넌트에 prop으로 전달

결국, react에서 데이터는 아래로, 이벤트는 위로 올라가는 구조가 된다.


  1. 일기 데이터를 저장할 state생성
function App() {
  // 일기를 저장할 배열 data
  const [data, setData] = useState([]);
  const dataId = useRef(0);  // 어떠한 DOM도 선택하지 않고 0이라는 값만 가지고 있음
  // 새로운 일기를 추가하는 함수
  const onCreate = (author, content, emotion) => {
    const created_date = new Date().getTime();
    const newItem = {
      author,
      content,
      emotion,
      created_date,
      id: dataId.current, // dataId의 초기값 = 0 , 현재 dataId의 값을 가져옴
    };
    dataId.current += 1; // dataId 사용 후, 현재값을 1씩 추가해주기
    // setData함수로 data 배열 변경시키기
    // 전개구문을 통해 기존 일기배열을 모두 가져온 후, 새로 추가될 아이템을 뒤에 작성하여 state 배열 마짐막에 추가함.
    // 새로 작성한 일기를 가장 위로 올리기 위해, newItem을 앞에 추가하고 그 뒤에 기존 일기 아이템을 전개구문으로 작성
    setData([newItem, ...data]);
  }
  
  return (
    <div className="App">
      {/* DiaryEditor에 일기생성함수를 prop으로 전달 */}
      <DiaryEditor onCreate={onCreate} />
      {/* DiaryList 컴포넌트에 diaryList라는 이름의 prop으로 일기 배열을 전달 */}
      <DiaryList diaryList={data} />
    </div>
  );
}
  1. DiaryEditor 에서 onCreate 함수 받아서 세팅
// 주의! prop을 받을때는 {} 안에서 받아야함
const DiaryEditor = ({ onCreate }) => {
  const authorInput = useRef();
  const contentInput = useRef();

  // handleSubmit 함수 안에서 onCreate() 함수를 실행시켜주면 됨.
  const handleSubmit = () => {
    let athr = state.author;
    let cntnt = state.content;
    let emstn = state.emotion;
    if (athr.length < 1) {
      authorInput.current.focus();
      return;
    }

    alert("일기를 저장하시겠습니까?");
    onCreate(state.author, state.content, state.emotion);
    // 일기 등록 후 input, textarea 초기화
    setState({
      author: "",
      content: "",
      emotion: 1,
    });
  };

useRef() 용도
1. 컴포넌트에 focus를 위치시킬 필요가 있는 경우 사용
2. 속성 값을 초기화(clear)할 필요가 있는 경우.
3. useRef로 컴포넌트 안의 변수 관리하기

  • useRefs로 컴포넌트 안에서 조회 및 수정 가능한 변수를 관리 가능
  • useRef로 변수를 관리하게 되면, 그 변수가 업데이트 된다고 해서 컴포넌트가 리렌더링 되지 않는다.
    즉, 굳이 리렌더링 할 필요가 없는 변수라면 useRef로 관리해주는 것이 효율적이다.
// App.js
import React, { useRef } from 'react';
import UserList from './UserList';
function App() {
  const users = [
    {
      id: 1,
      username: 'subin',
      email: 'subin@example.com'
    },
    {
      id: 2,
      username: 'user1',
      email: 'user1@example.com'
    },
    {
      id: 3,
      username: 'user2',
      email: 'user2@example.com'
    }
  ];
  const nextId = useRef(4);
  const onCreate = () => {
    // 배열에 새로운 항복 추가하는 로직 생략
    nextId.current += 1;
  };
  return <UserList users={users} />;
}
export default App;

(1) import React, { useRef } from 'react';
: useRef 함수를 불러온다.
(2) const nextId = useRef(4);
: 배열의 고유값 변수로 nextId를 설정해주고, useRef() 파라타미터로 다음 id가 될 숫자 4를 넣어준다.
파라미터 값을 넣어주면 해당 값이 변수의 current 값이 된다.
그리고 nextId 변수를 수정하거나 조회려면 .current 값을 수정하거나 조회한다.
(3) nextId.current += 1;
: 변수에 1씩 더하여 업데이트를 한다.

  • 참고 : 공식문서에 쓰인 Ref를 사용해야 하는 경우
    - 포커스, 텍스트 선택영역, 혹은 미디어의 재생을 관리할 때.
    - 애니메이션을 직접적으로 실행시킬 때.
    - 서드 파티 DOM 라이브러리를 React와 같이 사용할 때.

0개의 댓글