import type { ComponentProps } from "react";
import { toast, Toaster } from "sonner";
import { cn } from "@/shared/ui/cn";
import { MAP_ICON_CELL_RADIUS_CLASS_NAME } from "./map-control-styles";
import { MapNoticeCloseIcon, MapNoticeContent } from "./notice-presentation";
import type { MapNoticeOptions, MapNoticePosition } from "./notice-types";

type SonnerPosition = NonNullable<ComponentProps<typeof Toaster>["position"]>;

const DEFAULT_POSITION: MapNoticePosition = "top-center";

const positionClassNames: Record<MapNoticePosition, string> = {
  "top-center": "left-1/2! right-auto! top-[84px] [translate:-50%_0]",
  "top-right": "top-[84px] right-[72px]",
  "bottom-left": "bottom-12 left-4",
  "bottom-right": "bottom-12 right-4"
};

const sonnerPositions: Record<MapNoticePosition, SonnerPosition> = {
  "top-center": "top-center",
  "top-right": "top-right",
  "bottom-left": "bottom-left",
  "bottom-right": "bottom-right"
};

export function showMapNotice(options: MapNoticeOptions) {
  const tone = options.tone ?? "info";
  const position = options.position ?? DEFAULT_POSITION;
  const duration = options.duration ?? (tone === "info" || tone === "success" ? 3200 : Infinity);
  const dismissible = options.dismissible ?? tone !== "loading";

  return toast.custom(
    () => <MapNoticeContent {...options} tone={tone} />,
    {
      id: options.id,
      duration,
      position: sonnerPositions[position],
      dismissible,
      cancel: dismissible
        ? {
            label: <MapNoticeCloseIcon />,
            onClick: (event) => event.stopPropagation()
          }
        : undefined,
      classNames: {
        cancelButton: cn(
          "absolute right-2 top-2 z-10 grid h-8 w-8 place-items-center border border-transparent bg-transparent p-0 text-slate-400 after:absolute after:-inset-1 after:content-[''] hover:border-slate-200 hover:bg-slate-50 hover:text-slate-700",
          MAP_ICON_CELL_RADIUS_CLASS_NAME
        )
      },
      className: cn("fixed! z-[60]! w-[min(420px,calc(100vw-24px))]!", positionClassNames[position])
    }
  );
}

export function dismissMapNotice(id?: string | number) {
  toast.dismiss(id);
}
