사고쳤어요
[React / ts] Task App 만들기 - ② list, task 만들기 본문
board에 이어서 각 board마다 존재하는 list와 task를 만들어보자.
현재 만드려고 하는 Task-App의 구조는 board - list - task 이다.
board 내에는 여러 개의 list가 있고, list 내에는 여러 개의 task가 있으며
각 board, list, task는 자유롭게 제거하거나 추가할 수 있다.
List
// ListContainer.tsx
import React from "react";
import { IList } from "../../types";
import List from "../List/List";
import { listContainer } from "./ListsContainer.css";
import ActionButton from "../ActionButton/ActionButton";
type TListsContainerProps = {
lists: IList[];
boardId: string;
};
const ListsContainer: React.FC<TListsContainerProps> = ({ lists, boardId }) => {
return (
<div className={listContainer}>
{lists.map((list) => (
<List key={list.listId} list={list} boardId={boardId} />
))}
<ActionButton boardId={boardId} listId={""} list />
</div>
);
};
export default ListsContainer;
// List.tsx
import React from "react";
import { GrSubtract } from "react-icons/gr";
import { IList, ITask } from "../../types";
import { useTypedDispatch } from "../../hooks/redux";
import { deleteList, setModalActive } from "../../store/slices/boardsSlice";
import { addLog } from "../../store/slices/loggerSlice";
import { v4 } from "uuid";
import { setModalData } from "../../store/slices/modalSlice";
import Task from "../Task/Task";
import { deleteButton, header, listWrapper, name } from "./List.css";
import ActionButton from "../ActionButton/ActionButton";
type TListProps = {
list: IList;
boardId: string;
};
const List: React.FC<TListProps> = ({ list, boardId }) => {
const dispatch = useTypedDispatch();
const handleListDelete = (listId: string) => {
dispatch(deleteList({ boardId, listId }));
dispatch(
addLog({
logId: v4(),
logMessage: "리스트 삭제하기",
logAuthor: "User",
logTimestamp: Date.now().toString(),
})
);
};
const handleTaskChange = (
boardId: string,
listId: string,
taskId: string,
task: ITask
) => {
dispatch(setModalData({ boardId, listId, task }));
dispatch(setModalActive(true));
};
return (
<div className={listWrapper}>
<div className={header}>
<div className={name}>{list.listName}</div>
<GrSubtract
className={deleteButton}
onClick={() => handleListDelete(list.listId)}
/>
</div>
{list.tasks.map((task, index) => (
<div
key={task.taskId}
onClick={() =>
handleTaskChange(boardId, list.listId, task.taskId, task)
}
>
<Task
taskName={task.taskName}
taskDescription={task.taskDescription}
boardId={boardId}
id={task.taskId}
index={index}
/>
</div>
))}
<ActionButton boardId={boardId} listId={list.listId} />
</div>
);
};
export default List;
// boardsSlice.ts
const boardsSlice = createSlice({
name: "boards",
initialState,
reducers: {
addBoard: (state, { payload }: PayloadAction<TAddBoardAction>) => {
state.boardArray.push(payload.board);
},
deleteList: (state, { payload }: PayloadAction<TDeleteListAction>) => {
state.boardArray = state.boardArray.map((board) =>
board.boardId === payload.boardId
? {
...board,
lists: board.lists.filter(
(list) => list.listId !== payload.listId
),
}
: board
);
},
setModalActive: (state, { payload }: PayloadAction<boolean>) => {
state.modalActive = payload;
},
},
});
// modalSlice.ts
const modalSlice = createSlice({
name: "modal",
initialState: initialState,
reducers: {
setModalData: (state, { payload }: PayloadAction<TSetModalDataAction>) => {
state.boardId = payload.boardId;
state.listId = payload.listId;
state.task = payload.task;
},
},
});
리스트에서는 리스트 추가하기, 리스트 제거하기 기능을 수행할 수 있어야 하며
리스트에 존재하는 task들을 모두 보여주어야 한다.
dispatch(deleteList())를 통해 리스트 삭제하기를 구현하였고, (리스트 추가하기는 나중에 ActionButton에 구현할 예정이다)
list.tasks.map()을 통해 task들을 모두 보여주며 task를 선택했을 때 처리를 위해
task에 onclick={() => handleTaskChange()}를 설정해주었다.
Task
// Task.tsx
import React from "react";
import { container, description, title } from "./Task.css";
type TTaskProps = {
index: number;
id: string;
boardId: string;
taskName: string;
taskDescription: string;
};
const Task: React.FC<TTaskProps> = ({
index,
id,
boardId,
taskName,
taskDescription,
}) => {
return (
<div className={container}>
<div>
<div className={title}>{taskName}</div>
<div className={description}>{taskDescription}</div>
</div>
</div>
);
};
export default Task;
Task는 간단히 이름, 설명을 보여주는 것으로 구현하였다.
'웹 풀스택' 카테고리의 다른 글
[React / ts] Task App 만들기 - ④ Modal 만들기 (0) | 2025.04.17 |
---|---|
[React / ts] Task App 만들기 - ③ ActionButton 만들기 (0) | 2025.04.15 |
[React / ts] Task App 만들기 - ① board 만들기 (0) | 2025.04.15 |
[React] Redux 사용하기 (1) | 2025.04.14 |
[React / ts] props 사용해보기 (0) | 2025.04.10 |