// ─────────────────────────────────────────────────────
// GUT-65 (F3.3) — BomPanel: lista de materiales por expediente.
// Sustituye `LISTA MATERIALES NNNN.xlsx`. Tabla agrupada por
// proveedor (como el Excel), edición inline de estado
// (pendiente → pedido → recibido) con fecha, alta/edición/borrado
// de líneas, y cabecera con % pedido / % recibido.
//
// Lo consume el drawer de expediente (GUT-63) vía window.BomPanel.
// expedienteId = pedidos.id.
// API REST bajo /api/expedientes/:pedidoId/bom (GUT-65 bom.js).
// ─────────────────────────────────────────────────────

const BOM_ESTADO_PILL = {
  pendiente: { cls: 'warn', label: 'Pendiente' },
  pedido:    { cls: 'info', label: 'Pedido' },
  recibido:  { cls: 'ok',   label: 'Recibido' },
};

const BOM_CAMPOS_VACIOS = {
  proveedor_id: '', material_id: '', codigo: '', nombre: '', dimensiones: '',
  cantidad: '', unidad: '', ral: '', apertura: '', guia: '',
  estado: 'pendiente', fecha_pedido: '', fecha_recepcion: '', observacion: '',
};

function fmtFechaBom(val) {
  if (!val) return '';
  const s = String(val).slice(0, 10);
  const [y, m, d] = s.split('-');
  return (y && m && d) ? `${d}/${m}/${y}` : s;
}

// ── Barra de progreso simple (% pedido / % recibido) ──
const BomBarra = ({ label, pct, cls }) => (
  <div style={{flex:'1 1 160px',minWidth:140}}>
    <div style={{display:'flex',justifyContent:'space-between',fontSize:11.5,marginBottom:3}}>
      <span className="muted">{label}</span><span style={{fontWeight:600}}>{pct}%</span>
    </div>
    <div style={{height:7,borderRadius:4,background:'var(--line)',overflow:'hidden'}}>
      <div style={{height:'100%',width:`${pct}%`,background:`var(--${cls})`,transition:'width .25s'}}/>
    </div>
  </div>
);

// ── Fila editable de línea BOM ──
const BomFila = ({ pedidoId, linea, idx, onChanged, onToast }) => {
  const [editing, setEditing] = React.useState(false);
  const [draft, setDraft] = React.useState(linea);
  const [busy, setBusy] = React.useState(false);
  React.useEffect(() => { setDraft(linea); }, [linea]);

  const toast = (m, e) => onToast && onToast(m, e);

  const cambiarEstado = async (estado) => {
    setBusy(true);
    try {
      await API.put(`/api/expedientes/${pedidoId}/bom/${linea.id}/estado`, { estado });
      onChanged && onChanged();
    } catch (e) { toast(e.message || 'Error al cambiar estado', true); }
    finally { setBusy(false); }
  };

  const guardar = async () => {
    setBusy(true);
    try {
      await API.put(`/api/expedientes/${pedidoId}/bom/${linea.id}`, {
        codigo: draft.codigo, nombre: draft.nombre, dimensiones: draft.dimensiones,
        cantidad: draft.cantidad === '' ? null : draft.cantidad, unidad: draft.unidad,
        ral: draft.ral, apertura: draft.apertura, guia: draft.guia,
        proveedor_id: draft.proveedor_id || null,
        fecha_pedido: draft.fecha_pedido || '', fecha_recepcion: draft.fecha_recepcion || '',
        observacion: draft.observacion,
      });
      setEditing(false);
      onChanged && onChanged();
    } catch (e) { toast(e.message || 'Error al guardar', true); }
    finally { setBusy(false); }
  };

  const borrar = async () => {
    if (!confirm('¿Eliminar esta línea?')) return;
    try {
      await API.del(`/api/expedientes/${pedidoId}/bom/${linea.id}`);
      onChanged && onChanged();
    } catch (e) { toast(e.message || 'Error al eliminar', true); }
  };

  const pill = BOM_ESTADO_PILL[linea.estado] || { cls: 'info', label: linea.estado };
  const idArticulo = linea.codigo || linea.material_referencia || '';
  const nombreArticulo = linea.nombre || linea.material_nombre || '—';

  if (editing) {
    const set = (k, val) => setDraft(d => ({ ...d, [k]: val }));
    return (
      <tr style={{background:'var(--bg-soft, #f9fafb)'}}>
        <td colSpan={10} style={{padding:8}}>
          <div className="fields-grid" style={{alignItems:'end'}}>
            <div className="field"><label>ID de artículo</label><input value={draft.codigo || ''} onChange={e=>set('codigo', e.target.value)} placeholder="C1, 6078, CC-1005…"/></div>
            <div className="field"><label>Nombre del artículo</label><input value={draft.nombre || ''} onChange={e=>set('nombre', e.target.value)}/></div>
            <div className="field"><label>Dimensiones</label><input value={draft.dimensiones || ''} onChange={e=>set('dimensiones', e.target.value)}/></div>
            <div className="field"><label>Cantidad</label><input type="number" value={draft.cantidad ?? ''} onChange={e=>set('cantidad', e.target.value)}/></div>
            <div className="field"><label>Unidad</label><input value={draft.unidad || ''} onChange={e=>set('unidad', e.target.value)}/></div>
            <div className="field"><label>RAL</label><input value={draft.ral || ''} onChange={e=>set('ral', e.target.value)}/></div>
            <div className="field"><label>Apertura</label><input value={draft.apertura || ''} onChange={e=>set('apertura', e.target.value)}/></div>
            <div className="field"><label>Guía inferior</label><input value={draft.guia || ''} onChange={e=>set('guia', e.target.value)}/></div>
            <div className="field"><label>F. pedido</label><input type="date" value={draft.fecha_pedido || ''} onChange={e=>set('fecha_pedido', e.target.value)}/></div>
            <div className="field"><label>F. recepción</label><input type="date" value={draft.fecha_recepcion || ''} onChange={e=>set('fecha_recepcion', e.target.value)}/></div>
            <div className="field" style={{gridColumn:'1 / -1'}}><label>Observación</label><input value={draft.observacion || ''} onChange={e=>set('observacion', e.target.value)}/></div>
            <div className="field" style={{display:'flex',gap:6}}>
              <button className="btn primary sm" onClick={guardar} disabled={busy}>Guardar</button>
              <button className="btn ghost sm" onClick={()=>{setEditing(false);setDraft(linea);}}>Cancelar</button>
            </div>
          </div>
        </td>
      </tr>
    );
  }

  return (
    <tr>
      <td className="mono">{idArticulo || '—'}</td>
      <td>
        {nombreArticulo}
        {linea.es_comparativa && (
          <span className="pill" style={{marginLeft:6,fontSize:10,opacity:.7}}>
            <span className="d"/>comparativa
          </span>
        )}
      </td>
      <td>{linea.dimensiones || '—'}</td>
      <td className="num">{linea.cantidad != null ? `${Number(linea.cantidad)}${linea.unidad ? ' ' + linea.unidad : ''}` : '—'}</td>
      <td>{linea.ral || '—'}</td>
      <td>{linea.apertura || '—'}</td>
      <td>{linea.guia || '—'}</td>
      <td>
        {linea.oc_id ? (
          // GUT-67: línea ligada a una OC → estado de solo lectura (la OC manda).
          <div style={{display:'flex',alignItems:'center',gap:6,flexWrap:'wrap'}}>
            <span className={`pill ${pill.cls}`}><span className="d"/>{pill.label}</span>
            <button
              className="btn ghost sm"
              title="estado gobernado por la OC"
              onClick={()=>window.dispatchEvent(new CustomEvent('erp:open-orden', { detail: { id: linea.oc_id } }))}
            >Ir a OC {linea.oc_numero || linea.oc_id}</button>
          </div>
        ) : (
          <>
            <select
              value={linea.estado}
              disabled={busy}
              onChange={e=>cambiarEstado(e.target.value)}
              title="Cambiar estado"
            >
              <option value="pendiente">Pendiente</option>
              <option value="pedido">Pedido</option>
              <option value="recibido">Recibido</option>
            </select>
            <span className={`pill ${pill.cls}`} style={{marginLeft:6}}><span className="d"/>{pill.label}</span>
          </>
        )}
      </td>
      <td className="num muted" style={{whiteSpace:'nowrap'}}>
        {linea.fecha_pedido ? `P: ${fmtFechaBom(linea.fecha_pedido)}` : ''}
        {linea.fecha_pedido && linea.fecha_recepcion ? <br/> : ''}
        {linea.fecha_recepcion ? `R: ${fmtFechaBom(linea.fecha_recepcion)}` : ''}
        {!linea.fecha_pedido && !linea.fecha_recepcion ? '—' : ''}
      </td>
      <td style={{whiteSpace:'nowrap'}}>
        <button className="btn ghost sm tip" data-tip="Editar" onClick={()=>setEditing(true)}><Icon name="edit" size={12}/></button>
        <button className="btn ghost sm tip" data-tip="Eliminar" style={{color:'var(--err)'}} onClick={borrar}><Icon name="trash" size={12}/></button>
      </td>
    </tr>
  );
};

// ── Formulario de alta de línea ──
const BomAlta = ({ pedidoId, proveedores, materiales, onAdded, onCancel, onToast }) => {
  const [draft, setDraft] = React.useState({ ...BOM_CAMPOS_VACIOS });
  const [busy, setBusy] = React.useState(false);
  const set = (k, val) => setDraft(d => ({ ...d, [k]: val }));

  // GUT-65: al elegir material del catálogo (GUT-64) se fija material_id y
  // se autocompletan nombre + unidad. Vaciar vuelve a texto libre.
  const elegirMaterial = (id) => {
    const m = materiales.find(x => String(x.id) === String(id));
    if (!m) { setDraft(d => ({ ...d, material_id: '' })); return; }
    setDraft(d => ({
      ...d,
      material_id: m.id,
      codigo: d.codigo || m.referencia || '',
      nombre: m.nombre || d.nombre,
      unidad: d.unidad || m.unidad_medida || '',
    }));
  };

  const guardar = async () => {
    if (!String(draft.nombre || '').trim()) { onToast && onToast('Indica el nombre/artículo de la línea', true); return; }
    setBusy(true);
    try {
      await API.post(`/api/expedientes/${pedidoId}/bom`, {
        ...draft,
        proveedor_id: draft.proveedor_id || null,
        cantidad: draft.cantidad === '' ? null : draft.cantidad,
      });
      onAdded && onAdded();
    } catch (e) { onToast && onToast(e.message || 'Error al crear línea', true); }
    finally { setBusy(false); }
  };

  return (
    <div style={{padding:12,marginBottom:12,border:'1px solid var(--line)',borderRadius:8}}>
      <div className="section-title" style={{marginTop:0}}>Nueva línea</div>
      <div className="fields-grid" style={{alignItems:'end'}}>
        <div className="field">
          <label>Proveedor</label>
          <select value={draft.proveedor_id} onChange={e=>set('proveedor_id', e.target.value)}>
            <option value="">— Sin proveedor —</option>
            {proveedores.map(p => <option key={p.id} value={p.id}>{p.nombre}</option>)}
          </select>
        </div>
        <div className="field">
          <label>Material (catálogo)</label>
          <select value={draft.material_id} onChange={e=>elegirMaterial(e.target.value)}>
            <option value="">— Texto libre —</option>
            {materiales.map(m => (
              <option key={m.id} value={m.id}>{m.referencia ? `${m.referencia} · ${m.nombre}` : m.nombre}</option>
            ))}
          </select>
        </div>
        <div className="field"><label>ID de artículo</label><input value={draft.codigo} onChange={e=>set('codigo', e.target.value)} placeholder="C1, 6078, CC-1005…"/></div>
        <div className="field"><label>Nombre del artículo *</label><input value={draft.nombre} onChange={e=>set('nombre', e.target.value)}/></div>
        <div className="field"><label>Dimensiones</label><input value={draft.dimensiones} onChange={e=>set('dimensiones', e.target.value)}/></div>
        <div className="field"><label>Cantidad</label><input type="number" value={draft.cantidad} onChange={e=>set('cantidad', e.target.value)}/></div>
        <div className="field"><label>Unidad</label><input value={draft.unidad} onChange={e=>set('unidad', e.target.value)} placeholder="ud, barra, m…"/></div>
        <div className="field"><label>RAL</label><input value={draft.ral} onChange={e=>set('ral', e.target.value)}/></div>
        <div className="field"><label>Apertura</label><input value={draft.apertura} onChange={e=>set('apertura', e.target.value)}/></div>
        <div className="field"><label>Guía inferior</label><input value={draft.guia} onChange={e=>set('guia', e.target.value)}/></div>
        <div className="field" style={{gridColumn:'1 / -1'}}><label>Observación</label><input value={draft.observacion} onChange={e=>set('observacion', e.target.value)}/></div>
        <div className="field" style={{display:'flex',gap:6}}>
          <button className="btn primary sm" onClick={guardar} disabled={busy}>{busy ? 'Guardando…' : 'Añadir'}</button>
          <button className="btn ghost sm" onClick={onCancel}>Cancelar</button>
        </div>
      </div>
    </div>
  );
};

const BomPanel = ({ expedienteId, onToast }) => {
  const [data, setData] = React.useState(null);
  const [proveedores, setProveedores] = React.useState([]);
  const [materiales, setMateriales] = React.useState([]);
  const [adding, setAdding] = React.useState(false);
  const [exporting, setExporting] = React.useState(false);

  // Genera el .xlsx de la lista y lo guarda en Documentos del expediente.
  const exportarExcel = async () => {
    if (exporting) return;
    setExporting(true);
    try {
      const r = await API.post(`/api/expedientes/${expedienteId}/bom/export-excel`, {});
      onToast && onToast(`Excel generado en Documentos › Lista de materiales (${r.lineas} línea${r.lineas === 1 ? '' : 's'}) ✓`);
    } catch (e) {
      onToast && onToast(e.message || 'Error al exportar', true);
    } finally {
      setExporting(false);
    }
  };

  const load = React.useCallback(() => {
    if (!expedienteId) return;
    API.get(`/api/expedientes/${expedienteId}/bom`)
      .then(d => setData(d))
      .catch(e => { setData({ lineas: [], resumen: null, proveedores: [] }); onToast && onToast(e.message || 'Error al cargar BOM', true); });
  }, [expedienteId]);

  React.useEffect(() => { load(); }, [load]);
  React.useEffect(() => {
    API.get('/api/proveedores')
      .then(rows => setProveedores(Array.isArray(rows) ? rows : (rows && rows.data) || []))
      .catch(() => setProveedores([]));
    API.get('/api/materiales')
      .then(rows => setMateriales(Array.isArray(rows) ? rows : (rows && rows.data) || []))
      .catch(() => setMateriales([]));
  }, []);

  if (!expedienteId) return <p className="muted" style={{fontSize:12}}>Expediente no disponible.</p>;
  if (data === null) return <p className="muted" style={{fontSize:12}}>Cargando…</p>;

  const r = data.resumen || { total: 0, pedido: 0, recibido: 0, pct_pedido: 0, pct_recibido: 0 };
  // Agrupar líneas por proveedor (orden ya viene del backend).
  const grupos = [];
  const byKey = {};
  for (const l of data.lineas) {
    const key = l.proveedor_id == null ? 'sin' : String(l.proveedor_id);
    if (!byKey[key]) { byKey[key] = { nombre: l.proveedor_nombre || 'Sin proveedor', proveedor_id: l.proveedor_id, lineas: [] }; grupos.push(byKey[key]); }
    byKey[key].lineas.push(l);
  }
  const resumenProv = {};
  for (const g of (data.proveedores || [])) {
    resumenProv[g.proveedor_id == null ? 'sin' : String(g.proveedor_id)] = g.resumen;
  }

  return (
    <div>
      {/* Cabecera con % pedido / % recibido */}
      <div style={{display:'flex',justifyContent:'space-between',alignItems:'center',gap:12,marginBottom:12,flexWrap:'wrap'}}>
        <div className="section-title" style={{margin:0}}>Lista de materiales (BOM)</div>
        <div style={{display:'flex',gap:6}}>
          <button className="btn ghost sm" onClick={exportarExcel} disabled={exporting || !(data.lineas||[]).length} title="Genera el Excel y lo guarda en Documentos del expediente">
            <Icon name="download" size={12}/> {exporting ? 'Exportando…' : 'Exportar a Excel'}
          </button>
          <button className="btn primary sm" onClick={()=>setAdding(a=>!a)}><Icon name="plus" size={12}/> Línea</button>
        </div>
      </div>
      <div style={{display:'flex',gap:18,marginBottom:16,flexWrap:'wrap'}}>
        <BomBarra label={`Pedido (${r.pedido}/${r.total})`} pct={r.pct_pedido} cls="info"/>
        <BomBarra label={`Recibido (${r.recibido}/${r.total})`} pct={r.pct_recibido} cls="ok"/>
      </div>

      {adding && (
        <BomAlta
          pedidoId={expedienteId}
          proveedores={proveedores}
          materiales={materiales}
          onAdded={()=>{ setAdding(false); load(); }}
          onCancel={()=>setAdding(false)}
          onToast={onToast}
        />
      )}

      {data.lineas.length === 0 && !adding && (
        <p className="muted" style={{fontSize:12}}>Sin líneas todavía. Añade líneas a mano o llegarán del configurador (Fase 4).</p>
      )}

      {grupos.map(g => {
        const rp = resumenProv[g.proveedor_id == null ? 'sin' : String(g.proveedor_id)];
        return (
          <div key={g.proveedor_id == null ? 'sin' : g.proveedor_id} style={{marginBottom:18}}>
            <div style={{display:'flex',alignItems:'center',gap:10,marginBottom:6}}>
              <span style={{fontWeight:700,fontSize:13}}>{g.nombre}</span>
              {rp && (
                <span className="muted" style={{fontSize:11.5}}>
                  {rp.pct_pedido}% pedido · {rp.pct_recibido}% recibido ({rp.recibido}/{rp.total})
                </span>
              )}
            </div>
            <table className="tbl" style={{fontSize:12.5}}>
              <thead>
                <tr>
                  <th>ID</th><th>Nombre del artículo</th><th>Dimensiones</th><th>Cantidad</th>
                  <th>RAL</th><th>Apertura</th><th>Guía inferior</th>
                  <th>Estado</th><th>Fechas</th><th></th>
                </tr>
              </thead>
              <tbody>
                {g.lineas.map((l, i) => (
                  <BomFila key={l.id} pedidoId={expedienteId} linea={l} idx={i} onChanged={load} onToast={onToast}/>
                ))}
              </tbody>
            </table>
          </div>
        );
      })}
    </div>
  );
};

window.BomPanel = BomPanel;
