728x90
// CreateToDo.tsx
import { useForm } from "react-hook-form";
import { useRecoilValue, useSetRecoilState } from "recoil";
import { categoryState, toDoState } from "../atoms";
interface IForm {
toDo: string;
}
function CreateToDo(){
// component를 가져올때 다시 사용하는것이아니라
// 수정할수 있도록만 해주면됨.
const setToDos = useSetRecoilState(toDoState);
const category = useRecoilValue(categoryState);
const {register,handleSubmit,setValue} = useForm<IForm>();
const handleValid = ({toDo}:IForm) =>{
// console.log("add to do",data.toDo);
setToDos((prev) =>[
{
text: toDo,
id:Date.now(),
category
} ,
...prev,
]);
// prev을 받아서 prev배열 자체가 아닌
// prev안의 요소들을 return 할것이기때문에 '...'를 붙여준다.
setValue("toDo","");
// console.log(toDos);
};
return(
<form onSubmit=
{handleSubmit(handleValid)}>
<input
{...register("toDo",{
required: "please write a To Do",
})}
placeholder="Write a to do"
/>
<button>Add</button>
</form>
);
}
export default CreateToDo;
ToDo.tsx
import React from "react";
import { useSetRecoilState } from "recoil";
import { Categories, IToDo,toDoState } from "../atoms";
function ToDo({text,category,id}:IToDo){
const setToDos = useSetRecoilState(toDoState);
const deleteToDos = () => {
setToDos((oldToDos) => {
const targetIndex = oldToDos.findIndex((toDo) => toDo.id === id);
return[
...oldToDos.slice(0,targetIndex),
...oldToDos.slice(targetIndex+1),
];
});
};
const onClick = (event:React.MouseEvent<HTMLButtonElement>) =>
{
const {
currentTarget:{name},
}
= event;
setToDos((oldToDos) => {
const targetIndex = oldToDos.findIndex((toDo) => toDo.id === id);
// console.log(targetIndex);
// const oldToDos = oldToDos[targetIndex];
const newToDos = {text, id, category: name as any};
// as any라고 적음으로써 타입스크립트에게 체크하지 말라함
return [...oldToDos.slice(0,targetIndex),
newToDos,
...oldToDos.slice(targetIndex+1)
];
});
};
return (
<li>
<span>{text}</span>
{category !== Categories.DOING && (
<button name={Categories.DOING+""} onClick={onClick}>
Doing
</button>
)}
{category !== Categories.TO_DO && (
<button name={Categories.TO_DO+""} onClick={onClick}>
To Do
</button>
)}
{category !== Categories.DONE &&(
<button name={Categories.DONE+""} onClick={onClick}>
Done
</button>
)}
<button onClick={deleteToDos}>
Delete
</button>
</li>
);
}
export default ToDo;
// ToDoList.tsx
import React from "react";
import { useRecoilState, useRecoilValue} from "recoil";
import { Categories, categoryState, toDoSelector } from "../atoms";
import CreateToDo from "./CreateToDo";
import ToDo from "./ToDo";
function ToDoList(){
const toDos = useRecoilValue(toDoSelector);
// useRecoilValue는 atom과 selector의 값만 반환한다.
const [category, setCategory] = useRecoilState(categoryState);
// useRecoilState는 값과 더불어 modifier함수도 제공
const onInput =(event:React.FormEvent<HTMLSelectElement>) =>
{ setCategory(event.currentTarget.value as any)};
console.log(category);
return(
<div>
<h1>To Dos</h1>
<hr/>
<select value={category} onInput={onInput}>
<option value={Categories.TO_DO}>To Do</option>
<option value={Categories.DOING}>Doing</option>
<option value={Categories.DONE}>Done</option>
</select>
<CreateToDo/>
{toDos?.map((toDo) => (
<ToDo key={toDo.id} {...toDo}/>
))}
</div>
);
}
export default ToDoList;
728x90
'Frontend > React' 카테고리의 다른 글
ToDoList에 현재시간 만들기 (0) | 2023.01.31 |
---|---|
ToDoList에 localstorage 만들기 (0) | 2023.01.31 |
(19) React -To Do App (1) (0) | 2023.01.26 |
(18) React - selector modify (0) | 2023.01.25 |
(17) React- React hook form (0) | 2023.01.23 |