2022. 1. 24. 22:19ใWEB Dev/ToyProject
๐ท CloneTodo โ - Todomate Clone Project | Team CloneMate
CloneTodo : ๋ง์ ์ฌ๋๋ค์ด ์ฌ๋ํ๋ ํฌ๋๋ฉ์ดํธ๋ฅผ ํด๋ก ํ์ฌ ์น ์๋น์ค๋ฅผ ๋ฐฐํฌํด๋ณด๋ ํ๋ก์ ํธ
๋ฒ์จ 31๋ฒ์งธ ๊ธ์ด๋ค.
๊ทธ๋์ ํ ์ด ์ข ์์๋๋ฐ ํ์๋ฅผ ํตํด ๋ฐฑ์๋ ํ์๋ถ๋ค๊ณผ ์ํตํ๊ณ ์์๊ณ , MUI์ ์บ๋ฆฐ๋ ์ปดํฌ๋ํธ์ธ DatePicker๋ฅผ ๊ฐ์ง๊ณ ํฌ๋๋ฉ์ดํธ์ ์บ๋ฆฐ๋์ฒ๋ผ ๊ตฌํํ๋ ์๊ฐ์ด ๊ฝค๋ ์์๋์๋ค.
์บ๋ฆฐ๋ ๋ง๋๋ ๊ฒ์ ์ด ์ฝ๋๋ฅผ ๊ฑฐ์ ๋๋ถ๋ถ ์ฐธ์กฐํ๋ค. renderDay ํจ์๋ฅผ ์ด์ฉํด์ ๊ฐ ๋ ์ง์ ํ ์นธ ํ ์นธ์ ์๋ก ๋ ๋๋ง ํด ์ฃผ๋ ๋ฐฉ๋ฒ์ด๋ค.
ํด๋์ค๋ฅผ ๋ถ์ฌ ์คํ์ผ์ ์ฃผ๋ ๊ฒ์ผ๋ก ๋๋ถ๋ถ ํด๊ฒฐํ๋ค.
์บ๋ฆฐ๋๋ฅผ ๋ง๋ค๋ฉด์ ๋ฐฑ์๋์ ์ฃผ๊ณ ๋ฐ๋ ๋ถ๋ถ์ ์๊ฐํด ๋ณผ ๊ธฐํ๊ฐ ๋์๋ค.
์์ฒญํ์ ๋๋ก '๋ฐ์ดํฐ ์์' ์ด ์ด๋ป๊ฒ ๋ ์ง ๊ณ ๋ฏผํด๋ณด์๊ณ ํ์ฌ์์ JSON ๋ฐฉ์์ผ๋ก ํต์ ํ๋ฉด์ ๋ฐ์ดํฐ๋ฅผ ๋ฐ์๋ค ์ด ๊ฒฝํ์ ํ ๋๋ก ๋ฐ์ดํฐ ์์์ ๋ง๋ค์๋ค.
1. DatePicker๋ก ์บ๋ฆฐ๋ ๊ตฌํํ๊ธฐ
renderDay props๋ก ํจ์๊ฐ ํ์ํจ
day: Date, selectedDate : Date, isInCrrentMonth: boolean, dayComponent: Element
์ด props๋ฅผ ์ ๋ ฅํ ๋ค์ ๋ ์ง ํ์ผ๋ก ๋ ๋๋ง ํ ์ ์๋ ์์๋ฅผ ๋ฐํํ๋ค.
DatePicker๋ ์ด ํจ์๋ฅผ ํ์๋ ๋ชจ๋ ๋ ์ง๋ก ํธ์ถ
ํ์ํ ์ ๋ณด
- ํฌ๋๊ฐ ์๋ ๋ : normal date tile
- ํฌ๋๊ฐ ์๋ ๋ : todo date tile (๊ฐฏ์)
- ํฌ๋๋ฅผ ๋ชจ๋ ์๋ฃํ ๋ : complete date tile(์์, check โ)
๋ง๋ ํจ์๋ฅผ enderDate ์์์ ์ง์
๊ทธ๋ฌ๋ฉด DatePicker๊ฐ ๋ ์ง๋ฅผ ๋ ๋๋ง ํ๊ณ ๋ ์ง ํ์ผ์ ์์ฒญํ ๋๋ง๋ค ํธ์ถํด์ค๋ค.
๋ง๋ ํจ์๊ฐ ๋ ์ง๋ฅผ ํ์ธํ๊ณ ์ ์ ํ ๋ ์ง ํ์ผ์ ๋ฐํํ๋ค.
๋ฐ๋ผ์ ๋ฐ์ดํฐ๋
- ํฌ๋๊ฐ ์๋ ๋ theDayhasTodo
- ํฌ๋๊ฐ ์๋ ๋ ์ ํฌ๋ ๊ฐฏ์ todoNum
- ํฌ๋๊ฐ ์๋ ๋ ์ ํฌ๋ ์๋ฃ ์ ๋ณด (ํด๋น ๋ ์ง์ checked ์ ๊ฐ์ด ๋ชจ๋ y์ธ๊ฐ?) todoChecked
if ํฌ๋ ์์ผ๋ฉด -> dateTile์ ํฌ๋๊ฐ ์๋ ๋ ์ ํฌ๋ ๊ฐฏ์ ๋ฃ์
if ํฌ๋๊ฐ ๋ชจ๋ ์๋ฃ ๋๋ฉด -> ํฌ๋ ๊ฐฏ์๊ฐ v ํ์๋ก ๋ณํ๋จ
์๊ฐ์ ๊ตฌ์กฐ๋ ์์ ๊ฐ์๋ค.
์ฌ๋ฌ๋ฒ ์ฝ๋๋ฅผ ๊ณ ์ณ์จ๊ฐ๋ฉด์ ๋ฐ์ดํฐ๊ฐ ์์ ๋์ ์์ ๋ ์ซ์๋ฅผ ๋ฟ๋ ค์ฃผ๋ ๊ฒ, ์๋ฃ๋์์ ๋ ์ซ์ ๋์ ์ฒดํฌํ์๊ฐ ๋ํ๋๊ฒ ํ๋ ๊ฒ ๋ชจ๋ renderDay ํจ์๋ฅผ ํตํด ํด๋์ค๋ฅผ ๋ถ์ด๋ ๋ฐฉ๋ฒ๊ณผ ๊ฐ์ฒด์ key์ value๋ฅผ ํ์ํ๋ ๊ฒ์ผ๋ก ๊ตฌํํ๋ค.
์์ ์๊ฐ ๊ตฌ์กฐ๋ฅผ ํ ๋๋ก ๋ง๋ ๋ฐ์ดํฐ ์์์ ์๋์ ๊ฐ๋ค.
//ajax ํต์ ์ ํตํด ๋ฐ์์จ ๊ฐ (theDayhasTodo, todoNum, todoChecked)
const getTodoDataForCalendar = [
{ theDayhasTodo: '2022-01-08', todoNum: 2, todoChecked: 'n' },
{ theDayhasTodo: '2022-01-14', todoNum: 4, todoChecked: 'n', },
{ theDayhasTodo: '2022-01-27', todoNum: 6, todoChecked: 'y' }
];
๋ฐ์ดํฐ๋ฒ ์ด์ค์ theDayhasTodo๊ฐ YYYY-MM-DD ํํ๋ก ์ ์ฅ๋์ด ์๊ธฐ ๋๋ฌธ์ ๊ทธ๋๋ก ๊ฐ์ ๋ฐ์์ค๋ฉด
renderDay ํจ์๋ ๋ ์ง ์ค DD๋ถ๋ถ๋ง ์ธ์ํ๊ณ 01, 02, 03 ์ฒ๋ผ ์์ 0๋ ๋น ์ ธ์ผํ๋ค.
๊ทธ๋ฆฌ๊ณ ๊ฐ์ ๋ถ๋ถ์ todoNum ๊ณผ todoChecked๊ฐ ๊ฐ๊ฐ ์ ๋ ฅ๋์ด์ผ ํด์
๊ฒฐ๊ณผ์ ์ผ๋ก ์ฌ์ฉํ๋ ๋ฐ์ดํฐ์ ํํ๋ { 8: '2', 14: '4', 27: 'y' }์ ๊ฐ๊ฒ ๋ณํํด์ ์ฌ์ฉํ๊ณ ์๋ค.
์ง๊ธ๋ถํฐ ํด์ผํ ๊ฒ์ ๋๋์ด recoil์ ์ ์ฉํด์ ๋ณ์ getTodoDataForCalendar์ ๊ฐ์ ๋ฐ์์ฌ ์ ์๋๋ก ์ํ๊ด๋ฆฌ์ ํต์ ๋ชจ๋์ ๋ง๋ค์ด์ผ ํ๋ค.
2. Recoil ์ ์ฉํ๊ธฐ
Recoil ๊ณต์ ์์ต์๋ ์๋๋ฅผ ์ฐธ๊ณ ํ๋ฉด ๋๋ค.
์ฐ์ ๊ณต์ ์์ต์์ ์์ํ๊ธฐ๋ฅผ ์ฐธ์กฐํด Recoil์ atom์ ์ ์ฉํด๋ณธ๋ค.
์ค์น
์๋์ ๊ฐ์ด npm ํน์ yarn์ ์ด์ฉํ๋ค.
// npm
npm install recoil
// yarn
yarn add recoil
<RecoilRoot> ๋ก ๊ฐ์ธ๊ธฐ
Recoil์ ์ด์ฉํ๊ธฐ ์ํด์๋ <RecoilRoot> ์ปดํฌ๋ํธ๋ก recoil์ ์ฌ์ฉํ๋ ค๊ณ ํ๋ ์ปดํฌ๋ํธ๋ค์ ๊ฐ์ธ์ค์ผ ํ๋ค.
๊ธฐ์กด state๋ฅผ ์ด์ฉํ๋ ๊ฒ์ฒ๋ผ ๊ฐ์ฅ ์์์ธ App ์ปดํฌ๋ํธ๋ฅผ ๊ฐ์ธ์ฃผ๋ ๊ฒ์ด ์ข๋ค.
index.js์ ๊ฐ์ RecoilRoot๋ก ๊ฐ์ธ์ฃผ์.
import React from 'react';
import ReactDOM from 'react-dom';
import './stylesheets/index.css';
import App from './components/App';
import { BrowserRouter } from 'react-router-dom';
import { RecoilRoot } from "recoil";
ReactDOM.render(
<RecoilRoot>
<BrowserRouter>
<App />
</BrowserRouter>
</RecoilRoot>,
document.getElementById('root')
);
Atom ๋ง๋ค๊ธฐ
recoil์์ states๋ 'atom' ์ด๋ผ๋ ์ด๋ฆ์ผ๋ก ์ฌ์ฉํ๋ค.
๊ทธ๋์ atom์ ๊ฐ์ ๋ณํ๊ฐ ์์ผ๋ฉด atom์ ์ฐธ์กฐํ๋ ๋ชจ๋ ์ปดํฌ๋ํธ๋ค์ด ์ฌ๋ ๋๋ง ๋๋ค.
atom์ ๋ณ์์ฒ๋ผ ์ ์ธ๋๋ค.
๋ณ๋๋ก ๋ง๋ ํด๋์ ์ ์ธํ atom์ด๊ธฐ ๋๋ฌธ์ recoil ์์ atom์ import ํด์ฃผ๊ณ
atom์ผ๋ก ๋ง๋ textState๋ฅผ ์ฌ์ฉํ๊ธฐ ์ํด export ํด์ค๋ค.
import { atom } from "recoil";
export const textState = atom({
key: 'textState', // unique ID (with respect to other atoms/selectors)
default: '', // default value (aka initial value)
});
useRecoilState Hook
์ด textState๋ผ๋ atom์ ์ฌ์ฉํ๊ธฐ ์ํด์๋ ์ด atom ์ ์ฌ์ฉํ ์ปดํฌ๋ํธ์ ์๋์ ๊ฐ์ useRecoilState ํ ์ ์ฌ์ฉํ๋ค.
const [text, setText] = useRecoilState(textState);
์์ ์์๋๋ก recoil์ ์ ์ฉํด๋ณด์๋ฉด
Recoil์ ์ค์นํ ํ atom์ผ๋ก ๋ง๋ state๋ค์ ๋ชจ์๋ atoms ์ด๋ผ๋ ํด๋๋ฅผ ํ๋ ์์ฑํ๊ณ ๊ทธ ์์ todoData๋ผ๋ ์ปดํฌ๋ํธ๋ฅผ ํ๋ ๋ง๋ ๋ค.
๋ด๋ถ์ ์ฝ๋๋ฅผ ์๋์ ๊ฐ์ด ๋ฃ์ด์ค๋ค.
const textState = atom({
key: 'textState', // unique ID (with respect to other atoms/selectors)
default: '', // default value (aka initial value)
});
์์ textState๋ฅผ ๊ฐ์ง๊ณ atom์ ์ ์ฉํ CalendarBox ์ปดํฌ๋ํธ์ ์ด๋ฐ ํ ์คํธ ํ๊ทธ๋ฅผ ๋ฃ์ด์ค๋ค.
function TextInput() {
const [text, setText] = useRecoilState(textState);
const onChange = (event) => {
setText(event.target.value);
};
return (
<div>
<input type="text" value={text} onChange={onChange} />
<br />
{text}
</div>
);
}
๊ทธ๋ฆฌ๊ณ ๋ฆฌ์กํธ๋ฅผ ์คํํด๋ณด๋ฉด ์๋์ ๊ฐ์ ์๋ฌ ๋ฉ์์ง๊ฐ ๋ฌ๋ค.
'useRecoilState' is not defined no-undef
'useRecoilState' is not defined no-undef
ํด๋น ์ค๋ฅ๋ ์๋จ์ useRecoilState๊ณผ atom์ด ์๋ ์ปดํฌ๋ํธ๋ฅผ ๋ฃ์ด์ค์ผ๋ก์จ ํด๊ฒฐํ ์ ์๋ค.
import { useRecoilState } from "recoil";
import { textState } from "../atoms/todoData";
์คํ
ํด๋น input ํ๊ทธ์ ๊ธ์๋ฅผ ์ ๋ ฅํ๋ฉด state๊ฐ ๋ณํ๋ฉด์ ๊ธ์๋ฅผ ์ถ๋ ฅํด์ฃผ๋ ๊ฒ์ ๋ณผ ์ ์๋ค.
๊ทธ๋ผ ์ด์ ๋ฐ์ดํฐ๋ฅผ ์๋ฒ์์ ๋ฐ์์ค๋ fetch, promise, axios ๊ฐ์ ๋น๋๊ธฐ ํต์ ๋ฉ์๋๋ก
๋น๋๊ธฐ ํต์ ์ ๋ด๋นํ๋ ๋ชจ๋์ ๋ง๋ค์ด ๋ณด์!
'WEB Dev > ToyProject' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[ToyProject-Todomate] ํฌ๋๋ฉ์ดํธ ํด๋ก ํ๋ก์ ํธ 33 (0) | 2022.02.01 |
---|---|
[ToyProject-Todomate] ํฌ๋๋ฉ์ดํธ ํด๋ก ํ๋ก์ ํธ 32 (0) | 2022.01.26 |
[ToyProject-Todomate] ํฌ๋๋ฉ์ดํธ ํด๋ก ํ๋ก์ ํธ 30 (0) | 2022.01.16 |
[ToyProject-Todomate] ํฌ๋๋ฉ์ดํธ ํด๋ก ํ๋ก์ ํธ 29 (0) | 2022.01.16 |
[ToyProject-Todomate] ํฌ๋๋ฉ์ดํธ ํด๋ก ํ๋ก์ ํธ 28 (0) | 2022.01.16 |