2021.03.15 - [React] - [React] typescript 시작하기 - 떽떽대는 개발공부
이전 글에서 typescript 로 react 프로젝트를 만들어 보았다.
이번 글에선 typescript 를 이용하여 예제를 한번 만들어 보았다.
아래의 블로그에서 예제를 참조하였다.
먼저 App.tsx 컴포넌트를 아래와 같이 구성할 것이다.
src/components/App.tsx
import * as React from 'react';
import { Profile } from '@components/study/Profile';
import { Counter } from '@components/study/Counter';
import { TodoList } from '@components/study/TodoList';
const App = () => {
return (
<div className='App'>
<Profile name='name' job='job' />
<Counter />
<TodoList />
</div>
);
};
export default App;
총 3개의 컴포넌트로 각각 다른 작업을 구성할 것이다. 이 중 Profile 컴포넌트는 props 로 값을 전달한다.
먼저, Profile 컴포넌트는 아래와 같이 작성한다.
src/components/study/Profile.tsx
import * as React from 'react';
// props 받아올 값의 type 을 선언
interface Iprops {
name: string,
job: string,
}
// props type 설정
export function Profile(props: Iprops){
return(
<div>
<h2>프로필</h2>
<div>
<b>이름 : { props.name }</b>
</div>
<div>
<b>직업 : { props.job }</b>
</div>
</div>
)
}
위와 같이 간단하게 작성하면 아래와 같은 결과가 나온다.
부모 컴포넌트에서 props 값을 주고, 자식 컴포넌트에서는 prop 받을 값의 type 을 설정한 게 전부다.
다음은 Counter 를 구현 해보자.
src/components/study/Counter.tsx
import * as React from 'react';
import { useState } from 'react';
// state type 선언
interface Istate {
counter: number
}
export function Counter() {
// useState로 관리해 줄 state 의 type 설정
const [state, setState] = useState<Istate>({
counter: 0
})
const onIncrement = () => {
setState({
counter: state.counter+1
})
}
const onDecrement = () => {
setState({
counter: state.counter-1
})
}
return(
<div>
<h2>카운터</h2>
<div>
{state.counter}
</div>
<div>
<button onClick={onIncrement}>+</button>
<button onClick={onDecrement}>-</button>
</div>
</div>
)
}
이 부분도 아주 간단하게 구성 하였다.
내가 작성한 컴포넌트는 함수형 컴포넌트 이므로 useState 를 사용하였다.
이제 내가 좀 애를 먹었던 TodoList 부분이다.
src/components/study/TodoList.tsx
import * as React from 'react';
import { useState, useEffect } from 'react';
import { TodoItem } from './TodoItem';
// 타입을 인터페이스로 선언
interface todoItem{
item:string
}
interface ItodoItems {
idx: number,
item: string,
isDelete: boolean
onDelete?: Function,
}
interface ItodoList {
todoItems: ItodoItems[],
}
export function TodoList() {
const [todoItem, setTodoItem] = useState<todoItem>({
item:''
})
const [todoList, setTodoList] = useState<ItodoItems>({
idx: 0,
item: '',
isDelete: false,
})
const [todoData, setTodoData] = useState<ItodoList>({
todoItems: [todoList],
})
const onSubmit = (e:React.FormEvent<HTMLFormElement>):void => {
e.preventDefault() // 페이지 전환 막기
setTodoList({
idx: todoList.idx+1,
item: todoItem.item,
isDelete: false,
})
}
useEffect(() => {
setTodoItem({// input 창 초기화
item: ''
})
setTodoData({
todoItems: todoData.todoItems.concat(todoList),
})
}, [todoList])
useEffect(() => {
//console.log('todoData 변경 :: ', todoData )
}, [todoData])
const handleInput = (e:React.ChangeEvent<HTMLInputElement>) => {
const {name, value} = e.target
setTodoItem({
item: value
})
}
const onDelete = (idx: number) => {
let temp2:Array<ItodoItems> = []
const deleteTodoList = todoData.todoItems.map(
data => {
let temp1: ItodoItems = {
idx: data.idx,
item: data.item,
isDelete: data.idx === idx ? true : false
}
if(temp2.length < 1){
temp2 = [temp1]
} else {
temp2 = temp2.concat(temp1)
}
setTodoData({
todoItems: temp3
})
}
)
}
const TodoList = todoData.todoItems.map(
(data, idx) => (
<React.Fragment key={idx}>
<TodoItem
idx={data.idx}
item={data.item}
isDelete={data.isDelete}
onDelete={onDelete}
/>
</React.Fragment>
)
)
return(
<div>
<h2>할일</h2>
<div>
<form onSubmit={onSubmit}>
<input type='text' name='content' value={todoItem.item} onChange={handleInput} />
<button type='submit'>추가</button>
</form>
</div>
<div>
{TodoList}
</div>
</div>
)
}
delete 부분에서 배열 때문에 애를 먹었다.
새 배열을 만들어 사용하는 것으로 정리하였다.
src/components/study/TodoItem.tsx
import * as React from 'react';
interface IList {
idx: number,
item: string,
isDelete: boolean,
onDelete: Function,
}
export function TodoItem(props: IList){
const handleDelete = () => {
props.onDelete(props.idx)
}
return(
<div>
{props.idx !== 0 && !props.isDelete && (
<div>
{props.item}
<span onClick={handleDelete}>
삭제
</span>
</div>
)}
</div>
)
}
'React' 카테고리의 다른 글
[React] react 에서 다국어 처리 적용하기(4) - 떽떽대는 개발공부 (0) | 2021.03.31 |
---|---|
[React] html 파일에서 css 파일 연결하기 - 떽떽대는 개발공부 (0) | 2021.03.24 |
[React] typescript 시작하기 - 떽떽대는 개발공부 (0) | 2021.03.15 |
[React] redux-saga 이용하기 - 떽떽대는 개발공부 (0) | 2021.03.12 |
[React] cross-env 를 이용하여 환경변수 관리하기(2) - 떽떽대는 개발공부 (0) | 2021.03.11 |
댓글