import Link from "next/link";
import { cn } from "@/shared/utils";
import { ArrowRight } from "lucide-react";
import type { ReactNode } from "react";
import React from "react";

/**
 * Accent color options for ServiceCard
 */
export type ServiceCardAccentColor =
  | "blue"
  | "green"
  | "purple"
  | "orange"
  | "cyan"
  | "pink"
  | "amber"
  | "rose";

/**
 * Variant options for ServiceCard
 * - default: Standard card with icon, title, description, price
 * - featured: Premium styling with gradient accents and more lift
 * - minimal: Compact icon + title only (no description)
 * - bento-sm: Small bento grid card
 * - bento-md: Medium bento grid card
 * - bento-lg: Large bento grid card with decorative elements
 */
export type ServiceCardVariant =
  | "default"
  | "featured"
  | "minimal"
  | "bento-sm"
  | "bento-md"
  | "bento-lg";

export interface ServiceCardProps {
  /** Link destination (renders as div when omitted) */
  href?: string;
  /**
   * Icon element to display.
   * Pass a pre-styled JSX element: `icon={<Wifi className="h-6 w-6" />}`
   * Or a component reference (className will be applied): `icon={Wifi}`
   */
  icon: ReactNode;
  /** Card title */
  title: string;
  /** Card description (optional for minimal variant) */
  description?: string;
  /** Starting price text e.g. "¥3,200/mo" */
  price?: string;
  /** Badge text shown at top-right e.g. "1st month free" */
  badge?: string;
  /** Highlight text shown as a pill (alternative to badge) */
  highlight?: string;
  /** Accent color for icon background */
  accentColor?: ServiceCardAccentColor;
  /** Card variant */
  variant?: ServiceCardVariant;
  /** Additional CSS classes */
  className?: string;
}

/**
 * Accent color styles mapping
 * All classes must be complete strings (no dynamic interpolation) for Tailwind JIT
 */
const TRANSITION_NORMAL = "transition-all duration-[var(--cp-duration-normal)]";

const accentColorStyles: Record<
  ServiceCardAccentColor,
  {
    bg: string;
    text: string;
    border: string;
    gradient: string;
    hoverBorder: string;
    cardBg: string;
  }
> = {
  blue: {
    bg: "bg-blue-500/10",
    text: "text-blue-600 dark:text-blue-400",
    border: "border-blue-500/20",
    gradient: "from-blue-500/30 to-transparent",
    hoverBorder: "hover:border-blue-500/40",
    cardBg: "from-blue-500/10 via-card to-card",
  },
  green: {
    bg: "bg-green-500/10",
    text: "text-green-600 dark:text-green-400",
    border: "border-green-500/20",
    gradient: "from-green-500/30 to-transparent",
    hoverBorder: "hover:border-green-500/40",
    cardBg: "from-green-500/10 via-card to-card",
  },
  purple: {
    bg: "bg-purple-500/10",
    text: "text-purple-600 dark:text-purple-400",
    border: "border-purple-500/20",
    gradient: "from-purple-500/30 to-transparent",
    hoverBorder: "hover:border-purple-500/40",
    cardBg: "from-purple-500/10 via-card to-card",
  },
  orange: {
    bg: "bg-orange-500/10",
    text: "text-orange-600 dark:text-orange-400",
    border: "border-orange-500/20",
    gradient: "from-orange-500/30 to-transparent",
    hoverBorder: "hover:border-orange-500/40",
    cardBg: "from-orange-500/10 via-card to-card",
  },
  cyan: {
    bg: "bg-cyan-500/10",
    text: "text-cyan-600 dark:text-cyan-400",
    border: "border-cyan-500/20",
    gradient: "from-cyan-500/30 to-transparent",
    hoverBorder: "hover:border-cyan-500/40",
    cardBg: "from-cyan-500/10 via-card to-card",
  },
  pink: {
    bg: "bg-pink-500/10",
    text: "text-pink-600 dark:text-pink-400",
    border: "border-pink-500/20",
    gradient: "from-pink-500/30 to-transparent",
    hoverBorder: "hover:border-pink-500/40",
    cardBg: "from-pink-500/10 via-card to-card",
  },
  amber: {
    bg: "bg-amber-500/10",
    text: "text-amber-600 dark:text-amber-400",
    border: "border-amber-500/20",
    gradient: "from-amber-500/30 to-transparent",
    hoverBorder: "hover:border-amber-500/40",
    cardBg: "from-amber-500/10 via-card to-card",
  },
  rose: {
    bg: "bg-rose-500/10",
    text: "text-rose-600 dark:text-rose-400",
    border: "border-rose-500/20",
    gradient: "from-rose-500/30 to-transparent",
    hoverBorder: "hover:border-rose-500/40",
    cardBg: "from-rose-500/10 via-card to-card",
  },
};

/**
 * Render icon - handles both component references and pre-styled JSX elements
 * @param icon - Either a component reference (function) or a ReactNode (JSX element)
 * @param className - Applied only when icon is a component reference
 */
function renderIcon(icon: ReactNode, className: string): ReactNode {
  // If icon is a component reference (function), instantiate it with className
  if (typeof icon === "function") {
    const IconComponent = icon as React.ComponentType<{ className?: string }>;
    return <IconComponent className={className} />;
  }
  // Otherwise, return the pre-styled JSX element as-is
  return icon;
}

/**
 * Shared wrapper that renders <Link> when href is provided, <div> otherwise
 */
function CardWrapper({
  href,
  className,
  children,
}: {
  href?: string | undefined;
  className?: string;
  children: ReactNode;
}) {
  if (href) {
    return (
      <Link href={href} className={className}>
        {children}
      </Link>
    );
  }
  return <div className={className}>{children}</div>;
}

/**
 * Default variant - Standard service card
 */
function DefaultCard({
  href,
  icon,
  title,
  description,
  price,
  badge,
  accentColor = "blue",
  className,
}: ServiceCardProps) {
  const colors = accentColorStyles[accentColor];

  return (
    <CardWrapper href={href} className={cn("group block", className)}>
      <div
        className={cn(
          "relative h-full flex flex-col rounded-2xl border bg-card p-6",
          TRANSITION_NORMAL,
          "hover:-translate-y-1 hover:shadow-lg hover:border-primary/30"
        )}
      >
        {badge && (
          <span className="absolute -top-2.5 right-4 rounded-full bg-success px-2.5 py-0.5 text-xs font-medium text-success-foreground">
            {badge}
          </span>
        )}

        <div className="flex items-start gap-4 mb-4">
          <div
            className={cn(
              "flex h-12 w-12 items-center justify-center rounded-xl border",
              colors.bg,
              colors.text,
              colors.border
            )}
          >
            {renderIcon(icon, "h-6 w-6")}
          </div>
          <div className="flex-1">
            <h3 className="text-lg font-semibold text-foreground font-heading">{title}</h3>
            {price && (
              <span className="text-sm text-muted-foreground">
                From <span className="font-medium text-foreground">{price}</span>
              </span>
            )}
          </div>
        </div>

        {description && (
          <p className="text-sm text-muted-foreground leading-relaxed flex-grow">{description}</p>
        )}

        {href && (
          <div className="mt-4 flex items-center gap-1 text-sm font-medium text-primary">
            Learn more
            <ArrowRight className="h-4 w-4 transition-transform group-hover:translate-x-0.5" />
          </div>
        )}
      </div>
    </CardWrapper>
  );
}

/**
 * Featured variant - Premium styling with enhanced shadows
 */
function FeaturedCard({ href, icon, title, description, highlight, className }: ServiceCardProps) {
  return (
    <CardWrapper href={href} className={cn("group block h-full", className)}>
      <div
        className={cn(
          "h-full flex flex-col",
          "rounded-xl border bg-card",
          "p-6",
          TRANSITION_NORMAL,
          "border-primary/20",
          "shadow-md shadow-primary/5",
          "hover:border-primary/40 hover:shadow-xl hover:shadow-primary/10",
          "hover:-translate-y-1"
        )}
      >
        {/* Icon with solid primary background */}
        <div
          className={cn(
            "flex h-12 w-12 items-center justify-center rounded-xl mb-4",
            "transition-all group-hover:scale-105",
            "bg-primary shadow-md shadow-primary/20 group-hover:shadow-lg group-hover:shadow-primary/30"
          )}
        >
          {renderIcon(icon, "h-6 w-6 text-primary-foreground")}
        </div>

        {/* Content */}
        <h3 className="text-lg font-semibold text-foreground mb-2 font-heading">{title}</h3>
        {description && (
          <p className="text-sm text-muted-foreground leading-relaxed flex-grow">{description}</p>
        )}

        {/* Highlight badge */}
        {highlight && (
          <span
            className={cn(
              "inline-flex self-start mt-3 rounded-full px-3 py-1 text-xs font-semibold",
              "bg-success text-success-foreground shadow-sm"
            )}
          >
            {highlight}
          </span>
        )}

        {/* Link indicator */}
        {href && (
          <div
            className={cn(
              "flex items-center gap-1.5 mt-4 pt-4 border-t",
              "text-sm font-medium text-primary",
              "transition-colors group-hover:text-primary-hover",
              "border-primary/10"
            )}
          >
            Learn more
            <ArrowRight className="h-4 w-4 transition-transform group-hover:translate-x-1" />
          </div>
        )}
      </div>
    </CardWrapper>
  );
}

/**
 * Minimal variant - Compact icon + title only
 */
function MinimalCard({ href, icon, title, className }: ServiceCardProps) {
  return (
    <CardWrapper href={href} className={cn("group block", className)}>
      <div
        className={cn(
          "flex flex-col items-center text-center",
          "rounded-xl border border-border bg-card",
          "p-6",
          TRANSITION_NORMAL,
          "hover:border-primary/30 hover:shadow-md",
          "hover:-translate-y-0.5"
        )}
      >
        <div className="flex h-12 w-12 items-center justify-center rounded-xl bg-primary/10 mb-3 transition-all group-hover:bg-primary/15">
          {renderIcon(icon, "h-6 w-6 text-primary")}
        </div>
        <h3 className="text-sm font-semibold text-foreground font-heading">{title}</h3>
      </div>
    </CardWrapper>
  );
}

/**
 * Bento Small variant - Compact inline card
 */
function BentoSmallCard({ href, icon, title, accentColor = "blue", className }: ServiceCardProps) {
  const colors = accentColorStyles[accentColor];

  return (
    <CardWrapper
      href={href}
      className={cn(
        "group rounded-xl bg-card/80 backdrop-blur-sm border border-border/50",
        "p-4",
        TRANSITION_NORMAL,
        "hover:bg-card hover:border-border",
        className
      )}
    >
      <div className="flex items-center gap-3">
        <div className={cn("h-10 w-10 rounded-lg flex items-center justify-center", colors.text)}>
          {renderIcon(icon, "h-5 w-5")}
        </div>
        <span className="font-semibold text-foreground">{title}</span>
      </div>
    </CardWrapper>
  );
}

/**
 * Bento Medium variant - Standard bento card
 */
function BentoMediumCard({
  href,
  icon,
  title,
  description,
  accentColor = "blue",
  className,
}: ServiceCardProps) {
  const colors = accentColorStyles[accentColor];

  return (
    <CardWrapper
      href={href}
      className={cn(
        "group rounded-xl bg-card border",
        colors.border,
        colors.hoverBorder,
        "p-6",
        TRANSITION_NORMAL,
        "hover:-translate-y-0.5",
        className
      )}
    >
      <div
        className={cn(
          "inline-flex items-center justify-center h-12 w-12 rounded-lg mb-4",
          "bg-gradient-to-br from-card to-muted",
          colors.text
        )}
      >
        {renderIcon(icon, "h-6 w-6")}
      </div>

      <h3 className="text-lg font-bold text-foreground mb-2 font-heading">{title}</h3>
      {description && (
        <p className="text-sm text-muted-foreground leading-relaxed">{description}</p>
      )}
    </CardWrapper>
  );
}

/**
 * Bento Large variant - Hero-style bento card with decorative elements
 */
function BentoLargeCard({
  href,
  icon,
  title,
  description,
  accentColor = "blue",
  className,
}: ServiceCardProps) {
  const colors = accentColorStyles[accentColor];

  return (
    <CardWrapper
      href={href}
      className={cn(
        "group relative overflow-hidden rounded-2xl",
        "bg-gradient-to-br",
        colors.cardBg,
        "border",
        colors.border,
        colors.hoverBorder,
        "p-8",
        TRANSITION_NORMAL,
        "hover:-translate-y-1",
        className
      )}
    >
      {/* Decorative gradient orb */}
      <div
        className={cn(
          "absolute -top-20 -right-20 w-64 h-64 rounded-full",
          "bg-gradient-to-br opacity-30",
          colors.gradient,
          "blur-2xl"
        )}
        aria-hidden="true"
      />

      <div className="relative">
        <div
          className={cn(
            "inline-flex items-center justify-center h-14 w-14 rounded-xl mb-6",
            "bg-background/50 backdrop-blur-sm border border-border/50",
            colors.text
          )}
        >
          {renderIcon(icon, "h-7 w-7")}
        </div>

        <h3 className="text-2xl font-bold text-foreground mb-3 font-heading">{title}</h3>
        {description && (
          <p className="text-muted-foreground leading-relaxed max-w-sm mb-6">{description}</p>
        )}

        {href && (
          <span
            className={cn(
              "inline-flex items-center gap-2 font-semibold",
              colors.text,
              "transition-transform duration-[var(--cp-duration-normal)]",
              "group-hover:translate-x-1"
            )}
          >
            Learn more
            <ArrowRight className="h-4 w-4" />
          </span>
        )}
      </div>
    </CardWrapper>
  );
}

/**
 * ServiceCard - Unified service card component
 *
 * A flexible card component for displaying services with multiple variants:
 * - default: Standard card with icon, title, description, price, badge
 * - featured: Premium styling with enhanced shadows and highlights
 * - minimal: Compact icon + title only
 * - bento-sm/md/lg: Bento grid cards in different sizes
 *
 * @example
 * ```tsx
 * // Default variant
 * <ServiceCard
 *   href="/services/internet"
 *   icon={<Wifi className="h-6 w-6" />}
 *   title="Internet"
 *   description="High-speed fiber internet"
 *   price="¥3,200/mo"
 *   accentColor="blue"
 * />
 *
 * // Featured variant
 * <ServiceCard
 *   variant="featured"
 *   href="/services/sim"
 *   icon={Smartphone}
 *   title="SIM & eSIM"
 *   description="Mobile data plans"
 *   highlight="1st month free"
 * />
 *
 * // Minimal variant
 * <ServiceCard
 *   variant="minimal"
 *   href="/services/vpn"
 *   icon={ShieldCheck}
 *   title="VPN"
 * />
 * ```
 */
export function ServiceCard(props: ServiceCardProps) {
  const { variant = "default" } = props;

  switch (variant) {
    case "featured":
      return <FeaturedCard {...props} />;
    case "minimal":
      return <MinimalCard {...props} />;
    case "bento-sm":
      return <BentoSmallCard {...props} />;
    case "bento-md":
      return <BentoMediumCard {...props} />;
    case "bento-lg":
      return <BentoLargeCard {...props} />;
    default:
      return <DefaultCard {...props} />;
  }
}

export default ServiceCard;
