"use client";

import { useEffect, useRef, useState } from "react";
import { KeyRound, LogOut, Palette, UserCircle2 } from "lucide-react";
import { api } from "@/lib/api-client";
import { Button, Modal } from "@/components/ui";
import { getEffectiveTheme, setTheme, THEMES, type Theme } from "@/lib/theme";

export function ProfileMenu({ username }: { username: string }) {
  const [open, setOpen] = useState(false);
  const [showPasswordDialog, setShowPasswordDialog] = useState(false);
  const [theme, setThemeState] = useState<Theme>("light");
  const menuRef = useRef<HTMLDivElement | null>(null);

  useEffect(() => {
    // eslint-disable-next-line react-hooks/set-state-in-effect -- einmalige Übernahme aus localStorage
    setThemeState(getEffectiveTheme());
  }, []);

  useEffect(() => {
    function handleClickOutside(e: MouseEvent) {
      if (menuRef.current && !menuRef.current.contains(e.target as Node)) setOpen(false);
    }
    document.addEventListener("mousedown", handleClickOutside);
    return () => document.removeEventListener("mousedown", handleClickOutside);
  }, []);

  function chooseTheme(t: Theme) {
    setTheme(t);
    setThemeState(t);
  }

  return (
    <div className="relative" ref={menuRef}>
      <button
        type="button"
        onClick={() => setOpen((v) => !v)}
        className="flex items-center gap-2 rounded-full border border-border bg-surface py-1 pl-1 pr-3 text-sm shadow-sm hover:bg-surface-2"
      >
        <span className="flex h-7 w-7 items-center justify-center rounded-full bg-accent-soft text-xs font-semibold uppercase text-accent-soft-fg">
          {username.slice(0, 2)}
        </span>
        <span className="hidden font-medium text-fg sm:inline">{username}</span>
      </button>

      {open && (
        <div className="absolute right-0 top-11 z-30 w-60 overflow-hidden rounded-xl border border-border bg-surface shadow-lg">
          <div className="border-b border-border px-4 py-3">
            <div className="flex items-center gap-2">
              <UserCircle2 className="h-4 w-4 text-accent" />
              <span className="text-sm font-medium text-fg">{username}</span>
            </div>
          </div>

          <div className="border-b border-border px-4 py-3">
            <div className="mb-2 flex items-center gap-2 text-xs font-medium text-muted">
              <Palette className="h-3.5 w-3.5" /> Farbschema
            </div>
            <div className="grid grid-cols-3 gap-1">
              {THEMES.map((t) => (
                <button
                  key={t.value}
                  type="button"
                  onClick={() => chooseTheme(t.value)}
                  className={`rounded-lg border px-2 py-1.5 text-xs font-medium ${
                    theme === t.value
                      ? "border-accent bg-accent-soft text-accent-soft-fg"
                      : "border-border text-muted hover:bg-surface-2"
                  }`}
                >
                  {t.label}
                </button>
              ))}
            </div>
          </div>

          <MenuItem
            icon={<KeyRound className="h-4 w-4" />}
            label="Passwort ändern"
            onClick={() => {
              setOpen(false);
              setShowPasswordDialog(true);
            }}
          />
          <MenuItem
            icon={<LogOut className="h-4 w-4" />}
            label="Abmelden"
            onClick={async () => {
              await api.post("/api/auth/logout");
              window.location.href = "/login";
            }}
          />
        </div>
      )}

      {showPasswordDialog && <ChangePasswordDialog onClose={() => setShowPasswordDialog(false)} />}
    </div>
  );
}

function MenuItem({ icon, label, onClick }: { icon: React.ReactNode; label: string; onClick: () => void }) {
  return (
    <button
      type="button"
      onClick={onClick}
      className="flex w-full items-center gap-2.5 px-4 py-2.5 text-left text-sm text-muted hover:bg-accent-soft hover:text-accent-soft-fg"
    >
      {icon}
      {label}
    </button>
  );
}

function ChangePasswordDialog({ onClose }: { onClose: () => void }) {
  const [currentPassword, setCurrentPassword] = useState("");
  const [newPassword, setNewPassword] = useState("");
  const [newPasswordConfirm, setNewPasswordConfirm] = useState("");
  const [error, setError] = useState<string | null>(null);
  const [saving, setSaving] = useState(false);
  const [done, setDone] = useState(false);

  async function handleSubmit(e: React.FormEvent) {
    e.preventDefault();
    setError(null);
    if (newPassword !== newPasswordConfirm) {
      setError("Die neuen Passwörter stimmen nicht überein.");
      return;
    }
    setSaving(true);
    try {
      await api.post("/api/auth/change-password", { currentPassword, newPassword });
      setDone(true);
      setTimeout(onClose, 1200);
    } catch (err) {
      setError(err instanceof Error ? err.message : "Passwort ändern fehlgeschlagen.");
    } finally {
      setSaving(false);
    }
  }

  const inputClass =
    "w-full rounded-lg border border-border bg-input px-3 py-2 text-sm text-fg shadow-sm focus:border-accent focus:outline-none focus:ring-2 focus:ring-accent/25";

  // Über die zentrale Modal-Komponente: bringt Esc, Fokus-Falle und aria-modal mit
  // (SPEZIFIKATION 3.7.6) -- der Dialog war zuvor von Hand gebaut und ignorierte Esc.
  return (
    <Modal title="Passwort ändern" onClose={onClose}>
      <form onSubmit={handleSubmit} className="flex flex-col gap-3">
        <input type="password" placeholder="Aktuelles Passwort" autoComplete="current-password" value={currentPassword} onChange={(e) => setCurrentPassword(e.target.value)} className={inputClass} />
        <input type="password" placeholder="Neues Passwort" autoComplete="new-password" value={newPassword} onChange={(e) => setNewPassword(e.target.value)} className={inputClass} />
        <input type="password" placeholder="Neues Passwort bestätigen" autoComplete="new-password" value={newPasswordConfirm} onChange={(e) => setNewPasswordConfirm(e.target.value)} className={inputClass} />
        {error && <p className="text-sm text-danger">{error}</p>}
        {done && <p className="text-sm text-success">Passwort geändert.</p>}
        <div className="flex gap-2 pt-1">
          <Button type="submit" disabled={saving}>{saving ? "..." : "Speichern"}</Button>
          <Button type="button" variant="secondary" onClick={onClose}>Abbrechen</Button>
        </div>
      </form>
    </Modal>
  );
}
