import {
  Trash2,
  Edit3,
  ZoomIn,
  Users,
  Check,
  X,
  Hand,
  Download,
  Plus,
} from 'lucide-react';
import React, { useState, useEffect, useMemo } from 'react';
import Table from '@/components/Table';
import Popup from '@/components/Popup';
import InputText from '@/components/Form/InputText';
import SelectChoice from '@/components/Form/SelectChoice';
import TeacherItem from '@/components/Structure/Configuration/TeacherItem';
import MultiSelect from '@/components/Form/MultiSelect';
import LevelLabel from '@/components/CustomLabels/LevelLabel';
import { DndProvider, useDrop } from 'react-dnd';
import { HTML5Backend } from 'react-dnd-html5-backend';
import logger from '@/utils/logger';
import SectionHeader from '@/components/SectionHeader';
import { useEstablishment } from '@/context/EstablishmentContext';
import { FE_ADMIN_STRUCTURE_SCHOOLCLASS_MANAGEMENT_URL } from '@/utils/Url';
import { usePlanning } from '@/context/PlanningContext';
import { useClasses } from '@/context/ClassesContext';
import { useRouter } from 'next/navigation';
import EmptyState from '@/components/EmptyState';
import { getCurrentSchoolYear, getNextSchoolYear } from '@/utils/Date';
import { exportToCSV } from '@/utils/exportCSV';

const ItemTypes = {
  TEACHER: 'teacher',
};

const CLASS_PLANNING_COLORS = [
  '#EF4444',
  '#3B82F6',
  '#F59E0B',
  '#8B5CF6',
  '#EC4899',
  '#14B8A6',
  '#F97316',
  '#6366F1',
  '#06B6D4',
  '#84CC16',
];

const getClassPlanningColor = (schoolClass) => {
  const numericId = Number(schoolClass?.id);
  if (!Number.isFinite(numericId) || numericId <= 0) {
    return CLASS_PLANNING_COLORS[0];
  }

  const index = (numericId - 1) % CLASS_PLANNING_COLORS.length;
  return CLASS_PLANNING_COLORS[index];
};

const TeachersDropZone = ({
  classe,
  handleTeachersChange,
  teachers,
  isEditing,
}) => {
  const [localTeachers, setLocalTeachers] = useState(
    classe.teachers_details || []
  );

  useEffect(() => {}, [teachers]);

  useEffect(() => {
    setLocalTeachers(classe.teachers_details || []);
  }, [classe.teachers_details]);

  useEffect(() => {
    handleTeachersChange(localTeachers.map((teacher) => teacher.id));
  }, [localTeachers]);

  const [{ isOver, canDrop }, drop] = useDrop({
    accept: ItemTypes.TEACHER,
    drop: (item) => {
      const teacherDetails = teachers.find((teacher) => teacher.id === item.id);
      const exists = localTeachers.some((teacher) => teacher.id === item.id);
      if (!exists) {
        setLocalTeachers((prevTeachers) => {
          const updatedTeachers = [
            ...prevTeachers,
            {
              id: item.id,
              last_name: teacherDetails.last_name,
              first_name: teacherDetails.first_name,
            },
          ];
          return updatedTeachers;
        });
      }
    },
    collect: (monitor) => ({
      isOver: !!monitor.isOver(),
      canDrop: !!monitor.canDrop(),
    }),
    canDrop: () => {
      return isEditing;
    },
  });

  const handleRemoveTeacher = (id) => {
    setLocalTeachers((prevTeachers) => {
      const updatedTeachers = prevTeachers.filter(
        (teacher) => teacher.id !== id
      );
      return updatedTeachers;
    });
  };

  return (
    <div
      ref={drop}
      className={`p-2 rounded-md flex flex-col items-center ${isEditing ? 'border-2 border-dashed border-blue-500 bg-blue-50' : ''} ${
        isOver && canDrop ? 'border-2 border-solid border-blue-300' : ''
      }`}
    >
      {isEditing && (
        <div className="mb-2 text-blue-500 font-semibold flex items-center space-x-2">
          <Hand className="w-5 h-5" /> {/* Ajoutez l'icône Hand */}
          <span>Déposez un enseignant ici</span>
        </div>
      )}
      {localTeachers.map((teacher, index) => (
        <div
          key={`${teacher.id}-${index}`}
          className="flex items-center space-x-2 mb-2"
        >
          <TeacherItem key={teacher.id} teacher={teacher} isDraggable={false} />
          {isEditing && (
            <button
              type="button"
              onClick={() => handleRemoveTeacher(teacher.id)}
              className="text-red-500 hover:text-red-700"
            >
              <X className="w-4 h-4" />
            </button>
          )}
        </div>
      ))}
    </div>
  );
};

const ClassesSection = ({
  classes,
  allClasses,
  setClasses,
  teachers,
  handleCreate,
  handleEdit,
  handleDelete,
}) => {
  const [formData, setFormData] = useState({});
  const [editingClass, setEditingClass] = useState(null);
  const [newClass, setNewClass] = useState(null);
  const [localErrors, setLocalErrors] = useState({});
  const [popupVisible, setPopupVisible] = useState(false);
  const [popupMessage, setPopupMessage] = useState('');
  const [removePopupVisible, setRemovePopupVisible] = useState(false);
  const [removePopupMessage, setRemovePopupMessage] = useState('');
  const [removePopupOnConfirm, setRemovePopupOnConfirm] = useState(() => {});
  const ITEMS_PER_PAGE = 10;
  const [currentPage, setCurrentPage] = useState(1);

  // Les classes arrivent déjà filtrées depuis le parent
  useEffect(() => {
    setCurrentPage(1);
  }, [classes]);
  useEffect(() => {
    if (newClass) setCurrentPage(1);
  }, [newClass]);
  const totalPages = Math.ceil(classes.length / ITEMS_PER_PAGE);
  const pagedClasses = classes.slice(
    (currentPage - 1) * ITEMS_PER_PAGE,
    currentPage * ITEMS_PER_PAGE
  );
  const { selectedEstablishmentId, profileRole } = useEstablishment();
  const { addSchedule, reloadPlanning, reloadEvents } = usePlanning();
  const { getNiveauxLabels, getNiveauLabel, allNiveaux } = useClasses();
  const router = useRouter();

  // Fonction pour générer les années scolaires
  const getSchoolYearChoices = () => {
    const currentDate = new Date();
    const currentYear = currentDate.getFullYear();
    const currentMonth = currentDate.getMonth() + 1; // Les mois sont indexés à partir de 0

    // Si nous sommes avant septembre, l'année scolaire en cours a commencé l'année précédente
    const startYear = currentMonth >= 9 ? currentYear : currentYear - 1;

    const choices = [];
    for (let i = 0; i < 3; i++) {
      const year = startYear + i;
      choices.push({
        value: `${year}-${year + 1}`,
        label: `${year}-${year + 1}`,
      });
    }
    return choices;
  };

  // Récupération des messages d'erreur
  const getError = (field) => {
    return localErrors?.[field]?.[0];
  };

  const handleAddClass = () => {
    setNewClass({
      id: Date.now(),
      atmosphere_name: '',
      age_range: '',
      levels: [],
      number_of_students: null,
      school_year: '',
      teachers: [],
      establishment: selectedEstablishmentId,
    });
    setFormData({
      atmosphere_name: '',
      age_range: '',
      levels: [],
      number_of_students: null,
      school_year: '',
      teachers: [],
      establishment: selectedEstablishmentId,
    });
  };

  // Export CSV
  const handleExportCSV = () => {
    const exportColumns = [
      { key: 'id', label: 'ID' },
      { key: 'atmosphere_name', label: "Nom d'ambiance" },
      { key: 'age_range', label: "Tranche d'âge" },
      {
        key: 'levels',
        label: 'Niveaux',
        transform: (value) =>
          value ? value.map((l) => getNiveauLabel(l)).join(', ') : '',
      },
      { key: 'number_of_students', label: 'Capacité max' },
      { key: 'school_year', label: 'Année scolaire' },
      {
        key: 'teachers_details',
        label: 'Enseignants',
        transform: (value) =>
          value
            ? value.map((t) => `${t.last_name} ${t.first_name}`).join(', ')
            : '',
      },
      { key: 'updated_date_formatted', label: 'Date de mise à jour' },
    ];
    const filename = `classes_${new Date().toISOString().split('T')[0]}`;
    exportToCSV(classes, exportColumns, filename);
  };

  const handleChange = (e) => {
    const { name, value } = e.target;

    if (editingClass) {
      setFormData((prevData) => ({
        ...prevData,
        [name]: value,
      }));
    } else if (newClass) {
      setNewClass((prevData) => ({
        ...prevData,
        [name]: value,
      }));
    }
  };

  const handleSaveNewClass = () => {
    if (
      newClass.atmosphere_name &&
      newClass.levels.length > 0 &&
      newClass.school_year
    ) {
      handleCreate(newClass)
        .then((createdClass) => {
          setClasses((prevClasses) => [createdClass, ...classes]);
          setNewClass(null);
          setLocalErrors({});
          // Creation des plannings associé à la classe
          const classPlanningColor = getClassPlanningColor(createdClass);

          createdClass.levels.forEach((level) => {
            const levelName = allNiveaux.find((lvl) => lvl.id === level)?.name;
            const planningName = `${createdClass.atmosphere_name} - ${levelName}`;
            const newPlanning = {
              name: planningName,
              color: classPlanningColor,
              school_class: createdClass.id,
            };
            addSchedule(newPlanning);
          });
        })
        .catch((error) => {
          logger.error('Error:', error.message);
          if (error.details) {
            logger.error('Form errors:', error.details);
            setLocalErrors(error.details);
          }
        });
    } else {
      setPopupMessage('Tous les champs doivent être remplis et valides');
      setPopupVisible(true);
    }
  };

  const handleUpdateClass = (id, updatedData) => {
    if (
      updatedData.atmosphere_name &&
      updatedData.levels.length > 0 &&
      updatedData.school_year
    ) {
      handleEdit(id, updatedData)
        .then((updatedClass) => {
          setClasses((prevClasses) =>
            prevClasses.map((classe) =>
              classe.id === id ? updatedClass : classe
            )
          );
          setEditingClass(null);
          setFormData({});
          setLocalErrors({});
        })
        .catch((error) => {
          logger.error('Error:', error.message);
          if (error.details) {
            logger.error('Form errors:', error.details);
            setLocalErrors(error.details);
          }
        });
    } else {
      setPopupMessage('Tous les champs doivent être remplis et valides');
      setPopupVisible(true);
    }
  };

  const handleTeachersChange = (selectedTeachers) => {
    if (editingClass) {
      setFormData((prevData) => ({
        ...prevData,
        teachers: selectedTeachers,
      }));
    } else if (newClass) {
      setNewClass((prevData) => ({
        ...prevData,
        teachers: selectedTeachers,
      }));
      setFormData((prevData) => ({
        ...prevData,
        teachers: selectedTeachers,
      }));
    }
  };

  const handleMultiSelectChange = (selectedOptions) => {
    const levels = selectedOptions.map((option) => option.id);

    if (editingClass) {
      setFormData((prevData) => ({
        ...prevData,
        levels,
      }));
    } else if (newClass) {
      setNewClass((prevData) => ({
        ...prevData,
        levels,
      }));
      setFormData((prevData) => ({
        ...prevData,
        levels,
      }));
    }
  };

  const renderClassCell = (classe, column) => {
    const isEditing = editingClass === classe.id;
    const isCreating = newClass && newClass.id === classe.id;
    const currentData = isEditing ? formData : newClass || {};

    if (isEditing || isCreating) {
      switch (column) {
        case 'AMBIANCE':
          return (
            <InputText
              name="atmosphere_name"
              value={currentData.atmosphere_name}
              onChange={handleChange}
              placeholder="Nom d'ambiance"
              errorMsg={getError('atmosphere_name')}
            />
          );
        case "TRANCHE D'AGE":
          return (
            <InputText
              name="age_range"
              value={currentData.age_range}
              onChange={handleChange}
              placeholder="Tranche d'âge (ex: 3-6)"
              errorMsg={getError('age_range')}
            />
          );
        case 'NIVEAUX':
          return (
            <MultiSelect
              name="levels"
              label="Sélection de niveaux"
              options={allNiveaux}
              selectedOptions={
                currentData.levels
                  ? currentData.levels.map((levelId) =>
                      allNiveaux.find((level) => level.id === levelId)
                    )
                  : []
              }
              onChange={handleMultiSelectChange}
              errorMsg={getError('levels')}
            />
          );
        case 'CAPACITE':
          return (
            <InputText
              name="number_of_students"
              type="number"
              value={currentData.number_of_students}
              onChange={handleChange}
              placeholder="Capacité"
              errorMsg={getError('number_of_students')}
            />
          );
        case 'ANNÉE SCOLAIRE':
          return (
            <SelectChoice
              type="select"
              name="school_year"
              placeHolder="Sélectionnez une année scolaire"
              choices={getSchoolYearChoices()}
              callback={handleChange}
              selected={currentData.school_year || ''}
              errorMsg={getError('school_year')}
              IconItem={null}
              disabled={false}
            />
          );
        case 'ENSEIGNANTS':
          return (
            <TeachersDropZone
              classe={currentData}
              handleTeachersChange={handleTeachersChange}
              teachers={teachers}
              isEditing={isEditing || isCreating}
            />
          );
        case 'ACTIONS':
          return (
            <div className="flex justify-center space-x-2">
              <button
                type="button"
                onClick={() =>
                  isEditing
                    ? handleUpdateClass(editingClass, formData)
                    : handleSaveNewClass()
                }
                className="text-primary hover:text-secondary"
              >
                <Check className="w-5 h-5" />
              </button>
              <button
                type="button"
                onClick={() =>
                  isEditing ? setEditingClass(null) : setNewClass(null)
                }
                className="text-red-500 hover:text-red-700"
              >
                <X className="w-5 h-5" />
              </button>
            </div>
          );
        default:
          return null;
      }
    } else {
      switch (column) {
        case 'AMBIANCE':
          return classe.atmosphere_name;
        case "TRANCHE D'AGE":
          return classe.age_range;
        case 'NIVEAUX':
          const levelLabels = Array.isArray(classe.levels)
            ? getNiveauxLabels(classe.levels.sort((a, b) => a - b)) // Trier les niveaux par ordre croissant
            : [];
          return (
            <div className="flex flex-wrap justify-center items-center space-x-2">
              {levelLabels.length > 0
                ? levelLabels.map((label, index) => (
                    <LevelLabel key={index} label={label} index={index} />
                  ))
                : 'Aucun niveau'}
            </div>
          );
        case 'CAPACITE':
          return classe.number_of_students;
        case 'ANNÉE SCOLAIRE':
          return classe.school_year;
        case 'ENSEIGNANTS':
          return (
            <div className="flex justify-center space-x-2 flex-wrap">
              {classe.teachers_details.map((teacher) => (
                <TeacherItem
                  key={teacher.id}
                  teacher={teacher}
                  isDraggable={false}
                />
              ))}
            </div>
          );
        case 'MISE A JOUR':
          return classe.updated_date_formatted;
        case 'ACTIONS':
          // Affichage des actions en mode affichage (hors édition/création)
          if (profileRole === 0) {
            // Si professeur, uniquement le bouton ZoomIn
            return (
              <div className="flex justify-center space-x-2">
                <button
                  type="button"
                  onClick={() => {
                    const url = `${FE_ADMIN_STRUCTURE_SCHOOLCLASS_MANAGEMENT_URL}?schoolClassId=${classe.id}`;
                    router.push(`${url}`);
                  }}
                  className="text-gray-500 hover:text-gray-700"
                >
                  <ZoomIn className="w-5 h-5" />
                </button>
              </div>
            );
          }
          // Sinon, toutes les actions (admin)
          return (
            <div className="flex justify-center space-x-2">
              <button
                type="button"
                onClick={() =>
                  setEditingClass(classe.id) || setFormData(classe)
                }
                className="text-blue-500 hover:text-blue-700"
              >
                <Edit3 className="w-5 h-5" />
              </button>
              <button
                type="button"
                onClick={() => {
                  setRemovePopupVisible(true);
                  setRemovePopupMessage(
                    'Attention ! \nVous êtes sur le point de supprimer la classe ' +
                      classe.atmosphere_name +
                      ".\nÊtes-vous sûr(e) de vouloir poursuivre l'opération ?"
                  );
                  setRemovePopupOnConfirm(() => () => {
                    handleDelete(classe.id)
                      .then((data) => {
                        logger.debug('Success:', data);
                        setPopupMessage(
                          'La classe ' +
                            classe.atmosphere_name +
                            ' a été correctement supprimée'
                        );
                        setPopupVisible(true);
                        setRemovePopupVisible(false);
                        reloadPlanning();
                        reloadEvents();
                      })
                      .catch((error) => {
                        logger.error('Error archiving data:', error);
                        setPopupMessage(
                          'Erreur lors de la suppression de la classe  ' +
                            classe.atmosphere_name
                        );
                        setPopupVisible(true);
                        setRemovePopupVisible(false);
                      });
                  });
                }}
                className="text-red-500 hover:text-red-700"
              >
                <Trash2 className="w-5 h-5" />
              </button>
              <button
                type="button"
                onClick={() => {
                  const url = `${FE_ADMIN_STRUCTURE_SCHOOLCLASS_MANAGEMENT_URL}?schoolClassId=${classe.id}`;
                  router.push(`${url}`);
                }}
                className="text-gray-500 hover:text-gray-700"
              >
                <ZoomIn className="w-5 h-5" />
              </button>
            </div>
          );
        default:
          return null;
      }
    }
  };

  const columns = [
    { name: 'AMBIANCE', label: "Nom d'ambiance" },
    { name: "TRANCHE D'AGE", label: "Tranche d'âge" },
    { name: 'NIVEAUX', label: 'Niveaux' },
    { name: 'CAPACITE', label: 'Capacité max' },
    { name: 'ANNÉE SCOLAIRE', label: 'Année scolaire' },
    { name: 'ENSEIGNANTS', label: 'Enseignants' },
    { name: 'MISE A JOUR', label: 'Date mise à jour' },
    { name: 'ACTIONS', label: 'Actions' },
  ];

  return (
    <DndProvider backend={HTML5Backend}>
      <div className="space-y-4">
        {(pagedClasses.length > 0 || newClass) && (
          <SectionHeader
            icon={Users}
            title="Liste des classes"
            description="Gérez les classes de votre école"
            button={profileRole !== 0}
            onClick={handleAddClass}
            secondaryButton={
              <button
                onClick={handleExportCSV}
                className="flex items-center gap-2 px-4 py-2 text-sm font-medium text-secondary bg-primary/10 rounded-lg hover:bg-primary/20 transition-colors"
                title="Exporter en CSV"
              >
                <Download className="w-4 h-4" />
                Exporter
              </button>
            }
          />
        )}
        <Table
          data={newClass ? [newClass, ...pagedClasses] : pagedClasses}
          columns={columns}
          renderCell={renderClassCell}
          emptyMessage={
            <EmptyState
              icon={Users}
              title="Aucune classe enregistrée"
              description="Ajoutez une classe pour organiser vos niveaux, enseignants et emplois du temps."
              actionLabel={profileRole !== 0 ? 'Ajouter une classe' : undefined}
              onAction={profileRole !== 0 ? handleAddClass : undefined}
              actionIcon={profileRole !== 0 ? Plus : undefined}
            />
          }
          itemsPerPage={ITEMS_PER_PAGE}
          currentPage={currentPage}
          totalPages={totalPages}
          onPageChange={setCurrentPage}
        />
        <Popup
          isOpen={popupVisible}
          message={popupMessage}
          onConfirm={() => setPopupVisible(false)}
          onCancel={() => setPopupVisible(false)}
          uniqueConfirmButton={true}
        />
        <Popup
          isOpen={removePopupVisible}
          message={removePopupMessage}
          onConfirm={removePopupOnConfirm}
          onCancel={() => setRemovePopupVisible(false)}
        />
      </div>
    </DndProvider>
  );
};

export default ClassesSection;
