diff options
author | polwex <polwex@sortug.com> | 2025-05-29 15:16:41 +0700 |
---|---|---|
committer | polwex <polwex@sortug.com> | 2025-05-29 15:16:41 +0700 |
commit | 8e0965f5274635f609972ef85802675af64df0f4 (patch) | |
tree | cc82db5928d49bede5c162cd22ab2a4e36cbdc6b /src/components/Flashcard | |
parent | 490388360a0852bcf8ee054e96fa90e166df5792 (diff) |
this is mostly me
Diffstat (limited to 'src/components/Flashcard')
-rw-r--r-- | src/components/Flashcard/StudySession.tsx | 75 |
1 files changed, 42 insertions, 33 deletions
diff --git a/src/components/Flashcard/StudySession.tsx b/src/components/Flashcard/StudySession.tsx index 1f79e09..c58531b 100644 --- a/src/components/Flashcard/StudySession.tsx +++ b/src/components/Flashcard/StudySession.tsx @@ -13,37 +13,43 @@ import { cn } from "@/lib/utils"; interface StudySessionProps { userId: number; lessonId: number; - initialData?: DeckResponse; + initialData: DeckResponse; } -export default function StudySession({ userId, lessonId, initialData }: StudySessionProps) { - const [deckData, setDeckData] = useState<DeckResponse | null>(initialData || null); +export default function StudySession({ + userId, + lessonId, + initialData, +}: StudySessionProps) { + const [deckData, setDeckData] = useState<DeckResponse | null>( + initialData || null, + ); const [currentCardIndex, setCurrentCardIndex] = useState(0); const [reviewedCards, setReviewedCards] = useState<CardResponse[]>([]); const [isLoading, setIsLoading] = useState(!initialData); const [isCompleted, setIsCompleted] = useState(false); const [stats, setStats] = useState<any>(null); const [error, setError] = useState<string | null>(null); - + // Load the deck data if not provided useEffect(() => { if (!initialData) { loadDeck(); } - + // Load user stats loadStats(); }, []); - + // Load deck data const loadDeck = async () => { setIsLoading(true); setError(null); - + try { const result = await startStudySession(userId, lessonId, true); - - if ('error' in result) { + + if ("error" in result) { setError(result.error); setDeckData(null); } else { @@ -56,7 +62,7 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes setIsLoading(false); } }; - + // Load user stats const loadStats = async () => { try { @@ -66,12 +72,12 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes console.error("Error loading stats:", error); } }; - + // Handle card completion const handleCardComplete = (updatedCard: CardResponse) => { // Add to reviewed cards - setReviewedCards(prev => [...prev, updatedCard]); - + setReviewedCards((prev) => [...prev, updatedCard]); + // Move to next card if (deckData && currentCardIndex < deckData.cards.length - 1) { setCurrentCardIndex(currentCardIndex + 1); @@ -79,18 +85,18 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes // End of deck setIsCompleted(true); } - + // Refresh stats loadStats(); }; - + // Skip current card const handleSkip = () => { if (deckData && currentCardIndex < deckData.cards.length - 1) { setCurrentCardIndex(currentCardIndex + 1); } }; - + // Restart session const handleRestart = () => { setCurrentCardIndex(0); @@ -98,19 +104,20 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes setIsCompleted(false); loadDeck(); }; - + // Calculate completion percentage const getCompletionPercentage = () => { if (!deckData) return 0; return (reviewedCards.length / deckData.cards.length) * 100; }; - + // Get current card const getCurrentCard = (): CardResponse | null => { - if (!deckData || !deckData.cards || deckData.cards.length === 0) return null; - return deckData.cards[currentCardIndex]; + if (!deckData || !deckData.cards || deckData.cards.length === 0) + return null; + return deckData.cards[currentCardIndex]!; }; - + // Render loading state if (isLoading) { return ( @@ -128,7 +135,7 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes </div> ); } - + // Render error state if (error) { return ( @@ -140,16 +147,20 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes </div> ); } - + // Render completion state if (isCompleted || !getCurrentCard()) { return ( <div className="w-full max-w-3xl mx-auto p-4"> <Card className="p-6"> <div className="text-center"> - <h2 className="text-2xl font-bold mb-4">Study Session Completed!</h2> + <h2 className="text-2xl font-bold mb-4"> + Study Session Completed! + </h2> <div className="mb-6"> - <p className="text-lg">You've reviewed {reviewedCards.length} cards.</p> + <p className="text-lg"> + You've reviewed {reviewedCards.length} cards. + </p> {stats && ( <div className="mt-4 text-sm text-gray-600"> <p>Total cards: {stats.totalCards}</p> @@ -169,29 +180,27 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes </div> ); } - + // Render study session return ( <div className="w-full max-w-3xl mx-auto p-4"> <div className="mb-6"> <div className="flex justify-between items-center mb-2"> - <h2 className="text-xl font-bold"> - {deckData?.lesson.name} - </h2> + <h2 className="text-xl font-bold">{deckData?.lesson.name}</h2> <div className="text-sm text-gray-500"> {reviewedCards.length} / {deckData?.cards.length} cards </div> </div> <Progress value={getCompletionPercentage()} className="h-2" /> </div> - + <StudyCard card={getCurrentCard()!} userId={userId} onComplete={handleCardComplete} onSkip={handleSkip} /> - + <div className="mt-6 flex justify-between"> <Button variant="ghost" onClick={() => window.history.back()}> Exit @@ -200,7 +209,7 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes Skip </Button> </div> - + {stats && ( <div className="mt-8 p-4 bg-gray-50 rounded-lg"> <h3 className="font-medium mb-2">Your Progress</h3> @@ -226,4 +235,4 @@ export default function StudySession({ userId, lessonId, initialData }: StudySes )} </div> ); -}
\ No newline at end of file +} |