"use client";

import React, { useState, useEffect, useRef } from "react";
import { X, ChevronLeft, ChevronRight } from "lucide-react";
import {
  parseDateString,
  formatGroupsToInput,
  formatGroupsToPDFMonkey,
  hasMultipleMoons,
  convertIsoDatesToGroups,
  formatDateFr,
  parseFrenchedDate,
} from "@/lib/dateFormatter";

interface DatePickerCalendarProps {
  isOpen: boolean;
  onClose: () => void;
  onApply: (result: {
    selectedDates: string[]; // format input "12/10, 13/10, ..."
    hasMultiMonth: boolean;
    pdfFormatted: string; // "le 12/10 ; du 14/10 au 17/10."
  }) => void;
  initialDates?: string[]; // format input "12/10, 13/10, ..."
  title: string;
  minDate?: string; // "2025-10-01"
  maxDate?: string; // "2025-10-31"
}

export default function DatePickerCalendar({
  isOpen,
  onClose,
  onApply,
  initialDates = [],
  title,
  minDate,
  maxDate,
}: DatePickerCalendarProps) {
  const [selectedIsos, setSelectedIsos] = useState<string[]>([]);
  const [currentMonth, setCurrentMonth] = useState(new Date());
  const [position, setPosition] = useState<{ x: number; y: number } | null>(null);
  const [isDragging, setIsDragging] = useState(false);
  const [dragOffset, setDragOffset] = useState({ x: 0, y: 0 });
  const modalRef = useRef<HTMLDivElement>(null);
  const prevIsOpenRef = useRef(isOpen);

  // Initialiser avec les dates initiales
  useEffect(() => {
    // Vérifier si la modale vient de s'ouvrir (transition de false à true)
    const justOpened = isOpen && !prevIsOpenRef.current;
    prevIsOpenRef.current = isOpen;

    if (justOpened) {
      if (initialDates.length > 0) {
        // Convertir format input "12/10" en ISO
        // On utilise le minDate ou maxDate comme contexte d'année
        const yearContext = minDate || maxDate || new Date().toISOString().slice(0, 10);
        const isos = initialDates
          .map(d => parseFrenchedDate(d.trim(), yearContext))
          .filter(iso => iso.length === 10);
        setSelectedIsos(isos);

        // Mettre le calendrier sur le premier mois
        if (isos.length > 0) {
          const firstDate = new Date(isos[0] + "T00:00:00Z");
          setCurrentMonth(firstDate);
        }
      } else {
        // Réinitialiser les sélections si pas de dates initiales
        setSelectedIsos([]);
        if (minDate) {
          // Si pas de dates initiales, utiliser la date de début du contrat
          const startDate = new Date(minDate + "T00:00:00Z");
          setCurrentMonth(startDate);
        }
      }
    }
  }, [isOpen, initialDates, minDate, maxDate]);

  // Initialiser la position au centre
  useEffect(() => {
    if (isOpen && position === null) {
      const centerX = (typeof window !== "undefined" ? window.innerWidth : 1024) - 450;
      const centerY = Math.max(20, ((typeof window !== "undefined" ? window.innerHeight : 768) - 500) * 0.4);
      setPosition({ x: Math.max(20, centerX), y: centerY });
    }
  }, [isOpen, position]);

  const handleMouseDown = (e: React.MouseEvent<HTMLDivElement>) => {
    if (!position || !modalRef.current) return;
    setIsDragging(true);
    setDragOffset({
      x: e.clientX - position.x,
      y: e.clientY - position.y,
    });
  };

  useEffect(() => {
    const handleMouseMove = (e: MouseEvent) => {
      if (!isDragging || !position) return;
      setPosition({
        x: e.clientX - dragOffset.x,
        y: e.clientY - dragOffset.y,
      });
    };

    const handleMouseUp = () => {
      setIsDragging(false);
    };

    if (isDragging) {
      document.addEventListener("mousemove", handleMouseMove);
      document.addEventListener("mouseup", handleMouseUp);
    }

    return () => {
      document.removeEventListener("mousemove", handleMouseMove);
      document.removeEventListener("mouseup", handleMouseUp);
    };
  }, [isDragging, dragOffset, position]);

  const handleDateClick = (day: number) => {
    // Créer la date en UTC pour éviter les décalages de fuseau horaire
    const isoStr = new Date(Date.UTC(currentMonth.getFullYear(), currentMonth.getMonth(), day))
      .toISOString()
      .slice(0, 10);

    if (isDateOutOfRange(isoStr)) return;

    setSelectedIsos(prev => {
      if (prev.includes(isoStr)) {
        return prev.filter(d => d !== isoStr);
      } else {
        return [...prev, isoStr].sort();
      }
    });
  };

  const isDateOutOfRange = (isoStr: string): boolean => {
    if (minDate && isoStr < minDate) return true;
    if (maxDate && isoStr > maxDate) return true;
    return false;
  };

  const isDateSelected = (day: number): boolean => {
    // Créer la date en UTC
    const isoStr = new Date(Date.UTC(currentMonth.getFullYear(), currentMonth.getMonth(), day))
      .toISOString()
      .slice(0, 10);
    return selectedIsos.includes(isoStr);
  };

  const isDateDisabled = (day: number): boolean => {
    // Créer la date en UTC
    const isoStr = new Date(Date.UTC(currentMonth.getFullYear(), currentMonth.getMonth(), day))
      .toISOString()
      .slice(0, 10);
    return isDateOutOfRange(isoStr);
  };

  const getDaysInMonth = (date: Date) => {
    return new Date(date.getFullYear(), date.getMonth() + 1, 0).getDate();
  };

  const getFirstDayOfMonth = (date: Date) => {
    return new Date(date.getFullYear(), date.getMonth(), 1).getDay();
  };

  const renderCalendar = () => {
    const daysInMonth = getDaysInMonth(currentMonth);
    const firstDay = getFirstDayOfMonth(currentMonth);
    const days: (number | null)[] = Array(firstDay === 0 ? 6 : firstDay - 1).fill(null);

    for (let i = 1; i <= daysInMonth; i++) {
      days.push(i);
    }

    return days;
  };

  const handleApply = () => {
    if (selectedIsos.length === 0) {
      onApply({
        selectedDates: [],
        hasMultiMonth: false,
        pdfFormatted: "",
      });
      onClose();
      return;
    }

    // Convertir en format input (DD/MM)
    const inputFormat = selectedIsos.map(iso => formatDateFr(iso)).join(", ");

    // Détecter multi-mois
    const isMultiMonth = hasMultipleMoons(selectedIsos);

    // Générer les groupes et formatter pour PDFMonkey
    const groups = convertIsoDatesToGroups(selectedIsos);
    const pdfFormatted = groups.map(g => g.displayFr).join(" ; ") + ".";

    onApply({
      selectedDates: inputFormat.split(", "),
      hasMultiMonth: isMultiMonth,
      pdfFormatted,
    });

    onClose();
  };

  const handleReset = () => {
    setSelectedIsos([]);
  };

  if (!isOpen) return null;

  const monthName = currentMonth.toLocaleDateString("fr-FR", { month: "long", year: "numeric" });
  const daysArray = renderCalendar();
  const dayNames = ["Lun", "Mar", "Mer", "Jeu", "Ven", "Sam", "Dim"];

  return (
    <>
      {/* Overlay semi-transparent */}
      <div
        className="fixed inset-0 bg-black/50 z-[100]"
        onClick={(e) => {
          e.stopPropagation();
          onClose();
        }}
      />

      {/* Modale draggable */}
      <div
        ref={modalRef}
        className="fixed z-[101] w-[420px] bg-white rounded-2xl shadow-2xl flex flex-col overflow-hidden"
        style={{
          left: position?.x || 0,
          top: position?.y || 0,
          cursor: isDragging ? "grabbing" : "grab",
        }}
        onClick={(e) => e.stopPropagation()}
      >
        {/* Header draggable */}
        <div
          onMouseDown={handleMouseDown}
          className="flex items-center justify-between p-4 bg-gradient-to-r from-indigo-50 to-purple-50 border-b cursor-grab active:cursor-grabbing"
        >
          <h2 className="text-lg font-semibold text-slate-900">{title}</h2>
          <button
            onClick={onClose}
            className="p-1 hover:bg-white/50 rounded-lg transition"
          >
            <X className="w-5 h-5 text-slate-500" />
          </button>
        </div>

        {/* Contenu */}
        <div className="flex-1 overflow-y-auto p-4 space-y-4">
          {/* Navigation mois */}
          <div className="flex items-center justify-between">
            <button
              onClick={() => setCurrentMonth(new Date(currentMonth.getFullYear(), currentMonth.getMonth() - 1))}
              className="p-2 hover:bg-slate-100 rounded-lg transition"
            >
              <ChevronLeft className="w-4 h-4" />
            </button>
            <span className="text-sm font-semibold text-slate-700 capitalize">{monthName}</span>
            <button
              onClick={() => setCurrentMonth(new Date(currentMonth.getFullYear(), currentMonth.getMonth() + 1))}
              className="p-2 hover:bg-slate-100 rounded-lg transition"
            >
              <ChevronRight className="w-4 h-4" />
            </button>
          </div>

          {/* Calendrier */}
          <div className="grid grid-cols-7 gap-1">
            {/* Headers des jours */}
            {dayNames.map(day => (
              <div key={day} className="text-center text-xs font-semibold text-slate-500 py-2">
                {day}
              </div>
            ))}

            {/* Jours */}
            {daysArray.map((day, idx) => (
              <div key={idx}>
                {day === null ? (
                  <div />
                ) : (
                  <button
                    onClick={() => handleDateClick(day)}
                    disabled={isDateDisabled(day)}
                    className={`
                      w-full aspect-square rounded-lg text-sm font-medium transition
                      ${isDateDisabled(day)
                        ? "bg-slate-100 text-slate-300 cursor-not-allowed"
                        : isDateSelected(day)
                          ? "bg-indigo-600 text-white hover:bg-indigo-700"
                          : "bg-white text-slate-700 hover:bg-indigo-50 border border-slate-200"
                      }
                    `}
                  >
                    {day}
                  </button>
                )}
              </div>
            ))}
          </div> 

          {/* Sélection actuelle */}
          {selectedIsos.length > 0 && (
            <div className="bg-slate-50 rounded-lg p-3 border border-slate-200">
              <p className="text-xs font-semibold text-slate-600 mb-2">Dates sélectionnées :</p>
              <div className="text-sm text-slate-700 leading-relaxed">
                {selectedIsos.map(iso => formatDateFr(iso)).join(", ")}
              </div>
              {hasMultipleMoons(selectedIsos) && (
                <p className="text-xs text-amber-700 mt-2 bg-amber-50 p-2 rounded border border-amber-200">
                  Attention : multi-mois détecté (le champ sera auto-set à "Oui")
                </p>
              )}
            </div>
          )}

        </div>

        {/* Footer avec boutons */}
        <div className="border-t p-4 bg-slate-50 flex items-center gap-2">
          {selectedIsos.length > 0 && (
            <button
              onClick={handleReset}
              className="px-3 py-2 text-sm rounded-lg border border-slate-300 text-slate-700 hover:bg-slate-100 transition"
            >
              Réinitialiser
            </button>
          )}
          <button
            onClick={onClose}
            className="px-3 py-2 text-sm rounded-lg border border-slate-300 text-slate-700 hover:bg-slate-100 transition ml-auto"
          >
            Annuler
          </button>
          <button
            onClick={handleApply}
            disabled={selectedIsos.length === 0}
            className={`
              px-4 py-2 text-sm font-semibold rounded-lg transition
              ${selectedIsos.length === 0
                ? "bg-slate-200 text-slate-400 cursor-not-allowed"
                : "bg-indigo-600 text-white hover:bg-indigo-700"
              }
            `}
          >
            Appliquer ({selectedIsos.length})
          </button>
        </div>
      </div>
    </>
  );
}
