"use client";

import React, { useState, useCallback, useEffect } from "react";
import { X, ChevronLeft, ChevronRight, Check } from "lucide-react";
import * as Dialog from "@radix-ui/react-dialog";
import { cn } from "@/lib/utils";

export interface TourStep {
  /**
   * Identifiant unique de l'étape
   */
  id: string;
  /**
   * Titre de l'étape
   */
  title: string;
  /**
   * Contenu de l'étape
   */
  content: string | React.ReactNode;
  /**
   * Sélecteur CSS de l'élément à highlighter
   * @example "#file-uploader", ".tab-button", "[data-tab='correlation']"
   */
  target?: string;
  /**
   * Position du tooltip par rapport à la cible
   * @default "bottom"
   */
  position?: "top" | "bottom" | "left" | "right" | "center";
  /**
   * Image optionnelle pour illustrer l'étape
   */
  image?: string;
  /**
   * Action optionnelle à exécuter quand l'étape est affichée
   */
  onEnter?: () => void;
  /**
   * Action optionnelle à exécuter quand l'étape est quittée
   */
  onExit?: () => void;
}

interface TourGuideProps {
  /**
   * Étapes du tour
   */
  steps: TourStep[];
  /**
   * Contrôle l'ouverture du tour
   */
  open?: boolean;
  /**
   * Callback lors de la fermeture
   */
  onOpenChange?: (open: boolean) => void;
  /**
   * Callback à la fin du tour
   */
  onComplete?: () => void;
  /**
   * Callback quand une étape est_skippée
   */
  onSkip?: () => void;
  /**
   * Texte du bouton de fin
   * @default "Compris !"
   */
  completeButtonText?: string;
  /**
   * Texte du bouton pour passer
   * @default "Passer"
   */
  skipButtonText?: string;
  /**
   * Si true, affiche une barre de progression
   * @default true
   */
  showProgress?: boolean;
  /**
   * Si true, le tour ne peut pas être fermé en cliquant en dehors
   * @default false
   */
  closeOnOutsideClick?: boolean;
}

export function TourGuide({
  steps,
  open: controlledOpen,
  onOpenChange,
  onComplete,
  onSkip,
  completeButtonText = "Compris !",
  skipButtonText = "Passer",
  showProgress = true,
  closeOnOutsideClick = false,
}: TourGuideProps) {
  const [internalOpen, setInternalOpen] = useState(false);
  const [currentStepIndex, setCurrentStepIndex] = useState(0);
  const [isHighlighted, setIsHighlighted] = useState(false);

  const open = controlledOpen !== undefined ? controlledOpen : internalOpen;
  const currentStep = steps[currentStepIndex];
  const isLastStep = currentStepIndex === steps.length - 1;
  const isFirstStep = currentStepIndex === 0;

  const setOpen = (newOpen: boolean) => {
    if (controlledOpen === undefined) {
      setInternalOpen(newOpen);
    }
    onOpenChange?.(newOpen);
  };

  // Gérer l'entrée dans une étape
  useEffect(() => {
    if (open && currentStep) {
      currentStep.onEnter?.();
      setIsHighlighted(true);

      // Scroll vers l'élément cible si nécessaire
      if (currentStep.target) {
        const element = document.querySelector(currentStep.target);
        if (element) {
          element.scrollIntoView({ behavior: "smooth", block: "center" });
        }
      }
    }

    return () => {
      if (currentStep) {
        currentStep.onExit?.();
      }
      setIsHighlighted(false);
    };
  }, [currentStepIndex, open, currentStep]);

  const nextStep = useCallback(() => {
    if (isLastStep) {
      onComplete?.();
      setOpen(false);
      setCurrentStepIndex(0);
    } else {
      setCurrentStepIndex((prev) => prev + 1);
    }
  }, [isLastStep, onComplete, setOpen]);

  const prevStep = useCallback(() => {
    if (!isFirstStep) {
      setCurrentStepIndex((prev) => prev - 1);
    }
  }, [isFirstStep]);

  const handleSkip = useCallback(() => {
    onSkip?.();
    setOpen(false);
    setCurrentStepIndex(0);
  }, [onSkip, setOpen]);

  const handleOpenChange = useCallback(
    (newOpen: boolean) => {
      if (newOpen === false && !closeOnOutsideClick) {
        // Empêcher la fermeture si closeOnOutsideClick est false
        return;
      }
      setOpen(newOpen);
      if (!newOpen) {
        setCurrentStepIndex(0);
      }
    },
    [setOpen, closeOnOutsideClick]
  );

  // Calculer la position du tooltip
  const getTooltipPosition = () => {
    if (!currentStep?.target) return "center";

    const element = document.querySelector(currentStep.target);
    if (!element) return "center";

    const rect = element.getBoundingClientRect();
    const viewportWidth = window.innerWidth;
    const viewportHeight = window.innerHeight;

    // Déterminer la meilleure position automatiquement si non spécifiée
    if (!currentStep.position || currentStep.position === "center") {
      const centerX = rect.left + rect.width / 2;
      const centerY = rect.top + rect.height / 2;

      if (centerY < viewportHeight * 0.3) return "bottom";
      if (centerY > viewportHeight * 0.7) return "top";
      if (centerX < viewportWidth * 0.3) return "right";
      if (centerX > viewportWidth * 0.7) return "left";
      return "bottom";
    }

    return currentStep.position;
  };

  const position = getTooltipPosition();

  if (!open || !currentStep) return null;

  return (
    <>
      {/* Overlay avec spotlight */}
      <div
        className={cn(
          "fixed inset-0 z-[60] bg-black/60 transition-opacity duration-300",
          isHighlighted && "opacity-100"
        )}
        onClick={() => handleOpenChange(false)}
        aria-hidden="true"
      />

      {/* Spotlight sur l'élément cible */}
      {currentStep.target && isHighlighted && (
        <div
          className={cn(
            "fixed z-[61] pointer-events-none transition-all duration-300",
            "border-4 border-indigo-500 rounded-lg shadow-[0_0_0_9999px_rgba(0,0,0,0.6)]"
          )}
          style={{
            ...((() => {
              const element = document.querySelector(currentStep.target!);
              if (!element) return {};
              const rect = element.getBoundingClientRect();
              return {
                top: rect.top - 4,
                left: rect.left - 4,
                width: rect.width + 8,
                height: rect.height + 8,
              };
            })()),
          }}
        />
      )}

      {/* Tooltip du tour */}
      <Dialog.Root open={open} onOpenChange={handleOpenChange}>
        <Dialog.Portal>
          <Dialog.Content
            className={cn(
              "fixed z-[70] w-[400px] max-w-[90vw]",
              "bg-white rounded-2xl shadow-2xl border border-slate-200",
              "transition-all duration-300",
              position === "center" && "left-1/2 top-1/2 -translate-x-1/2 -translate-y-1/2",
              position === "top" && "left-1/2 -translate-x-1/2 bottom-8",
              position === "bottom" && "left-1/2 -translate-x-1/2 top-8",
              position === "left" && "right-8 top-1/2 -translate-y-1/2",
              position === "right" && "left-8 top-1/2 -translate-y-1/2"
            )}
            onPointerDownOutside={(e) => {
              if (!closeOnOutsideClick) {
                e.preventDefault();
              }
            }}
            onEscapeKeyDown={(e) => {
              if (!closeOnOutsideClick) {
                e.preventDefault();
              }
            }}
          >
            {/* Header */}
            <div className="px-6 pt-5 pb-3">
              <div className="flex items-start justify-between gap-4">
                <Dialog.Title className="text-lg font-bold text-slate-900">
                  {currentStep.title}
                </Dialog.Title>
                <button
                  onClick={() => handleOpenChange(false)}
                  className={cn(
                    "shrink-0 w-6 h-6 rounded flex items-center justify-center",
                    "text-slate-400 hover:text-slate-600 hover:bg-slate-100",
                    "transition-colors duration-150"
                  )}
                >
                  <X className="w-4 h-4" />
                </button>
              </div>

              {/* Progress */}
              {showProgress && steps.length > 1 && (
                <div className="mt-3">
                  <div className="flex items-center justify-between text-xs text-slate-500 mb-2">
                    <span>Étape {currentStepIndex + 1} sur {steps.length}</span>
                    <span>{Math.round(((currentStepIndex + 1) / steps.length) * 100)}%</span>
                  </div>
                  <div className="h-1.5 bg-slate-100 rounded-full overflow-hidden">
                    <div
                      className="h-full bg-gradient-to-r from-indigo-500 to-purple-600 transition-all duration-300 ease-out"
                      style={{
                        width: `${((currentStepIndex + 1) / steps.length) * 100}%`,
                      }}
                    />
                  </div>
                </div>
              )}
            </div>

            {/* Content */}
            <div className="px-6 pb-4">
              {currentStep.image && (
                <div className="mb-4 rounded-lg overflow-hidden border border-slate-200">
                  <img
                    src={currentStep.image}
                    alt={currentStep.title}
                    className="w-full h-auto"
                  />
                </div>
              )}
              <div className="text-sm text-slate-600 leading-relaxed space-y-2">
                {typeof currentStep.content === "string" ? (
                  <p>{currentStep.content}</p>
                ) : (
                  currentStep.content
                )}
              </div>
            </div>

            {/* Footer */}
            <div className="flex items-center justify-between px-6 py-4 bg-slate-50 border-t border-slate-200 rounded-b-2xl">
              <button
                onClick={handleSkip}
                className="text-sm text-slate-500 hover:text-slate-700 transition-colors"
              >
                {skipButtonText}
              </button>

              <div className="flex items-center gap-2">
                {!isFirstStep && (
                  <button
                    onClick={prevStep}
                    className={cn(
                      "flex items-center gap-1.5 px-4 py-2 rounded-lg",
                      "text-sm font-medium text-slate-700",
                      "hover:bg-slate-200",
                      "transition-colors duration-150"
                    )}
                  >
                    <ChevronLeft className="w-4 h-4" />
                    Précédent
                  </button>
                )}

                <button
                  onClick={nextStep}
                  className={cn(
                    "flex items-center gap-1.5 px-4 py-2 rounded-lg",
                    "text-sm font-semibold text-white",
                    "bg-gradient-to-r from-indigo-600 to-purple-600",
                    "hover:from-indigo-700 hover:to-purple-700",
                    "shadow-md hover:shadow-lg",
                    "transition-all duration-150"
                  )}
                >
                  {isLastStep ? (
                    <>
                      <Check className="w-4 h-4" />
                      {completeButtonText}
                    </>
                  ) : (
                    <>
                      Suivant
                      <ChevronRight className="w-4 h-4" />
                    </>
                  )}
                </button>
              </div>
            </div>
          </Dialog.Content>
        </Dialog.Portal>
      </Dialog.Root>
    </>
  );
}
