"use client";

import Image, { type StaticImageData } from "next/image";
import type { HTMLAttributes, ReactNode } from "react";
import { useCallback, useEffect, useRef, useState } from "react";
import Button from "./button";
import { LoadingSkeleton } from "./loading-skeleton";
import { LoadingThreeDot } from "./loading-three-dot";
import { useI18n } from "@/translations/provider";

const EXIT_ANIMATION_MS = 220;

type InformationSheetPresetIcon =
  | "play"
  | "warning"
  | "coin"
  | "check"
  | "stash_play-solid.svg"
  | "warning.svg"
  | "coin.svg"
  | "Vectorcheck.svg";

type InformationSheetIcon =
  | InformationSheetPresetIcon
  | string
  | {
      src: string | StaticImageData;
      alt?: string;
      width?: number;
      height?: number;
    };

export type InformationSheetProps = Omit<
  HTMLAttributes<HTMLDivElement>,
  "children" | "title"
> & {
  icon?: InformationSheetIcon | null;
  title?: ReactNode | ((controls: { close: () => void }) => ReactNode);
  description?: ReactNode;
  buttons?: ReactNode | ((controls: { close: () => void }) => ReactNode);
  closeOnOutside?: boolean;
  onClose?: () => void;
  isLoading?: boolean;
};

const DEFAULT_ICON = {
  src: "/assets/images/stash_play-solid.svg",
  alt: "Play",
  width: 50,
  height: 50,
} as const;

const ICON_PRESETS: Record<
  InformationSheetPresetIcon,
  {
    src: string;
    alt: string;
    width: number;
    height: number;
  }
> = {
  play: DEFAULT_ICON,
  "stash_play-solid.svg": DEFAULT_ICON,
  warning: {
    src: "/assets/images/Vector.svg",
    alt: "Warning",
    width: 36,
    height: 36,
  },
  "warning.svg": {
    src: "/assets/images/Vector.svg",
    alt: "Warning",
    width: 36,
    height: 36,
  },
  coin: {
    src: "/assets/images/Inner Plugdsain Iframe.svg",
    alt: "Coin",
    width: 56,
    height: 56,
  },
  "coin.svg": {
    src: "/assets/images/Inner Plugdsain Iframe.svg",
    alt: "Coin",
    width: 56,
    height: 56,
  },
  check: {
    src: "/assets/images/Vectofdasr.svg",
    alt: "Check",
    width: 36,
    height: 36,
  },
  "Vectorcheck.svg": {
    src: "/assets/images/Vectorcheck.svg",
    alt: "Check",
    width: 36,
    height: 36,
  },
};

function resolveIcon(icon: InformationSheetIcon | null | undefined) {
  if (icon === null) {
    return null;
  }

  if (!icon) {
    return DEFAULT_ICON;
  }

  if (typeof icon === "string") {
    return (
      ICON_PRESETS[icon as InformationSheetPresetIcon] ?? {
        src: icon,
        alt: "Information",
        width: DEFAULT_ICON.width,
        height: DEFAULT_ICON.height,
      }
    );
  }

  return {
    src: icon.src,
    alt: icon.alt ?? "Information",
    width: icon.width ?? DEFAULT_ICON.width,
    height: icon.height ?? DEFAULT_ICON.height,
  };
}

export function InformationSheet({
  icon,
  title,
  description,
  buttons,
  closeOnOutside = true,
  onClose,
  className,
  isLoading = false,
  ...props
}: InformationSheetProps) {
  const { locale, dictionary: t } = useI18n();
  const isRtl =
    locale === "fa" ||
    locale === "ar" ||
    locale === "ur" ||
    locale === "he" ||
    locale === "ks";
  const [isVisible, setIsVisible] = useState(true);
  const [isClosing, setIsClosing] = useState(false);
  const isMountedRef = useRef(true);

  useEffect(() => {
    isMountedRef.current = true;
    return () => {
      isMountedRef.current = false;
    };
  }, []);

  const resolvedIcon = resolveIcon(icon);
  const closeSheet = useCallback(() => {
    if (isClosing) {
      return;
    }

    setIsClosing(true);
    window.setTimeout(() => {
      if (isMountedRef.current) {
        setIsVisible(false);
      }
      onClose?.();
    }, EXIT_ANIMATION_MS);
  }, [isClosing, onClose]);

  const controls = { close: closeSheet };
  const resolvedTitle = typeof title === "function" ? title(controls) : title;
  const resolvedButtons =
    typeof buttons === "string" ? (
      <Button onClick={closeSheet}>{buttons}</Button>
    ) : typeof buttons === "function" ? (
      buttons(controls)
    ) : (
      buttons
    );

  useEffect(() => {
    if (!isVisible) {
      return;
    }

    const previousBodyOverflow = document.body.style.overflow;
    const previousHtmlOverflow = document.documentElement.style.overflow;

    document.body.style.overflow = "hidden";
    document.documentElement.style.overflow = "hidden";

    return () => {
      document.body.style.overflow = previousBodyOverflow;
      document.documentElement.style.overflow = previousHtmlOverflow;
    };
  }, [isVisible]);

  if (!isVisible) {
    return null;
  }

  return (
    <div
      className={[
        "fixed inset-0 z-50 flex items-end justify-center overflow-y-auto transition-all duration-[220ms] animate-in fade-in",
        isClosing ? "bg-[#171717]/0 opacity-0" : "bg-[#171717]/55 opacity-100",
      ]
        .filter(Boolean)
        .join(" ")}
      role="dialog"
      aria-modal="true"
      aria-label={t["Information sheet"]}
      tabIndex={-1}
      dir={isRtl ? "rtl" : "ltr"}
      onClick={(event) => {
        if (closeOnOutside && event.target === event.currentTarget) {
          closeSheet();
        }
      }}
      onKeyDown={(event) => {
        if (
          closeOnOutside &&
          event.target === event.currentTarget &&
          (event.key === "Escape" || event.key === "Enter" || event.key === " ")
        ) {
          event.preventDefault();
          closeSheet();
        }
      }}
    >
      <section
        {...props}
        className={[
          "w-full sm:max-w-[375px] rounded-t-[22px] bg-[#F9F8F8] px-4 pt-4 pb-[max(24px,calc(24px+var(--safe-bottom)))] text-center shadow-[0_20px_60px_rgba(15,23,42,0.08)] transition-transform duration-[220ms] ease-out will-change-transform animate-in slide-in-from-bottom",
          isClosing ? "translate-y-full" : "translate-y-0",
          className,
        ]
          .filter(Boolean)
          .join(" ")}
      >
        <div className="mx-auto flex flex-col items-center w-full">
          {isLoading ? (
            <div className="flex h-[280px] min-h-[280px] w-full items-center justify-center">
              <LoadingThreeDot className="text-[#FF4E67]" />
            </div>
          ) : (
            <>
              {resolvedIcon ? (
                <Image
                  src={resolvedIcon.src}
                  alt={resolvedIcon.alt}
                  width={resolvedIcon.width}
                  height={resolvedIcon.height}
                  priority
                />
              ) : null}

              <h2
                className={[
                  resolvedIcon ? "mt-2.5" : "mt-0",
                  "w-full group-16 leading-[1.2] font-bold tracking-[-0.03em] text-[#171717]",
                ].join(" ")}
              >
                {resolvedTitle}
              </h2>

              {description ? (
                <div className="mt-3 group-12 text-[#4D4D4D]">
                  {description}
                </div>
              ) : null}

              {resolvedButtons ? (
                <div className="mt-4 flex w-full flex-col gap-3">
                  {resolvedButtons}
                </div>
              ) : null}
            </>
          )}
        </div>
      </section>
    </div>
  );
}

export default InformationSheet;
