import React, {
  createContext,
  useContext,
  useState,
  useEffect,
  useCallback,
} from "react";

export interface ToastType {
  id: string;
  type: "success" | "error" | "loading" | "info";
  message: React.ReactNode;
  duration?: number;
  dismissible?: boolean;
}

interface ToastContextType {
  toasts: ToastType[];
  addToast: (toast: Omit<ToastType, "id">) => string;
  removeToast: (id: string) => void;
  updateToast: (id: string, updates: Partial<ToastType>) => void;
}

const ToastContext = createContext<ToastContextType | null>(null);

export const useToast = () => {
  const context = useContext(ToastContext);
  if (!context) {
    throw new Error("useToast must be used within a ToastProvider");
  }
  return context;
};

// Toast utility functions (similar to react-hot-toast API)
let toastContext: ToastContextType | null = null;

export const toast = {
  success: (message: React.ReactNode, options?: { duration?: number }) => {
    if (!toastContext) return "";
    return toastContext.addToast({
      type: "success",
      message,
      duration: options?.duration || 4000,
      dismissible: true,
    });
  },
  error: (message: React.ReactNode, options?: { duration?: number }) => {
    if (!toastContext) return "";
    return toastContext.addToast({
      type: "error",
      message,
      duration: options?.duration || 5000,
      dismissible: true,
    });
  },
  loading: (message: React.ReactNode) => {
    if (!toastContext) return "";
    return toastContext.addToast({
      type: "loading",
      message,
      dismissible: false,
    });
  },
  info: (message: React.ReactNode, options?: { duration?: number }) => {
    if (!toastContext) return "";
    return toastContext.addToast({
      type: "info",
      message,
      duration: options?.duration || 4000,
      dismissible: true,
    });
  },
  dismiss: (id: string) => {
    if (!toastContext) return;
    toastContext.removeToast(id);
  },
  update: (id: string, updates: Partial<ToastType>) => {
    if (!toastContext) return;
    toastContext.updateToast(id, updates);
  },
};

interface ToastProviderProps {
  children: React.ReactNode;
}

export const ToastProvider: React.FC<ToastProviderProps> = ({ children }) => {
  const [toasts, setToasts] = useState<ToastType[]>([]);

  const addToast = useCallback((toast: Omit<ToastType, "id">) => {
    const id = Math.random().toString(36).substring(2, 9);
    const newToast: ToastType = { ...toast, id };

    setToasts((prev) => [...prev, newToast]);

    // Auto-dismiss if duration is set
    if (toast.duration) {
      setTimeout(() => {
        removeToast(id);
      }, toast.duration);
    }

    return id;
  }, []);

  const removeToast = useCallback((id: string) => {
    setToasts((prev) => prev.filter((toast) => toast.id !== id));
  }, []);

  const updateToast = useCallback((id: string, updates: Partial<ToastType>) => {
    setToasts((prev) =>
      prev.map((toast) => (toast.id === id ? { ...toast, ...updates } : toast))
    );
  }, []);

  const contextValue = {
    toasts,
    addToast,
    removeToast,
    updateToast,
  };

  // Set global context reference
  useEffect(() => {
    toastContext = contextValue;
    return () => {
      toastContext = null;
    };
  }, [contextValue]);

  return (
    <ToastContext.Provider value={contextValue}>
      {children}
      <ToastContainer />
    </ToastContext.Provider>
  );
};

const ToastContainer: React.FC = () => {
  const { toasts, removeToast } = useToast();

  return (
    <div
      style={{
        position: "fixed",
        top: "20px",
        left: "50%",
        transform: "translateX(-50%)",
        zIndex: 9999,
        display: "flex",
        flexDirection: "column",
        gap: "8px",
        pointerEvents: "none",
      }}
    >
      {toasts.map((toast) => (
        <ToastItem
          key={toast.id}
          toast={toast}
          onDismiss={() => removeToast(toast.id)}
        />
      ))}
    </div>
  );
};

interface ToastItemProps {
  toast: ToastType;
  onDismiss: () => void;
}

const ToastItem: React.FC<ToastItemProps> = ({ toast, onDismiss }) => {
  const [isVisible, setIsVisible] = useState(false);
  const [isExiting, setIsExiting] = useState(false);

  useEffect(() => {
    // Trigger entrance animation
    const timer = setTimeout(() => setIsVisible(true), 10);
    return () => clearTimeout(timer);
  }, []);

  const handleDismiss = () => {
    if (!toast.dismissible) return;

    setIsExiting(true);
    setTimeout(() => {
      onDismiss();
    }, 200);
  };

  const getIcon = () => {
    switch (toast.type) {
      case "success":
        return (
          <svg width="16" height="16" viewBox="0 0 16 16" fill="none">
            <path
              d="M13.5 4.5L6 12L2.5 8.5"
              stroke="currentColor"
              strokeWidth="2"
              strokeLinecap="round"
              strokeLinejoin="round"
            />
          </svg>
        );
      case "error":
        return (
          <svg width="16" height="16" viewBox="0 0 16 16" fill="none">
            <path
              d="M12 4L4 12M4 4L12 12"
              stroke="currentColor"
              strokeWidth="2"
              strokeLinecap="round"
              strokeLinejoin="round"
            />
          </svg>
        );
      case "loading":
        return (
          <div
            style={{
              width: "16px",
              height: "16px",
              border: "2px solid rgba(255, 255, 255, 0.3)",
              borderTop: "2px solid currentColor",
              borderRadius: "50%",
              animation: "spin 1s linear infinite",
            }}
          />
        );
      case "info":
        return (
          <svg width="16" height="16" viewBox="0 0 16 16" fill="none">
            <circle cx="8" cy="8" r="7" stroke="currentColor" strokeWidth="2" />
            <path
              d="M8 12V8"
              stroke="currentColor"
              strokeWidth="2"
              strokeLinecap="round"
            />
            <path
              d="M8 4H8.01"
              stroke="currentColor"
              strokeWidth="2"
              strokeLinecap="round"
            />
          </svg>
        );
      default:
        return null;
    }
  };

  const getBackgroundColor = () => {
    return "#000000";
  };

  return (
    <>
      <style>
        {`
          @keyframes spin {
            from { transform: rotate(0deg); }
            to { transform: rotate(360deg); }
          }
        `}
      </style>
      <div
        style={{
          borderRadius: "50px",
          padding: "8px 16px",
          fontSize: "15px",
          fontWeight: "500",
          minHeight: "48px",
          width: "fit-content",
          maxWidth: "420px",
          fontFamily: "Inter, -apple-system, BlinkMacSystemFont, sans-serif",
          background: getBackgroundColor(),
          color: "#f9fafb",
          boxShadow:
            "0 8px 25px rgba(0, 0, 0, 0.4), 0 4px 10px rgba(0, 0, 0, 0.2)",
          border: "1px solid rgba(255, 255, 255, 0.33)",
          display: "flex",
          alignItems: "center",
          gap: "12px",
          pointerEvents: "auto",
          cursor: toast.dismissible ? "pointer" : "default",
          transform: `translateY(${
            isVisible && !isExiting ? "0" : "-20px"
          }) scale(${isVisible && !isExiting ? "1" : "0.95"})`,
          opacity: isVisible && !isExiting ? 1 : 0,
          transition: "all 0.2s cubic-bezier(0.16, 1, 0.3, 1)",
          whiteSpace: "nowrap",
          flexWrap: "nowrap",
        }}
        onClick={handleDismiss}
      >
        {getIcon()}
        <div
          style={{
            flex: 1,
            whiteSpace: "nowrap",
            overflow: "hidden",
            textOverflow: "ellipsis",
          }}
        >
          {toast.message}
        </div>
        {toast.dismissible && (
          <button
            onClick={(e) => {
              e.stopPropagation();
              handleDismiss();
            }}
            style={{
              background: "none",
              border: "none",
              color: "currentColor",
              cursor: "pointer",
              padding: "2px",
              borderRadius: "50%",
              display: "flex",
              alignItems: "center",
              justifyContent: "center",
              opacity: 0.7,
              transition: "opacity 0.2s",
            }}
            onMouseEnter={(e) => {
              e.currentTarget.style.opacity = "1";
            }}
            onMouseLeave={(e) => {
              e.currentTarget.style.opacity = "0.7";
            }}
          >
            <svg width="14" height="14" viewBox="0 0 14 14" fill="none">
              <path
                d="M10.5 3.5L3.5 10.5M3.5 3.5L10.5 10.5"
                stroke="currentColor"
                strokeWidth="1.5"
                strokeLinecap="round"
                strokeLinejoin="round"
              />
            </svg>
          </button>
        )}
      </div>
    </>
  );
};

export default ToastProvider;
