"use client"; import { useState, useEffect } from "react"; interface QuizQuestion { id: string; question: string; options: string[]; correct: number[]; type?: 'multiple-choice' | 'true-false' | 'multiple-select'; } interface QuizPlayerProps { id: string; title?: string; quizData: { questions: QuizQuestion[]; }; allowRetry?: boolean; maxAttempts?: number; initialAttempts?: number; onAttempt?: () => void; } export default function QuizPlayer({ id, title, quizData, allowRetry = true, maxAttempts = 0, initialAttempts = 0, onAttempt }: QuizPlayerProps) { const [userAnswers, setUserAnswers] = useState>({}); const [submitted, setSubmitted] = useState(false); const [attempts, setAttempts] = useState(initialAttempts || 0); const questions = quizData?.questions || []; // Sync attempts with prop useEffect(() => { if (initialAttempts !== undefined) { setAttempts(initialAttempts); } }, [initialAttempts]); const handleAnswer = (qId: string, optionIndex: number, isMulti: boolean) => { if (submitted) return; setUserAnswers(prev => { const current = prev[qId] || []; if (isMulti) { const next = current.includes(optionIndex) ? current.filter(i => i !== optionIndex) : [...current, optionIndex].sort((a, b) => a - b); return { ...prev, [qId]: next }; } else { return { ...prev, [qId]: [optionIndex] }; } }); }; const handleValidate = () => { if (maxAttempts > 0 && attempts >= maxAttempts) return; setSubmitted(true); if (onAttempt) { onAttempt(); setAttempts(prev => prev + 1); } }; return (

{title || "Verificación de Conocimientos"}

{maxAttempts > 0 && ( Intento {attempts} / {maxAttempts} )}
{questions.map((q) => (
{q.question}
{q.options.map((opt, oIdx) => { const isSelected = userAnswers[q.id]?.includes(oIdx); const isCorrect = q.correct?.includes(oIdx); const isActuallyCorrect = isCorrect && isSelected; const isWrongSelection = !isCorrect && isSelected; const missedCorrect = isCorrect && !isSelected; let style = "glass border-black/10 dark:border-white/10 hover:bg-black/5 dark:hover:bg-white/5 text-gray-700 dark:text-gray-300"; if (submitted) { if (isActuallyCorrect) style = "bg-green-500/20 border-green-500 text-green-400"; else if (isWrongSelection) style = "bg-red-500/20 border-red-500 text-red-100"; else if (missedCorrect) style = "border-orange-500/50 text-orange-400 animate-pulse"; else style = "opacity-50 grayscale border-white/5"; } else if (isSelected) { style = "bg-blue-600/10 dark:bg-blue-500/20 border-blue-600 dark:border-blue-500 text-blue-700 dark:text-white shadow-[0_0_20px_rgba(59,130,246,0.2)]"; } return ( ); })}
))} {allowRetry && ( <> {!submitted && questions.length > 0 && ( )} {submitted && ( )} )}
); }