import type { ReactNode } from "react";

// ─────────────────────────────────────────────────────────────────────────────
// Spinner — an elegant two-tone ring. Inherits `currentColor`, so set the colour
// with a text-* class on the element or a parent (e.g. text-forest, text-white).
// ─────────────────────────────────────────────────────────────────────────────

type SpinnerSize = "sm" | "md" | "lg" | "xl";
const SPINNER_PX: Record<SpinnerSize, number> = { sm: 16, md: 22, lg: 40, xl: 56 };

export function Spinner({ size = "md", className = "" }: { size?: SpinnerSize; className?: string }) {
  const px = SPINNER_PX[size];
  return (
    <svg
      width={px}
      height={px}
      viewBox="0 0 50 50"
      className={`animate-spin ${className}`}
      role="status"
      aria-label="Loading"
    >
      <circle cx="25" cy="25" r="20" fill="none" stroke="currentColor" strokeWidth="5" strokeOpacity="0.16" />
      <circle
        cx="25"
        cy="25"
        r="20"
        fill="none"
        stroke="currentColor"
        strokeWidth="5"
        strokeLinecap="round"
        strokeDasharray="90 200"
      />
    </svg>
  );
}

// ─────────────────────────────────────────────────────────────────────────────
// PageLoader — a centred, branded preloader for full-page / route-level waits.
// ─────────────────────────────────────────────────────────────────────────────

export function PageLoader({ label = "Loading", className = "" }: { label?: string; className?: string }) {
  return (
    <div className={`villa-fade-in flex flex-col items-center justify-center gap-5 py-24 ${className}`}>
      <div className="relative flex items-center justify-center text-forest">
        <Spinner size="xl" />
        <span className="absolute w-3 h-3 rounded-full bg-gold villa-pulse-soft" />
      </div>
      <p className="font-mono text-xs uppercase tracking-widest text-ink-soft">{label}…</p>
    </div>
  );
}

// ─────────────────────────────────────────────────────────────────────────────
// Skeleton primitive — a shimmering placeholder block.
// ─────────────────────────────────────────────────────────────────────────────

export function Skeleton({ className = "" }: { className?: string }) {
  return <div className={`villa-skeleton rounded-md ${className}`} />;
}

// ─────────────────────────────────────────────────────────────────────────────
// Card skeletons — match the real card silhouettes so the layout doesn't jump.
// ─────────────────────────────────────────────────────────────────────────────

export function PropertyCardSkeleton({ layout = "grid" }: { layout?: "grid" | "list" }) {
  const isList = layout === "list";
  return (
    <div className={`bg-white rounded-lg border border-mist shadow-card overflow-hidden flex ${isList ? "flex-col sm:flex-row" : "flex-col"}`}>
      <Skeleton className={`rounded-none ${isList ? "h-44 sm:h-auto sm:w-60 shrink-0" : "h-44"}`} />
      <div className="p-4 pb-5 flex flex-col flex-1 gap-3">
        <Skeleton className="h-5 w-3/4" />
        <Skeleton className="h-4 w-1/2" />
        <Skeleton className="h-5 w-24 mt-1" />
        <div className="flex gap-2 mt-2">
          <Skeleton className="h-6 w-20 rounded-pill" />
          <Skeleton className="h-6 w-16 rounded-pill" />
        </div>
        <div className="flex items-center justify-between mt-3">
          <Skeleton className="h-6 w-24 rounded-pill" />
          <Skeleton className="h-8 w-16 rounded-pill" />
        </div>
      </div>
    </div>
  );
}

export function StayCardSkeleton() {
  return (
    <div className="bg-white rounded-lg border border-mist shadow-card overflow-hidden flex flex-col">
      <Skeleton className="rounded-none h-48" />
      <div className="p-5 flex flex-col gap-3">
        <Skeleton className="h-5 w-2/3" />
        <Skeleton className="h-4 w-1/2" />
        <div className="flex gap-2 mt-1">
          <Skeleton className="h-6 w-16 rounded-pill" />
          <Skeleton className="h-6 w-20 rounded-pill" />
        </div>
        <div className="flex items-center justify-between mt-2">
          <Skeleton className="h-6 w-28" />
          <Skeleton className="h-9 w-20 rounded-pill" />
        </div>
      </div>
    </div>
  );
}

// A generic grid of skeleton cards.
export function CardGridSkeleton({ count = 6, children }: { count?: number; children: (i: number) => ReactNode }) {
  return <>{Array.from({ length: count }).map((_, i) => children(i))}</>;
}

// ─────────────────────────────────────────────────────────────────────────────
// InlineLoader — spinner + label, for section-level loads inside a card.
// ─────────────────────────────────────────────────────────────────────────────

export function InlineLoader({ label = "Loading", className = "" }: { label?: string; className?: string }) {
  return (
    <div className={`flex items-center justify-center gap-3 py-10 text-ink-soft ${className}`}>
      <span className="text-forest"><Spinner size="md" /></span>
      <span className="text-sm">{label}…</span>
    </div>
  );
}

// ─────────────────────────────────────────────────────────────────────────────
// TopProgressBar — a slim indeterminate bar, e.g. pinned to a search results area.
// ─────────────────────────────────────────────────────────────────────────────

export function TopProgressBar({ className = "" }: { className?: string }) {
  return (
    <div className={`h-0.5 w-full overflow-hidden rounded-full bg-mist/60 ${className}`} role="status" aria-label="Loading">
      <div className="h-full w-full origin-left rounded-full bg-forest villa-bar-slide" />
    </div>
  );
}
