Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[DEV] 감정 모아보기 페이지 구현 #45

Open
wants to merge 15 commits into
base: main
Choose a base branch
from
Open
56 changes: 45 additions & 11 deletions Junghyun/react-ts/src/app/detail/[id]/page.tsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,49 @@
import { useParams } from 'react-router-dom'
import { useDiaryValue } from '../../../provider/Diary'
import { useParams, useNavigate } from 'react-router-dom'
import { useEffect } from 'react'
import { useDiaryValue, useDiaryUpdate } from '../../../provider/Diary'
import { Diary } from '../../../interface/diary'
import { formatDate } from '../../../utils/formatDate'

type DiaryDetailPageParams = {
id: string
}

export default function DiaryDetailPage() {
const { id } = useParams<DiaryDetailPageParams>()
const diary = useDiaryValue().find((diary) => diary.id === id)
const formattedDate = new Date(diary!.date).toLocaleDateString('ko-KR', {
year: 'numeric',
month: 'long',
day: 'numeric',
weekday: 'long',
})
const navigate = useNavigate()
const diaries = useDiaryValue()
const diary = diaries.find((diary) => diary.id === id)
const updateDiaries = useDiaryUpdate()
const formattedDate = formatDate(new Date(diary!.date), 'long')

// 조회수 증가
useEffect(() => {
if (diary)
updateDiaries((prev: Diary[]) => {
const newDiaries = prev.map((diary) => (diary.id === id ? { ...diary, views: diary.views + 1 } : diary))
localStorage.setItem('diaries', JSON.stringify(newDiaries))
return newDiaries
})
}, [id, diary, updateDiaries])

// 현재 일기 삭제
const handleDelete = () => {
if (!diary || !id) return

try {
updateDiaries((prev: Diary[]) => {
const newDiaries = prev.filter((diary) => diary.id !== id)
localStorage.setItem('diaries', JSON.stringify(newDiaries))
return newDiaries
})

alert('일기가 삭제되었습니다.')
navigate('/')
} catch (error) {
console.error('일기 삭제 실패:', error)
alert('일기 삭제에 실패하였습니다.')
}
}

return (
<div className="flex flex-col h-full w-1/2 justify-center gap-10">
Expand All @@ -28,8 +58,12 @@ export default function DiaryDetailPage() {

<div className="flex h-1/2 text-xl">{diary!.content}</div>
<div className="flex flex-row gap-2">
<button className="green-btn flex-1 p-2">새로운 일기 작성하기</button>
<button className="red-btn flex-1 p-2">현재 일기 삭제하기</button>
<button className="green-btn flex-1 p-2" onClick={() => navigate('/')}>
새로운 일기 작성하기
</button>
<button className="red-btn flex-1 p-2" onClick={handleDelete}>
현재 일기 삭제하기
</button>
</div>
</div>
)
Expand Down
10 changes: 9 additions & 1 deletion Junghyun/react-ts/src/app/emotions/[emotion]/page.tsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,17 @@
import { useParams } from 'react-router-dom'
import { useDiaryValue } from '../../../provider/Diary'
import { EmojiBox } from '../../../components/EmotionCard'
import { Diary } from '../../../interface/diary'

type EmotionPageParams = {
emotion: string
}
export default function EmotionPage() {
const { emotion } = useParams<EmotionPageParams>()
return <>{emotion} Emotion page </>
const diaries = useDiaryValue()
return (
<div className="flex flex-col">
<EmojiBox emotion={emotion as Diary['emotion']} />
</div>
)
}
18 changes: 17 additions & 1 deletion Junghyun/react-ts/src/app/emotions/page.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,19 @@
import EmotionCard from '../../components/EmotionCard'
import { EMOTION_DATA } from '../../constants'
import { Diary } from '../../interface/diary'

export default function EmotionLinkPage() {
return <>Emotion Link Page</>
return (
<div className="flex flex-col items-start justify-center gap-10">
<div className="flex flex-col justify-center items-start gap-4">
<h1 className="text-3xl font-semibold">감정 상자</h1>
<span className="text-gray-400">나만의 감정을 돌아보고 생각에 잠겨보아요 :)</span>
</div>
<div className="grid grid-cols-2 gap-5 justify-center items-center">
{Object.keys(EMOTION_DATA).map((emotion) => (
<EmotionCard key={emotion} emotion={emotion as Diary['emotion']} />
))}
</div>
</div>
)
}
10 changes: 3 additions & 7 deletions Junghyun/react-ts/src/components/DiaryCard.tsx
Original file line number Diff line number Diff line change
@@ -1,13 +1,9 @@
import { Diary } from '../interface/diary'
import { Link } from 'react-router-dom'
import { formatDate } from '../utils/formatDate'

export default function DiaryCard({ title, date, emotion, weather, id }: Diary) {
const formattedDate = new Date(date).toLocaleDateString('ko-KR', {
year: 'numeric',
month: 'numeric',
day: 'numeric',
formatMatcher: 'basic',
})
const formattedDate = formatDate(new Date(date))

const emotionEmoji = {
bad: '🤬',
Expand All @@ -26,7 +22,7 @@ export default function DiaryCard({ title, date, emotion, weather, id }: Diary)
return (
<Link
to={`/detail/${id}`}
className="flex flex-col gap-2 w-full p-3 border border-gray-200 rounded-lg items-start justify-center"
className="flex flex-col gap-2 w-full p-3 border border-gray-200 rounded-lg items-start justify-center hover:bg-gray-100"
>
<h1 className="text-grey-600">{title}</h1>
<div className="flex flex-row justify-between w-full">
Expand Down
31 changes: 31 additions & 0 deletions Junghyun/react-ts/src/components/EmotionCard.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import { Link } from 'react-router-dom'
import { Diary } from '../interface/diary'
import { EMOTION_DATA } from '../constants'

type EmotionProps = {
emotion: Diary['emotion']
}

export const EmojiBox = ({ emotion }: EmotionProps) => {
const { emoji, color } = EMOTION_DATA[emotion]

return (
<div className={`flex w-24 h-24 text-6xl justify-center items-center bg-${color}-50 rounded-2xl`}>{emoji}</div>
)
}

export default function EmotionCard({ emotion }: EmotionProps) {
const { description } = EMOTION_DATA[emotion]

return (
<Link to={`/emotions/${emotion}`}>
<div className="flex flex-row items-center justify-center gap-4 border border-gray-100 rounded-3xl p-5 hover:scale-105 transition-all duration-300 hover:shadow-xl hover:border-transparent cursor-pointer">
<EmojiBox emotion={emotion} />
<div className="flex flex-col items-start justify-center gap-1">
<div className="text-2xl capitalize">{emotion}</div>
<div className="text-m text-gray-400">{description}</div>
</div>
</div>
</Link>
)
}
36 changes: 36 additions & 0 deletions Junghyun/react-ts/src/constants/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
import { Diary } from '../interface/diary'

export const EMOTION_DATA: Record<
Diary['emotion'],
{
color: 'yellow' | 'blue' | 'green' | 'purple' | 'red'
emoji: string
description: string
}
> = {
awesome: {
emoji: '😆',
color: 'yellow',
description: '최고의 하루였어요',
},
great: {
emoji: '😊',
color: 'blue',
description: '멋진 하루였어요',
},
good: {
emoji: '😙',
color: 'green',
description: '좋은 하루였어요',
},
soso: {
emoji: '🙂',
color: 'purple',
description: '괜찮은 하루였어요',
},
bad: {
emoji: '🤬',
color: 'red',
description: '최악의 하루였어요!',
},
}
2 changes: 1 addition & 1 deletion Junghyun/react-ts/src/tailwind.css
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

@layer components {
.gray-btn {
@apply rounded-lg border border-transparent bg-gray-200 text-gray-500 hover:border-gray-600 hover:text-gray-600;
@apply rounded-lg border border-transparent bg-gray-100 text-gray-400 hover:border-gray-600 hover:text-gray-600;
}
.green-btn {
@apply rounded-lg border border-transparent bg-green-100 text-green-600 hover:border-green-600;
Expand Down
10 changes: 10 additions & 0 deletions Junghyun/react-ts/src/utils/formatDate.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
type DateFormat = 'long' | 'short'

export const formatDate = (date: Date, format: DateFormat = 'short') => {
return date.toLocaleDateString('ko-KR', {
year: 'numeric',
month: format === 'long' ? 'long' : 'numeric',
day: 'numeric',
weekday: format === 'long' ? 'long' : undefined,
})
}