import { useQuery } from '@tanstack/react-query'; import { BookOpenCheck, ChevronLeft, Loader2, Menu, X } from 'lucide-react'; import { useState } from 'react'; import { type AiCourse } from '../../lib/ai'; import { cn } from '../../lib/classname'; import { slugify } from '../../lib/slugger'; import { getAiCourseProgressOptions } from '../../queries/ai-course'; import { queryClient } from '../../stores/query-client'; import { CheckIcon } from '../ReactIcons/CheckIcon'; import { ErrorIcon } from '../ReactIcons/ErrorIcon'; import { AICourseLimit } from './AICourseLimit'; import { AICourseModuleList } from './AICourseModuleList'; import { AICourseModuleView } from './AICourseModuleView'; type AICourseContentProps = { courseSlug?: string; course: AiCourse; isLoading: boolean; error?: string; }; export function AICourseContent(props: AICourseContentProps) { const { course, courseSlug, isLoading, error } = props; const [activeModuleIndex, setActiveModuleIndex] = useState(0); const [activeLessonIndex, setActiveLessonIndex] = useState(0); const [sidebarOpen, setSidebarOpen] = useState(true); const [viewMode, setViewMode] = useState<'module' | 'full'>('full'); const { data: aiCourseProgress } = useQuery( getAiCourseProgressOptions({ aiCourseSlug: courseSlug || '' }), queryClient, ); const [expandedModules, setExpandedModules] = useState< Record >({}); const goToNextModule = () => { if (activeModuleIndex < course.modules.length - 1) { const nextModuleIndex = activeModuleIndex + 1; setActiveModuleIndex(nextModuleIndex); setActiveLessonIndex(0); setExpandedModules((prev) => { const newState: Record = {}; course.modules.forEach((_, idx) => { newState[idx] = false; }); newState[nextModuleIndex] = true; return newState; }); } }; const goToNextLesson = () => { const currentModule = course.modules[activeModuleIndex]; if (currentModule && activeLessonIndex < currentModule.lessons.length - 1) { setActiveLessonIndex(activeLessonIndex + 1); } else { goToNextModule(); } }; const goToPrevLesson = () => { if (activeLessonIndex > 0) { setActiveLessonIndex(activeLessonIndex - 1); } else { const prevModule = course.modules[activeModuleIndex - 1]; if (prevModule) { const prevModuleIndex = activeModuleIndex - 1; setActiveModuleIndex(prevModuleIndex); setActiveLessonIndex(prevModule.lessons.length - 1); // Expand the previous module in the sidebar setExpandedModules((prev) => { const newState: Record = {}; // Set all modules to collapsed course.modules.forEach((_, idx) => { newState[idx] = false; }); // Expand only the previous module newState[prevModuleIndex] = true; return newState; }); } } }; const currentModule = course.modules[activeModuleIndex]; const currentLesson = currentModule?.lessons[activeLessonIndex]; const totalModules = course.modules.length; const totalLessons = currentModule?.lessons.length || 0; const totalCourseLessons = course.modules.reduce( (total, module) => total + module.lessons.length, 0, ); const totalDoneLessons = aiCourseProgress?.done?.length || 0; const finishedPercentage = Math.round( (totalDoneLessons / totalCourseLessons) * 100, ); if (error && !isLoading) { return (

Error Generating Course

{error}

); } return (

{course.title || 'Loading Course...'}

{totalModules} modules {totalCourseLessons} lessons {finishedPercentage > 0 && ( <> {finishedPercentage}% complete )}
{viewMode === 'module' && ( )}
{viewMode === 'module' && ( )} {viewMode === 'full' && (

{course.title || 'Loading course ..'}

{course.title ? course.difficulty : 'Please wait ..'}

{course.title ? (
{course.modules.map((courseModule, moduleIdx) => { return (

{courseModule.title}

{courseModule.lessons.map((lesson, lessonIdx) => { const key = `${slugify(courseModule.title)}__${slugify(lesson)}`; const isCompleted = aiCourseProgress?.done.includes(key); return (
{ setActiveModuleIndex(moduleIdx); setActiveLessonIndex(lessonIdx); setExpandedModules((prev) => { const newState: Record = {}; course.modules.forEach((_, idx) => { newState[idx] = false; }); newState[moduleIdx] = true; return newState; }); setViewMode('module'); }} > {!isCompleted && ( {lessonIdx + 1} )} {isCompleted && ( )}

{lesson.replace(/^Lesson\s*?\d+[\.:]\s*/, '')}

{isCompleted ? 'View' : 'Start'} →
); })}
); })}
) : (
)}
)}
{sidebarOpen && (
setSidebarOpen(false)} >
)}
); }