/* global React, Icon, Button, Badge, Card, brl, PageHead, Toolbar, FooterPager, KpiMini, ChartCanvas,
          useContasReceberList, useContasPagarList, Drawer,
          BLANK_CONTA_REC, BLANK_CONTA_PAG, ContaRecForm, ContaPagForm, ParcelamentoModal,
          FIN_STATUS_TONE, CATEGORIAS_DESPESA, FORMAS_PAGAMENTO,
          computeFinStatus, FinStatusBadge, finRecKpis, finPagKpis,
          FinRowActions, FluxoCaixaChart, buildFluxoData, FinDashKpi, FinanceiroTabs, addDaysIso,
          DRE_MAP, buildDRE, TimelineParcela */

// ─── Dashboard Financeiro ───────────────────────────────────────────────────

function FinDashboard({ onNav }) {
  const { rows: recRows } = useContasReceberList([]);
  const { rows: pagRows } = useContasPagarList([]);

  const recKpi = React.useMemo(() => finRecKpis(recRows), [recRows]);
  const pagKpi = React.useMemo(() => finPagKpis(pagRows), [pagRows]);
  const hasData = recRows.length > 0 || pagRows.length > 0;

  // Dados para gráfico de composição de despesas (doughnut)
  const despesasPorCat = React.useMemo(() => {
    const map = {};
    pagRows.forEach(r => {
      const cat = r.cat || r.categoria || 'Outros';
      map[cat] = (map[cat] || 0) + (parseFloat(r.valor) || 0);
    });
    return map;
  }, [pagRows]);

  const doughnutData = React.useMemo(() => {
    const entries = Object.entries(despesasPorCat).sort((a, b) => b[1] - a[1]).slice(0, 8);
    const colors = [
      'rgba(201,163,107,0.85)', 'rgba(91,177,122,0.85)', 'rgba(217,101,94,0.85)',
      'rgba(100,149,237,0.85)', 'rgba(186,85,211,0.85)', 'rgba(255,165,0,0.85)',
      'rgba(0,206,209,0.85)', 'rgba(169,169,169,0.7)',
    ];
    return {
      labels: entries.map(e => e[0]),
      datasets: [{
        data: entries.map(e => e[1]),
        backgroundColor: colors.slice(0, entries.length),
        borderWidth: 0,
      }],
    };
  }, [despesasPorCat]);

  // Entradas vs Saidas por mês (bar chart - ultimos 6 meses)
  const barData = React.useMemo(() => {
    const today = new Date();
    const meses = [];
    for (let i = 5; i >= 0; i--) {
      const d = new Date(today.getFullYear(), today.getMonth() - i, 1);
      meses.push(d.toISOString().slice(0, 7));
    }
    const labels = meses.map(m => {
      const [y, mo] = m.split('-');
      const d = new Date(+y, +mo - 1, 1);
      return d.toLocaleDateString('pt-BR', { month: 'short' });
    });
    const entradas = meses.map(m => {
      return recRows.filter(r => {
        if (r.status !== 'Recebido') return false;
        const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
        return String(dp).slice(0, 7) === m;
      }).reduce((a, r) => a + (parseFloat(r.valor_recebido || r.recebido || r.valor) || 0), 0);
    });
    const saidas = meses.map(m => {
      return pagRows.filter(r => {
        if (r.status !== 'Pago') return false;
        const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
        return String(dp).slice(0, 7) === m;
      }).reduce((a, r) => a + (parseFloat(r.valor) || 0), 0);
    });
    return {
      labels,
      datasets: [
        { label: 'Entradas', data: entradas, backgroundColor: 'rgba(91,177,122,0.7)', borderRadius: 4 },
        { label: 'Saidas', data: saidas, backgroundColor: 'rgba(217,101,94,0.7)', borderRadius: 4 },
      ],
    };
  }, [recRows, pagRows]);

  const lucroMes = recKpi.totalRecMes - pagKpi.totalPagoMes;

  return (
    <div className="canvas">
      <PageHead title="Financeiro" sub="Visao geral do fluxo financeiro"
        right={<>
          <Button variant="secondary" icon="plus" size="sm" onClick={() => onNav('financeiro/contas-receber')}>Lancar titulo</Button>
          <Button variant="primary" icon="plus" size="sm" onClick={() => onNav('financeiro/contas-pagar')}>Lancar despesa</Button>
        </>} />
      <FinanceiroTabs active="dashboard" onNav={onNav} />

      {!hasData ? (
        <Card>
          <div style={{ padding: '64px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="bar-chart-2" size={48} style={{ opacity: 0.25, marginBottom: 16 }} />
            <div style={{ fontSize: 16, marginBottom: 8 }}>Dashboard Financeiro</div>
            <div style={{ fontSize: 13, maxWidth: 360, margin: '0 auto' }}>
              Cadastre contas a receber e a pagar para visualizar KPIs, graficos e projecoes de fluxo de caixa.
            </div>
            <div style={{ marginTop: 20, display: 'flex', gap: 8, justifyContent: 'center' }}>
              <Button variant="primary" size="sm" icon="plus" onClick={() => onNav('financeiro/contas-receber')}>Lancar titulo</Button>
              <Button variant="secondary" size="sm" icon="plus" onClick={() => onNav('financeiro/contas-pagar')}>Lancar despesa</Button>
            </div>
          </div>
        </Card>
      ) : (<>
        {/* KPI Grid */}
        <div style={{ display: 'grid', gridTemplateColumns: 'repeat(auto-fit, minmax(160px, 1fr))', gap: 12, marginBottom: 20 }}>
          <FinDashKpi label="A receber" value={`R$ ${brl(recKpi.totalAberto)}`} sub={`${recKpi.abertosCount} titulos`} tone="brand" onClick={() => onNav('financeiro/contas-receber')} />
          <FinDashKpi label="A pagar" value={`R$ ${brl(pagKpi.totalAberto)}`} sub={`${pagKpi.abertosCount} pendentes`} tone="danger" onClick={() => onNav('financeiro/contas-pagar')} />
          <FinDashKpi label="Vencidos" value={`R$ ${brl(recKpi.vencidos.valor + pagKpi.totalVencido)}`} sub={`${recKpi.vencidos.count + pagKpi.vencidosCount} titulos`} tone="danger" />
          <FinDashKpi label="Recebido (mes)" value={`R$ ${brl(recKpi.totalRecMes)}`} sub="mes atual" tone="success" />
          <FinDashKpi label="Pago (mes)" value={`R$ ${brl(pagKpi.totalPagoMes)}`} sub={`${pagKpi.pagosMesCount} pagamentos`} />
          <FinDashKpi label="Lucro do mes" value={`R$ ${brl(Math.abs(lucroMes))}`} sub={lucroMes >= 0 ? 'positivo' : 'negativo'} tone={lucroMes >= 0 ? 'success' : 'danger'} />
          <FinDashKpi label="Inadimplencia" value={`${recKpi.inadPct}%`} sub="sobre abertos" tone={recKpi.inadPct > 30 ? 'danger' : recKpi.inadPct > 10 ? 'warning' : 'success'} />
        </div>

        {/* Charts */}
        <div style={{ display: 'grid', gridTemplateColumns: '2fr 1fr', gap: 16, marginBottom: 20 }}>
          <Card title="Entradas vs Saidas - Ultimos 6 meses">
            <div style={{ padding: '12px 8px' }}>
              <ChartCanvas type="bar" data={barData} height={220} options={{
                scales: {
                  x: { grid: { color: 'rgba(255,255,255,0.06)' }, ticks: { color: 'rgba(255,255,255,0.55)', font: { size: 10 } } },
                  y: { grid: { color: 'rgba(255,255,255,0.06)' }, ticks: { color: 'rgba(255,255,255,0.55)', font: { size: 10 }, callback: v => v >= 1000 ? `${(v/1000).toFixed(0)}k` : v } },
                },
                plugins: {
                  legend: { display: true, position: 'bottom', labels: { color: 'rgba(255,255,255,0.7)', font: { size: 11 }, boxWidth: 12, padding: 16 } },
                  tooltip: { callbacks: { label: ctx => `${ctx.dataset.label}: R$ ${brl(ctx.raw)}` } },
                },
              }} />
            </div>
          </Card>
          <Card title="Composicao de despesas">
            {Object.keys(despesasPorCat).length === 0 ? (
              <div style={{ padding: '40px 16px', textAlign: 'center', color: 'var(--tm-fg-3)', fontSize: 12.5 }}>
                Sem despesas cadastradas
              </div>
            ) : (
              <div style={{ padding: '12px 8px' }}>
                <ChartCanvas type="doughnut" data={doughnutData} height={220} options={{
                  plugins: {
                    legend: { display: true, position: 'bottom', labels: { color: 'rgba(255,255,255,0.7)', font: { size: 10 }, boxWidth: 10, padding: 8 } },
                    tooltip: { callbacks: { label: ctx => `${ctx.label}: R$ ${brl(ctx.raw)}` } },
                  },
                }} />
              </div>
            )}
          </Card>
        </div>

        {/* Fluxo de Caixa mini */}
        <Card title="Fluxo de Caixa - Proximos 30 dias">
          <div style={{ padding: '12px 8px' }}>
            <FluxoCaixaChart receber={recRows} pagar={pagRows} periodo="30d" />
          </div>
        </Card>
      </>)}
    </div>
  );
}

// ─── Contas a Receber (Enhanced) ────────────────────────────────────────────

function ContasReceber({ onNav }) {
  const s = useContasReceberList([]);
  const dados = s.rows;
  const [searchQ, setSearchQ] = React.useState('');
  const [fStatus, setFStatus] = React.useState('');
  const [fPeriodo, setFPeriodo] = React.useState('');
  const [fCliente, setFCliente] = React.useState('');
  const [fForma, setFForma] = React.useState('');
  const [parcModal, setParcModal] = React.useState(null);

  const kpis = React.useMemo(() => finRecKpis(dados), [dados]);

  // Opcoes de filtro dinamicas
  const statusOpts  = [...new Set(dados.map(r => r.status).filter(Boolean))].sort();
  const clienteOpts = [...new Set(dados.map(r => r.cli || r.cliente_nome).filter(Boolean))].sort();
  const formaOpts   = [...new Set(dados.map(r => r.forma_pagamento).filter(Boolean))].sort();
  const filterOpts = [
    { key: 'status',  label: 'Todos os status', options: statusOpts },
    { key: 'periodo', label: 'Periodo',         options: ['Hoje','Esta semana','Este mes','Ultimos 3 meses','Este ano'] },
    { key: 'cliente', label: 'Cliente',          options: clienteOpts },
    { key: 'forma',   label: 'Forma',            options: formaOpts },
  ];
  const filterValues = { status: fStatus, periodo: fPeriodo, cliente: fCliente, forma: fForma };
  const handleFilter = (k, v) => {
    if (k === 'status')  setFStatus(v);
    if (k === 'periodo') setFPeriodo(v);
    if (k === 'cliente') setFCliente(v);
    if (k === 'forma')   setFForma(v);
  };

  let filtered = dados;
  if (fStatus)  filtered = filtered.filter(r => computeFinStatus(r) === fStatus || r.status === fStatus);
  if (fCliente) filtered = filtered.filter(r => (r.cli || r.cliente_nome) === fCliente);
  if (fForma)   filtered = filtered.filter(r => r.forma_pagamento === fForma);
  if (fPeriodo) {
    const now = new Date();
    filtered = filtered.filter(r => {
      const venc = r.vencimento ? String(r.vencimento).slice(0, 10) : null;
      if (!venc) return true;
      const dt = new Date(venc + 'T12:00:00');
      if (fPeriodo === 'Hoje')            return dt.toDateString() === now.toDateString();
      if (fPeriodo === 'Esta semana')     { const d = new Date(now); d.setDate(d.getDate() - d.getDay()); d.setHours(0,0,0,0); return dt >= d; }
      if (fPeriodo === 'Este mes')        return dt.getMonth() === now.getMonth() && dt.getFullYear() === now.getFullYear();
      if (fPeriodo === 'Ultimos 3 meses') { const d = new Date(now); d.setMonth(d.getMonth() - 3); return dt >= d; }
      if (fPeriodo === 'Este ano')        return dt.getFullYear() === now.getFullYear();
      return true;
    });
  }
  if (searchQ) {
    const q = searchQ.toLowerCase();
    filtered = filtered.filter(r =>
      String(r.ref || r.referencia || '').toLowerCase().includes(q) ||
      String(r.cli || r.cliente_nome || '').toLowerCase().includes(q) ||
      String(r.ped || r.pedido_ref || '').toLowerCase().includes(q) ||
      String(r.forma_pagamento || '').toLowerCase().includes(q) ||
      String(r.status || '').toLowerCase().includes(q)
    );
  }

  const clienteNomes = [...new Set(dados.map(r => r.cli || r.cliente_nome).filter(Boolean))].sort();

  // Acoes de linha
  const handleReceber = (origIdx) => {
    s.open('edit', origIdx);
    setTimeout(() => {
      s.set('status', 'Recebido');
      s.set('data_pagamento', new Date().toISOString().slice(0, 10));
      s.set('valor_recebido', dados[origIdx].valor);
    }, 50);
  };

  const handleDuplicar = (row) => {
    const dup = { ...BLANK_CONTA_REC };
    Object.keys(dup).forEach(k => { if (row[k] !== undefined) dup[k] = row[k]; });
    dup.status = 'Em aberto';
    dup.valor_recebido = 0;
    dup.data_pagamento = '';
    s.open('new', null, dup);
  };

  const handleParcelar = (row, origIdx) => {
    setParcModal({
      valor: row.valor,
      vencimento: row.vencimento ? String(row.vencimento).slice(0, 10) : '',
      clienteNome: row.cli || row.cliente_nome || '',
      pedidoRef: row.ped || row.pedido_ref || '',
      formaPagamento: row.forma_pagamento || 'Boleto',
      origIdx,
    });
  };

  const handleParcelasConfirm = async (records) => {
    // Remover o titulo original
    if (parcModal.origIdx != null) {
      await s.remove(parcModal.origIdx);
    }
    // Criar cada parcela
    for (const rec of records) {
      s.open('new', null, rec);
      await s.save();
    }
    setParcModal(null);
    s.reload();
  };

  const formatVenc = (r) => {
    const v = r.vencimento ? String(r.vencimento).slice(0, 10) : (r.venc || '');
    if (!v || v.length < 10) return v;
    if (v.includes('-')) {
      const [y, m, d] = v.split('-');
      return `${d}/${m}/${y}`;
    }
    return v;
  };

  return (<>
    <ContaRecForm edit={s.edit} set={s.set} onSave={s.save} onCancel={s.close}
      onDelete={s.edit && s.edit.mode !== 'new' ? () => s.remove(s.edit.idx) : null} clientes={clienteNomes} allRows={dados} />
    {parcModal && (
      <ParcelamentoModal
        valor={parcModal.valor} vencimento={parcModal.vencimento}
        clienteNome={parcModal.clienteNome} pedidoRef={parcModal.pedidoRef}
        formaPagamento={parcModal.formaPagamento}
        onConfirm={handleParcelasConfirm} onCancel={() => setParcModal(null)}
      />
    )}
    <div className="canvas">
      <PageHead title="Contas a Receber"
        sub={dados.length > 0 ? `${kpis.abertosCount} titulo${kpis.abertosCount !== 1 ? 's' : ''} em aberto` : 'Nenhum titulo cadastrado'}
        right={<>
          <Button variant="secondary" icon="download" size="sm">Exportar</Button>
          <Button variant="primary" icon="plus" size="sm" onClick={() => s.open('new', null, BLANK_CONTA_REC)}>Lancar titulo</Button>
        </>} />
      <FinanceiroTabs active="contas-receber" onNav={onNav} />

      {/* KPIs inteligentes */}
      <div className="grid-4" style={{ marginBottom: 16 }}>
        <KpiMini lbl="Vencendo hoje" v={kpis.vencendoHoje.count > 0 ? `R$ ${brl(kpis.vencendoHoje.valor)}` : '—'} sub={kpis.vencendoHoje.count > 0 ? `${kpis.vencendoHoje.count} titulo${kpis.vencendoHoje.count > 1 ? 's' : ''}` : 'nenhum'} />
        <KpiMini lbl="Vencidos" v={kpis.vencidos.count > 0 ? `R$ ${brl(kpis.vencidos.valor)}` : '—'} sub={kpis.vencidos.count > 0 ? `${kpis.vencidos.count} titulo${kpis.vencidos.count > 1 ? 's' : ''}` : 'nenhum'} />
        <KpiMini lbl="Inadimplencia" v={`${kpis.inadPct}%`} sub="sobre abertos" />
        <KpiMini lbl="Previsao 30d" v={kpis.previsao30 > 0 ? `R$ ${brl(kpis.previsao30)}` : '—'} sub="a receber" />
      </div>

      <Card>
        <Toolbar search="Buscar titulo, cliente, pedido..." filterOpts={filterOpts} filterValues={filterValues} onFilter={handleFilter} onSearch={setSearchQ} />
        {dados.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="file-text" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Nenhum titulo a receber</div>
            <div style={{ fontSize: 12 }}>Clique em "Lancar titulo" para registrar</div>
          </div>
        ) : filtered.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="search" size={22} style={{ opacity: 0.3, marginBottom: 8 }} />
            <div style={{ fontSize: 13 }}>Nenhum titulo corresponde aos filtros</div>
          </div>
        ) : (<>
          <table className="tbl">
            <thead><tr>
              <th>Ref.</th><th>Cliente</th><th>Pedido</th><th>Vencimento</th><th>Parcela</th>
              <th className="num right">Valor</th><th className="num right">Recebido</th><th>Status</th><th></th>
            </tr></thead>
            <tbody>
              {filtered.map((r, i) => {
                const origIdx = dados.indexOf(r);
                return (
                  <tr key={origIdx} className="clickable" onClick={() => s.open('edit', origIdx)}>
                    <td><span className="ref-mono">{r.ref || r.referencia}</span></td>
                    <td>{r.cli || r.cliente_nome}</td>
                    <td><span className="ref-mono gold">{r.ped || r.pedido_ref}</span></td>
                    <td>{formatVenc(r)}</td>
                    <td>{r.parc || r.parcela}</td>
                    <td className="num right">R$ {brl(r.valor)}</td>
                    <td className="num right">R$ {brl(r.valor_recebido || r.recebido || 0)}</td>
                    <td><FinStatusBadge row={r} /></td>
                    <td onClick={e => e.stopPropagation()}>
                      <FinRowActions row={r} tipo="receber"
                        onReceber={() => handleReceber(origIdx)}
                        onEdit={() => s.open('edit', origIdx)}
                        onDuplicar={() => handleDuplicar(r)}
                        onParcelar={() => handleParcelar(r, origIdx)}
                      />
                    </td>
                  </tr>
                );
              })}
            </tbody>
          </table>
          <FooterPager total={filtered.length} from={1} to={Math.min(filtered.length, 20)} />
        </>)}
      </Card>
    </div>
  </>);
}

// ─── Contas a Pagar (Enhanced) ──────────────────────────────────────────────

function ContasPagar({ onNav }) {
  const sp = useContasPagarList([]);
  const dadosPag = sp.rows;
  const [searchQ, setSearchQ] = React.useState('');
  const [fStatus, setFStatus] = React.useState('');
  const [fCat, setFCat]       = React.useState('');
  const [fVenc, setFVenc]     = React.useState('');

  const kpis = React.useMemo(() => finPagKpis(dadosPag), [dadosPag]);

  const statusOpts = [...new Set(dadosPag.map(r => r.status).filter(Boolean))].sort();
  const catOpts    = [...new Set(dadosPag.map(r => r.cat || r.categoria).filter(Boolean))].sort();
  const filterOpts = [
    { key: 'status', label: 'Todos',      options: statusOpts },
    { key: 'cat',    label: 'Categoria',   options: catOpts },
    { key: 'venc',   label: 'Vencimento',  options: ['Hoje','Esta semana','Este mes','Ultimos 3 meses','Este ano'] },
  ];
  const filterValues = { status: fStatus, cat: fCat, venc: fVenc };
  const handleFilter = (k, v) => {
    if (k === 'status') setFStatus(v);
    if (k === 'cat')    setFCat(v);
    if (k === 'venc')   setFVenc(v);
  };

  let filtered = dadosPag;
  if (fStatus) filtered = filtered.filter(r => r.status === fStatus);
  if (fCat)    filtered = filtered.filter(r => (r.cat || r.categoria) === fCat);
  if (fVenc) {
    const now = new Date();
    filtered = filtered.filter(r => {
      const venc = r.vencimento ? String(r.vencimento).slice(0, 10) : null;
      if (!venc) return true;
      const dt = new Date(venc + 'T12:00:00');
      if (fVenc === 'Hoje')            return dt.toDateString() === now.toDateString();
      if (fVenc === 'Esta semana')     { const d = new Date(now); d.setDate(d.getDate() - d.getDay()); d.setHours(0,0,0,0); return dt >= d; }
      if (fVenc === 'Este mes')        return dt.getMonth() === now.getMonth() && dt.getFullYear() === now.getFullYear();
      if (fVenc === 'Ultimos 3 meses') { const d = new Date(now); d.setMonth(d.getMonth() - 3); return dt >= d; }
      if (fVenc === 'Este ano')        return dt.getFullYear() === now.getFullYear();
      return true;
    });
  }
  if (searchQ) {
    const q = searchQ.toLowerCase();
    filtered = filtered.filter(r =>
      String(r.ref || r.referencia || '').toLowerCase().includes(q) ||
      String(r.forn || r.fornecedor || '').toLowerCase().includes(q) ||
      String(r.cat || r.categoria || '').toLowerCase().includes(q) ||
      String(r.status || '').toLowerCase().includes(q)
    );
  }

  const handlePagar = (origIdx) => {
    sp.open('edit', origIdx);
    setTimeout(() => {
      sp.set('status', 'Pago');
      sp.set('data_pagamento', new Date().toISOString().slice(0, 10));
    }, 50);
  };

  const handleDuplicar = (row) => {
    const dup = { ...BLANK_CONTA_PAG };
    Object.keys(dup).forEach(k => { if (row[k] !== undefined) dup[k] = row[k]; });
    dup.status = 'Em aberto';
    dup.data_pagamento = '';
    sp.open('new', null, dup);
  };

  const formatVenc = (r) => {
    const v = r.vencimento ? String(r.vencimento).slice(0, 10) : (r.venc || '');
    if (!v || v.length < 10) return v;
    if (v.includes('-')) {
      const [y, m, d] = v.split('-');
      return `${d}/${m}/${y}`;
    }
    return v;
  };

  return (<>
    <ContaPagForm edit={sp.edit} set={sp.set} onSave={sp.save} onCancel={sp.close}
      onDelete={sp.edit && sp.edit.mode !== 'new' ? () => sp.remove(sp.edit.idx) : null} />
    <div className="canvas">
      <PageHead title="Contas a Pagar"
        sub={dadosPag.length > 0 ? `${kpis.abertosCount} titulo${kpis.abertosCount !== 1 ? 's' : ''} em aberto` : 'Nenhuma despesa cadastrada'}
        right={<Button variant="primary" icon="plus" size="sm" onClick={() => sp.open('new', null, BLANK_CONTA_PAG)}>Lancar despesa</Button>} />
      <FinanceiroTabs active="contas-pagar" onNav={onNav} />

      {/* KPIs */}
      <div className="grid-4" style={{ marginBottom: 16 }}>
        <KpiMini lbl="Total em aberto" v={kpis.totalAberto > 0 ? `R$ ${brl(kpis.totalAberto)}` : '—'} sub={`${kpis.abertosCount} pendentes`} />
        <KpiMini lbl="Vencidos" v={kpis.totalVencido > 0 ? `R$ ${brl(kpis.totalVencido)}` : '—'} sub={kpis.vencidosCount > 0 ? `${kpis.vencidosCount} despesas` : 'nenhum'} />
        <KpiMini lbl="Pago no mes" v={kpis.totalPagoMes > 0 ? `R$ ${brl(kpis.totalPagoMes)}` : '—'} sub={`${kpis.pagosMesCount} pagamentos`} />
        <KpiMini lbl="Recorrentes" v={kpis.recorrentesCount > 0 ? `${kpis.recorrentesCount}` : '—'} sub="despesas fixas" />
      </div>

      <Card>
        <Toolbar search="Fornecedor, ref, categoria..." filterOpts={filterOpts} filterValues={filterValues} onFilter={handleFilter} onSearch={setSearchQ} />
        {dadosPag.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="receipt" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Nenhuma despesa cadastrada</div>
            <div style={{ fontSize: 12 }}>Clique em "Lancar despesa" para registrar</div>
          </div>
        ) : filtered.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="search" size={22} style={{ opacity: 0.3, marginBottom: 8 }} />
            <div style={{ fontSize: 13 }}>Nenhuma despesa corresponde aos filtros</div>
          </div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th>Ref.</th><th>Fornecedor</th><th>Categoria</th><th>Vencimento</th>
              <th className="num right">Valor</th><th>Status</th><th></th>
            </tr></thead>
            <tbody>
              {filtered.map((r, i) => {
                const origIdx = dadosPag.indexOf(r);
                return (
                  <tr key={origIdx} className="clickable" onClick={() => sp.open('edit', origIdx)}>
                    <td><span className="ref-mono">{r.ref || r.referencia}</span></td>
                    <td>
                      {r.forn || r.fornecedor}
                      {(r.recorrente || r.recorrenteFlag) && (
                        <Icon name="repeat" size={12} style={{ marginLeft: 6, color: 'var(--tm-brand-champagne)', verticalAlign: 'middle' }} />
                      )}
                    </td>
                    <td><span className="ch-chip">{r.cat || r.categoria}</span></td>
                    <td>{formatVenc(r)}</td>
                    <td className="num right">R$ {brl(r.valor)}</td>
                    <td><FinStatusBadge row={r} /></td>
                    <td onClick={e => e.stopPropagation()}>
                      <FinRowActions row={r} tipo="pagar"
                        onReceber={() => handlePagar(origIdx)}
                        onEdit={() => sp.open('edit', origIdx)}
                        onDuplicar={() => handleDuplicar(r)}
                      />
                    </td>
                  </tr>
                );
              })}
            </tbody>
          </table>
        )}
      </Card>
    </div>
  </>);
}

// ─── Entradas ───────────────────────────────────────────────────────────────

function Entradas({ onNav }) {
  const se = useContasReceberList([]);
  const dadosRec = se.rows;
  const today = new Date().toISOString().slice(0, 10);
  const thisMonth = today.slice(0, 7);
  const thisWeekStart = (() => { const d = new Date(); d.setDate(d.getDate() - d.getDay()); return d.toISOString().slice(0, 10); })();

  const recebidos = dadosRec.filter(r => r.status === 'Recebido');
  const recHoje = recebidos.filter(r => {
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 10) === today;
  });
  const recSemana = recebidos.filter(r => {
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 10) >= thisWeekStart;
  });
  const recMes = recebidos.filter(r => {
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 7) === thisMonth;
  });

  const totalHoje = recHoje.reduce((a, r) => a + (parseFloat(r.valor_recebido || r.recebido || r.valor) || 0), 0);
  const totalSemana = recSemana.reduce((a, r) => a + (parseFloat(r.valor_recebido || r.recebido || r.valor) || 0), 0);
  const totalMes = recMes.reduce((a, r) => a + (parseFloat(r.valor_recebido || r.recebido || r.valor) || 0), 0);

  // PIX % do mes
  const pixMes = recMes.filter(r => r.forma_pagamento === 'PIX');
  const pixPct = recMes.length > 0 ? Math.round((pixMes.length / recMes.length) * 100) : 0;

  const clienteNomes = [...new Set(dadosRec.map(r => r.cli || r.cliente_nome).filter(Boolean))].sort();

  return (<>
    <ContaRecForm edit={se.edit} set={se.set} onSave={se.save} onCancel={se.close}
      onDelete={se.edit && se.edit.mode !== 'new' ? () => se.remove(se.edit.idx) : null} clientes={clienteNomes} allRows={dadosRec} />
    <div className="canvas">
      <PageHead title="Entradas" sub="Recebimentos confirmados"
        right={<Button variant="primary" icon="plus" size="sm" onClick={() => se.open('new', null, { ...BLANK_CONTA_REC, status: 'Recebido', data_pagamento: today })}>Registrar entrada</Button>} />
      <FinanceiroTabs active="entradas" onNav={onNav} />
      <div className="grid-4" style={{ marginBottom: 16 }}>
        <KpiMini lbl="Entradas hoje" v={totalHoje > 0 ? `R$ ${brl(totalHoje)}` : '—'} sub={recHoje.length > 0 ? `${recHoje.length} recebimento${recHoje.length > 1 ? 's' : ''}` : 'nenhum'} />
        <KpiMini lbl="Entradas semana" v={totalSemana > 0 ? `R$ ${brl(totalSemana)}` : '—'} sub={recSemana.length > 0 ? `${recSemana.length} recebimentos` : 'nenhum'} />
        <KpiMini lbl="Entradas mes" v={totalMes > 0 ? `R$ ${brl(totalMes)}` : '—'} sub={recMes.length > 0 ? `${recMes.length} recebimentos` : 'nenhum'} />
        <KpiMini lbl="PIX (% do mes)" v={recMes.length > 0 ? `${pixPct}%` : '—'} sub={pixMes.length > 0 ? `${pixMes.length} via PIX` : 'sem dados'} />
      </div>
      <Card>
        {recebidos.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="trending-up" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Nenhuma entrada registrada</div>
            <div style={{ fontSize: 12 }}>Os recebimentos confirmados aparecerão aqui</div>
          </div>
        ) : (
          <table className="tbl">
            <thead><tr><th>Data</th><th>Cliente</th><th>Pedido</th><th>Forma</th><th>Ref.</th><th className="num right">Valor</th></tr></thead>
            <tbody>
              {recebidos.map((r, i) => {
                const origIdx = dadosRec.indexOf(r);
                const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
                const dataStr = dp ? (() => {
                  const v = String(dp).slice(0, 10);
                  if (v.includes('-')) { const [y, m, d] = v.split('-'); return `${d}/${m}/${y}`; }
                  return v;
                })() : '—';
                return (
                  <tr key={origIdx} className="clickable" onClick={() => se.open('edit', origIdx)}>
                    <td className="muted">{dataStr}</td>
                    <td>{r.cli || r.cliente_nome}</td>
                    <td><span className="ref-mono gold">{r.ped || r.pedido_ref}</span></td>
                    <td><span className="ch-chip">{r.forma_pagamento || '—'}</span></td>
                    <td><span className="ref-mono">{r.ref || r.referencia}</span></td>
                    <td className="num right" style={{ color: 'var(--tm-success)' }}>+ R$ {brl(r.valor_recebido || r.recebido || r.valor)}</td>
                  </tr>
                );
              })}
            </tbody>
          </table>
        )}
      </Card>
    </div>
  </>);
}

// ─── Saidas ─────────────────────────────────────────────────────────────────

function Saidas({ onNav }) {
  const ss = useContasPagarList([]);
  const dadosPag = ss.rows;
  const today = new Date().toISOString().slice(0, 10);
  const thisMonth = today.slice(0, 7);
  const thisWeekStart = (() => { const d = new Date(); d.setDate(d.getDate() - d.getDay()); return d.toISOString().slice(0, 10); })();

  const pagos = dadosPag.filter(r => r.status === 'Pago');
  const pagosHoje = pagos.filter(r => {
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 10) === today;
  });
  const pagosSemana = pagos.filter(r => {
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 10) >= thisWeekStart;
  });
  const pagosMes = pagos.filter(r => {
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 7) === thisMonth;
  });

  const totalHoje = pagosHoje.reduce((a, r) => a + (parseFloat(r.valor) || 0), 0);
  const totalSemana = pagosSemana.reduce((a, r) => a + (parseFloat(r.valor) || 0), 0);
  const totalMes = pagosMes.reduce((a, r) => a + (parseFloat(r.valor) || 0), 0);

  // Saldo do mes (entradas - saidas)
  const { rows: recRows } = useContasReceberList([]);
  const recMes = recRows.filter(r => {
    if (r.status !== 'Recebido') return false;
    const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
    return String(dp).slice(0, 7) === thisMonth;
  });
  const totalRecMes = recMes.reduce((a, r) => a + (parseFloat(r.valor_recebido || r.recebido || r.valor) || 0), 0);
  const saldoMes = totalRecMes - totalMes;

  return (<>
    <ContaPagForm edit={ss.edit} set={ss.set} onSave={ss.save} onCancel={ss.close}
      onDelete={ss.edit && ss.edit.mode !== 'new' ? () => ss.remove(ss.edit.idx) : null} />
    <div className="canvas">
      <PageHead title="Saidas" sub="Despesas e pagamentos confirmados"
        right={<Button variant="primary" icon="plus" size="sm" onClick={() => ss.open('new', null, { ...BLANK_CONTA_PAG, status: 'Pago', data_pagamento: today })}>Registrar saida</Button>} />
      <FinanceiroTabs active="saidas" onNav={onNav} />
      <div className="grid-4" style={{ marginBottom: 16 }}>
        <KpiMini lbl="Saidas hoje" v={totalHoje > 0 ? `R$ ${brl(totalHoje)}` : '—'} sub={pagosHoje.length > 0 ? `${pagosHoje.length} pagamento${pagosHoje.length > 1 ? 's' : ''}` : 'nenhum'} />
        <KpiMini lbl="Saidas semana" v={totalSemana > 0 ? `R$ ${brl(totalSemana)}` : '—'} sub={pagosSemana.length > 0 ? `${pagosSemana.length} pagamentos` : 'nenhum'} />
        <KpiMini lbl="Saidas mes" v={totalMes > 0 ? `R$ ${brl(totalMes)}` : '—'} sub={pagosMes.length > 0 ? `${pagosMes.length} pagamentos` : 'nenhum'} />
        <KpiMini lbl="Saldo do mes" v={`R$ ${brl(Math.abs(saldoMes))}`} sub={saldoMes >= 0 ? 'positivo' : 'negativo'} />
      </div>
      <Card>
        {pagos.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="trending-down" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Nenhuma saida registrada</div>
            <div style={{ fontSize: 12 }}>Os pagamentos confirmados aparecerão aqui</div>
          </div>
        ) : (
          <table className="tbl">
            <thead><tr><th>Data</th><th>Fornecedor</th><th>Categoria</th><th>Forma</th><th className="num right">Valor</th></tr></thead>
            <tbody>
              {pagos.map((r, i) => {
                const origIdx = dadosPag.indexOf(r);
                const dp = r.data_pagamento || r.dataPagamento || r.vencimento || '';
                const dataStr = dp ? (() => {
                  const v = String(dp).slice(0, 10);
                  if (v.includes('-')) { const [y, m, d] = v.split('-'); return `${d}/${m}/${y}`; }
                  return v;
                })() : '—';
                return (
                  <tr key={origIdx} className="clickable" onClick={() => ss.open('edit', origIdx)}>
                    <td className="muted">{dataStr}</td>
                    <td>{r.forn || r.fornecedor}</td>
                    <td><span className="ch-chip">{r.cat || r.categoria}</span></td>
                    <td><span className="ch-chip">{r.forma_pagamento || '—'}</span></td>
                    <td className="num right" style={{ color: 'var(--tm-danger)' }}>- R$ {brl(r.valor)}</td>
                  </tr>
                );
              })}
            </tbody>
          </table>
        )}
      </Card>
    </div>
  </>);
}

// ─── Fluxo de Caixa ─────────────────────────────────────────────────────────

function FluxoCaixa({ onNav }) {
  const { rows: dadosRec } = useContasReceberList([]);
  const { rows: dadosPag } = useContasPagarList([]);
  const [periodo, setPeriodo] = React.useState('30d');

  const hasData = dadosRec.length > 0 || dadosPag.length > 0;

  const abertosRec = dadosRec.filter(r => r.status !== 'Recebido');
  const abertosPag = dadosPag.filter(r => r.status !== 'Pago');
  const totalPrevRec = abertosRec.reduce((a, r) => a + ((parseFloat(r.valor) || 0) - (parseFloat(r.valor_recebido || r.recebido) || 0)), 0);
  const totalPrevPag = abertosPag.reduce((a, r) => a + (parseFloat(r.valor) || 0), 0);
  const saldoProj = totalPrevRec - totalPrevPag;

  // Proximos vencimentos
  const today = new Date().toISOString().slice(0, 10);
  const proxPagar = abertosPag
    .filter(r => { const v = r.vencimento ? String(r.vencimento).slice(0, 10) : null; return v && v >= today; })
    .sort((a, b) => String(a.vencimento).localeCompare(String(b.vencimento)))
    .slice(0, 5);
  const proxReceber = abertosRec
    .filter(r => { const v = r.vencimento ? String(r.vencimento).slice(0, 10) : null; return v && v >= today; })
    .sort((a, b) => String(a.vencimento).localeCompare(String(b.vencimento)))
    .slice(0, 5);

  const formatVencShort = (r) => {
    const v = r.vencimento ? String(r.vencimento).slice(0, 10) : '';
    if (v.includes('-')) { const [y, m, d] = v.split('-'); return `${d}/${m}`; }
    return v;
  };

  return (
    <div className="canvas">
      <PageHead title="Fluxo de Caixa" sub="Projecao de entradas, saidas e saldo acumulado"
        right={<>
          <select className="input" style={{ width: 'auto', fontSize: 12 }} value={periodo} onChange={e => setPeriodo(e.target.value)}>
            <option value="7d">7 dias</option>
            <option value="30d">30 dias</option>
            <option value="90d">90 dias</option>
            <option value="365d">12 meses</option>
          </select>
          <Button variant="secondary" icon="download" size="sm">Exportar</Button>
        </>} />
      <FinanceiroTabs active="fluxo-caixa" onNav={onNav} />

      <div className="grid-4" style={{ marginBottom: 16 }}>
        <KpiMini lbl="Saldo atual" v="—" sub="conecte conta bancaria" />
        <KpiMini lbl="Entradas previstas" v={hasData ? `R$ ${brl(totalPrevRec)}` : '—'} sub={`${abertosRec.length} titulos`} />
        <KpiMini lbl="Saidas previstas" v={hasData ? `R$ ${brl(totalPrevPag)}` : '—'} sub={`${abertosPag.length} despesas`} />
        <KpiMini lbl="Saldo projetado" v={hasData ? `R$ ${brl(Math.abs(saldoProj))}` : '—'} sub={saldoProj >= 0 ? 'positivo' : 'negativo'} />
      </div>

      <Card title={`Curva de caixa - proximos ${periodo === '7d' ? '7 dias' : periodo === '30d' ? '30 dias' : periodo === '90d' ? '90 dias' : '12 meses'}`}>
        {!hasData ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="bar-chart-2" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Sem dados para projecao</div>
            <div style={{ fontSize: 12 }}>Cadastre contas a pagar e a receber para visualizar o grafico</div>
          </div>
        ) : (
          <div style={{ padding: '16px 8px' }}>
            <FluxoCaixaChart receber={dadosRec} pagar={dadosPag} periodo={periodo} />
          </div>
        )}
      </Card>

      <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr', gap: 16, marginTop: 16 }}>
        <Card title="Proximos vencimentos - A pagar">
          {proxPagar.length === 0 ? (
            <div style={{ padding: '20px 16px', color: 'var(--tm-fg-3)', fontSize: 12.5 }}>Nenhum vencimento pendente</div>
          ) : (
            <table className="tbl">
              <tbody>
                {proxPagar.map((r, i) => (
                  <tr key={i}>
                    <td>{r.forn || r.fornecedor}<div className="muted" style={{ fontSize: 11 }}>{r.cat || r.categoria}</div></td>
                    <td className="muted">{formatVencShort(r)}</td>
                    <td className="num right" style={{ color: 'var(--tm-danger)' }}>- R$ {brl(r.valor)}</td>
                  </tr>
                ))}
              </tbody>
            </table>
          )}
        </Card>
        <Card title="Proximos recebimentos">
          {proxReceber.length === 0 ? (
            <div style={{ padding: '20px 16px', color: 'var(--tm-fg-3)', fontSize: 12.5 }}>Nenhum recebimento pendente</div>
          ) : (
            <table className="tbl">
              <tbody>
                {proxReceber.map((r, i) => (
                  <tr key={i}>
                    <td>{r.cli || r.cliente_nome}<div className="muted" style={{ fontSize: 11 }}>{r.ref || r.referencia}</div></td>
                    <td className="muted">{formatVencShort(r)}</td>
                    <td className="num right" style={{ color: 'var(--tm-success)' }}>+ R$ {brl((parseFloat(r.valor) || 0) - (parseFloat(r.valor_recebido || r.recebido) || 0))}</td>
                  </tr>
                ))}
              </tbody>
            </table>
          )}
        </Card>
      </div>
    </div>
  );
}

// ─── Extrato Consolidado ────────────────────────────────────────────────────

function ExtratoConsolidado({ onNav }) {
  const { rows: recRows } = useContasReceberList([]);
  const { rows: pagRows } = useContasPagarList([]);
  const [searchQ, setSearchQ] = React.useState('');
  const [fTipo, setFTipo] = React.useState('');
  const [fPer, setFPer] = React.useState('');

  // Mesclar entradas + saidas confirmadas
  const transacoes = React.useMemo(() => {
    const items = [];
    recRows.filter(r => r.status === 'Recebido').forEach(r => {
      items.push({
        tipo: 'entrada',
        data: r.data_pagamento || r.dataPagamento || r.vencimento || '',
        descricao: r.ref || r.referencia || 'Recebimento',
        contraparte: r.cli || r.cliente_nome || '',
        forma: r.forma_pagamento || '',
        valor: parseFloat(r.valor_recebido || r.recebido || r.valor) || 0,
        categoria: '',
      });
    });
    pagRows.filter(r => r.status === 'Pago').forEach(r => {
      items.push({
        tipo: 'saida',
        data: r.data_pagamento || r.dataPagamento || r.vencimento || '',
        descricao: r.ref || r.referencia || 'Pagamento',
        contraparte: r.forn || r.fornecedor || '',
        forma: r.forma_pagamento || '',
        valor: parseFloat(r.valor) || 0,
        categoria: r.cat || r.categoria || '',
      });
    });
    // Ordenar por data decrescente
    items.sort((a, b) => {
      const da = String(a.data).slice(0, 10);
      const db = String(b.data).slice(0, 10);
      return db.localeCompare(da);
    });
    return items;
  }, [recRows, pagRows]);

  const filterOpts = [
    { key: 'tipo', label: 'Tipo',    options: ['Entrada', 'Saida'] },
    { key: 'per',  label: 'Periodo', options: ['Hoje', 'Esta semana', 'Este mes', 'Ultimos 3 meses', 'Este ano'] },
  ];
  const filterValues = { tipo: fTipo, per: fPer };
  const handleFilter = (k, v) => {
    if (k === 'tipo') setFTipo(v);
    if (k === 'per')  setFPer(v);
  };

  let filtered = transacoes;
  if (fTipo) {
    const t = fTipo === 'Entrada' ? 'entrada' : 'saida';
    filtered = filtered.filter(r => r.tipo === t);
  }
  if (fPer) {
    const now = new Date();
    const todayStr = now.toISOString().slice(0, 10);
    filtered = filtered.filter(r => {
      const d = String(r.data).slice(0, 10);
      if (!d) return true;
      if (fPer === 'Hoje') return d === todayStr;
      if (fPer === 'Esta semana') { const ws = new Date(now); ws.setDate(ws.getDate() - ws.getDay()); return d >= ws.toISOString().slice(0, 10); }
      if (fPer === 'Este mes') return d.slice(0, 7) === todayStr.slice(0, 7);
      if (fPer === 'Ultimos 3 meses') { const m3 = new Date(now); m3.setMonth(m3.getMonth() - 3); return d >= m3.toISOString().slice(0, 10); }
      if (fPer === 'Este ano') return d.slice(0, 4) === todayStr.slice(0, 4);
      return true;
    });
  }
  if (searchQ) {
    const q = searchQ.toLowerCase();
    filtered = filtered.filter(r =>
      r.descricao.toLowerCase().includes(q) ||
      r.contraparte.toLowerCase().includes(q) ||
      r.categoria.toLowerCase().includes(q) ||
      r.forma.toLowerCase().includes(q)
    );
  }

  // Saldo acumulado running
  let saldoAcum = 0;

  const formatDataExtrato = (d) => {
    const v = String(d).slice(0, 10);
    if (v.includes('-')) { const [y, m, dd] = v.split('-'); return `${dd}/${m}/${y}`; }
    return v || '—';
  };

  return (
    <div className="canvas">
      <PageHead title="Extrato Consolidado" sub="Todas as transacoes confirmadas"
        right={<Button variant="secondary" icon="download" size="sm">Exportar</Button>} />
      <FinanceiroTabs active="extrato" onNav={onNav} />
      <Card>
        <Toolbar search="Buscar descricao, contraparte..." filterOpts={filterOpts} filterValues={filterValues} onFilter={handleFilter} onSearch={setSearchQ} />
        {filtered.length === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="book-open" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Nenhuma transacao registrada</div>
            <div style={{ fontSize: 12 }}>As transacoes aparecerão aqui conforme forem confirmadas</div>
          </div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th></th><th>Data</th><th>Descricao</th><th>Contraparte</th><th>Forma</th>
              <th className="num right">Valor</th><th className="num right">Saldo</th>
            </tr></thead>
            <tbody>
              {filtered.map((r, i) => {
                saldoAcum += r.tipo === 'entrada' ? r.valor : -r.valor;
                return (
                  <tr key={i}>
                    <td>
                      <Icon name={r.tipo === 'entrada' ? 'arrow-up-right' : 'arrow-down-left'}
                        size={14} style={{ color: r.tipo === 'entrada' ? 'var(--tm-success)' : 'var(--tm-danger)' }} />
                    </td>
                    <td className="muted">{formatDataExtrato(r.data)}</td>
                    <td>{r.descricao}</td>
                    <td>{r.contraparte}</td>
                    <td><span className="ch-chip">{r.forma || '—'}</span></td>
                    <td className="num right" style={{ color: r.tipo === 'entrada' ? 'var(--tm-success)' : 'var(--tm-danger)' }}>
                      {r.tipo === 'entrada' ? '+' : '-'} R$ {brl(r.valor)}
                    </td>
                    <td className="num right" style={{ color: saldoAcum >= 0 ? 'var(--tm-success)' : 'var(--tm-danger)' }}>
                      R$ {brl(Math.abs(saldoAcum))}
                    </td>
                  </tr>
                );
              })}
            </tbody>
          </table>
        )}
      </Card>
    </div>
  );
}

// ─── DRE (Demonstrativo de Resultados) ──────────────────────────────────────

function DRESection({ onNav }) {
  const { rows: recRows } = useContasReceberList([]);
  const { rows: pagRows } = useContasPagarList([]);

  const today = new Date().toISOString().slice(0, 10);
  const [mesAtual, setMesAtual] = React.useState(today.slice(0, 7));
  const [expandido, setExpandido] = React.useState({});

  // Mes anterior para comparacao
  const mesAnterior = React.useMemo(() => {
    const [y, m] = mesAtual.split('-').map(Number);
    const prev = m === 1 ? `${y - 1}-12` : `${y}-${String(m - 1).padStart(2, '0')}`;
    return prev;
  }, [mesAtual]);

  const dreAtual = React.useMemo(() => buildDRE(recRows, pagRows, mesAtual), [recRows, pagRows, mesAtual]);
  const dreAnterior = React.useMemo(() => buildDRE(recRows, pagRows, mesAnterior), [recRows, pagRows, mesAnterior]);

  const toggle = (key) => setExpandido(prev => ({ ...prev, [key]: !prev[key] }));

  // Gerar lista de meses disponiveis (ultimos 12)
  const mesesOpts = React.useMemo(() => {
    const opts = [];
    const d = new Date();
    for (let i = 0; i < 12; i++) {
      const iso = d.toISOString().slice(0, 7);
      const label = d.toLocaleDateString('pt-BR', { month: 'long', year: 'numeric' });
      opts.push({ value: iso, label: label.charAt(0).toUpperCase() + label.slice(1) });
      d.setMonth(d.getMonth() - 1);
    }
    return opts;
  }, []);

  const delta = (atual, anterior) => {
    if (anterior === 0) return atual > 0 ? '+100%' : '—';
    const pct = ((atual - anterior) / Math.abs(anterior)) * 100;
    const sign = pct >= 0 ? '+' : '';
    return `${sign}${Math.round(pct)}%`;
  };

  const DRELinha = ({ label, valor, valorAnterior, tone, bold, indent, expandKey, children }) => {
    const isExpandable = !!expandKey && children;
    const isOpen = expandido[expandKey];
    return (<>
      <tr style={{ cursor: isExpandable ? 'pointer' : 'default' }}
        onClick={isExpandable ? () => toggle(expandKey) : undefined}>
        <td style={{
          paddingLeft: indent ? 28 : 12,
          fontWeight: bold ? 700 : 400,
          fontSize: bold ? 13.5 : 12.5,
          color: tone ? `var(--tm-${tone})` : 'var(--tm-fg-1)',
        }}>
          {isExpandable && (
            <Icon name={isOpen ? 'chevron-down' : 'chevron-right'} size={12}
              style={{ marginRight: 6, opacity: 0.5, verticalAlign: 'middle' }} />
          )}
          {label}
        </td>
        <td className="num right" style={{
          fontWeight: bold ? 700 : 400,
          color: tone ? `var(--tm-${tone})` : 'var(--tm-fg-1)',
          fontVariantNumeric: 'tabular-nums',
        }}>
          R$ {brl(Math.abs(valor))}
        </td>
        <td className="num right" style={{ fontSize: 11.5, color: 'var(--tm-fg-4)' }}>
          R$ {brl(Math.abs(valorAnterior || 0))}
        </td>
        <td className="num right" style={{
          fontSize: 11, fontWeight: 600,
          color: valor >= (valorAnterior || 0) ? 'var(--tm-success)' : 'var(--tm-danger)',
        }}>
          {delta(valor, valorAnterior || 0)}
        </td>
      </tr>
      {isOpen && children}
    </>);
  };

  const DetalheRows = ({ items }) => {
    if (!items || items.length === 0) return (
      <tr><td colSpan={4} style={{ paddingLeft: 44, fontSize: 11.5, color: 'var(--tm-fg-4)', fontStyle: 'italic' }}>Nenhum lancamento</td></tr>
    );
    return items.map((it, i) => (
      <tr key={i} style={{ background: 'var(--tm-bg-1)' }}>
        <td style={{ paddingLeft: 44, fontSize: 11.5, color: 'var(--tm-fg-3)' }}>
          {it.desc} <span style={{ fontSize: 10, color: 'var(--tm-fg-4)' }}>({it.cat})</span>
        </td>
        <td className="num right" style={{ fontSize: 11.5, color: 'var(--tm-fg-3)' }}>R$ {brl(it.valor)}</td>
        <td colSpan={2}></td>
      </tr>
    ));
  };

  const mesLabel = mesesOpts.find(m => m.value === mesAtual)?.label || mesAtual;

  return (
    <div className="canvas">
      <PageHead title="DRE" sub={`Demonstrativo de Resultados - ${mesLabel}`}
        right={<>
          <select className="input" style={{ width: 'auto', fontSize: 12 }} value={mesAtual}
            onChange={e => setMesAtual(e.target.value)}>
            {mesesOpts.map(m => <option key={m.value} value={m.value}>{m.label}</option>)}
          </select>
          <Button variant="secondary" icon="download" size="sm">Exportar</Button>
        </>} />
      <FinanceiroTabs active="dre" onNav={onNav} />

      {/* KPIs resumo */}
      <div className="grid-4" style={{ marginBottom: 16 }}>
        <KpiMini lbl="Receita Bruta" v={dreAtual.receitaBruta > 0 ? `R$ ${brl(dreAtual.receitaBruta)}` : '—'} sub={`${dreAtual.recCount} recebimentos`} />
        <KpiMini lbl="Lucro Bruto" v={dreAtual.receitaBruta > 0 ? `R$ ${brl(dreAtual.lucroBruto)}` : '—'} sub={`margem ${Math.round(dreAtual.margemBruta)}%`} />
        <KpiMini lbl="Resultado Liquido" v={dreAtual.receitaBruta > 0 || dreAtual.pagCount > 0 ? `R$ ${brl(Math.abs(dreAtual.resultadoLiquido))}` : '—'} sub={dreAtual.resultadoLiquido >= 0 ? 'positivo' : 'negativo'} />
        <KpiMini lbl="Margem Liquida" v={dreAtual.receitaBruta > 0 ? `${Math.round(dreAtual.margemLiquida)}%` : '—'} sub="sobre receita" />
      </div>

      <Card>
        {dreAtual.receitaBruta === 0 && dreAtual.pagCount === 0 ? (
          <div style={{ padding: '48px 0', textAlign: 'center', color: 'var(--tm-fg-3)' }}>
            <Icon name="file-bar-chart" size={36} style={{ opacity: 0.3, marginBottom: 12 }} />
            <div style={{ fontSize: 14, marginBottom: 6 }}>Sem dados para este periodo</div>
            <div style={{ fontSize: 12 }}>O DRE sera gerado com base nos recebimentos e pagamentos confirmados</div>
          </div>
        ) : (
          <table className="tbl" style={{ fontSize: 13 }}>
            <thead>
              <tr>
                <th style={{ width: '50%' }}>Conta</th>
                <th className="num right">{mesLabel}</th>
                <th className="num right" style={{ fontSize: 11, color: 'var(--tm-fg-4)' }}>Mes anterior</th>
                <th className="num right" style={{ fontSize: 11 }}>Delta</th>
              </tr>
            </thead>
            <tbody>
              {/* Receita Bruta */}
              <DRELinha label="(+) Receita Bruta" valor={dreAtual.receitaBruta}
                valorAnterior={dreAnterior.receitaBruta} tone="success" bold />

              {/* Custos */}
              <DRELinha label="(-) Custos (CMV)" valor={dreAtual.custoTotal}
                valorAnterior={dreAnterior.custoTotal} tone="danger" bold
                expandKey="custos">
                <DetalheRows items={dreAtual.detalhes.custo} />
              </DRELinha>

              {/* Lucro Bruto */}
              <tr style={{ borderTop: '2px solid var(--tm-line-1)' }}>
                <td style={{ fontWeight: 800, fontSize: 14, color: dreAtual.lucroBruto >= 0 ? 'var(--tm-success)' : 'var(--tm-danger)' }}>
                  (=) Lucro Bruto
                </td>
                <td className="num right" style={{ fontWeight: 800, fontSize: 14, color: dreAtual.lucroBruto >= 0 ? 'var(--tm-success)' : 'var(--tm-danger)' }}>
                  R$ {brl(Math.abs(dreAtual.lucroBruto))}
                </td>
                <td className="num right" style={{ fontSize: 11.5, color: 'var(--tm-fg-4)' }}>R$ {brl(Math.abs(dreAnterior.lucroBruto))}</td>
                <td className="num right" style={{ fontSize: 11, fontWeight: 600, color: dreAtual.lucroBruto >= dreAnterior.lucroBruto ? 'var(--tm-success)' : 'var(--tm-danger)' }}>
                  {delta(dreAtual.lucroBruto, dreAnterior.lucroBruto)}
                </td>
              </tr>

              {/* Despesas Comerciais */}
              <DRELinha label="(-) Despesas Comerciais" valor={dreAtual.grupos.despesa_comercial}
                valorAnterior={dreAnterior.grupos.despesa_comercial} indent
                expandKey="comercial">
                <DetalheRows items={dreAtual.detalhes.despesa_comercial} />
              </DRELinha>

              {/* Despesas Folha */}
              <DRELinha label="(-) Folha de Pagamento" valor={dreAtual.grupos.despesa_folha}
                valorAnterior={dreAnterior.grupos.despesa_folha} indent
                expandKey="folha">
                <DetalheRows items={dreAtual.detalhes.despesa_folha} />
              </DRELinha>

              {/* Despesas Operacionais */}
              <DRELinha label="(-) Despesas Operacionais" valor={dreAtual.grupos.despesa_operacional}
                valorAnterior={dreAnterior.grupos.despesa_operacional} indent
                expandKey="operacional">
                <DetalheRows items={dreAtual.detalhes.despesa_operacional} />
              </DRELinha>

              {/* Impostos */}
              <DRELinha label="(-) Impostos" valor={dreAtual.impostoTotal}
                valorAnterior={dreAnterior.impostoTotal} indent
                expandKey="impostos">
                <DetalheRows items={dreAtual.detalhes.imposto} />
              </DRELinha>

              {/* Resultado Liquido */}
              <tr style={{ borderTop: '3px solid var(--tm-brand-champagne)' }}>
                <td style={{ fontWeight: 800, fontSize: 15, color: dreAtual.resultadoLiquido >= 0 ? 'var(--tm-success)' : 'var(--tm-danger)', padding: '12px' }}>
                  (=) Resultado Liquido
                </td>
                <td className="num right" style={{ fontWeight: 800, fontSize: 15, color: dreAtual.resultadoLiquido >= 0 ? 'var(--tm-success)' : 'var(--tm-danger)', padding: '12px' }}>
                  R$ {brl(Math.abs(dreAtual.resultadoLiquido))}
                </td>
                <td className="num right" style={{ fontSize: 12, color: 'var(--tm-fg-4)', padding: '12px' }}>R$ {brl(Math.abs(dreAnterior.resultadoLiquido))}</td>
                <td className="num right" style={{ fontSize: 12, fontWeight: 700, padding: '12px', color: dreAtual.resultadoLiquido >= dreAnterior.resultadoLiquido ? 'var(--tm-success)' : 'var(--tm-danger)' }}>
                  {delta(dreAtual.resultadoLiquido, dreAnterior.resultadoLiquido)}
                </td>
              </tr>

              {/* Margem */}
              <tr>
                <td style={{ fontSize: 11.5, color: 'var(--tm-fg-4)', paddingLeft: 24 }}>Margem Bruta</td>
                <td className="num right" style={{ fontSize: 11.5, color: 'var(--tm-fg-4)' }}>{Math.round(dreAtual.margemBruta)}%</td>
                <td className="num right" style={{ fontSize: 11, color: 'var(--tm-fg-4)' }}>{Math.round(dreAnterior.margemBruta)}%</td>
                <td></td>
              </tr>
              <tr>
                <td style={{ fontSize: 11.5, color: 'var(--tm-fg-4)', paddingLeft: 24 }}>Margem Liquida</td>
                <td className="num right" style={{ fontSize: 11.5, color: 'var(--tm-fg-4)' }}>{Math.round(dreAtual.margemLiquida)}%</td>
                <td className="num right" style={{ fontSize: 11, color: 'var(--tm-fg-4)' }}>{Math.round(dreAnterior.margemLiquida)}%</td>
                <td></td>
              </tr>
            </tbody>
          </table>
        )}
      </Card>
    </div>
  );
}

// ─── Exports ────────────────────────────────────────────────────────────────

Object.assign(window, {
  FinDashboard, ContasReceber, ContasPagar, Entradas, Saidas, FluxoCaixa, ExtratoConsolidado, DRESection,
});
