import React, { useEffect, useRef, useMemo, useState } from 'react'
import { useParams, Link } from 'react-router-dom'
import QRCode from 'qrcode'
import { sha256 } from 'js-sha256'
import { getConfigValue, getNavigationValue } from '@brojs/cli'
import { motion, AnimatePresence } from 'framer-motion'
import {
  Box,
  Container,
  VStack,
  Heading,
  Stack,
  useColorMode,
  Flex,
} from '@chakra-ui/react'
import { useTranslation } from 'react-i18next'

import { api } from '../__data__/api/api'
import { User, Reaction } from '../__data__/model'
import { UserCard } from '../components/user-card'
import { formatDate } from '../utils/dayjs-config'
import { useSetBreadcrumbs } from '../components'

import {
  QRCanvas,
  StudentList,
} from './style'
import { useAppSelector } from '../__data__/store'
import { isTeacher } from '../utils/user'

export function getGravatarURL(email, user) {
  if (!email) return void 0
  const address = String(email).trim().toLowerCase()
  const hash = sha256(address)

  // Grab the actual image URL
  return `https://www.gravatar.com/avatar/${hash}?d=robohash`
}

const LessonDetail = () => {
  const { lessonId, courseId } = useParams()
  const canvRef = useRef(null)
  const user = useAppSelector((s) => s.user)
  const { t } = useTranslation()
  const { colorMode } = useColorMode()
  
  // Получаем данные о курсе и уроке
  const { data: courseData } = api.useGetCourseByIdQuery(courseId)
  const { data: lessonData } = api.useLessonByIdQuery(lessonId)
  
  // Устанавливаем хлебные крошки
  useSetBreadcrumbs([
    {
      title: t('journal.pl.breadcrumbs.home'),
      path: '/'
    },
    {
      title: courseData?.name || t('journal.pl.breadcrumbs.course'),
      path: `${getNavigationValue('journal.main')}/lessons-list/${courseId}`
    },
    {
      title: lessonData?.body?.name || t('journal.pl.breadcrumbs.lesson'),
      isCurrentPage: true
    }
  ])
  
  // Создаем ref для отслеживания ранее присутствовавших студентов
  const prevPresentStudentsRef = useRef(new Set<string>())
  
  // Добавляем состояние для отслеживания пульсации
  const [isPulsing, setIsPulsing] = useState(false)
  // Отслеживаем предыдущее количество студентов
  const prevStudentCountRef = useRef(0)
  // Отслеживаем предыдущие реакции для определения новых
  const prevReactionsRef = useRef<Record<string, Reaction[]>>({})
  // Храним актуальные реакции студентов
  const [studentReactions, setStudentReactions] = useState<Record<string, Reaction[]>>({})
  
  const {
    isFetching,
    data: accessCode,
    isSuccess,
    refetch,
  } = api.useCreateAccessCodeQuery(
    { lessonId },
    {
      skip: !isTeacher(user),
      pollingInterval:
        Number(getConfigValue('journal.polling-interval')) || 3000,
      skipPollingIfUnfocused: true,
    },
  )
  const AllStudents = api.useCourseAllStudentsQuery(courseId)
  const [manualAdd, manualAddRqst] = api.useManualAddStudentMutation()
  const userUrl = useMemo(
    () => `${location.origin}/journal/u/${lessonId}/${accessCode?.body?._id}`,
    [accessCode, lessonId],
  )

  // Эффект для обнаружения и обновления новых присутствующих студентов
  useEffect(() => {
    if (accessCode?.body) {
      const currentPresent = new Set(accessCode.body.lesson.students.map(s => s.sub))
      
      // Проверяем, изменилось ли количество студентов
      const currentCount = accessCode.body.lesson.students.length;
      if (prevStudentCountRef.current !== currentCount && prevStudentCountRef.current > 0) {
        // Запускаем эффект пульсации
        setIsPulsing(true);
        // Сбрасываем эффект через 1.5 секунды
        setTimeout(() => {
          setIsPulsing(false);
        }, 1500);
      }
      
      // Обновляем предыдущее количество
      prevStudentCountRef.current = currentCount;
      
      // Очищаем флаги предыдущего состояния после задержки
      const timeoutId = setTimeout(() => {
        prevPresentStudentsRef.current = currentPresent
      }, 3000)
      
      return () => clearTimeout(timeoutId)
    }
  }, [accessCode])

  // Эффект для обработки новых реакций
  useEffect(() => {
    if (accessCode?.body?.lesson?.reactions) {
      const reactions = accessCode.body.lesson.reactions;
      
      // Группируем реакции по sub (идентификатору студента)
      const groupedReactions: Record<string, Reaction[]> = {};
      
      reactions.forEach(reaction => {
        if (!groupedReactions[reaction.sub]) {
          groupedReactions[reaction.sub] = [];
        }
        
        // Добавляем только новые реакции
        const isNewReaction = !prevReactionsRef.current[reaction.sub]?.some(
          r => r._id === reaction._id
        );
        
        if (isNewReaction) {
          groupedReactions[reaction.sub].push(reaction);
        }
      });
      
      // Обновляем отображаемые реакции
      setStudentReactions(groupedReactions);
      
      // Обновляем предыдущие реакции
      prevReactionsRef.current = { ...groupedReactions };
      
      // Сбрасываем отображаемые реакции через некоторое время
      const clearReactionsTimeout = setTimeout(() => {
        setStudentReactions({});
      }, 5000);
      
      return () => clearTimeout(clearReactionsTimeout);
    }
  }, [accessCode?.body?.lesson?.reactions]);

  useEffect(() => {
    if (manualAddRqst.isSuccess) {
      refetch()
    }
  }, [manualAddRqst.isSuccess])

  useEffect(() => {
    if (!isFetching && isSuccess) {
      const generateQRCode = () => {
        if (!canvRef.current) return;
        
        // Получаем текущую ширину канваса, гарантируя квадратный QR-код
        const canvas = canvRef.current;
        const containerWidth = canvas.clientWidth;
        
        // Очищаем canvas перед новой генерацией
        const ctx = canvas.getContext('2d');
        ctx.clearRect(0, 0, canvas.width, canvas.height);
        
        // Устанавливаем одинаковые размеры для ширины и высоты (1:1)
        canvas.width = containerWidth;
        canvas.height = containerWidth;
        
        QRCode.toCanvas(
          canvas,
          userUrl,
          { 
            width: containerWidth,
            margin: 1 // Небольшой отступ для лучшей читаемости
          },
          function (error) {
            if (error) console.error(error)
            console.log('success!')
          },
        )
      }
      
      // Генерируем QR-код
      generateQRCode();
      
      // Перегенерируем при изменении размера окна
      const handleResize = () => {
        generateQRCode();
      };
      
      window.addEventListener('resize', handleResize);
      
      return () => {
        window.removeEventListener('resize', handleResize);
      };
    }
  }, [isFetching, isSuccess, userUrl])

  const studentsArr = useMemo(() => {
    let allStudents: (User & { present?: boolean; recentlyPresent?: boolean })[] = [
      ...(AllStudents.data?.body || []),
    ].map((st) => ({ ...st, present: false, recentlyPresent: false }))
    let presentStudents: (User & { present?: boolean })[] = [
      ...(accessCode?.body.lesson.students || []),
    ]

    // Находим новых студентов по сравнению с предыдущим состоянием
    const currentPresent = new Set(presentStudents.map(s => s.sub))
    const newlyPresent = [...currentPresent].filter(id => !prevPresentStudentsRef.current.has(id))

    while (presentStudents.length) {
      const student = presentStudents.pop()

      const present = allStudents.find((st) => st.sub === student.sub)

      if (present) {
        present.present = true
        present.recentlyPresent = newlyPresent.includes(student.sub)
      } else {
        allStudents.push({ 
          ...student, 
          present: true, 
          recentlyPresent: newlyPresent.includes(student.sub) 
        })
      }
    }

    // Removing the sorting to prevent reordering animation
    return allStudents
  }, [accessCode?.body, AllStudents.data, prevPresentStudentsRef.current])

  // Функция для определения цвета на основе посещаемости
  const getAttendanceColor = (attendance: number, total: number) => {
    const percentage = total > 0 ? (attendance / total) * 100 : 0
    
    if (percentage > 80) return { bg: 'green.100', color: 'green.800', dark: { bg: 'green.800', color: 'green.100' } }
    if (percentage > 60) return { bg: 'teal.100', color: 'teal.800', dark: { bg: 'teal.800', color: 'teal.100' } }
    if (percentage > 40) return { bg: 'yellow.100', color: 'yellow.800', dark: { bg: 'yellow.800', color: 'yellow.100' } }
    if (percentage > 20) return { bg: 'orange.100', color: 'orange.800', dark: { bg: 'orange.800', color: 'orange.100' } }
    return { bg: 'red.100', color: 'red.800', dark: { bg: 'red.800', color: 'red.100' } }
  }

  return (
    <>
      <Container maxW="2280px">
        <VStack align="left">
          <Heading as="h3" mt="4" mb="3">
            {t('journal.pl.lesson.topicTitle')}
          </Heading>
          <Box as="span">{accessCode?.body?.lesson?.name}</Box>
          
        </VStack>
        <Stack spacing="8" direction={{ base: "column", md: "row" }} mt={6}>
          <Box 
            flexShrink={0} 
            alignSelf="flex-start" 
            p={4} 
            borderRadius="xl" 
            bg={colorMode === "light" ? "gray.50" : "gray.700"}
            boxShadow="md"
            position="sticky"
            top="20px"
            zIndex="2"
          ><Box pb={3}>
          {formatDate(accessCode?.body?.lesson?.date, t('journal.pl.lesson.dateFormat'))}{' '}
          {t('journal.pl.common.marked')} - 
          {AllStudents.isSuccess && (
            <Box 
              as="span" 
              px={2} 
              py={1} 
              ml={2}
              borderRadius="md"
              fontWeight="bold"
              bg={getAttendanceColor(
                accessCode?.body?.lesson?.students?.length || 0, 
                AllStudents?.data?.body?.length || 1
              ).bg}
              color={getAttendanceColor(
                accessCode?.body?.lesson?.students?.length || 0, 
                AllStudents?.data?.body?.length || 1
              ).color}
              _dark={{ 
                bg: getAttendanceColor(
                  accessCode?.body?.lesson?.students?.length || 0, 
                  AllStudents?.data?.body?.length || 1
                ).dark.bg, 
                color: getAttendanceColor(
                  accessCode?.body?.lesson?.students?.length || 0, 
                  AllStudents?.data?.body?.length || 1
                ).dark.color 
              }}
              position="relative"
              animation={isPulsing ? "pulse 1.5s ease-in-out" : "none"}
              sx={{
                '@keyframes pulse': {
                  '0%': { transform: 'scale(1)' },
                  '50%': { transform: 'scale(1.15)', boxShadow: '0 0 10px rgba(66, 153, 225, 0.7)' },
                  '100%': { transform: 'scale(1)' }
                }
              }}
            >
              {accessCode?.body?.lesson?.students?.length} / {AllStudents?.data?.body?.length}
            </Box>
          )}
          {!AllStudents.isSuccess && (
            <span> {accessCode?.body?.lesson?.students?.length}</span>
          )}{' '}
          {t('journal.pl.common.people')}
        </Box>
            <a href={userUrl}>
              <QRCanvas ref={canvRef} />
            </a>
          </Box>
          <Box 
            flex={1} 
            p={4} 
            borderRadius="xl" 
            bg={colorMode === "light" ? "gray.50" : "gray.700"}
            boxShadow="md"
          >
            <StudentList>
              {isTeacher(user) && (
                <AnimatePresence initial={false}>
                  {studentsArr.map((student) => (
                    <motion.li
                      key={student.sub}
                      animate={{ 
                        rotateY: student.present ? 0 : 180,
                        boxShadow: student.recentlyPresent 
                          ? ['0 0 0 0 rgba(66, 153, 225, 0)', '0 0 20px 5px rgba(66, 153, 225, 0.7)', '0 0 0 0 rgba(66, 153, 225, 0)'] 
                          : '0 0 0 0 rgba(0, 0, 0, 0)'
                      }}
                      transition={{ 
                        rotateY: { type: "spring", stiffness: 300, damping: 20 },
                        boxShadow: {
                          repeat: student.recentlyPresent ? 3 : 0,
                          duration: 1.5
                        }
                      }}
                      style={{ 
                        transformStyle: "preserve-3d",
                        perspective: "1000px",
                        aspectRatio: "1",
                        width: "100%",
                        display: "block"
                      }}
                    >
                      {/* Front side - visible when present */}
                      <Box 
                        position="relative" 
                        width="100%" 
                        height="100%"
                        style={{
                          transformStyle: "preserve-3d"
                        }}
                      >
                        <Box
                          position="absolute"
                          top="0"
                          left="0"
                          width="100%"
                          height="100%"
                          style={{
                            backfaceVisibility: "hidden",
                            transform: "rotateY(0deg)",
                            zIndex: student.present ? 1 : 0
                          }}
                        >
                          <UserCard
                            wrapperAS="div"
                            student={student}
                            present={student.present}
                            recentlyPresent={student.recentlyPresent}
                            onAddUser={(user: User) => manualAdd({ lessonId, user })}
                            reactions={studentReactions[student.sub] || []}
                          />
                        </Box>
                        
                        {/* Back side - visible when not present */}
                        <Flex
                          position="absolute"
                          top="0"
                          left="0"
                          width="100%"
                          height="100%"
                          bg={colorMode === "light" ? "gray.100" : "gray.600"}
                          borderRadius="12px"
                          align="center"
                          justify="center"
                          p={4}
                          overflow="hidden"
                          style={{
                            backfaceVisibility: "hidden",
                            transform: "rotateY(180deg)",
                            zIndex: student.present ? 0 : 1,
                            aspectRatio: "1"
                          }}
                        >
                          <Box 
                            position="absolute"
                            top="0"
                            left="0"
                            right="0"
                            bottom="0"
                            opacity="0.2"
                            className="animated-bg"
                            sx={{
                              background: `linear-gradient(135deg, 
                                ${colorMode === "light" ? "#e3f2fd, #bbdefb, #90caf9" : "#1a365d, #2a4365, #2c5282"})`,
                              backgroundSize: "400% 400%",
                              animation: "gradientAnimation 8s ease infinite",
                              "@keyframes gradientAnimation": {
                                "0%": { backgroundPosition: "0% 50%" },
                                "50%": { backgroundPosition: "100% 50%" },
                                "100%": { backgroundPosition: "0% 50%" }
                              }
                            }}
                          />
                          <Box 
                            position="relative" 
                            textAlign="center"
                            zIndex="1"
                          >
                            <Box 
                              width="60px" 
                              height="60px" 
                              mx="auto" 
                              mb={2}
                              sx={{
                                animation: "float 3s ease-in-out infinite",
                                "@keyframes float": {
                                  "0%": { transform: "translateY(0px)" },
                                  "50%": { transform: "translateY(-10px)" },
                                  "100%": { transform: "translateY(0px)" }
                                }
                              }}
                            >
                              <svg viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
                                {/* Академическая шапочка */}
                                <path 
                                  d="M12 2L2 6.5L12 11L22 6.5L12 2Z" 
                                  fill={colorMode === "light" ? "#3182CE" : "#63B3ED"}
                                />
                                <path 
                                  d="M19 9V14.5C19 15.163 18.6839 15.7989 18.1213 16.2678C17.0615 17.1301 13.7749 19 12 19C10.2251 19 6.93852 17.1301 5.87868 16.2678C5.31607 15.7989 5 15.163 5 14.5V9L12 12.5L19 9Z" 
                                  fill={colorMode === "light" ? "#2C5282" : "#4299E1"}
                                />
                                <path 
                                  d="M21 7V14M21 14L19 16M21 14L23 16" 
                                  stroke={colorMode === "light" ? "#2C5282" : "#4299E1"}
                                  strokeWidth="1.5"
                                  strokeLinecap="round"
                                  strokeLinejoin="round"
                                />
                                
                                {/* Лицо студента */}
                                <circle 
                                  cx="12" 
                                  cy="15" 
                                  r="2.5" 
                                  fill={colorMode === "light" ? "#3182CE" : "#63B3ED"}
                                />
                                
                                {/* Тело студента */}
                                <path 
                                  d="M8 18.5C8 17.1193 9.11929 16 10.5 16H13.5C14.8807 16 16 17.1193 16 18.5V21H8V18.5Z" 
                                  fill={colorMode === "light" ? "#3182CE" : "#63B3ED"}
                                />
                              </svg>
                            </Box>
                            <Box fontSize="sm" fontWeight="medium">
                              {student.name || student.preferred_username}
                            </Box>
                            <Box 
                              fontSize="xs" 
                              opacity={0.8}
                              color={colorMode === "light" ? "gray.600" : "gray.300"}
                            >
                              {t('journal.pl.lesson.notMarked')}
                            </Box>
                          </Box>
                        </Flex>
                      </Box>
                    </motion.li>
                  ))}
                </AnimatePresence>
              )}
            </StudentList>
          </Box>
        </Stack>
      </Container>
    </>
  )
}

export default LessonDetail
