"use client";

import type { CSSProperties } from "react";
import {
  DEFAULT_CATEGORY_ICON_STYLE,
  getCategoryIconPreset,
  getCategoryIconStroke,
  isCategoryIconStyle,
  type CategoryIconStyleId,
} from "@/lib/category-icon-presets";
import type { CafeThemePalette } from "@/lib/cafe-theme";
import { cn } from "@/lib/utils";

type CategoryPresetIconProps = {
  presetId: string;
  style?: string | null;
  size?: "xs" | "sm" | "md";
  className?: string;
  /** When set (QR guest menu), icon shell uses café theme instead of default Meezi green. */
  brandColors?: Pick<
    CafeThemePalette,
    "primary" | "secondary" | "accent" | "surface" | "textMuted"
  >;
};

function themedIconShellStyle(
  styleId: CategoryIconStyleId,
  c: NonNullable<CategoryPresetIconProps["brandColors"]>
): CSSProperties {
  const primaryRing = `0 0 0 2px color-mix(in srgb, ${c.primary} 20%, transparent)`;
  switch (styleId) {
    case "flat":
      return {
        backgroundColor: c.secondary,
        color: c.primary,
        border: `1px solid color-mix(in srgb, ${c.primary} 15%, transparent)`,
      };
    case "modern":
      return {
        background: `linear-gradient(135deg, ${c.secondary}, ${c.surface}, color-mix(in srgb, ${c.secondary} 60%, transparent))`,
        color: c.primary,
        border: `1px solid color-mix(in srgb, ${c.primary} 20%, transparent)`,
      };
    case "minimal":
      return { backgroundColor: "transparent", color: c.textMuted, border: "1px solid transparent" };
    case "outline":
      return {
        backgroundColor: c.surface,
        color: c.primary,
        border: `2px solid color-mix(in srgb, ${c.primary} 35%, transparent)`,
      };
    case "soft":
      return {
        backgroundColor: `color-mix(in srgb, ${c.secondary} 70%, transparent)`,
        color: c.primary,
        border: "none",
        borderRadius: "0.75rem",
      };
    case "bold":
      return { backgroundColor: c.primary, color: "#fff", border: "none" };
    case "gradient":
      return {
        background: `linear-gradient(to top right, ${c.primary}, color-mix(in srgb, ${c.primary} 75%, ${c.accent}), color-mix(in srgb, ${c.primary} 40%, #fff))`,
        color: "#fff",
        border: "none",
      };
    case "pastel":
      return {
        backgroundColor: `color-mix(in srgb, ${c.secondary} 40%, ${c.surface})`,
        color: c.accent,
        border: `1px solid color-mix(in srgb, ${c.accent} 20%, transparent)`,
      };
    case "duotone":
      return {
        backgroundColor: c.secondary,
        color: c.accent,
        border: `1px solid color-mix(in srgb, ${c.accent} 15%, transparent)`,
        boxShadow: primaryRing,
      };
    default:
      return { backgroundColor: c.secondary, color: c.primary };
  }
}

const boxSize = {
  xs: "h-5 w-5",
  sm: "h-7 w-7",
  md: "h-10 w-10",
} as const;

const iconSize = {
  xs: "h-3 w-3",
  sm: "h-4 w-4",
  md: "h-5 w-5",
} as const;

function resolveStyle(style: string | null | undefined): CategoryIconStyleId {
  return isCategoryIconStyle(style) ? style : DEFAULT_CATEGORY_ICON_STYLE;
}

const styleShell: Record<CategoryIconStyleId, string> = {
  flat: "bg-[#E1F5EE] text-[#0F6E56] border border-[#0F6E56]/15",
  modern:
    "bg-gradient-to-br from-[#E1F5EE] via-white to-[#E1F5EE]/60 text-[#0F6E56] border border-[#0F6E56]/20 shadow-sm",
  minimal: "bg-transparent text-muted-foreground border border-transparent",
  outline: "bg-white text-[#0F6E56] border-2 border-[#0F6E56]/35",
  real: "bg-muted/30 border border-border/80 overflow-hidden p-0",
  soft: "bg-[#E1F5EE]/70 text-[#0F6E56] border-0 shadow-md rounded-xl",
  bold: "bg-[#0F6E56] text-white border-0 shadow-sm",
  gradient:
    "bg-gradient-to-tr from-[#0F6E56] via-[#1a8f6e] to-[#5ec4a8] text-white border-0 shadow-md",
  pastel: "bg-[#FDF8F3] text-[#BA7517] border border-[#BA7517]/20",
  duotone: "bg-[#E1F5EE] text-[#0C447C] border border-[#0C447C]/15 ring-2 ring-[#0F6E56]/20",
};

export function CategoryPresetIcon({
  presetId,
  style,
  size = "sm",
  className,
  brandColors,
}: CategoryPresetIconProps) {
  const preset = getCategoryIconPreset(presetId);
  if (!preset) return null;

  const styleId = resolveStyle(style);
  const Icon = preset.icon;
  const stroke = getCategoryIconStroke(styleId);

  if (styleId === "real") {
    return (
      // eslint-disable-next-line @next/next/no-img-element
      <img
        src={preset.realImageUrl}
        alt=""
        className={cn(
          "shrink-0 rounded-md object-cover",
          boxSize[size],
          styleShell.real,
          className
        )}
      />
    );
  }

  const shellStyle = brandColors ? themedIconShellStyle(styleId, brandColors) : undefined;

  return (
    <span
      className={cn(
        "flex shrink-0 items-center justify-center rounded-md",
        boxSize[size],
        !brandColors && styleShell[styleId],
        className
      )}
      style={shellStyle}
      aria-hidden
    >
      <Icon
        className={cn(iconSize[size], stroke.className)}
        strokeWidth={stroke.strokeWidth}
        fill={styleId === "bold" || styleId === "gradient" ? "currentColor" : "none"}
        fillOpacity={styleId === "bold" || styleId === "gradient" ? 0.15 : 0}
      />
    </span>
  );
}
