"use client";

import { useMemo, useState } from "react";
import { useRouter } from "@/i18n/navigation";
import { useTranslations } from "next-intl";
import { Loader2, Palette, Sparkles, Type } from "lucide-react";
import Input from "@/components/ui/Input";
import Button from "@/components/ui/Button";
import BrandImagePicker from "@/components/brand/BrandImagePicker";
import BrandPreview from "@/components/brand/BrandPreview";
import { useBrand } from "@/components/providers/BrandProvider";
import { accentDerivedColors, brandToCssVars, type Brand } from "@/lib/brand";
import { readApiJson, toastPromise } from "@/lib/toast";

interface BrandingFormProps {
  canUpdate: boolean;
}

function normalizeAccent(value: string) {
  const trimmed = value.trim();
  if (/^#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$/.test(trimmed)) {
    return accentDerivedColors(trimmed).accent;
  }
  return accentDerivedColors("#d4a574").accent;
}

export default function BrandingForm({ canUpdate }: BrandingFormProps) {
  const t = useTranslations("branding");
  const tc = useTranslations("common");
  const brand = useBrand();
  const router = useRouter();

  const [form, setForm] = useState({
    name: brand.name,
    tagline: brand.tagline ?? "",
    logoUrl: brand.logoUrl ?? "",
    faviconUrl: brand.faviconUrl ?? "",
    accentColor: brand.colors.accent,
  });
  const [saving, setSaving] = useState(false);

  const previewAccent = useMemo(
    () => normalizeAccent(form.accentColor),
    [form.accentColor]
  );

  async function handleSubmit(e: React.FormEvent) {
    e.preventDefault();
    if (!canUpdate) return;
    setSaving(true);

    const payload = {
      name: form.name.trim() || null,
      tagline: form.tagline.trim() || null,
      logoUrl: form.logoUrl.trim() || null,
      faviconUrl: form.faviconUrl.trim() || null,
      accentColor: normalizeAccent(form.accentColor),
    };

    try {
      const next = await toastPromise(
        readApiJson<Brand>(
          await fetch("/api/brand", {
            method: "PUT",
            headers: { "Content-Type": "application/json" },
            body: JSON.stringify(payload),
          }),
          tc("somethingWrong")
        ),
        {
          loading: tc("saving"),
          success: t("saved"),
        }
      );

      const vars = brandToCssVars(next);
      for (const [key, value] of Object.entries(vars)) {
        document.documentElement.style.setProperty(key, value);
      }

      setForm({
        name: next.name,
        tagline: next.tagline ?? "",
        logoUrl: next.logoUrl ?? "",
        faviconUrl: next.faviconUrl ?? "",
        accentColor: next.colors.accent,
      });
      router.refresh();
    } catch {
      // surfaced via toast
    } finally {
      setSaving(false);
    }
  }

  return (
    <div className="grid gap-6 xl:grid-cols-[minmax(0,1fr)_360px] xl:items-start">
      <form onSubmit={handleSubmit} className="space-y-6">
        <section className="rounded-xl border border-[var(--border)] bg-[var(--bg-elevated)] p-4 sm:p-6">
          <div className="mb-5 flex items-center gap-3">
            <div className="flex h-9 w-9 items-center justify-center rounded-lg bg-[var(--accent-muted)] text-[var(--accent)]">
              <Type className="h-4 w-4" />
            </div>
            <div>
              <h2 className="text-sm font-semibold">{t("identitySection")}</h2>
              <p className="text-xs text-[var(--text-faint)]">{t("identityHint")}</p>
            </div>
          </div>
          <div className="space-y-4">
            <Input
              label={t("appName")}
              value={form.name}
              onChange={(e) => setForm({ ...form, name: e.target.value })}
              disabled={!canUpdate}
              placeholder="Cuppa"
            />
            <Input
              label={t("tagline")}
              value={form.tagline}
              onChange={(e) => setForm({ ...form, tagline: e.target.value })}
              disabled={!canUpdate}
              placeholder={t("taglinePlaceholder")}
            />
          </div>
        </section>

        <section className="space-y-4">
          <div className="flex items-center gap-3 px-1">
            <div className="flex h-9 w-9 items-center justify-center rounded-lg bg-[var(--accent-muted)] text-[var(--accent)]">
              <Sparkles className="h-4 w-4" />
            </div>
            <div>
              <h2 className="text-sm font-semibold">{t("assetsSection")}</h2>
              <p className="text-xs text-[var(--text-faint)]">{t("assetsHint")}</p>
            </div>
          </div>

          <BrandImagePicker
            label={t("logo")}
            kind="logo"
            value={form.logoUrl}
            disabled={!canUpdate}
            onChange={(logoUrl) => setForm({ ...form, logoUrl })}
          />

          <BrandImagePicker
            label={t("favicon")}
            kind="favicon"
            value={form.faviconUrl}
            disabled={!canUpdate}
            onChange={(faviconUrl) => setForm({ ...form, faviconUrl })}
          />
        </section>

        <section className="rounded-xl border border-[var(--border)] bg-[var(--bg-elevated)] p-4 sm:p-6">
          <div className="mb-5 flex items-center gap-3">
            <div className="flex h-9 w-9 items-center justify-center rounded-lg bg-[var(--accent-muted)] text-[var(--accent)]">
              <Palette className="h-4 w-4" />
            </div>
            <div>
              <h2 className="text-sm font-semibold">{t("themeSection")}</h2>
              <p className="text-xs text-[var(--text-faint)]">{t("themeHint")}</p>
            </div>
          </div>

          <div className="space-y-1.5">
            <label htmlFor="accent-color" className="block text-sm font-medium text-[var(--text-muted)]">
              {t("accentColor")}
            </label>
            <div className="flex items-center gap-3">
              <input
                id="accent-color"
                type="color"
                value={previewAccent}
                onChange={(e) => setForm({ ...form, accentColor: e.target.value })}
                disabled={!canUpdate}
                className="h-11 w-14 cursor-pointer rounded-lg border border-[var(--border)] bg-transparent p-1 disabled:cursor-not-allowed disabled:opacity-60"
              />
              <input
                type="text"
                value={form.accentColor}
                onChange={(e) => setForm({ ...form, accentColor: e.target.value })}
                disabled={!canUpdate}
                className="flex-1 rounded-lg border border-[var(--border)] bg-[var(--bg)] px-3.5 py-2.5 text-sm text-[var(--text)] focus:border-[var(--accent)]/60 focus:outline-none focus:ring-2 focus:ring-[var(--accent)]/40 disabled:cursor-not-allowed disabled:opacity-60"
                placeholder="#d4a574"
              />
            </div>
          </div>
        </section>

        {canUpdate && (
          <div className="flex items-center justify-end gap-3 border-t border-[var(--border)] pt-4">
            <Button type="submit" disabled={saving} size="lg">
              {saving ? (
                <>
                  <Loader2 className="h-4 w-4 animate-spin" />
                  {tc("saving")}
                </>
              ) : (
                tc("save")
              )}
            </Button>
          </div>
        )}
      </form>

      <aside className="xl:sticky xl:top-6">
        <BrandPreview
          name={form.name}
          tagline={form.tagline}
          logoUrl={form.logoUrl}
          accentColor={previewAccent}
        />
      </aside>
    </div>
  );
}
