import { FilyxClient } from "../api/filyxClient";
import type { FilyxSettings, FilyxTheme } from "../types";

type ImageTarget = { setImage(image: string): Promise<void> };

const esc = (value: string): string => value.replace(/[&<>"']/g, (character) => ({ "&": "&amp;", "<": "&lt;", ">": "&gt;", '"': "&quot;", "'": "&#39;" }[character] || character));

function iconForButton(iconId: string, title: string, accent: string, text: string): string {
  const key = title.normalize("NFD").replace(/[\u0300-\u036f]/g, "").toUpperCase();
  const stroke = `stroke="${text}" stroke-width="4" stroke-linecap="round" stroke-linejoin="round"`;
  if (iconId === "play") return `<circle cx="72" cy="57" r="23" fill="none" ${stroke}/><path d="m65 44 22 13-22 13Z" fill="${accent}"/>`;
  if (iconId === "pause") return `<circle cx="72" cy="57" r="23" fill="none" ${stroke}/><path d="M63 44h7v26h-7zm12 0h7v26h-7z" fill="${accent}"/>`;
  if (iconId === "next") return `<path d="m54 43 18 14-18 14zm19 0 18 14-18 14z" fill="${accent}"/><path d="M94 41v32" ${stroke}/>`;
  if (iconId === "camera") return `<rect x="45" y="43" width="54" height="35" rx="7" fill="none" ${stroke}/><path d="m55 43 6-10h22l6 10" ${stroke}/><circle cx="72" cy="60" r="9" fill="${accent}"/>`;
  if (iconId === "mic") return `<rect x="66" y="35" width="12" height="31" rx="6" fill="none" ${stroke}/><path d="M57 58a15 15 0 0 0 30 0M72 73v14m-12 0h24" ${stroke}/>`;
  if (iconId === "chat") return `<path d="M45 42h54v32a8 8 0 0 1-8 8H65L51 93v-11h-6a8 8 0 0 1-8-8Z" fill="none" ${stroke}/><path d="M58 59h28" stroke="${accent}" stroke-width="4" stroke-linecap="round"/>`;
  if (iconId === "trophy") return `<path d="M57 35h30v12h9v7c0 10-8 16-17 16-2 8-6 12-7 12s-5-4-7-12c-9 0-17-6-17-16v-7h9Z" fill="none" ${stroke}/><path d="M60 91h24m-12-9v9" stroke="${accent}" stroke-width="4" stroke-linecap="round"/>`;
  if (iconId === "star") return `<path d="m72 31 9 20 22 2-17 15 5 22-19-11-19 11 5-22-17-15 22-2Z" fill="${accent}" ${stroke}/>`;
  if (iconId === "bolt") return `<path d="m78 29-27 34h18l-3 35 28-39H76Z" fill="${accent}" ${stroke}/>`;
  if (iconId === "gear") return `<path d="M72 38 80 42l8-3 7 7-3 8 4 8 8 3v10l-8 3-4 8 3 8-7 7-8-3-8 4-8-4-8 3-7-7 3-8-4-8-8-3V65l8-3 4-8-3-8 7-7 8 3Z" fill="none" ${stroke}/><circle cx="72" cy="70" r="9" fill="${accent}"/>`;
  if (iconId === "sound") return `<path d="M48 63h12l17-14v42L60 77H48Z" fill="${accent}" ${stroke}/><path d="M85 57q10 10 0 20m7-27q17 17 0 34" fill="none" ${stroke}/>`;
  if (iconId === "source") return `<path d="M51 42h42v42H51zM43 50h8m42 0h8M43 76h8m42 0h8" fill="none" ${stroke}/><path d="M60 54h24v18H60z" fill="${accent}" opacity=".85"/>`;
  if (iconId === "stop") return `<circle cx="72" cy="57" r="23" fill="none" ${stroke}/><rect x="62" y="47" width="20" height="20" rx="4" fill="${accent}"/>`;
  if (iconId === "record") return `<circle cx="72" cy="57" r="24" fill="none" ${stroke}/><circle cx="72" cy="57" r="10" fill="${accent}"/>`;
  if (iconId === "scene") return `<path d="M45 39h54v37H45z" fill="none" ${stroke}/><path d="m52 70 12-13 10 9 8-10 10 14" fill="none" stroke="${accent}" stroke-width="4" stroke-linejoin="round"/><path d="M54 88h36" stroke="${accent}" stroke-width="3" stroke-linecap="round"/>`;
  if (iconId === "timer") return `<path d="M62 33h20v9H62z" fill="${accent}"/><circle cx="72" cy="60" r="24" fill="none" ${stroke}/><path d="M72 44v17l12 8" ${stroke}/>`;
  if (iconId === "discord") return `<path d="M48 42q24-14 48 0l5 38q-14 11-29 10-15 1-29-10Z" fill="none" ${stroke}/><circle cx="63" cy="61" r="5" fill="${accent}"/><circle cx="81" cy="61" r="5" fill="${accent}"/><path d="M63 75q9 6 18 0" ${stroke}/>`;
  if (iconId === "marker") return `<path d="M72 32c-15 0-26 12-26 26 0 20 26 39 26 39s26-19 26-39c0-14-11-26-26-26Z" fill="none" ${stroke}/><circle cx="72" cy="58" r="8" fill="${accent}"/>`;
  if (iconId === "refresh") return `<path d="M92 51a24 24 0 1 0 1 19" fill="none" ${stroke}/><path d="m92 39 10 15-18 2Z" fill="${accent}"/>`;
  if (/(SR|SOUND|PLAY|SUIVANT)/.test(key)) return `<circle cx="72" cy="57" r="20" fill="none" ${stroke}/><path d="M76 39v31a10 10 0 1 1-6-9V44l20-5v25a10 10 0 1 1-6-9V32Z" fill="${accent}"/>`;
  if (/(MINI|JEU|QUIZ)/.test(key)) return `<path d="M48 61c2-16 8-23 18-23h12c10 0 16 7 18 23l3 11c1 6-5 9-10 6l-9-7H64l-9 7c-5 3-11 0-10-6Z" fill="none" ${stroke}/><path d="M59 51v12m-6-6h12" ${stroke}/><circle cx="81" cy="53" r="4" fill="${accent}"/><circle cx="90" cy="62" r="4" fill="${accent}"/>`;
  if (/(STOP|REC|LIVE)/.test(key)) return `<circle cx="72" cy="57" r="22" fill="none" ${stroke}/><rect x="62" y="47" width="20" height="20" rx="4" fill="${accent}"/><path d="M46 82h52" stroke="${accent}" stroke-width="3" stroke-linecap="round"/>`;
  if (/(SUBATHON|TEMPS|TIMER)/.test(key)) return `<path d="M62 33h20v9H62z" fill="${accent}"/><circle cx="72" cy="60" r="24" fill="none" ${stroke}/><path d="M72 44v17l12 8" ${stroke}/>`;
  if (/(DISCORD)/.test(key)) return `<path d="M48 42q24-14 48 0l5 38q-14 11-29 10-15 1-29-10Z" fill="none" ${stroke}/><circle cx="63" cy="61" r="5" fill="${accent}"/><circle cx="81" cy="61" r="5" fill="${accent}"/><path d="M63 75q9 6 18 0" ${stroke}/>`;
  if (/(OBS|SCENE|SOURCE)/.test(key)) return `<path d="M45 39h54v37H45z" fill="none" ${stroke}/><path d="m52 70 12-13 10 9 8-10 10 14" fill="none" stroke="${accent}" stroke-width="4" stroke-linejoin="round"/><path d="M54 88h36" stroke="${accent}" stroke-width="3" stroke-linecap="round"/>`;
  if (/(MARQUEUR|MARKER)/.test(key)) return `<path d="M72 32c-15 0-26 12-26 26 0 20 26 39 26 39s26-19 26-39c0-14-11-26-26-26Z" fill="none" ${stroke}/><circle cx="72" cy="58" r="8" fill="${accent}"/>`;
  if (/(RAFRAICHIR|REFRESH)/.test(key)) return `<path d="M92 51a24 24 0 1 0 1 19" fill="none" ${stroke}/><path d="m92 39 10 15-18 2Z" fill="${accent}"/>`;
  return `<path d="m72 31 25 14v29L72 88 47 74V45Z" fill="none" ${stroke}/><path d="M61 59h22M72 48v22" stroke="${accent}" stroke-width="4" stroke-linecap="round"/>`;
}

export function renderThemedButton(title: string, theme: FilyxTheme, iconId = "auto", footer = "FILYX"): string {
  const raw = title.replace(/\n/g, " ").trim().toUpperCase().split(/\s+/).filter(Boolean).slice(0, 4);
  const lines = raw.length > 2 ? [raw.slice(0, 2).join(" "), raw.slice(2).join(" ")] : raw;
  const label = lines.map((line, index) => `<tspan x="72" dy="${index === 0 ? 0 : 18}">${esc(line.slice(0, 15))}</tspan>`).join("");
  const glyph = iconForButton(iconId, title, theme.accent, theme.text);
  const signature = esc(String(footer || "FILYX").trim().toUpperCase().slice(0, 14));
  const svg = `<svg xmlns="http://www.w3.org/2000/svg" width="144" height="144" viewBox="0 0 144 144"><defs><linearGradient id="f" x1="0" y1="0" x2="1" y2="1"><stop stop-color="${theme.accent}"/><stop offset=".48" stop-color="${theme.background}"/><stop offset="1" stop-color="#050508"/></linearGradient><filter id="g"><feGaussianBlur stdDeviation="5"/></filter></defs><rect x="5" y="5" width="134" height="134" rx="20" fill="${theme.accent}" opacity=".44" filter="url(#g)"/><path d="M22 12h100l10 10v100l-10 10H22l-10-10V22z" fill="url(#f)" stroke="${theme.accent}" stroke-width="2"/><path d="M22 33h100M22 111h100" stroke="${theme.text}" stroke-opacity=".28"/><path d="M26 17h22M96 17h22M26 127h22M96 127h22" stroke="${theme.text}" stroke-width="3" stroke-linecap="round"/>${glyph}<text x="72" y="93" text-anchor="middle" fill="${theme.text}" font-family="Arial,sans-serif" font-size="15" font-weight="900" letter-spacing=".5">${label}</text><text x="72" y="120" text-anchor="middle" fill="${theme.muted}" font-family="Arial,sans-serif" font-size="8" font-weight="800" letter-spacing="2">${signature}</text></svg>`;
  return `data:image/svg+xml;charset=utf-8,${encodeURIComponent(svg)}`;
}

export async function applyFilyxTheme(target: ImageTarget, settings: FilyxSettings, title: string): Promise<void> {
  let theme: FilyxTheme = { accent: "#f27622", background: "#171719", text: "#fff7ed", muted: "#d4a77e" };
  try {
    if (String(settings.apiKey || "").startsWith("fxsd_")) {
      const session = await new FilyxClient(settings).bootstrap(Number(settings.channelId || 0) || undefined);
      if (session.theme?.theme) theme = session.theme.theme;
    }
  } catch (_) {
    // The local FilyX palette remains available if the theme API is offline.
  }
  await target.setImage(renderThemedButton(title, theme, String(settings.buttonIcon || "auto"), String(settings.buttonFooter || "FILYX")));
}
