'use client';
import { QuizAnswer } from '@/types/types';
import { useState, useEffect } from 'react';
import { FaRegClock, FaArrowRight, FaArrowLeft, FaCheck } from 'react-icons/fa';
import { motion } from 'framer-motion';
import { useSearchParams } from 'next/navigation';
type LatestAnswersProps = {
answers: QuizAnswer[];
onQuestionChange?: (slideNumber: number) => void;
currentQuestionNumber?: number | null;
};
export function LatestAnswers({ answers, onQuestionChange, currentQuestionNumber = null }: LatestAnswersProps) {
const [latestAnswers, setLatestAnswers] = useState<QuizAnswer[]>([]);
const searchParams = useSearchParams();
// For checking if we're on a special slide like instruction or answer
const isSpecialSlide = currentQuestionNumber === null;
// Sort answers by creation time (newest first) and take the latest 20
useEffect(() => {
// Filter answers for the current question number only
if (currentQuestionNumber !== null) {
// Get all answers for this question
const answersForQuestion = answers.filter(answer =>
answer.question_number === currentQuestionNumber
);
// Find the first submitted answer
const sortedByOldest = [...answersForQuestion].sort((a, b) =>
new Date(a.created_at).getTime() - new Date(b.created_at).getTime()
);
const firstAnswer = sortedByOldest.length > 0 ? sortedByOldest[0] : null;
// Get other answers (excluding the first one)
const otherAnswers = firstAnswer
? answersForQuestion.filter(a => a.id !== firstAnswer.id)
.sort((a, b) => new Date(b.created_at).getTime() - new Date(a.created_at).getTime())
.slice(0, 19) // One less to make room for the first answer
: answersForQuestion.sort((a, b) => new Date(b.created_at).getTime() - new Date(a.created_at).getTime())
.slice(0, 20);
// Combine first answer with others, putting first answer at the beginning
const orderedAnswers = firstAnswer
? [firstAnswer, ...otherAnswers]
: otherAnswers;
setLatestAnswers(orderedAnswers);
} else {
setLatestAnswers([]);
}
}, [answers, currentQuestionNumber]);
// New function to check if an answer is the first submitted for its question
const isFirstSubmittedAnswer = (answer: QuizAnswer) => {
const answersForQuestion = answers.filter(a => a.question_number === answer.question_number);
if (answersForQuestion.length === 0) return false;
// Sort by creation time (oldest first)
const sortedAnswers = [...answersForQuestion].sort((a, b) =>
new Date(a.created_at).getTime() - new Date(b.created_at).getTime()
);
// Check if this is the first answer
return answer.id === sortedAnswers[0].id;
};
const handleNextQuestion = () => {
// Get the current slide from URL
const currentSlide = parseInt(searchParams?.get('slide') || '1');
// Find the next question number in the dataset
if (answers.length > 0) {
const questionNumbers = Array.from(new Set(answers.map(a => a.question_number))).sort((a, b) => a - b);
const currentIndex = currentQuestionNumber !== null ?
questionNumbers.indexOf(currentQuestionNumber) : -1;
let nextQuestionNumber: number;
if (currentIndex < questionNumbers.length - 1) {
// Move to next question
nextQuestionNumber = questionNumbers[currentIndex + 1];
} else if (currentQuestionNumber !== null) {
// If we're at the last question, move to a hypothetical next one
nextQuestionNumber = currentQuestionNumber + 1;
} else {
// If no current question, start with 1
nextQuestionNumber = 1;
}
// Update the URL with the new slide number without triggering a navigation
// Simply increment the slide number
const nextSlide = currentSlide + 1;
const url = new URL(window.location.href);
url.searchParams.set('slide', nextSlide.toString());
window.history.pushState({}, '', url.toString());
// Call onQuestionChange with the new slide number
if (onQuestionChange) {
onQuestionChange(nextSlide);
}
} else {
// If no answers yet, simply increment the slide
const nextSlide = currentSlide + 1;
const url = new URL(window.location.href);
url.searchParams.set('slide', nextSlide.toString());
window.history.pushState({}, '', url.toString());
// Call onQuestionChange with the new slide number
if (onQuestionChange) {
onQuestionChange(nextSlide);
}
}
};
const handlePreviousQuestion = () => {
// Get the current slide from URL
const currentSlide = parseInt(searchParams?.get('slide') || '1');
// For special slides (instruction or answer slides)
if (isSpecialSlide) {
if (currentSlide > 1) {
// Simply decrement the slide number for special slides
const prevSlide = currentSlide - 1;
const url = new URL(window.location.href);
url.searchParams.set('slide', prevSlide.toString());
window.history.pushState({}, '', url.toString());
// Call onQuestionChange with the new slide number
if (onQuestionChange) {
onQuestionChange(prevSlide);
}
}
}
// For question slides (existing logic)
else if (currentQuestionNumber !== null && currentQuestionNumber > 1) {
// Find the previous question number in the dataset
const questionNumbers = Array.from(new Set(answers.map(a => a.question_number))).sort((a, b) => a - b);
const currentIndex = questionNumbers.indexOf(currentQuestionNumber);
let prevQuestionNumber: number;
if (currentIndex > 0) {
// Move to previous question
prevQuestionNumber = questionNumbers[currentIndex - 1];
} else {
// If not found in the set or at the beginning, just decrement
prevQuestionNumber = currentQuestionNumber - 1;
}
// Update the URL with the new slide number without triggering a navigation
// Simply decrement the slide number
const prevSlide = Math.max(1, currentSlide - 1); // Ensure we don't go below slide 1
const url = new URL(window.location.href);
url.searchParams.set('slide', prevSlide.toString());
window.history.pushState({}, '', url.toString());
// Call onQuestionChange with the new slide number
if (onQuestionChange) {
onQuestionChange(prevSlide);
}
}
};
if (isSpecialSlide) {
return (
<div className="mb-8 p-6 bg-amber-50 rounded-lg border border-amber-100 text-center">
<div className="text-lg font-semibold text-amber-800 mb-1">
Специален слайд (инструкции или отговори)
</div>
<p className="text-amber-600 mb-4">
Този слайд показва инструкции за кръг или отговори.
</p>
</div>
);
}
// If we have a question number but no answers for this question
if (currentQuestionNumber !== null && latestAnswers.length === 0) {
return (
<div className="mb-8">
<div className="mb-4">
<div className="text-xl font-bold text-amber-900 flex items-center gap-2">
<FaRegClock className="text-amber-500" />
0 отговора
</div>
</div>
<div className="p-6 bg-amber-50 rounded-lg border border-amber-100 text-center">
<p className="text-amber-700">
Все още няма отговори за този въпрос.
</p>
</div>
</div>
);
}
return (
<div className="mb-8">
<div className="mb-4">
<div className="text-xl font-bold text-amber-900 flex items-center gap-2">
<FaRegClock className="text-amber-500" />
{latestAnswers.length} {latestAnswers.length === 1 ? 'отговор' : 'отговора'}
</div>
</div>
<div className="grid grid-cols-1 gap-3">
{latestAnswers.length > 0 ? (
// Render just the team names with their status
<>
{latestAnswers.map((answer, index) => {
const isCorrect = answer.correct === true;
return (
<motion.div
key={answer.id}
initial={{ opacity: 0, y: 10 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 0.2, delay: index * 0.03 }}
className={`relative rounded-lg overflow-hidden shadow-sm ${
isCorrect
? 'border border-green-500 bg-green-50'
: isFirstSubmittedAnswer(answer)
? 'border-2 border-amber-500 bg-amber-50'
: 'border border-gray-200 bg-white'
}`}
>
{isFirstSubmittedAnswer(answer) && !isCorrect && (
<div className="absolute top-0 right-0 bg-amber-500 text-white text-xs px-2 py-0.5 rounded-bl-lg">
Първи
</div>
)}
{isCorrect && (
<div className="absolute top-0 right-0 bg-green-500 text-white text-xs px-2 py-0.5 rounded-bl-lg flex items-center gap-1">
<FaCheck size={10} />
</div>
)}
<div className="p-2 flex justify-between items-center">
<div className="font-medium text-lg text-gray-700 truncate">
{answer.team_name}
</div>
<div className="text-xs text-gray-500 flex-shrink-0">
{new Date(answer.created_at).toLocaleTimeString('bg-BG', {hour: '2-digit', minute:'2-digit', second: '2-digit'})}
</div>
</div>
</motion.div>
);
})}
</>
) : (
<div className="col-span-full p-6 bg-gray-50 rounded-lg text-center">
<p className="text-gray-500">
Няма отговори за показване.
</p>
</div>
)}
</div>
</div>
);
}