/* ============================================================
   <DropdownMenu /> — open-on-click menu with spring entry,
   keyboard/outside dismiss, optional asChild trigger.

   Usage:
     <DropdownMenu>
       <DropdownMenuTrigger asChild>
         <button>Open</button>
       </DropdownMenuTrigger>
       <DropdownMenuContent align="end">
         <DropdownMenuLabel>Section</DropdownMenuLabel>
         <DropdownMenuGroup>
           <DropdownMenuItem onSelect={…}>…</DropdownMenuItem>
         </DropdownMenuGroup>
         <DropdownMenuSeparator />
         <DropdownMenuItem disabled>…</DropdownMenuItem>
       </DropdownMenuContent>
     </DropdownMenu>
   ============================================================ */

const DropdownCtx = React.createContext(null);

function DropdownMenu({ children, defaultOpen = false }) {
  const [open, setOpen] = React.useState(defaultOpen);
  const wrapRef = React.useRef(null);

  React.useEffect(() => {
    if (!open) return;
    const onDoc = (e) => {
      if (wrapRef.current && !wrapRef.current.contains(e.target)) setOpen(false);
    };
    const onKey = (e) => { if (e.key === "Escape") setOpen(false); };
    document.addEventListener("mousedown", onDoc);
    document.addEventListener("keydown", onKey);
    return () => {
      document.removeEventListener("mousedown", onDoc);
      document.removeEventListener("keydown", onKey);
    };
  }, [open]);

  const ctx = React.useMemo(() => ({ open, setOpen }), [open]);

  return (
    <DropdownCtx.Provider value={ctx}>
      <span ref={wrapRef} className="dropdown-menu" data-state={open ? "open" : "closed"}>
        {children}
      </span>
    </DropdownCtx.Provider>
  );
}

function DropdownMenuTrigger({ children, asChild = false, className = "" }) {
  const ctx = React.useContext(DropdownCtx);
  const open = ctx?.open;
  const toggle = (e) => { e.stopPropagation(); ctx?.setOpen(!open); };

  if (asChild && React.isValidElement(children)) {
    return React.cloneElement(children, {
      onClick: (e) => { toggle(e); children.props.onClick?.(e); },
      "aria-expanded": open,
      "aria-haspopup": "menu",
      "data-state": open ? "open" : "closed",
    });
  }
  return (
    <button
      type="button"
      onClick={toggle}
      aria-expanded={open}
      aria-haspopup="menu"
      data-state={open ? "open" : "closed"}
      className={`dropdown-menu__trigger ${className}`}
    >
      {children}
    </button>
  );
}

function DropdownMenuContent({
  children,
  side = "bottom",
  align = "end",
  sideOffset = 10,
  className = "",
}) {
  const ctx = React.useContext(DropdownCtx);
  const open = ctx?.open ?? false;
  return (
    <div
      className={`dropdown-menu__content ${open ? "is-open" : ""} ${className}`}
      data-side={side}
      data-align={align}
      style={{ "--dm-offset": `${sideOffset}px` }}
      role="menu"
      aria-hidden={!open}
    >
      <div className="dropdown-menu__panel">{children}</div>
    </div>
  );
}

function DropdownMenuLabel({ children }) {
  return <div className="dropdown-menu__label">{children}</div>;
}

function DropdownMenuSeparator() {
  return <div className="dropdown-menu__sep" role="separator"></div>;
}

function DropdownMenuGroup({ children }) {
  return <div className="dropdown-menu__group" role="group">{children}</div>;
}

function DropdownMenuItem({
  children, onSelect, disabled = false, variant = "default", className = "",
}) {
  const ctx = React.useContext(DropdownCtx);
  return (
    <button
      type="button"
      role="menuitem"
      disabled={disabled}
      data-disabled={disabled || undefined}
      className={`dropdown-menu__item dropdown-menu__item--${variant} ${disabled ? "is-disabled" : ""} ${className}`}
      onClick={() => {
        if (disabled) return;
        onSelect?.();
        ctx?.setOpen(false);
      }}
    >
      {children}
    </button>
  );
}

function DropdownMenuShortcut({ children }) {
  return <span className="dropdown-menu__shortcut">{children}</span>;
}

Object.assign(window, {
  DropdownMenu, DropdownMenuTrigger, DropdownMenuContent,
  DropdownMenuLabel, DropdownMenuSeparator, DropdownMenuGroup,
  DropdownMenuItem, DropdownMenuShortcut,
});
