// ─────────────────────────────────────────────────────
// ORDENES drawer + create/edit modal.
// Detail from /api/ordenes/:id and material lines from /api/ordenes/:id/materiales.
// ─────────────────────────────────────────────────────

const ORDEN_LINE_ESTADOS = ['PENDIENTE','CONFIRMADA','EN_TRANSITO','RECIBIDA_PARCIAL','RECIBIDA','CANCELADA'];
const ORDEN_PEDIDO_MATERIAL_FIELDS = [
  ['medicion','Medición'],
  ['perfiles','Perfiles'],
  ['lacado','Lacado'],
  ['vidrios','Vidrios'],
  ['tubos','Tubos'],
  ['panel_sandwich','Panel Sándwich'],
  ['accesorios','Accesorios'],
  ['cerraduras','Cerraduras'],
  ['toldo_estores','Toldo / Estores'],
  ['otros_materiales','Otros materiales'],
];

const ordenDateToInput = (s) => {
  if (!s) return '';
  const t = String(s).trim();
  if (/^\d{4}-\d{2}-\d{2}/.test(t)) return t.slice(0, 10);
  const m = /^(\d{2})\/(\d{2})\/(\d{4})$/.exec(t);
  return m ? `${m[3]}-${m[2]}-${m[1]}` : '';
};

const blankOrdenMaterial = () => ({
  material_id: '', cantidad: 1, precio_unitario: '', estado: 'PENDIENTE',
  fecha_recepcion: '', notas: '', pedido_material_field: '',
});

const inputStyle = {
  width: '100%',
  padding: '6px 8px',
  border: '1px solid var(--line)',
  borderRadius: 4,
  background: 'var(--surface)',
  fontSize: 12.5,
};

const materialName = (m) => [m.codigo, m.nombre].filter(Boolean).join(' — ') || m.material_nombre || `Material ${m.id}`;

const OrdenesDrawer = ({ orden, estados, proveedores, onClose, onEdit, onDeleted, onChanged, onToast }) => {
  const [tab, setTab] = React.useState('detalle');
  const [detail, setDetail] = React.useState(null);
  const [materials, setMaterials] = React.useState([]);
  const [catalog, setCatalog] = React.useState([]);
  const [drafts, setDrafts] = React.useState({});
  const [adding, setAdding] = React.useState(false);
  const [newMat, setNewMat] = React.useState(blankOrdenMaterial());
  const [busyId, setBusyId] = React.useState(null);

  const loadDetail = React.useCallback((id) => {
    API.get(`/api/ordenes/${id}`).then(d => {
      setDetail(d);
      setMaterials(d.materiales || []);
      const next = {};
      (d.materiales || []).forEach(m => {
        next[m.id] = {
          cantidad: m.cantidad || 1,
          precio_unitario: m.precio_unitario == null ? '' : m.precio_unitario,
          estado: m.estado || 'PENDIENTE',
          fecha_recepcion: ordenDateToInput(m.fecha_recepcion),
          notas: m.notas || '',
          pedido_id: m.pedido_id || '',
          linea_pedido_id: m.linea_pedido_id || '',
          pedido_material_field: m.pedido_material_field || '',
        };
      });
      setDrafts(next);
    }).catch(e => onToast && onToast(e.message || 'Error al cargar orden', true));
  }, [onToast]);

  React.useEffect(() => {
    if (!orden) { setDetail(null); setMaterials([]); setDrafts({}); return; }
    setTab('detalle');
    setDetail(null);
    setAdding(false);
    loadDetail(orden.id);
    API.get('/api/materiales', { activo: 'true', solo_hijos: 'true' })
      .then(rows => setCatalog(Array.isArray(rows) ? rows : []))
      .catch(() => {});
  }, [orden && orden.id]);

  if (!orden) return null;
  const d = detail || orden;

  const setDraft = (id, key, value) => setDrafts(ds => ({ ...ds, [id]: { ...(ds[id] || {}), [key]: value } }));

  const saveMaterial = async (m) => {
    const draft = drafts[m.id] || {};
    setBusyId(m.id);
    try {
      await API.put(`/api/ordenes/${d.id}/materiales/${m.id}`, {
        cantidad: parseFloat(draft.cantidad) || 1,
        precio_unitario: draft.precio_unitario !== '' ? parseFloat(draft.precio_unitario) : null,
        estado: draft.estado || 'PENDIENTE',
        fecha_recepcion: draft.fecha_recepcion || null,
        notas: draft.notas || null,
        pedido_id: draft.pedido_id || null,
        linea_pedido_id: draft.linea_pedido_id || null,
        pedido_material_field: draft.pedido_material_field || null,
      });
      onToast && onToast('Material actualizado ✓');
      loadDetail(d.id);
      onChanged && onChanged();
    } catch (e) {
      onToast && onToast(e.message || 'Error al guardar material', true);
    } finally {
      setBusyId(null);
    }
  };

  const addMaterial = async () => {
    if (!newMat.material_id) {
      onToast && onToast('Selecciona un material', true);
      return;
    }
    setBusyId('new');
    try {
      await API.post(`/api/ordenes/${d.id}/materiales`, {
        material_id: parseInt(newMat.material_id, 10),
        cantidad: parseFloat(newMat.cantidad) || 1,
        precio_unitario: newMat.precio_unitario !== '' ? parseFloat(newMat.precio_unitario) : null,
        estado: newMat.estado || 'PENDIENTE',
        fecha_recepcion: newMat.fecha_recepcion || null,
        notas: newMat.notas || null,
        pedido_material_field: newMat.pedido_material_field || null,
      });
      setNewMat(blankOrdenMaterial());
      setAdding(false);
      onToast && onToast('Material añadido ✓');
      loadDetail(d.id);
      onChanged && onChanged();
    } catch (e) {
      onToast && onToast(e.message || 'Error al añadir material', true);
    } finally {
      setBusyId(null);
    }
  };

  const deleteMaterial = async (m) => {
    if (!confirm('¿Eliminar este material de la orden?')) return;
    try {
      await API.del(`/api/ordenes/${d.id}/materiales/${m.id}`);
      onToast && onToast('Material eliminado');
      loadDetail(d.id);
      onChanged && onChanged();
    } catch (e) {
      onToast && onToast(e.message || 'Error al eliminar material', true);
    }
  };

  const deleteOrden = async () => {
    if (!confirm(`¿Eliminar la orden ${d.numero || d.id}? No se puede deshacer.`)) return;
    try {
      await API.del(`/api/ordenes/${d.id}`);
      onToast && onToast('Orden eliminada');
      onDeleted && onDeleted();
    } catch (e) {
      onToast && onToast(e.message || 'Error al eliminar', true);
    }
  };

  const exportFile = (ext) => {
    const fname = `orden_${d.numero || d.id}.${ext === 'excel' ? 'xlsx' : 'pdf'}`;
    API.download(`/api/ordenes/export/${d.id}/${ext}`, fname)
      .catch(e => onToast && onToast(e.message || 'Error al exportar', true));
  };

  const total = materials.reduce((s, m) => s + ((parseFloat(m.cantidad) || 0) * (parseFloat(m.precio_unitario) || 0)), 0);
  const pedidosInfo = [d.pedidos_numeros, d.pedidos_clientes].filter(Boolean).join(' · ');

  return (
    <>
      <div className={`drawer-bg ${orden ? 'open' : ''}`} onClick={onClose}/>
      <div className={`drawer ${orden ? 'open' : ''}`}>
        <div className="dr-head">
          <span className="id mono">{d.numero || d.id}</span>
          <h2>{d.proveedor_nombre || 'Sin proveedor'}</h2>
          <OrdenEstadoPill estado={d.estado}/>
          <div className="actions">
            <button className="btn ghost sm tip" data-tip="Editar" onClick={() => onEdit && onEdit(d.id)}><Icon name="edit" size={13}/></button>
            <button className="btn ghost sm tip" data-tip="Exportar Excel" onClick={() => exportFile('excel')}><Icon name="download" size={13}/></button>
            <button className="btn ghost sm tip" data-tip="Exportar PDF" onClick={() => exportFile('pdf')}><Icon name="print" size={13}/></button>
            <button className="btn ghost sm tip" data-tip="Eliminar" onClick={deleteOrden} style={{color:'var(--err)'}}><Icon name="trash" size={13}/></button>
            <button className="icon-btn" onClick={onClose}><Icon name="x"/></button>
          </div>
        </div>

        <div className="dr-tabs">
          <button className={tab==='detalle'?'on':''} onClick={()=>setTab('detalle')}>Detalle</button>
          <button className={tab==='materiales'?'on':''} onClick={()=>setTab('materiales')}>Materiales ({materials.length})</button>
        </div>

        <div className="dr-body">
          {!detail && <div style={{padding:24,textAlign:'center',color:'var(--ink-3)'}}>Cargando…</div>}

          {detail && tab === 'detalle' && (
            <div>
              <div className="section-title">Identificación</div>
              <div className="fields-grid">
                <div className="field"><label>Nº orden</label><div className="v mono">{d.numero || '—'}</div></div>
                <div className="field"><label>Estado</label><div className="v"><OrdenEstadoPill estado={d.estado}/></div></div>
                <div className="field full"><label>Proveedor</label><div className="v">{d.proveedor_nombre || '—'}</div></div>
                <div className="field"><label>F. pedido</label><div className="v">{d.fecha_pedido || '—'}</div></div>
                <div className="field"><label>F. entrega estimada</label><div className="v">{d.fecha_entrega_estimada || '—'}</div></div>
                <div className="field"><label>F. entrega real</label><div className="v">{d.fecha_entrega_real || '—'}</div></div>
                <div className="field full"><label>Pedidos relacionados</label><div className="v">{pedidosInfo || '—'}</div></div>
                <div className="field"><label>Items</label><div className="v">{materials.length}</div></div>
                <div className="field"><label>Importe estimado</label><div className="v strong">{fmtOrdenMoney(total)}</div></div>
                <div className="field full"><label>Notas</label><div className="v">{d.notas || '—'}</div></div>
              </div>
            </div>
          )}

          {detail && tab === 'materiales' && (
            <div>
              <div style={{display:'flex',justifyContent:'space-between',alignItems:'center',marginBottom:10}}>
                <div className="section-title" style={{margin:0}}>Materiales de la orden</div>
                <button className="btn primary" style={{fontSize:12}} onClick={() => setAdding(true)}><Icon name="plus" size={12}/> Añadir</button>
              </div>

              {adding && (
                <div style={{padding:12,border:'1px solid var(--line)',borderRadius:6,background:'var(--surface)',marginBottom:12}}>
                  <MaterialEditGrid
                    value={newMat}
                    catalog={catalog}
                    onChange={(k,v) => setNewMat(m => ({ ...m, [k]: v }))}
                    includeMaterial
                  />
                  <div style={{display:'flex',gap:8,marginTop:10}}>
                    <button className="btn primary" style={{fontSize:12}} onClick={addMaterial} disabled={busyId === 'new'}>{busyId === 'new' ? 'Guardando…' : 'Guardar'}</button>
                    <button className="btn ghost" style={{fontSize:12}} onClick={() => setAdding(false)}>Cancelar</button>
                  </div>
                </div>
              )}

              {materials.length === 0 && !adding && (
                <div className="muted" style={{fontSize:12,padding:'16px 0'}}>Sin materiales registrados.</div>
              )}

              <div style={{display:'flex',flexDirection:'column',gap:10}}>
                {materials.map(m => {
                  const draft = drafts[m.id] || {};
                  return (
                    <div key={m.id} style={{padding:12,border:'1px solid var(--line)',borderRadius:6,background:'var(--surface)'}}>
                      <div style={{display:'flex',justifyContent:'space-between',gap:12,marginBottom:10}}>
                        <div>
                          <div style={{fontWeight:650,fontSize:13}}>{m.material_nombre || 'Material'}</div>
                          <div className="muted" style={{fontSize:11.5}}>{m.categoria_nombre || m.familia || '—'} · {m.unidad_medida || 'ud'}</div>
                        </div>
                        <div style={{display:'flex',gap:6,alignItems:'center'}}>
                          <button className="btn ghost sm" onClick={() => saveMaterial(m)} disabled={busyId === m.id}>{busyId === m.id ? 'Guardando…' : 'Guardar'}</button>
                          <button className="icon-btn" style={{color:'var(--err)'}} onClick={() => deleteMaterial(m)}><Icon name="trash" size={12}/></button>
                        </div>
                      </div>
                      <MaterialEditGrid
                        value={draft}
                        catalog={catalog}
                        onChange={(k,v) => setDraft(m.id, k, v)}
                      />
                    </div>
                  );
                })}
              </div>
            </div>
          )}
        </div>
      </div>
    </>
  );
};

const MaterialEditGrid = ({ value, catalog, onChange, includeMaterial }) => (
  <div className="fields-grid">
    {includeMaterial && (
      <div className="field full">
        <label>Material</label>
        <select value={value.material_id || ''} onChange={e => onChange('material_id', e.target.value)} style={inputStyle}>
          <option value="">— Material —</option>
          {catalog.map(m => <option key={m.id} value={m.id}>{materialName(m)}</option>)}
        </select>
      </div>
    )}
    <div className="field">
      <label>Cantidad</label>
      <input type="number" min="0.01" step="any" value={value.cantidad || ''} onChange={e => onChange('cantidad', e.target.value)} style={inputStyle}/>
    </div>
    <div className="field">
      <label>Precio unitario</label>
      <input type="number" min="0" step="0.01" value={value.precio_unitario || ''} onChange={e => onChange('precio_unitario', e.target.value)} style={inputStyle}/>
    </div>
    <div className="field">
      <label>Estado</label>
      <select value={value.estado || 'PENDIENTE'} onChange={e => onChange('estado', e.target.value)} style={inputStyle}>
        {ORDEN_LINE_ESTADOS.map(s => <option key={s} value={s}>{ordenEstadoMeta(s).label}</option>)}
      </select>
    </div>
    <div className="field">
      <label>Campo pedido</label>
      <select value={value.pedido_material_field || ''} onChange={e => onChange('pedido_material_field', e.target.value)} style={inputStyle}>
        <option value="">Auto</option>
        {ORDEN_PEDIDO_MATERIAL_FIELDS.map(([k, label]) => <option key={k} value={k}>{label}</option>)}
      </select>
    </div>
    <div className="field">
      <label>F. recepción</label>
      <input type="date" value={value.fecha_recepcion || ''} onChange={e => onChange('fecha_recepcion', e.target.value)} style={inputStyle}/>
    </div>
    <div className="field full">
      <label>Notas</label>
      <input value={value.notas || ''} onChange={e => onChange('notas', e.target.value)} style={inputStyle}/>
    </div>
  </div>
);

const OrdenesForm = ({ ordenId, estados, proveedores, onClose, onSaved, onToast }) => {
  const isEdit = ordenId != null;
  const [loading, setLoading] = React.useState(isEdit);
  const [saving, setSaving] = React.useState(false);
  const [catalog, setCatalog] = React.useState([]);
  const [data, setData] = React.useState({
    numero: '', proveedor_id: '', estado: 'PENDIENTE',
    fecha_pedido: new Date().toISOString().slice(0, 10),
    fecha_entrega_estimada: '', fecha_entrega_real: '', notas: '',
  });
  const [lines, setLines] = React.useState([]);

  React.useEffect(() => {
    let alive = true;
    API.get('/api/materiales', { activo: 'true', solo_hijos: 'true' })
      .then(rows => { if (alive) setCatalog(Array.isArray(rows) ? rows : []); })
      .catch(() => {});
    if (isEdit) {
      API.get(`/api/ordenes/${ordenId}`).then(d => {
        if (!alive) return;
        setData({
          numero: d.numero || '',
          proveedor_id: d.proveedor_id || '',
          estado: d.estado || 'PENDIENTE',
          fecha_pedido: ordenDateToInput(d.fecha_pedido),
          fecha_entrega_estimada: ordenDateToInput(d.fecha_entrega_estimada),
          fecha_entrega_real: ordenDateToInput(d.fecha_entrega_real),
          notas: d.notas || '',
        });
        setLoading(false);
      }).catch(e => { onToast && onToast(e.message || 'Error al cargar orden', true); onClose(); });
    }
    return () => { alive = false; };
  }, [ordenId]);

  const set = (k, v) => setData(d => ({ ...d, [k]: v }));
  const setLine = (idx, key, value) => setLines(ls => ls.map((l, i) => i === idx ? { ...l, [key]: value } : l));

  const submit = async (ev) => {
    ev.preventDefault();
    setSaving(true);
    try {
      const payload = {
        numero: data.numero || null,
        proveedor_id: data.proveedor_id || null,
        estado: data.estado,
        fecha_pedido: data.fecha_pedido || null,
        fecha_entrega_estimada: data.fecha_entrega_estimada || null,
        fecha_entrega_real: data.fecha_entrega_real || null,
        notas: data.notas || null,
      };
      let saved;
      if (isEdit) {
        saved = await API.put(`/api/ordenes/${ordenId}`, payload);
        onToast && onToast('Orden actualizada ✓');
      } else {
        saved = await API.post('/api/ordenes', payload);
        for (const line of lines.filter(l => l.material_id)) {
          await API.post(`/api/ordenes/${saved.id}/materiales`, {
            material_id: parseInt(line.material_id, 10),
            cantidad: parseFloat(line.cantidad) || 1,
            precio_unitario: line.precio_unitario !== '' ? parseFloat(line.precio_unitario) : null,
            estado: line.estado || 'PENDIENTE',
            fecha_recepcion: line.fecha_recepcion || null,
            notas: line.notas || null,
            pedido_material_field: line.pedido_material_field || null,
          });
        }
        onToast && onToast(`Orden creada · Nº ${saved.numero} ✓`);
      }
      onSaved && onSaved(saved);
    } catch (e) {
      onToast && onToast(e.message || 'Error al guardar', true);
    } finally {
      setSaving(false);
    }
  };

  const showRealDate = ['RECIBIDA', 'RECIBIDA_PARCIAL'].includes((data.estado || '').toUpperCase());

  return (
    <div className="modal-bg open"
      onClick={e => { if (e.target.classList.contains('modal-bg')) onClose(); }}
      style={{position:'fixed',inset:0,background:'rgba(0,0,0,.35)',zIndex:220,display:'flex',alignItems:'flex-start',justifyContent:'center',padding:'40px 20px',overflow:'auto'}}
    >
      <div className="modal"
        style={{background:'var(--surface)',border:'1px solid var(--line)',borderRadius:8,width:'min(840px,100%)',boxShadow:'0 20px 60px rgba(0,0,0,.18)'}}
        onClick={e => e.stopPropagation()}
      >
        <div style={{display:'flex',alignItems:'center',justifyContent:'space-between',padding:'14px 18px',borderBottom:'1px solid var(--line)'}}>
          <h3 style={{margin:0,fontSize:15}}>{isEdit ? `Editar orden · ${data.numero || ordenId}` : 'Nueva orden'}</h3>
          <button className="icon-btn" onClick={onClose}><Icon name="x"/></button>
        </div>

        {loading ? (
          <div style={{padding:40,textAlign:'center',color:'var(--ink-3)'}}>Cargando…</div>
        ) : (
          <form onSubmit={submit} autoComplete="off">
            <div style={{padding:18,display:'grid',gridTemplateColumns:isEdit ? '1fr' : '1fr 1fr',gap:18}}>
              <div>
                <div className="section-title">Datos de la orden</div>
                <div className="fields-grid">
                  <OrdenFld label="Nº orden">
                    <input value={data.numero} onChange={e => set('numero', e.target.value)} placeholder="Auto si se deja vacío"/>
                  </OrdenFld>
                  <OrdenFld label="Proveedor">
                    <select value={data.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>
                  </OrdenFld>
                  <OrdenFld label="Estado">
                    <select value={data.estado} onChange={e => set('estado', e.target.value)}>
                      {(estados || ORDEN_LINE_ESTADOS).map(s => <option key={s} value={s}>{ordenEstadoMeta(s).label}</option>)}
                    </select>
                  </OrdenFld>
                  <OrdenFld label="F. pedido">
                    <input type="date" value={data.fecha_pedido} onChange={e => set('fecha_pedido', e.target.value)}/>
                  </OrdenFld>
                  <OrdenFld label="F. entrega estimada">
                    <input type="date" value={data.fecha_entrega_estimada} onChange={e => set('fecha_entrega_estimada', e.target.value)}/>
                  </OrdenFld>
                  {showRealDate && (
                    <OrdenFld label="F. entrega real">
                      <input type="date" value={data.fecha_entrega_real} onChange={e => set('fecha_entrega_real', e.target.value)}/>
                    </OrdenFld>
                  )}
                  <OrdenFld label="Notas" full>
                    <textarea value={data.notas} onChange={e => set('notas', e.target.value)} rows="4"/>
                  </OrdenFld>
                </div>
              </div>

              {!isEdit && (
                <div>
                  <div style={{display:'flex',justifyContent:'space-between',alignItems:'center',marginBottom:10}}>
                    <div className="section-title" style={{margin:0}}>Materiales iniciales</div>
                    <button type="button" className="btn ghost" style={{fontSize:12}} onClick={() => setLines(ls => [...ls, blankOrdenMaterial()])}>
                      <Icon name="plus" size={12}/> Añadir línea
                    </button>
                  </div>
                  {lines.length === 0 && <div className="muted" style={{fontSize:12,padding:'12px 0'}}>Puedes crear la orden ahora y añadir materiales después.</div>}
                  <div style={{display:'flex',flexDirection:'column',gap:10}}>
                    {lines.map((line, idx) => (
                      <div key={idx} style={{padding:10,border:'1px solid var(--line)',borderRadius:6,background:'var(--surface)'}}>
                        <div style={{display:'flex',justifyContent:'space-between',alignItems:'center',marginBottom:8}}>
                          <span className="mono" style={{fontSize:11.5,color:'var(--ink-3)'}}>Línea {idx + 1}</span>
                          <button type="button" className="icon-btn" style={{color:'var(--err)'}} onClick={() => setLines(ls => ls.filter((_, i) => i !== idx))}>
                            <Icon name="trash" size={12}/>
                          </button>
                        </div>
                        <MaterialEditGrid
                          value={line}
                          catalog={catalog}
                          includeMaterial
                          onChange={(k,v) => setLine(idx, k, v)}
                        />
                      </div>
                    ))}
                  </div>
                </div>
              )}
            </div>

            <div style={{display:'flex',justifyContent:'flex-end',padding:'12px 18px',borderTop:'1px solid var(--line)',gap:8}}>
              <button type="button" className="btn ghost" onClick={onClose}>Cancelar</button>
              <button type="submit" className="btn primary" disabled={saving}>{saving ? 'Guardando…' : (isEdit ? 'Guardar cambios' : 'Crear orden')}</button>
            </div>
          </form>
        )}
      </div>
    </div>
  );
};

const OrdenFld = ({ label, children, full }) => (
  <div className={`field${full ? ' full' : ''}`}>
    <label>{label}</label>
    {React.cloneElement(children, { style: { ...inputStyle, ...(children.props.style || {}) } })}
  </div>
);

window.OrdenesDrawer = OrdenesDrawer;
window.OrdenesForm = OrdenesForm;
