/* LIA · ViewDetalle — con persistencia de análisis en Supabase */

const LIA_PROMPTS = {
  resumen: `Sos un abogado litigante costarricense con 20 años de experiencia EXCLUSIVA en contratacion publica. Dominas la Ley 9986, Reglamento 43808, Ley 8131, directrices CGR y procedimientos SICOP.
REGLAS: texto corrido profesional, sin markdown (**), sin ##, sin tablas. Parrafos separados. Maximo 380 palabras.
Realizá un RESUMEN EJECUTIVO con: (1) Objeto exacto y lo que realmente busca la institucion. (2) Monto estimado, modalidad (LP/LR/CD segun Art.33-35 Ley 9986) y numero SICOP. (3) Institucion contratante y unidad solicitante. (4) Plazo de ejecucion y lugar. (5) Fechas clave: apertura y cierre. (6) OPORTUNIDAD: por que este contrato es o no favorable. (7) RIESGOS: maximo 3, con impacto estimado. (8) RECOMENDACION FINAL con fundamento juridico: Participar activamente / Evaluar condiciones / No participar.`,

  condiciones: `Sos un abogado costarricense experto en contratacion publica (Ley 9986, Reglamento 43808). 20 años analizando carteles en SICOP.
REGLAS: sin markdown, numeracion simple 1. 2. 3., sin tablas. Maximo 380 palabras.
Extraé CONDICIONES CARTELARIAS con analisis juridico: (1) Objeto preciso y modalidad con fundamento (LP Art.33 / LR Art.34 / CD Art.35). (2) Plazo de ejecucion, inicio y posibles prorrogas (Art.53 Ley 9986). (3) Lugar y condiciones de entrega. (4) Garantia de participacion: porcentaje y vigencia (Art.52). (5) Garantia de cumplimiento: porcentaje y ejecucion automatica (Art.55). (6) Penalidades por atraso: porcentaje diario y maximo acumulado (Art.58 Reglamento 43808). (7) Condiciones de pago: plazo maximo 30 dias segun Ley 8131, forma, moneda. (8) Causales de resolucion contractual. (9) ALERTAS: clausulas que excedan lo normal o sean impugnables (Art.62 Ley 9986: especificaciones marcarias, plazos irrazonables, requisitos discriminatorios).`,

  admisibilidad: `Sos un abogado costarricense experto en requisitos de habilitacion (Ley 9986 Art.40, Reglamento 43808). Conoces SICOP y el sistema APC (Agenda de Proveedores de Costa Rica).
REGLAS: sin tablas, numeracion simple. Maximo 380 palabras. Se especifico sobre documentos, vigencias y donde se obtienen.
Lista REQUISITOS DE ADMISIBILIDAD en 3 grupos:
GRUPO A — DOCUMENTOS OBLIGATORIOS (descalifican si faltan): cada documento con vigencia maxima y donde se obtiene.
GRUPO B — CONDICIONES HABILITANTES: inscripcion APC/SICOP; Certificacion CCSS al dia (Art.74 Ley CCSS, vigencia 1 mes); Certificacion Hacienda al dia (vigencia 1 mes); Personeria Juridica o cedula fisica (vigencia 3 meses max); otros del cartel.
GRUPO C — CAUSALES DE RECHAZO AUTOMATICO (Art.40 Ley 9986): causales exactas del cartel; cuales son subsanables vs no subsanables.
ALERTA: indica si hay requisitos potencialmente impugnables como discriminatorios segun Art.62 Ley 9986.`,

  legales: `Sos un abogado costarricense con 20 años en contratacion publica. Especialista en Ley 9986, Ley 8131, Codigo de Comercio, normativa CCSS y Hacienda.
REGLAS: sin tablas, numeracion simple. Maximo 380 palabras. Cita el articulo exacto de cada requisito.
Extraé REQUISITOS LEGALES clasificados:
PERSONERIA Y CAPACIDAD: tipo de oferente habilitado (SA, SRL, persona fisica, consorcio Art.44 Ley 9986); certificacion de personeria Registro Nacional (vigencia max 3 meses); apoderados con poder suficiente.
SOLVENCIA TRIBUTARIA Y LABORAL: Certificacion CCSS al dia (Art.74, vigencia 1 mes); Certificacion Hacienda/FODESAF (vigencia 1 mes); Declaracion Jurada de no estar en lista negra CGR (Art.40 Ley 9986).
REGISTRO Y HABILITACION: inscripcion SICOP/APC (obligatorio Art.17 Ley 9986); permisos sectoriales (CFIA, SENASA, MS, ARESEP, etc.) si aplica; certificaciones tecnicas del objeto.
GARANTIAS LEGALES: forma admitida, porcentaje, banco emisor; carta compromiso garantia de cumplimiento.
PROHIBICIONES: Art.40 Ley 9986 (funcionarios, parientes, conflictos de interes).`,

  cronograma: `Sos un abogado costarricense experto en plazos legales de contratacion publica (Ley 9986, Reglamento 43808, directrices CGR para SICOP).
REGLAS: sin tablas, orden cronologico estricto, fechas exactas cuando esten en el cartel. Maximo 380 palabras.
Extraé el CRONOGRAMA COMPLETO — para cada hito: FECHA/PLAZO — DESCRIPCION — FUNDAMENTO LEGAL:
1. Publicacion SICOP y apertura del expediente.
2. Periodo de consultas (plazo minimo legal: 1/3 de dias hasta apertura segun Reglamento).
3. Respuesta de la Administracion a consultas.
4. Fecha y hora de apertura de ofertas.
5. Periodo estimado de evaluacion.
6. Estimacion de adjudicacion.
7. Recurso de apelacion: 10 dias habiles desde notificacion (Art.84 Ley 9986).
8. Formalizacion contractual / orden de inicio.
ALERTAS LEGALES: ¿El plazo de consultas cumple el minimo legal? ¿El plazo total es razonable? Calcula cuando vence el RECURSO DE OBJECION (5 dias habiles desde primera publicacion - Art.45 Ley 9986).`,

  checklist: `Sos un abogado costarricense experto en contratacion publica con 20 años en SICOP. Sabes exactamente que documentos pide el gobierno y cuales son los errores que hacen perder licitaciones.
FORMATO EXACTO por item: '[N]. [Nombre del documento] — [CRITICO/IMPORTANTE/OPCIONAL]: [razon breve + donde se obtiene + vigencia si aplica]'. Numeralos del 1 en adelante. Maximo 480 palabras.
Genera CHECKLIST en 3 secciones:
SECCION 1 — DOCUMENTOS LEGALES-ADMINISTRATIVOS: personeria, CCSS, Hacienda, APC, garantias, declaraciones juradas. Para cada CRITICO: consecuencia exacta de no presentarlo.
SECCION 2 — DOCUMENTOS TECNICOS: certificaciones tecnicas, especificaciones, muestras, fichas tecnicas, acreditaciones.
SECCION 3 — DOCUMENTOS ECONOMICO-FINANCIEROS: oferta economica, desglose de precios, estados financieros si aplica.`,

  evaluacion: `Sos un abogado costarricense experto en evaluacion de ofertas (Ley 9986 Art.60, Reglamento Art.55-65, directrices CGR). Conoces todas las metodologias de evaluacion usadas en SICOP.
REGLAS: sin tablas, numeracion clara. Maximo 380 palabras.
Analiza la METODOLOGIA DE EVALUACION: (1) Tipo: precio mas bajo / mejor valor / puntaje combinado (articulo aplicable). (2) Factores y ponderacion: precio (peso %), tecnico/calidad (peso %), experiencia (peso %), otros. (3) Formula de calculo del puntaje precio (tipo Pp = Po/Pi × peso o similar del cartel). (4) Requisitos de admisibilidad tecnica (pass/fail eliminatorios que no suman puntos). (5) ESTRATEGIA PARA MAXIMIZAR: en que factor hay mas posibilidad; que precio es competitivo; que documentos tecnicos marcan diferencia. (6) RIESGO: hay alguna metodologia impugnable o que favorezca a proveedor especifico (Art.62 Ley 9986).`,

  especificaciones: `Sos un abogado-tecnico costarricense experto en especificaciones de contratacion publica (Ley 9986 Art.62, Reglamento). Conoces estandares INTECO, SETENA, CFIA, MS, SENASA y normas ISO/ASTM aplicables en CR.
REGLAS: sin tablas, numeracion simple. Maximo 380 palabras.
Analiza ESPECIFICACIONES TECNICAS: (1) ESPECIFICACIONES MINIMAS INDISPENSABLES (eliminatorias si no se cumplen): lista numerada con consecuencia de incumplimiento. (2) ESPECIFICACIONES EVALUABLES (suman puntaje): lista numerada con peso o valor relativo. (3) NORMAS Y ESTANDARES APLICABLES: INTECO, ISO, ASTM, SETENA, CFIA, SENASA u otros. (4) PUNTOS CRITICOS: cuales son tecnicamente dificiles o requieren certificacion especial. (5) ALERTA ESPECIFICACIONES MARCARIAS (Art.62 Ley 9986): el cartel menciona marcas o modelos sin permitir equivalentes? Esto es IMPUGNABLE ante CGR. (6) RECOMENDACION: podrias cumplir todas? cuales verificar antes de ofertar.`,

  oferta: `Sos un abogado costarricense experto en redaccion de ofertas para contratacion publica (Ley 9986, Reglamento 43808, Ley del IVA). Has ganado cientos de licitaciones en SICOP.
REGLAS: sin tablas, texto profesional. Maximo 380 palabras.
Guia de OFERTA ECONOMICA: (1) ESTRUCTURA DE PRECIO: precio unitario vs global segun el cartel; desglose de componentes exigidos; IVA 13% (verificar si la institucion esta exonerada: CCSS, ICE, AyA tienen exoneracion parcial); moneda (colones o dolares). (2) PRECIO ESTRATEGICO: rango sugerido basado en el presupuesto estimado; margen de seguridad; conviene estar en el estimado o por debajo. (3) CONDICIONES COMERCIALES: plazo de validez (hasta adjudicacion firme minimo); forma de pago (Ley 8131: maximo 30 dias); condiciones de entrega / Incoterms si aplica. (4) AJUSTE DE PRECIOS: el cartel permite revision (Art.57 Ley 9986)? Indice INEC aplicable. (5) ERRORES COMUNES QUE DESCALIFICAN: no incluir desglose exigido; precios en moneda incorrecta; oferta condicionada (Art.40 Ley 9986 = causal de rechazo automatico).`,

  recursos: `Sos un abogado litigante costarricense especialista en recursos de contratacion publica ante CGR. Conoces perfectamente Ley 9986 Art.45 (recurso de objecion) y Art.84 (recurso de apelacion), y la jurisprudencia CGR reciente.
REGLAS: sin tablas, lenguaje juridico profesional. Maximo 420 palabras.
RECURSO DE OBJECION (Art.45 Ley 9986): PLAZO: 5 dias habiles desde primera publicacion SICOP. ANTE: la propia institucion contratante. Clausulas potencialmente objetables: para cada una indica (a) clausula exacta, (b) por que es ilegal, (c) articulo violado, (d) correccion solicitada.
RECURSO DE APELACION (Art.84 Ley 9986): PLAZO: 10 dias habiles desde notificacion de adjudicacion. ANTE: Contraloria General de la Republica (CGR). Condiciones del cartel que podrian fundamentar apelacion.
CONSULTA PREVIA: vale la pena hacer consultas formales al expediente antes de impugnar?
ESTRATEGIA: recomendas objetar alguna parte del cartel? Justifica con criterio juridico concreto.`,

  precios: `Sos un abogado costarricense experto en estructura de precios para licitaciones (Ley 9986, Ley del IVA, Ley 8131, indices INEC). Conoces los patrones de precios ganadores en SICOP.
REGLAS: sin tablas, numeracion simple. Maximo 380 palabras.
Analiza ESTRUCTURA DE PRECIOS: (1) Unidad de medida: precio unitario, global, por hora, por proyecto; cantidad de items. (2) Desglose exigido: lista exacta de columnas/rubros del formulario de oferta; requiere desglose por mano de obra, materiales, utilidad, gastos indirectos. (3) IVA Y EXONERACIONES: institucion exonerada del IVA? (CCSS, ICE, AyA exonerados parcialmente); cotizar con IVA, sin IVA, o IVA desglosado; tasa aplicable: 13% estandar o 4% servicios profesionales. (4) AJUSTE Y REAJUSTE: el cartel permite reajuste (Art.57 Ley 9986)? Formula e indices INEC si se especifican. (5) ANALISIS DE PRECIO ESTIMADO: el presupuesto es realista? hay riesgo de insuficiencia para cubrir costos reales. (6) TRAMPA COMUN: el cartel pide precio unitario pero evalua por precio total? Esto afecta la estrategia de presentacion.`,

  consultar: `Sos un abogado costarricense con 20 años de experiencia EXCLUSIVA en contratacion publica. Dominas: Ley 9986 (LGCP), Reglamento 43808, Ley 8131 (Administracion Financiera), Ley Organica CGR, Codigo de Comercio, normativa CCSS, Hacienda y FODESAF, directrices CGR, jurisprudencia administrativa y procedimientos SICOP/APC. Conoces los umbrales de modalidad (CD, LR, LP), plazos legales, causales de impugnacion, metodologias de evaluacion y practica real del mercado costarricense de licitaciones.
REGLAS: maximo 300 palabras, cita el articulo exacto de la ley, conclusion practica y accionable. Se especifico para Costa Rica.
Responde la siguiente consulta sobre el cartel:`,
};

function ViewDetalle({lic, onBack, credits, setCredits, userId}) {
  const D = window.LIA_DATA;
  const [tool, setTool]         = React.useState('resumen');
  const [results, setResults]   = React.useState({});
  const [loading, setLoading]   = React.useState(false);
  const [histLoaded, setHistLoaded] = React.useState(false);
  const [pregunta, setPregunta] = React.useState('');
  const [followupQ, setFollowupQ] = React.useState('');
  const [followupR, setFollowupR] = React.useState({});
  const [followupLoad, setFollowupLoad] = React.useState({});
  const [checks, setChecks]     = React.useState({});
  const [pdfReady, setPdfReady] = React.useState(!!window.LIA_PDF?.base64);
  const [histError, setHistError] = React.useState('');

  const dbId = lic._dbId && !String(lic._dbId).startsWith('local-') ? lic._dbId : null;

  /* Cargar análisis previos de Supabase al abrir */
  React.useEffect(() => {
    (async () => {
      await restaurarPDF();
      if (dbId && userId) cargarHistorial();
      else setHistLoaded(true);
      const savedChecks = localStorage.getItem('lia_checks_' + lic.id);
      if (savedChecks) try { setChecks(JSON.parse(savedChecks)); } catch(e) {}
    })();
  }, [lic.id, userId]);

  async function cargarHistorial() {
    if (!window._sb || !userId) { setHistLoaded(true); return; }
    setHistError('');
    try {
      const {data, error} = await window._sb.from('analyses')
        .select('analysis_type,result')
        .eq('user_id', userId)
        .eq('licitacion_id', dbId)
        .order('created_at', {ascending: false});
      if (error) throw error;
      if (data && data.length > 0) {
        const prev = {};
        data.forEach(a => { if (!prev[a.analysis_type]) prev[a.analysis_type] = a.result; });
        setResults(prev);
      } else {
        /* Fallback: buscar análisis sin licitacion_id que coincidan por nombre PDF */
        const pdfNom = (lic.nombre_pdf || lic.titulo || '').substring(0, 25);
        if (pdfNom) {
          const {data: fb} = await window._sb.from('analyses')
            .select('analysis_type,result')
            .eq('user_id', userId)
            .is('licitacion_id', null)
            .ilike('prompt_used', '%' + pdfNom + '%')
            .order('created_at', {ascending: false})
            .limit(20);
          if (fb && fb.length > 0) {
            const prev = {};
            fb.forEach(a => { if (!prev[a.analysis_type]) prev[a.analysis_type] = a.result; });
            setResults(prev);
          }
        }
      }
    } catch(e) {
      setHistError('Error cargando análisis guardados.');
      console.error('cargarHistorial:', e);
    }
    setHistLoaded(true);
  }

  async function restaurarPDF() {
    if (window.LIA_PDF?.base64) { setPdfReady(true); return; }
    /* IndexedDB — soporta PDFs de cualquier tamaño */
    if (window.LIA_PDF_STORE) {
      const idb = await window.LIA_PDF_STORE.load().catch(() => null);
      if (idb?.base64) {
        window.LIA_PDF = { base64: idb.base64, name: idb.name };
        setPdfReady(true); return;
      }
    }
    /* Fallback localStorage (solo PDFs < 4MB) */
    const n = localStorage.getItem('lia_pdf_name');
    const b = localStorage.getItem('lia_pdf_b64');
    if (n && b) {
      window.LIA_PDF = { base64: b, name: n };
      setPdfReady(true);
    } else {
      setPdfReady(false);
    }
  }

  function toggleCheck(key) {
    setChecks(prev => {
      const next = {...prev, [key]: !prev[key]};
      localStorage.setItem('lia_checks_' + lic.id, JSON.stringify(next));
      return next;
    });
  }

  async function run(id) {
    if (loading) return;

    /* Si ya existe resultado, solo mostrarlo SIN cobrar crédito */
    if (results[id]) { setTool(id); return; }

    if (credits <= 0) { alert('Sin créditos. Recargá en la sección Créditos.'); return; }

    const pdfBase64 = window.LIA_PDF?.base64;
    if (!pdfBase64 && id !== 'consultar') {
      alert('Primero cargá el PDF del cartel usando "Analizar cartel" en el menú lateral.');
      return;
    }

    let promptText = LIA_PROMPTS[id] || LIA_PROMPTS.consultar;
    if (id === 'consultar' && pregunta) promptText = LIA_PROMPTS.consultar + '\n\nConsulta: ' + pregunta;

    setLoading(true); setTool(id);
    try {
      const result = await window.LIA_CONFIG.analyze(promptText, pdfBase64, 2000);
      setResults(prev => ({...prev, [id]: result}));

      /* Guardar en servidor (bypasea RLS, descuenta crédito en DB) */
      try {
        const pdfNom = window.LIA_PDF?.name || lic.titulo;
        const { newCredits } = await window.LIA_CONFIG.serverCall('/api/save-analysis', {
          licitacion_id: dbId,
          analysis_type: id,
          prompt_used:   pdfNom,
          result:        result.substring(0, 8000),
        });
        setCredits(newCredits);
      } catch(saveErr) {
        setCredits(c => Math.max(0, c - 1));
        console.error('DB save-analysis:', saveErr.message);
        setHistError('⚠ Análisis ejecutado pero no guardado en BD: ' + saveErr.message);
      }
    } catch(e) { alert('Error: ' + e.message); }
    finally { setLoading(false); }
  }

  async function runFollowup(id) {
    if (!followupQ.trim() || followupLoad[id]) return;
    const pdfBase64 = window.LIA_PDF?.base64;
    const prev = results[id] || '';
    const prompt = 'Sos un abogado especialista en contratacion publica costarricense. Contexto previo:\n\n' + prev + '\n\nConsulta de seguimiento (max 200 palabras): ' + followupQ;
    setFollowupLoad(p => ({...p, [id]: true}));
    try {
      const r = await window.LIA_CONFIG.analyze(prompt, pdfBase64, 600);
      setFollowupR(p => ({...p, [id]: r}));
      setFollowupQ('');
    } catch(e) {}
    finally { setFollowupLoad(p => ({...p, [id]: false})); }
  }

  const herr = D.herramientas.find(h => h.id === tool) || D.herramientas[0];
  const isDone = !!results[tool];

  /* SICOP — siempre abre el portal, muestra el número para búsqueda manual */
  const sicopNumero = lic.sicop && !lic.sicop.toLowerCase().includes('manual') ? lic.sicop : null;

  return (
    <div className="fade-up">
      <button className="btn btn-ghost btn-sm" onClick={onBack} style={{marginBottom:16}}>
        <Icon name="back" size={14}/>Volver a licitaciones
      </button>

      {/* Header */}
      <div className="card" style={{marginBottom:'var(--gap-grid)'}}>
        <div style={{display:'flex',gap:16,alignItems:'flex-start',flexWrap:'wrap'}}>
          <InstBadge inst={lic.inst} size={54}/>
          <div style={{flex:1,minWidth:240}}>
            <div style={{display:'flex',alignItems:'center',gap:8,marginBottom:6,flexWrap:'wrap'}}>
              <span className="chip">{lic.modalidad}</span>
              <Estado e={lic.estado}/>
              {histLoaded && Object.keys(results).length > 0 &&
                <span className="tag" style={{color:'var(--success)',borderColor:'rgba(34,197,94,0.3)',background:'rgba(34,197,94,0.08)'}}>
                  <Icon name="check" size={11}/> {Object.keys(results).length} análisis guardados
                </span>
              }
            </div>
            <h1 className="font-display" style={{fontSize:22,fontWeight:800,letterSpacing:'-0.02em',lineHeight:1.2}}>{lic.titulo}</h1>
            <div style={{display:'flex',gap:14,marginTop:8,color:'var(--muted)',fontSize:12.5,flexWrap:'wrap'}}>
              <span>{D.instituciones[lic.inst]?.nombre || 'Institución Pública'}</span>
              <span className="mono">{lic.sicop}</span>
            </div>
          </div>
          <div style={{display:'flex',gap:22,alignItems:'center',flexWrap:'wrap'}}>
            <div style={{textAlign:'center'}}>
              <div style={{fontSize:10.5,color:'var(--muted)',textTransform:'uppercase',letterSpacing:'.08em',marginBottom:4}}>Monto estimado</div>
              <div className="amt" style={{fontSize:16}}>{D.fmtCRC(lic.monto)}</div>
            </div>
            <div style={{textAlign:'center'}}>
              <div style={{fontSize:10.5,color:'var(--muted)',textTransform:'uppercase',letterSpacing:'.08em',marginBottom:4}}>Cierre</div>
              <Plazo dias={lic.diasRestantes}/>
            </div>
            <div style={{textAlign:'center'}}>
              <div style={{fontSize:10.5,color:'var(--muted)',textTransform:'uppercase',letterSpacing:'.08em',marginBottom:6}}>Match IA</div>
              <MatchRing value={lic.match} size={42}/>
            </div>
          </div>
        </div>
        <hr className="divider"/>
        <div style={{display:'flex',gap:10,flexWrap:'wrap',alignItems:'center'}}>
          <div className="chip" style={{background: pdfReady ? 'rgba(34,197,94,0.08)' : 'rgba(248,113,113,0.08)', borderColor: pdfReady ? 'rgba(34,197,94,0.25)' : 'rgba(248,113,113,0.25)'}}>
            <Icon name="documentos" size={13} style={{color: pdfReady ? 'var(--success)' : '#f87171'}}/>
            {pdfReady ? 'PDF: ' + (window.LIA_PDF?.name||'').substring(0,40) : 'Sin PDF — subí el cartel para analizar'}
          </div>
          <div className="chip"><Icon name="check" size={13}/>Garantía {lic.garantia}</div>
          <div className="spacer"></div>
          {sicopNumero && (
            <div className="chip" style={{fontFamily:'var(--font-mono)',fontSize:11.5,letterSpacing:'.03em',userSelect:'all'}}
              title="Número para buscar en SICOP">
              {sicopNumero}
            </div>
          )}
          <a href="https://www.sicop.go.cr/" target="_blank" rel="noopener noreferrer" className="btn btn-ghost btn-sm">
            <Icon name="external" size={13}/>Abrir SICOP
          </a>
        </div>
      </div>

      {/* Workspace */}
      <div className="row" style={{alignItems:'flex-start'}}>
        {/* Tool rail */}
        <div style={{flex:'none',width:224}}>
          <div className="card" style={{padding:8,position:'sticky',top:0}}>
            <div style={{fontSize:10.5,color:'var(--muted-2)',textTransform:'uppercase',letterSpacing:'.12em',fontWeight:600,padding:'8px 10px 6px'}}>Herramientas LIA</div>
            <div style={{display:'flex',flexDirection:'column',gap:1}}>
              {D.herramientas.map(h => {
                const active = tool === h.id;
                const ready  = !!results[h.id];
                return (
                  <button key={h.id} onClick={() => { setTool(h.id); if (results[h.id]) return; }}
                    style={{display:'flex',alignItems:'center',gap:10,padding:'8px 10px',borderRadius:8,cursor:'pointer',textAlign:'left',width:'100%',transition:'all .14s',border:'1px solid '+(active?'var(--border-2)':'transparent'),background:active?'rgba(37,99,235,0.16)':'transparent',color:active?'#fff':'var(--silver)'}}>
                    <span className="font-display" style={{width:18,textAlign:'center',fontSize:14,color:active?'var(--accent-2)':'var(--muted)'}}>{h.icon}</span>
                    <span style={{flex:1,fontSize:12.5,fontWeight:active?600:500}}>{h.nombre}</span>
                    {ready
                      ? <span style={{width:7,height:7,borderRadius:99,background:'var(--success)',flex:'none'}}/>
                      : <span style={{fontSize:10,color:'var(--muted-2)',flex:'none'}}>1</span>}
                  </button>
                );
              })}
            </div>
          </div>
        </div>

        {/* Panel */}
        <div style={{flex:1,minWidth:0}}>
          <div className="card" style={{minHeight:420}}>
            <div className="section-head" style={{marginBottom:8}}>
              <span className="font-display" style={{fontSize:18,color:'var(--accent-2)'}}>{herr.icon}</span>
              <div>
                <div className="section-title">{herr.nombre}</div>
                <div className="section-sub">{herr.desc}</div>
              </div>
              <div className="spacer"/>
              {isDone && <span className="tag" style={{color:'var(--success)',borderColor:'rgba(34,197,94,0.3)',background:'rgba(34,197,94,0.08)',display:'inline-flex',alignItems:'center',gap:5}}><Icon name="check" size={12}/>Generado</span>}
            </div>
            <span style={{fontSize:10.5,color:'var(--muted)',border:'1px solid var(--border)',borderRadius:6,padding:'3px 9px'}}>§ {herr.ley}</span>
            <hr className="divider"/>

            {histError && <div style={{margin:'8px 0',padding:'8px 12px',background:'rgba(248,113,113,0.08)',border:'1px solid rgba(248,113,113,0.2)',borderRadius:8,fontSize:12,color:'#f87171'}}>{histError}</div>}
            {!histLoaded
              ? <div style={{textAlign:'center',padding:40,color:'var(--muted)'}}>Cargando historial…</div>
              : loading && tool === herr.id
                ? <LoadingPanel name={herr.nombre}/>
                : isDone
                  ? <ResultPanel
                      result={results[tool]}
                      toolId={tool}
                      followupQ={followupQ}
                      setFollowupQ={setFollowupQ}
                      followupR={followupR[tool]}
                      followupLoad={!!followupLoad[tool]}
                      onFollowup={() => runFollowup(tool)}
                      checks={checks}
                      onToggleCheck={toggleCheck}
                    />
                  : <RunPanel herr={herr} credits={credits} pregunta={pregunta} setPregunta={setPregunta} onRun={() => run(tool)}/>
            }
          </div>
        </div>
      </div>
    </div>
  );
}

function RunPanel({herr, credits, pregunta, setPregunta, onRun}) {
  return (
    <div style={{textAlign:'center',padding:'44px 20px'}}>
      <div style={{width:56,height:56,borderRadius:16,margin:'0 auto 18px',display:'grid',placeItems:'center',background:'rgba(37,99,235,0.12)',border:'1px solid var(--border-2)'}}>
        <span className="font-display" style={{fontSize:26,color:'var(--accent-2)'}}>{herr.icon}</span>
      </div>
      <div className="font-display" style={{fontSize:16,fontWeight:700}}>Ejecutar "{herr.nombre}"</div>
      <p className="muted" style={{fontSize:13,maxWidth:380,margin:'8px auto 20px',lineHeight:1.6}}>{herr.desc}. LIA lee el cartel y genera el resultado en segundos.</p>
      {herr.id === 'consultar' && (
        <div style={{maxWidth:440,margin:'0 auto 16px'}}>
          <input value={pregunta} onChange={e=>setPregunta(e.target.value)}
            placeholder="Escribí tu consulta sobre el cartel…"
            style={{width:'100%',background:'rgba(96,165,250,0.07)',border:'1px solid rgba(96,165,250,0.25)',borderRadius:10,padding:'10px 14px',color:'var(--text)',fontSize:14,fontFamily:'inherit',outline:'none',boxSizing:'border-box'}}/>
        </div>
      )}
      <button className="btn btn-primary" onClick={onRun} disabled={credits<=0||(herr.id==='consultar'&&!pregunta.trim())}>
        <Icon name="spark" size={15}/>Ejecutar · {herr.costo} crédito
      </button>
      <div className="muted" style={{fontSize:11.5,marginTop:12}}>
        {credits<=0?'⚠ Sin créditos — recargá en la sección Créditos':`Tenés ${credits} créditos disponibles`}
      </div>
    </div>
  );
}

function LoadingPanel({name}) {
  return (
    <div style={{textAlign:'center',padding:'60px 20px'}}>
      <div className="lia-spin" style={{width:40,height:40,margin:'0 auto 18px',border:'3px solid rgba(96,165,250,0.18)',borderTopColor:'var(--accent-2)',borderRadius:'99px'}}/>
      <div className="font-display" style={{fontSize:14,fontWeight:700,color:'var(--accent-2)'}}>Analizando con IA…</div>
      <div className="muted" style={{fontSize:12,marginTop:6}}>{name} · cruzando con Ley 9986</div>
    </div>
  );
}

function ResultPanel({result, toolId, followupQ, setFollowupQ, followupR, followupLoad, onFollowup, checks, onToggleCheck}) {
  const [copied, setCopied] = React.useState(false);
  function copy() { navigator.clipboard.writeText(result).then(()=>{setCopied(true);setTimeout(()=>setCopied(false),2000);}); }

  /* Checklist interactivo — parsear items numerados */
  const isChecklist = toolId === 'checklist';
  const checkItems = React.useMemo(() => {
    if (!isChecklist) return [];
    const lines = (result||'').split('\n').filter(l=>l.trim());
    const items = [];
    lines.forEach(line => {
      const m = line.match(/^[\*\s]*(\d+)\.\s+(.+)/);
      if (m) items.push({num: m[1], text: m[2], isCritico: line.toUpperCase().includes('CRÍTICO')||line.toUpperCase().includes('CRITICO')});
    });
    return items;
  }, [result, isChecklist]);

  return (
    <div>
      {/* Checklist interactivo */}
      {isChecklist && checkItems.length > 0 ? (
        <div style={{marginBottom:16}}>
          <div style={{fontSize:11.5,color:'var(--muted)',textTransform:'uppercase',letterSpacing:'.08em',fontWeight:600,marginBottom:12}}>
            {checkItems.filter(i=>checks['item_'+i.num]).length} / {checkItems.length} completados
          </div>
          <div style={{height:5,borderRadius:99,background:'rgba(96,165,250,0.1)',marginBottom:16,overflow:'hidden'}}>
            <div style={{height:'100%',background:'var(--success)',borderRadius:99,width:(checkItems.filter(i=>checks['item_'+i.num]).length/checkItems.length*100)+'%',transition:'width .4s'}}/>
          </div>
          <div style={{display:'flex',flexDirection:'column',gap:8}}>
            {checkItems.map(item => {
              const key = 'item_' + item.num;
              const done = !!checks[key];
              return (
                <div key={key} onClick={()=>onToggleCheck(key)}
                  style={{display:'flex',alignItems:'flex-start',gap:12,padding:'10px 14px',borderRadius:10,cursor:'pointer',transition:'all .15s',
                    background:done?'rgba(34,197,94,0.06)':'rgba(96,165,250,0.04)',
                    border:'1px solid '+(done?'rgba(34,197,94,0.25)':'rgba(96,165,250,0.12)'),
                    opacity:done?0.7:1}}>
                  <div style={{width:20,height:20,borderRadius:5,flex:'none',marginTop:1,display:'grid',placeItems:'center',
                    background:done?'var(--success)':'transparent',
                    border:'2px solid '+(done?'var(--success)':'var(--border-2)'),transition:'all .15s'}}>
                    {done&&<Icon name="check" size={12} style={{color:'#fff'}}/>}
                  </div>
                  <div style={{flex:1,minWidth:0}}>
                    <div style={{fontSize:13,fontWeight:500,textDecoration:done?'line-through':'none',color:done?'var(--muted)':'var(--text)'}}>{item.text}</div>
                    {item.isCritico&&!done&&<span style={{fontSize:10.5,fontWeight:700,color:'#f87171',marginTop:3,display:'inline-block'}}>CRÍTICO</span>}
                  </div>
                </div>
              );
            })}
          </div>
        </div>
      ) : (
        <div style={{background:'var(--surface-2)',border:'1px solid var(--border)',borderRadius:11,padding:18,fontSize:13.5,lineHeight:1.75,color:'var(--silver-2)',whiteSpace:'pre-wrap',marginBottom:16}}>
          {result}
        </div>
      )}

      {/* Followup */}
      {followupR && (
        <div style={{background:'rgba(37,99,235,0.07)',border:'1px solid rgba(37,99,235,0.2)',borderRadius:11,padding:16,fontSize:13,lineHeight:1.7,color:'var(--silver-2)',whiteSpace:'pre-wrap',marginBottom:16}}>
          <div style={{fontSize:10.5,color:'var(--accent-2)',fontWeight:700,marginBottom:8,textTransform:'uppercase',letterSpacing:'.06em'}}>✦ Respuesta LIA</div>
          {followupR}
        </div>
      )}

      <div style={{paddingTop:12,borderTop:'1px solid var(--border)',display:'flex',gap:8,alignItems:'center',flexWrap:'wrap'}}>
        <div className="search" style={{flex:1,minWidth:200,width:'auto',marginLeft:0,background:'var(--surface-2)'}}>
          <Icon name="spark" size={14} style={{color:'var(--accent-2)'}}/>
          <input placeholder="Preguntale a LIA sobre este resultado (gratis)…"
            value={followupQ} onChange={e=>setFollowupQ(e.target.value)}
            onKeyDown={e=>e.key==='Enter'&&onFollowup()}/>
        </div>
        <button className="btn btn-ghost btn-sm" onClick={onFollowup} disabled={followupLoad||!followupQ.trim()}>
          {followupLoad?'…':<><Icon name="spark" size={13}/>Preguntar</>}
        </button>
        <button className="btn btn-ghost btn-sm" onClick={copy}>
          <Icon name="download" size={13}/>{copied?'✓ Copiado':'Copiar'}
        </button>
      </div>
    </div>
  );
}

window.ViewDetalle = ViewDetalle;
