"use client";

import Link from "next/link";
import type { ReactNode } from "react";
import { useEffect, useId, useMemo, useState, useTransition } from "react";
import { useRouter } from "next/navigation";
import { Settings } from "lucide-react";
import type { PageContent } from "@/lib/blocks/layout";
import { createPanelFromEditorAction, savePanelAction } from "@/lib/actions/panels";
import type { PanelLocationOption } from "@/lib/public/panel-positions";
import { cn } from "@/lib/utils";
import { ContentEditor } from "@/components/features/page-editor/content-editor";
import { EdTabs, Modal, Pill, YesNo, edInput } from "@/components/features/page-editor/ed-ui";
import type { FieldContext } from "@/components/features/page-editor/types";

interface Props {
  /** null = Add Panel: nothing is stored until "Create Panel". */
  panel: { id: string; name: string; position: string; active: boolean; pageIds: string[] | null } | null;
  /** Location chosen before opening the editor (create mode). */
  presetLocation?: string;
  siteId: string;
  siteName: string;
  content: PageContent;
  pages: { id: string; title: string; slug: string }[];
  forms: { id: string; name: string }[];
  events: { id: string; name: string }[];
  locations: PanelLocationOption[];
  canManage: boolean;
  /** Super admin: the Website dropdown shown in the editor header. */
  websiteField?: ReactNode;
}

/** ShowOff-style panel editor: Title, Location, Content, and a bottom bar with Active, Panel Options and Save. */
export function PanelEditor({ panel, presetLocation = "", siteId, siteName, content: initial, pages, forms, events, locations, canManage, websiteField }: Props) {
  const router = useRouter();
  const creating = panel === null;
  const [name, setName] = useState(panel?.name ?? "");
  const [position, setPosition] = useState(panel?.position ?? presetLocation);
  const [active, setActive] = useState(panel?.active ?? true);
  const [scope, setScope] = useState<"all" | "selected">(panel?.pageIds ? "selected" : "all");
  const [pageIds, setPageIds] = useState<string[]>(panel?.pageIds ?? []);
  const [content, setContent] = useState(initial);
  const [errors, setErrors] = useState<Record<string, string>>({});
  const [status, setStatus] = useState<{ ok: boolean; text: string } | null>(null);
  const [dirty, setDirty] = useState(false);
  const [options, setOptions] = useState(false);
  const [saving, start] = useTransition();
  const titleId = useId();
  const locId = useId();
  const ctx: FieldContext = useMemo(() => ({ siteId, forms, events, disabled: !canManage }), [siteId, forms, events, canManage]);

  useEffect(() => {
    if (!dirty) return;
    const h = (e: BeforeUnloadEvent) => e.preventDefault();
    window.addEventListener("beforeunload", h);
    return () => window.removeEventListener("beforeunload", h);
  }, [dirty]);

  const touch = () => { setDirty(true); setStatus(null); };
  const meta = () => ({ name, position, active, pageIds: scope === "all" ? null : pageIds });
  function save() {
    if (!position) { setErrors({ position: "Choose a location" }); setStatus({ ok: false, text: "Choose a location for this panel" }); return; }
    start(async () => {
      if (creating) {
        const res = await createPanelFromEditorAction({ siteId, meta: meta(), content });
        if (res.ok && res.data) { setDirty(false); router.replace(`/dashboard/panels/${res.data.id}`); return; }
        if (!res.ok) { setErrors(res.fieldErrors ?? {}); setStatus({ ok: false, text: res.error }); }
        return;
      }
      const res = await savePanelAction({ panelId: panel.id, meta: meta(), content });
      if (res.ok) { setDirty(false); setErrors({}); setStatus({ ok: true, text: res.message ?? "Saved" }); router.refresh(); }
      else { setErrors(res.fieldErrors ?? {}); setStatus({ ok: false, text: res.error }); }
    });
  }
  const contentErrors = Object.fromEntries(Object.entries(errors).filter(([k]) => k.startsWith("sections")));
  const unavailable = position !== "" && !locations.some((l) => l.key === position);

  return (
    <div className="ed -m-1 space-y-5 rounded-3xl bg-[var(--ed-bg)] p-4 sm:p-6">
      <div>
        <p className="text-xs text-[var(--ed-soft)]"><Link href="/dashboard/panels" className="underline">Panels</Link> · {siteName}</p>
        <h1 className="text-4xl font-bold tracking-tight text-[var(--ed-ink)]">{creating ? "Add Panel" : "Panels"}</h1>
        {websiteField ? <div className="mt-3">{websiteField}</div> : null}
      </div>
      {!canManage ? <p role="note" className="rounded-xl bg-white p-3 text-sm text-[var(--ed-ink)] ring-1 ring-[var(--ed-line)]">You have view-only access to this panel.</p> : null}

      <div className="space-y-1">
        <label htmlFor={titleId} className="block border-b border-[var(--ed-line)] pb-2 text-sm font-bold text-[var(--ed-ink)]">Title</label>
        <input id={titleId} disabled={!canManage} value={name} maxLength={80} placeholder="Panel title…" aria-invalid={errors.name ? true : undefined} onChange={(e) => { setName(e.target.value); touch(); }} className={cn(edInput, "mt-3 bg-white")} />
        {errors.name ? <p role="alert" className="text-xs font-medium text-[#b91c1c]">{errors.name}</p> : null}
      </div>

      <div className="space-y-1">
        <label htmlFor={locId} className="block border-b border-[var(--ed-line)] pb-2 text-sm font-bold text-[var(--ed-ink)]">Location</label>
        <select id={locId} disabled={!canManage} value={position} aria-invalid={errors.position ? true : undefined} onChange={(e) => { setPosition(e.target.value); touch(); }} className={cn(edInput, "mt-3 bg-white")}>
          <option value="">-Please Choose-</option>
          {unavailable ? <option value={position}>{position} (no longer available)</option> : null}
          {locations.map((l) => <option key={l.key} value={l.key}>{l.name}{l.builtIn ? "" : " (custom)"}</option>)}
        </select>
        <p className="text-xs text-[var(--ed-soft)]">{unavailable ? "This location is no longer available to this website. Pick another one before saving." : locations.find((l) => l.key === position)?.help}</p>
        {errors.position ? <p role="alert" className="text-xs font-medium text-[#b91c1c]">{errors.position}</p> : null}
      </div>

      <div>
        <p className="border-b border-[var(--ed-line)] pb-2 text-sm font-bold text-[var(--ed-ink)]">Content</p>
        <div className="mt-3"><ContentEditor content={content} onChange={(c) => { setContent(c); touch(); }} ctx={ctx} errors={contentErrors} disabled={!canManage} noun="panel" /></div>
      </div>

      <div role="region" aria-label="Panel actions" data-keep-editing className="sticky bottom-0 z-30 mt-6 flex flex-wrap items-center justify-end gap-3 rounded-3xl bg-[var(--ed-dark)] px-4 py-3 text-white shadow-xl">
        <div className="min-w-0 basis-full text-xs sm:basis-0 sm:flex-1" aria-live="polite">
          {status ? <span className={cn("font-bold", status.ok ? "text-[#9be7c9]" : "text-[#ffb4c8]")}>{status.text}</span> : dirty ? <span className="font-bold text-[#ffe08a]">Unsaved changes</span> : creating ? <span className="text-white/80">This panel has not been saved yet.</span> : null}
        </div>
        <div className="flex items-center gap-2 text-xs font-bold">
          <span>Active:</span>
          <YesNo label="Panel is active (shown on the website)" value={active} disabled={!canManage || saving} onChange={(v) => { setActive(v); touch(); }} />
        </div>
        <Pill variant="grey" onClick={() => setOptions(true)}>Panel Options <Settings className="size-3.5" aria-hidden /></Pill>
        <Pill variant="green" disabled={!canManage || saving || (!creating && !dirty)} onClick={save}>{saving ? "Saving…" : creating ? "Create Panel" : "Save"}</Pill>
      </div>

      {options ? (
        <Modal title="Panel Options" onClose={() => setOptions(false)}>
          <div className="px-6 pb-6">
            <EdTabs label="Panel options" tabs={[{ id: "general", label: "General" }]} value="general" onChange={() => undefined}>
              <fieldset className="space-y-3">
                <legend className="mb-1 text-xs font-bold text-[var(--ed-ink)]">Where it appears</legend>
                <label className="flex items-center gap-2 text-sm"><input type="radio" name="pn-scope" disabled={!canManage} checked={scope === "all"} onChange={() => { setScope("all"); touch(); }} />Show on all pages</label>
                <label className="flex items-center gap-2 text-sm"><input type="radio" name="pn-scope" disabled={!canManage} checked={scope === "selected"} onChange={() => { setScope("selected"); touch(); }} />Show on selected pages only</label>
                {scope === "selected" ? (
                  <div className="max-h-56 overflow-auto rounded-lg border border-[var(--ed-line)] p-2" role="group" aria-label="Pages this panel appears on">
                    {pages.length === 0 ? <p className="text-sm text-[var(--ed-soft)]">This website has no pages yet.</p> : null}
                    {pages.map((p) => (
                      <label key={p.id} className="flex items-center gap-2 py-0.5 text-sm">
                        <input type="checkbox" disabled={!canManage} checked={pageIds.includes(p.id)} onChange={(e) => { setPageIds(e.target.checked ? [...pageIds, p.id] : pageIds.filter((x) => x !== p.id)); touch(); }} />
                        {p.title} <span className="text-xs text-[var(--ed-soft)]">/{p.slug === "home" ? "" : p.slug}</span>
                      </label>
                    ))}
                  </div>
                ) : null}
              </fieldset>
            </EdTabs>
            <div className="mt-4 flex justify-end"><Pill variant="dark" className="min-w-28 py-3" onClick={() => setOptions(false)}>Submit</Pill></div>
          </div>
        </Modal>
      ) : null}
    </div>
  );
}
