import {
  BRANCO,
  contraste,
  escaparHtml,
  familiaDaFonte,
  linkDasFontes,
  misturar,
  pesoDoTitulo,
  QUASE_PRETO,
  srcSeguro,
  textoSobre,
  type ImagemDoBanner,
} from "./gerador-de-banner-modelos.ts";

/*
 * O desenho da imagem de produto que o assistente gera (gerar_imagem_do_produto).
 * HTML puro, testado sem banco; quem fotografa é o Chrome do gerador de
 * banners. Dois jeitos:
 * - "foto em fundo": a foto do produto centralizada num fundo liso (branco,
 *   a cor da loja ou a escolhida), com sombra suave quando é recorte, e um
 *   nome opcional embaixo. Não inventa nada da peça: só arruma a foto.
 * - "cartão com nome": sem foto, o nome do produto grande sobre a cor; serve
 *   de imagem provisória até a foto de verdade chegar.
 */

export const MODOS_DA_IMAGEM = ["foto em fundo", "cartão com nome"] as const;
export type ModoDaImagem = (typeof MODOS_DA_IMAGEM)[number];

export const FORMATOS_DA_IMAGEM = {
  quadrado: { largura: 1200, altura: 1200 },
  retrato: { largura: 1200, altura: 1500 },
} as const;
export type FormatoDaImagem = keyof typeof FORMATOS_DA_IMAGEM;

export type PedidoDaImagem = {
  modo: ModoDaImagem;
  formato: FormatoDaImagem;
  fundo: string;
  imagem: ImagemDoBanner | null;
  titulo: string;
  subtitulo: string;
  fonte: string;
};

/** A cor do texto sobre o fundo: a que se lê melhor. */
export function corDoTextoSobre(fundo: string) {
  return textoSobre(fundo) === BRANCO ? BRANCO : QUASE_PRETO;
}

export function htmlDaImagemDoProduto(pedido: PedidoDaImagem): string {
  const { largura, altura } = FORMATOS_DA_IMAGEM[pedido.formato];
  const fundo = pedido.fundo;
  const texto = corDoTextoSobre(fundo);
  const suave = misturar(texto, fundo, 0.35);
  const fonte = pedido.fonte;
  const familia = `'${familiaDaFonte(fonte)}', 'Inter', system-ui, sans-serif`;
  const temTitulo = pedido.titulo.trim().length > 0;
  const src = pedido.imagem ? srcSeguro(pedido.imagem.src) : null;

  let miolo: string;
  if (pedido.modo === "foto em fundo" && src) {
    const recorte = pedido.imagem!.tipo !== "foto";
    const sombra = recorte ? "filter:drop-shadow(0 28px 34px rgba(0,0,0,.18)) drop-shadow(0 6px 10px rgba(0,0,0,.10));" : "box-shadow:0 26px 60px rgba(0,0,0,.18);border-radius:18px;";
    const espacoDoTexto = temTitulo ? 0.2 : 0;
    miolo = `<div class="palco" style="height:${Math.round(altura * (1 - espacoDoTexto))}px">
  <img src="${src}" alt="" style="max-width:${Math.round(largura * (recorte ? 0.78 : 0.84))}px;max-height:${Math.round(altura * (1 - espacoDoTexto) * (recorte ? 0.78 : 0.84))}px;${sombra}">
</div>
${temTitulo ? `<div class="legenda" style="height:${Math.round(altura * espacoDoTexto)}px"><div id="titulo" class="titulo" data-max="${Math.round(largura * 0.06)}">${escaparHtml(pedido.titulo)}</div>${pedido.subtitulo ? `<div class="sub">${escaparHtml(pedido.subtitulo)}</div>` : ""}</div>` : ""}`;
  } else {
    miolo = `<div class="cartao">
  <div class="faixa" style="background:${suave}"></div>
  <div id="titulo" class="titulo grande" data-max="${Math.round(largura * 0.12)}">${escaparHtml(pedido.titulo || "Produto")}</div>
  ${pedido.subtitulo ? `<div class="sub grande">${escaparHtml(pedido.subtitulo)}</div>` : ""}
</div>`;
  }

  return `<!doctype html><html><head><meta charset="utf-8">
<link rel="stylesheet" href="${linkDasFontes([fonte])}">
<style>
*{margin:0;padding:0;box-sizing:border-box}
html,body{width:${largura}px;height:${altura}px;overflow:hidden}
body{background:${fundo};color:${texto};font-family:${familia};-webkit-font-smoothing:antialiased}
.palco{display:flex;align-items:center;justify-content:center;width:100%}
.palco img{display:block;object-fit:contain}
.legenda{display:flex;flex-direction:column;align-items:center;justify-content:flex-start;padding:0 ${Math.round(largura * 0.08)}px;text-align:center}
.titulo{font-weight:${pesoDoTitulo(fonte)};line-height:1.08;font-size:${Math.round(largura * 0.06)}px;max-width:100%;overflow-wrap:anywhere}
.sub{margin-top:.5em;color:${suave};font-size:${Math.round(largura * 0.028)}px;line-height:1.3}
.cartao{position:relative;width:100%;height:100%;display:flex;flex-direction:column;align-items:center;justify-content:center;padding:${Math.round(largura * 0.1)}px;text-align:center}
.faixa{position:absolute;left:${Math.round(largura * 0.1)}px;right:${Math.round(largura * 0.1)}px;bottom:${Math.round(altura * 0.12)}px;height:${Math.max(6, Math.round(altura * 0.008))}px;border-radius:99px;opacity:.6}
.titulo.grande{font-size:${Math.round(largura * 0.12)}px;line-height:1.02}
.sub.grande{font-size:${Math.round(largura * 0.04)}px;margin-top:.8em}
</style></head><body>
${miolo}
<script>
(async function(){
  try{await Promise.race([document.fonts.load("${pesoDoTitulo(fonte)} 40px '${familiaDaFonte(fonte)}'"),new Promise(function(r){setTimeout(r,8000)})]);await document.fonts.ready}catch(e){}
  var t=document.getElementById("titulo");
  if(t){var p=t.parentElement,tam=parseFloat(getComputedStyle(t).fontSize),min=${Math.round(largura * 0.025)};
    var cabe=function(){return p.scrollHeight<=p.clientHeight+1&&t.scrollWidth<=t.clientWidth+1};
    for(var i=0;i<80&&!cabe()&&tam>min;i++){tam*=0.94;t.style.fontSize=tam+"px"}}
  var imgs=[].slice.call(document.images);
  await Promise.all(imgs.map(function(im){return im.complete?null:new Promise(function(r){im.onload=im.onerror=r})}));
  document.body.setAttribute("data-pronto","1");
})();
</script>
</body></html>`;
}

/** O fundo pedido, conferido: só cor em hexadecimal. */
export function fundoValido(cor: string | null | undefined, padrao: string) {
  const limpa = String(cor ?? "").trim();
  return /^#[0-9a-f]{6}$/i.test(limpa) ? limpa.toUpperCase() : padrao;
}

/** Texto escuro em fundo escuro (e o contrário) se lê mal: o aviso da prévia. */
export function contrasteBaixo(fundo: string) {
  return contraste(corDoTextoSobre(fundo), fundo) < 3;
}
