import { useEffect, useMemo, useState } from 'react';
import {
  Alert,
  Box,
  Button,
  Card,
  CardContent,
  Chip,
  CircularProgress,
  Collapse,
  Divider,
  IconButton,
  MenuItem,
  Pagination,
  Paper,
  Stack,
  TextField,
  ToggleButton,
  ToggleButtonGroup,
  Tooltip,
  Typography,
  Table,
  TableBody,
  TableCell,
  TableContainer,
  TableHead,
  TableRow,
  useMediaQuery,
  useTheme,
} from '@mui/material';
import AddIcon from '@mui/icons-material/Add';
import EditIcon from '@mui/icons-material/Edit';
import FilterAltIcon from '@mui/icons-material/FilterAlt';
import RestartAltIcon from '@mui/icons-material/RestartAlt';
import SearchIcon from '@mui/icons-material/Search';
import SwapHorizIcon from '@mui/icons-material/SwapHoriz';
import DeleteIcon from '@mui/icons-material/Delete';
import ArrowDownwardIcon from '@mui/icons-material/ArrowDownward';
import ArrowUpwardIcon from '@mui/icons-material/ArrowUpward';
import UndoIcon from '@mui/icons-material/Undo';
import HelpIcon from '@mui/icons-material/Help';
import AccountBalanceIcon from '@mui/icons-material/AccountBalance';
import CalendarMonthIcon from '@mui/icons-material/CalendarMonth';
import CategoryIcon from '@mui/icons-material/Category';
import ExpandLessIcon from '@mui/icons-material/ExpandLess';
import ExpandMoreIcon from '@mui/icons-material/ExpandMore';
import TableRowsIcon from '@mui/icons-material/TableRows';
import ViewAgendaIcon from '@mui/icons-material/ViewAgenda';
import { Link as RouterLink } from 'react-router-dom';
import {
  deletarMovimento,
  listarMovimentos,
  type DataCampo,
  type ListarMovimentosParams,
} from '../services/movimentosService';
import type {
  Movimento,
  MovimentoStatus,
  MovimentoTipo,
  MovimentosPagination,
  MovimentosSummary,
} from '../types/movimentoTypes';
import {
  listarBancos,
  listarCentrosCusto,
  listarClientes,
} from '../../referencias/services/referenciasService';
import type {
  Banco,
  CentroCusto,
  Cliente,
} from '../../referencias/types/referenciasTypes';

const LIMITE_PADRAO = 20;
const DIAS_ALERTA_VENCIMENTO = 5;
const LIMITE_AGRUPADO = 500;

type ModoVisualizacao = 'tabela' | 'agrupado';

type GrupoCentroMovimentos = {
  chave: string;
  nome: string;
  totalEntradas: number;
  totalSaidas: number;
  saldo: number;
  quantidade: number;
  movimentos: Movimento[];
};

type GrupoBancoMovimentos = {
  chave: string;
  nome: string;
  totalEntradas: number;
  totalSaidas: number;
  saldo: number;
  quantidade: number;
  centros: GrupoCentroMovimentos[];
};

type GrupoDiaMovimentos = {
  chave: string;
  dataLabel: string;
  totalEntradas: number;
  totalSaidas: number;
  saldo: number;
  quantidade: number;
  bancos: GrupoBancoMovimentos[];
};

function inicioMesAtual() {
  const hoje = new Date();
  return new Date(hoje.getFullYear(), hoje.getMonth(), 1).toISOString().slice(0, 10);
}

function fimMesAtual() {
  const hoje = new Date();
  return new Date(hoje.getFullYear(), hoje.getMonth() + 1, 0).toISOString().slice(0, 10);
}

function formatarValor(valor: number) {
  return new Intl.NumberFormat('pt-BR', {
    style: 'currency',
    currency: 'BRL',
  }).format(Number(valor || 0));
}

function formatarData(data: string | null) {
  if (!data) return '-';

  return new Date(`${String(data).slice(0, 10)}T00:00:00`).toLocaleDateString('pt-BR');
}

function campoDataLabel(campo: DataCampo) {
  const labels: Record<DataCampo, string> = {
    dataentrada: 'Entrada',
    datavencimento: 'Vencimento',
    databaixa: 'Baixa',
    insert_date: 'Cadastro',
    update_date: 'Atualização',
    deleted_at: 'Exclusão',
  };

  return labels[campo];
}

function movimentoChipColor(movimento: string) {
  if (movimento === 'Entrada') return 'success';
  if (movimento === 'Saida') return 'error';
  if (movimento === 'Sangria') return 'warning';
  return 'default';
}

function statusChipColor(status: string) {
  if (status === 'Pago' || status === 'Recebido') return 'success';
  if (status === 'A pagar' || status === 'A receber') return 'warning';
  return 'default';
}

function getDataPrincipal(item: Movimento, campo: DataCampo) {
  if (campo === 'dataentrada') return item.dataentrada;
  if (campo === 'datavencimento') return item.datavencimento;
  if (campo === 'databaixa') return item.databaixa;
  if (campo === 'insert_date') return item.insert_date;
  if (campo === 'update_date') return item.update_date;

  return item.datavencimento;
}

function getReferencia(item: Movimento) {
  if (item.cliente_nome) return item.cliente_nome;
  if (item.banco_referencia_descricao) return item.banco_referencia_descricao;
  return '-';
}

function dataSomenteDia(data: string | null | undefined) {
  if (!data) return null;

  const texto = String(data).slice(0, 10);

  if (!/^\d{4}-\d{2}-\d{2}$/.test(texto)) {
    return null;
  }

  return new Date(`${texto}T00:00:00`);
}

function diferencaDias(dataAlvo: Date, dataBase: Date) {
  const umDiaMs = 24 * 60 * 60 * 1000;

  const alvo = new Date(
    dataAlvo.getFullYear(),
    dataAlvo.getMonth(),
    dataAlvo.getDate()
  );

  const base = new Date(
    dataBase.getFullYear(),
    dataBase.getMonth(),
    dataBase.getDate()
  );

  return Math.floor((alvo.getTime() - base.getTime()) / umDiaMs);
}

function movimentoCompensado(item: Movimento) {
  return item.status === 'Pago' || item.status === 'Recebido';
}

function movimentoEmAberto(item: Movimento) {
  return item.status === 'A pagar' || item.status === 'A receber';
}

function getMovimentoRowVisual(item: Movimento) {
  if (movimentoExcluido(item)) {
    return {
      backgroundColor: 'rgba(148,163,184,0.10)',
      hoverColor: 'rgba(148,163,184,0.16)',
      borderLeftColor: 'rgba(100,116,139,0.65)',
    };
  }

  if (movimentoCompensado(item)) {
    return {
      backgroundColor: 'rgba(34,197,94,0.08)',
      hoverColor: 'rgba(34,197,94,0.13)',
      borderLeftColor: 'rgba(34,197,94,0.75)',
    };
  }

  if (movimentoEmAberto(item)) {
    const vencimento = dataSomenteDia(item.datavencimento);

    if (vencimento) {
      const dias = diferencaDias(vencimento, new Date());

      if (dias < 0) {
        return {
          backgroundColor: 'rgba(239,68,68,0.08)',
          hoverColor: 'rgba(239,68,68,0.14)',
          borderLeftColor: 'rgba(239,68,68,0.78)',
        };
      }

      if (dias <= DIAS_ALERTA_VENCIMENTO) {
        return {
          backgroundColor: 'rgba(245,158,11,0.10)',
          hoverColor: 'rgba(245,158,11,0.16)',
          borderLeftColor: 'rgba(245,158,11,0.85)',
        };
      }
    }
  }

  return {
    backgroundColor: '#FFFFFF',
    hoverColor: 'rgba(15,23,42,0.02)',
    borderLeftColor: 'transparent',
  };
}

function getMovimentoIconVisual(movimento: MovimentoTipo) {
  if (movimento === 'Entrada') {
    return {
      icon: <ArrowDownwardIcon fontSize="small" />,
      label: 'Entrada',
      color: 'success' as const,
    };
  }

  if (movimento === 'Saida') {
    return {
      icon: <ArrowUpwardIcon fontSize="small" />,
      label: 'Saída',
      color: 'error' as const,
    };
  }

  if (movimento === 'Sangria') {
    return {
      icon: <SwapHorizIcon fontSize="small" />,
      label: 'Sangria',
      color: 'warning' as const,
    };
  }

  if (movimento === 'Estorno') {
    return {
      icon: <UndoIcon fontSize="small" />,
      label: 'Estorno',
      color: 'info' as const,
    };
  }

  return {
    icon: <HelpIcon fontSize="small" />,
    label: movimento || 'Movimento',
    color: 'default' as const,
  };
}

function formatarDataGrupo(dataISO: string) {
  if (!dataISO || dataISO === 'sem-data') return 'Sem data';

  return new Date(`${dataISO}T00:00:00`).toLocaleDateString('pt-BR', {
    weekday: 'short',
    day: '2-digit',
    month: '2-digit',
    year: 'numeric',
  });
}

function getDataGrupo(item: Movimento, campo: DataCampo) {
  const data = getDataPrincipal(item, campo);
  const texto = data ? String(data).slice(0, 10) : '';

  if (!/^\d{4}-\d{2}-\d{2}$/.test(texto)) {
    return 'sem-data';
  }

  return texto;
}

function valorAssinadoMovimento(item: Movimento) {
  const valor = Number(item.valor || 0);

  if (item.movimento === 'Entrada' || item.movimento === 'Estorno') {
    return valor;
  }

  return valor * -1;
}

function criarResumoGrupo() {
  return {
    totalEntradas: 0,
    totalSaidas: 0,
    saldo: 0,
    quantidade: 0,
  };
}

function aplicarMovimentoNoResumo<T extends ReturnType<typeof criarResumoGrupo>>(
  resumo: T,
  item: Movimento
) {
  const valorAssinado = valorAssinadoMovimento(item);

  if (valorAssinado >= 0) {
    resumo.totalEntradas += valorAssinado;
  } else {
    resumo.totalSaidas += Math.abs(valorAssinado);
  }

  resumo.saldo += valorAssinado;
  resumo.quantidade += 1;
}

function agruparMovimentos(movimentos: Movimento[], campo: DataCampo): GrupoDiaMovimentos[] {
  const gruposDia = new Map<string, {
    resumo: ReturnType<typeof criarResumoGrupo>;
    bancos: Map<string, {
      nome: string;
      resumo: ReturnType<typeof criarResumoGrupo>;
      centros: Map<string, {
        nome: string;
        resumo: ReturnType<typeof criarResumoGrupo>;
        movimentos: Movimento[];
      }>;
    }>;
  }>();

  for (const item of movimentos) {
    const chaveDia = getDataGrupo(item, campo);
    const bancoNome = item.banco_descricao || 'Sem banco';
    const centroNome = item.centro_custo_descricao || 'Sem centro de custo';

    const chaveBanco = String(item.idbancos || bancoNome);
    const chaveCentro = String(item.idcentrodecustos || centroNome);

    if (!gruposDia.has(chaveDia)) {
      gruposDia.set(chaveDia, {
        resumo: criarResumoGrupo(),
        bancos: new Map(),
      });
    }

    const grupoDia = gruposDia.get(chaveDia)!;
    aplicarMovimentoNoResumo(grupoDia.resumo, item);

    if (!grupoDia.bancos.has(chaveBanco)) {
      grupoDia.bancos.set(chaveBanco, {
        nome: bancoNome,
        resumo: criarResumoGrupo(),
        centros: new Map(),
      });
    }

    const grupoBanco = grupoDia.bancos.get(chaveBanco)!;
    aplicarMovimentoNoResumo(grupoBanco.resumo, item);

    if (!grupoBanco.centros.has(chaveCentro)) {
      grupoBanco.centros.set(chaveCentro, {
        nome: centroNome,
        resumo: criarResumoGrupo(),
        movimentos: [],
      });
    }

    const grupoCentro = grupoBanco.centros.get(chaveCentro)!;
    aplicarMovimentoNoResumo(grupoCentro.resumo, item);
    grupoCentro.movimentos.push(item);
  }

  return Array
    .from(gruposDia.entries())
    .sort(([a], [b]) => b.localeCompare(a))
    .map(([chaveDia, dia]) => ({
      chave: chaveDia,
      dataLabel: formatarDataGrupo(chaveDia),
      totalEntradas: dia.resumo.totalEntradas,
      totalSaidas: dia.resumo.totalSaidas,
      saldo: dia.resumo.saldo,
      quantidade: dia.resumo.quantidade,
      bancos: Array
        .from(dia.bancos.entries())
        .sort(([, a], [, b]) => a.nome.localeCompare(b.nome))
        .map(([chaveBanco, banco]) => ({
          chave: chaveBanco,
          nome: banco.nome,
          totalEntradas: banco.resumo.totalEntradas,
          totalSaidas: banco.resumo.totalSaidas,
          saldo: banco.resumo.saldo,
          quantidade: banco.resumo.quantidade,
          centros: Array
            .from(banco.centros.entries())
            .sort(([, a], [, b]) => a.nome.localeCompare(b.nome))
            .map(([chaveCentro, centro]) => ({
              chave: chaveCentro,
              nome: centro.nome,
              totalEntradas: centro.resumo.totalEntradas,
              totalSaidas: centro.resumo.totalSaidas,
              saldo: centro.resumo.saldo,
              quantidade: centro.resumo.quantidade,
              movimentos: centro.movimentos.sort((a, b) => {
                const dataA = String(getDataPrincipal(a, campo) || '');
                const dataB = String(getDataPrincipal(b, campo) || '');

                return dataB.localeCompare(dataA);
              }),
            })),
        })),
    }));
}

function movimentoExcluido(item: Movimento) {
  return Boolean(item.deleted_at);
}

export function MovimentosPage() {
  const [sucesso, setSucesso] = useState('');

  const [movimentos, setMovimentos] = useState<Movimento[]>([]);
  const [pagination, setPagination] = useState<MovimentosPagination>({
    total: 0,
    limite: LIMITE_PADRAO,
    offset: 0,
    page: 1,
    totalPages: 1,
  });
  const [summary, setSummary] = useState<MovimentosSummary>({
    quantidade: 0,
    totalEntradas: 0,
    totalSaidas: 0,
    totalSangrias: 0,
    totalEstornos: 0,
    totalBaixado: 0,
    totalAberto: 0,
    saldoProcessado: 0,
    saldo: 0,
  });

  const [modoVisualizacao, setModoVisualizacao] = useState<ModoVisualizacao>('tabela');
  const [gruposAbertos, setGruposAbertos] = useState<Record<string, boolean>>({});

  const [bancos, setBancos] = useState<Banco[]>([]);
  const [centrosCusto, setCentrosCusto] = useState<CentroCusto[]>([]);
  const [clientes, setClientes] = useState<Cliente[]>([]);

  const [loading, setLoading] = useState(true);
  const [loadingRefs, setLoadingRefs] = useState(true);
  const [erro, setErro] = useState('');

  const [page, setPage] = useState(1);
  const [dataCampo, setDataCampo] = useState<DataCampo>('dataentrada');
  const [dataInicio, setDataInicio] = useState(inicioMesAtual());
  const [dataFim, setDataFim] = useState(fimMesAtual());
  const [busca, setBusca] = useState('');
  const [movimento, setMovimento] = useState<MovimentoTipo | ''>('');
  const [status, setStatus] = useState<MovimentoStatus | ''>('');
  const [idBanco, setIdBanco] = useState<number | ''>('');
  const [idCentroCusto, setIdCentroCusto] = useState<number | ''>('');
  const [idCliente, setIdCliente] = useState<number | ''>('');
  const [referenciaTipo, setReferenciaTipo] = useState('');
  const [competencia, setCompetencia] = useState('');
  const [origem, setOrigem] = useState('');
  const [saldoProcessado, setSaldoProcessado] = useState<number | ''>('');
  const [incluirExcluidos, setIncluirExcluidos] = useState<number | ''>('');

  const theme = useTheme();
  const isMobile = useMediaQuery(theme.breakpoints.down('md'));

  const filtrosAtivos = useMemo(() => {
    let count = 0;

    if (busca.trim()) count += 1;
    if (movimento) count += 1;
    if (status) count += 1;
    if (idBanco) count += 1;
    if (idCentroCusto) count += 1;
    if (idCliente) count += 1;
    if (referenciaTipo) count += 1;
    if (dataInicio || dataFim) count += 1;
    if (competencia.trim()) count += 1;
    if (origem) count += 1;
    if (saldoProcessado !== '') count += 1;
    if (incluirExcluidos !== '') count += 1;

    return count;
  }, [
    busca,
    movimento,
    status,
    idBanco,
    idCentroCusto,
    idCliente,
    referenciaTipo,
    dataInicio,
    dataFim,
    competencia,
    origem,
    saldoProcessado,
    incluirExcluidos,
  ]);

  const movimentosAgrupados = useMemo(() => {
    return agruparMovimentos(movimentos, dataCampo);
  }, [movimentos, dataCampo]);

  const totalMaiorQueLimiteAgrupado = modoVisualizacao === 'agrupado' && pagination.total > LIMITE_AGRUPADO;

  async function carregarReferencias() {
    try {
      setLoadingRefs(true);

      const [bancosData, centrosData, clientesData] = await Promise.all([
        listarBancos(),
        listarCentrosCusto(),
        listarClientes(),
      ]);

      setBancos(bancosData);
      setCentrosCusto(centrosData);
      setClientes(clientesData);
    } finally {
      setLoadingRefs(false);
    }
  }

  async function carregarMovimentos(
    pageToLoad = page,
    modoParaCarregar = modoVisualizacao
  ) {
    try {
      setLoading(true);
      setErro('');

      const params: ListarMovimentosParams = {
        limite: modoParaCarregar === 'agrupado' ? LIMITE_AGRUPADO : LIMITE_PADRAO,
        page: modoParaCarregar === 'agrupado' ? 1 : pageToLoad,
        dataCampo,
        dataInicio,
        dataFim,
        busca: busca.trim() || undefined,
        movimento: movimento || undefined,
        status: status || undefined,
        idbancos: idBanco || undefined,
        idcentrodecustos: idCentroCusto || undefined,
        idclientes: idCliente || undefined,
        referenciaTipo: referenciaTipo || undefined,
        competencia: competencia.trim() || undefined,
        origem: origem || undefined,
        saldo_processado: saldoProcessado,
        incluirExcluidos,
        orderBy: dataCampo,
        orderDirection: 'DESC',
      };

      const response = await listarMovimentos(params);

      setMovimentos(response.data);
      setPagination(response.pagination);
      setSummary(response.summary);
      setPage(response.pagination.page);
    } catch (error: any) {
      const message =
        error?.response?.data?.message ||
        'Não foi possível carregar os movimentos.';

      setErro(message);
    } finally {
      setLoading(false);
    }
  }

  function aplicarFiltros() {
    setGruposAbertos({});
    setPage(1);
    carregarMovimentos(1, modoVisualizacao);
  }

  function limparFiltros() {
    setDataCampo('dataentrada');
    setDataInicio(inicioMesAtual());
    setDataFim(fimMesAtual());
    setBusca('');
    setMovimento('');
    setStatus('');
    setIdBanco('');
    setIdCentroCusto('');
    setIdCliente('');
    setReferenciaTipo('');
    setCompetencia('');
    setOrigem('');
    setSaldoProcessado('');
    setIncluirExcluidos('');
    setGruposAbertos({});

    setTimeout(() => {
      setPage(1);
      carregarMovimentos(1, modoVisualizacao);
    }, 0);
  }

  function origemLabel(origem: string | null | undefined) {
    if (!origem) return 'Manual';

    const labels: Record<string, string> = {
      manual: 'Manual',
      parcelamento: 'Parcelamento',
      movimento_fixo: 'Movimento fixo',
      quitacao: 'Quitação',
      ajuste_saldo: 'Ajuste de saldo',
    };

    return labels[origem] || origem;
  }

  function origemChipColor(origem: string | null | undefined) {
    if (origem === 'movimento_fixo') return 'info';
    if (origem === 'parcelamento') return 'secondary';
    if (origem === 'quitacao') return 'success';
    if (origem === 'ajuste_saldo') return 'warning';

    return 'default';
  }

  function saldoProcessadoLabel(valor: number | null | undefined) {
    return Number(valor) === 1 ? 'Saldo processado' : 'Sem impacto';
  }

  function saldoProcessadoColor(valor: number | null | undefined) {
    return Number(valor) === 1 ? 'success' : 'default';
  }

  async function handleDeletarMovimento(item: Movimento) {
    const confirmou = window.confirm(
      `Deseja realmente excluir "${item.descricao}"?\n\n` +
        'Se o movimento já impactou saldo, a API vai reverter automaticamente.'
    );

    if (!confirmou) return;

    try {
      setLoading(true);
      setErro('');
      setSucesso('');

      await deletarMovimento(item.idcontasapagar);

      setSucesso('Movimento excluído com sucesso. O saldo foi revertido se necessário.');
      await carregarMovimentos(page);
    } catch (error: any) {
      const message =
        error?.response?.data?.message ||
        'Não foi possível excluir o movimento.';

      setErro(message);
    } finally {
      setLoading(false);
    }
  }

  useEffect(() => {
    carregarReferencias();
    carregarMovimentos(1);
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, []);

  function toggleGrupo(chave: string) {
    setGruposAbertos((estadoAtual) => ({
      ...estadoAtual,
      [chave]: !estadoAtual[chave],
    }));
  }

  function grupoAberto(chave: string) {
    return gruposAbertos[chave] === true;
  }

  function mudarModoVisualizacao(novoModo: ModoVisualizacao | null) {
    if (!novoModo) return;

    setModoVisualizacao(novoModo);
    setGruposAbertos({});
    setPage(1);

    setTimeout(() => {
      carregarMovimentos(1, novoModo);
    }, 0);
  }

  function ResumoGrupoValores({
    entradas,
    saidas,
    saldo,
  }: {
    entradas: number;
    saidas: number;
    saldo: number;
  }) {
    return (
      <Stack direction="row" flexWrap="wrap" spacing={1} useFlexGap>
        <Chip
          size="small"
          label={`Entradas ${formatarValor(entradas)}`}
          color="success"
          variant="outlined"
        />
        <Chip
          size="small"
          label={`Saídas ${formatarValor(saidas)}`}
          color="error"
          variant="outlined"
        />
        <Chip
          size="small"
          label={`Saldo ${formatarValor(saldo)}`}
          color={saldo >= 0 ? 'success' : 'error'}
        />
      </Stack>
    );
  }

  function renderExtratoAgrupado() {
    if (movimentosAgrupados.length === 0) {
      return (
        <Box padding={3}>
          <Typography fontWeight={800}>
            Nenhum movimento encontrado.
          </Typography>
          <Typography color="text.secondary" marginTop={0.5}>
            Ajuste os filtros ou cadastre um novo movimento.
          </Typography>
        </Box>
      );
    }

    return (
      <Stack spacing={2} padding={{ xs: 1.5, md: 2 }}>
        {movimentosAgrupados.map((dia) => {
          const chaveDia = `dia:${dia.chave}`;
          const abertoDia = grupoAberto(chaveDia);

          return (
            <Paper
              key={chaveDia}
              elevation={0}
              sx={{
                border: '1px solid',
                borderColor: 'divider',
                borderRadius: 3,
                overflow: 'hidden',
                background: 'linear-gradient(180deg, #FFFFFF 0%, #F8FAFC 100%)',
              }}
            >
              <Box
                onClick={() => toggleGrupo(chaveDia)}
                sx={{
                  cursor: 'pointer',
                  padding: { xs: 1.5, md: 2 },
                  backgroundColor: 'rgba(15,23,42,0.035)',
                }}
              >
                <Stack
                  direction={{ xs: 'column', md: 'row' }}
                  justifyContent="space-between"
                  alignItems={{ xs: 'stretch', md: 'center' }}
                  spacing={1.5}
                >
                  <Stack direction="row" alignItems="center" spacing={1.25}>
                    <CalendarMonthIcon color="primary" />

                    <Box>
                      <Typography fontWeight={950}>
                        {dia.dataLabel}
                      </Typography>
                      <Typography variant="body2" color="text.secondary">
                        {dia.quantidade} movimento(s)
                      </Typography>
                    </Box>
                  </Stack>

                  <Stack direction="row" alignItems="center" spacing={1}>
                    <ResumoGrupoValores
                      entradas={dia.totalEntradas}
                      saidas={dia.totalSaidas}
                      saldo={dia.saldo}
                    />

                    {abertoDia ? <ExpandLessIcon /> : <ExpandMoreIcon />}
                  </Stack>
                </Stack>
              </Box>

              <Collapse in={abertoDia} timeout="auto" unmountOnExit>
                <Stack spacing={1.5} padding={{ xs: 1.5, md: 2 }}>
                  {dia.bancos.map((banco) => {
                    const chaveBanco = `${chaveDia}:banco:${banco.chave}`;
                    const abertoBanco = grupoAberto(chaveBanco);

                    return (
                      <Paper
                        key={chaveBanco}
                        elevation={0}
                        sx={{
                          border: '1px solid',
                          borderColor: 'divider',
                          borderRadius: 2.5,
                          overflow: 'hidden',
                          backgroundColor: '#FFFFFF',
                        }}
                      >
                        <Box
                          onClick={() => toggleGrupo(chaveBanco)}
                          sx={{
                            cursor: 'pointer',
                            padding: 1.5,
                          }}
                        >
                          <Stack
                            direction={{ xs: 'column', md: 'row' }}
                            justifyContent="space-between"
                            alignItems={{ xs: 'stretch', md: 'center' }}
                            spacing={1}
                          >
                            <Stack direction="row" alignItems="center" spacing={1}>
                              <AccountBalanceIcon color="action" />

                              <Box>
                                <Typography fontWeight={900}>
                                  {banco.nome}
                                </Typography>
                                <Typography variant="caption" color="text.secondary">
                                  {banco.quantidade} movimento(s)
                                </Typography>
                              </Box>
                            </Stack>

                            <Stack direction="row" alignItems="center" spacing={1}>
                              <ResumoGrupoValores
                                entradas={banco.totalEntradas}
                                saidas={banco.totalSaidas}
                                saldo={banco.saldo}
                              />

                              {abertoBanco ? <ExpandLessIcon /> : <ExpandMoreIcon />}
                            </Stack>
                          </Stack>
                        </Box>

                        <Collapse in={abertoBanco} timeout="auto" unmountOnExit>
                          <Stack spacing={1} padding={1.5} paddingTop={0}>
                            {banco.centros.map((centro) => {
                              const chaveCentro = `${chaveBanco}:centro:${centro.chave}`;
                              const abertoCentro = grupoAberto(chaveCentro);

                              return (
                                <Paper
                                  key={chaveCentro}
                                  elevation={0}
                                  sx={{
                                    border: '1px solid',
                                    borderColor: 'divider',
                                    borderRadius: 2,
                                    overflow: 'hidden',
                                    backgroundColor: 'rgba(248,250,252,0.9)',
                                  }}
                                >
                                  <Box
                                    onClick={() => toggleGrupo(chaveCentro)}
                                    sx={{
                                      cursor: 'pointer',
                                      padding: 1.25,
                                    }}
                                  >
                                    <Stack
                                      direction={{ xs: 'column', md: 'row' }}
                                      justifyContent="space-between"
                                      alignItems={{ xs: 'stretch', md: 'center' }}
                                      spacing={1}
                                    >
                                      <Stack direction="row" alignItems="center" spacing={1}>
                                        <CategoryIcon color="action" />

                                        <Box>
                                          <Typography fontWeight={850}>
                                            {centro.nome}
                                          </Typography>
                                          <Typography variant="caption" color="text.secondary">
                                            {centro.quantidade} movimento(s)
                                          </Typography>
                                        </Box>
                                      </Stack>

                                      <Stack direction="row" alignItems="center" spacing={1}>
                                        <ResumoGrupoValores
                                          entradas={centro.totalEntradas}
                                          saidas={centro.totalSaidas}
                                          saldo={centro.saldo}
                                        />

                                        {abertoCentro ? <ExpandLessIcon /> : <ExpandMoreIcon />}
                                      </Stack>
                                    </Stack>
                                  </Box>

                                  <Collapse in={abertoCentro} timeout="auto" unmountOnExit>
                                    <Stack spacing={0.75} padding={1.25} paddingTop={0}>
                                      {centro.movimentos.map((item) => {
                                        const rowVisual = getMovimentoRowVisual(item);
                                        const movimentoIcon = getMovimentoIconVisual(item.movimento);
                                        const dataPrincipal = getDataPrincipal(item, dataCampo);

                                        return (
                                          <Paper
                                            key={item.idcontasapagar}
                                            elevation={0}
                                            sx={{
                                              padding: 1.25,
                                              borderRadius: 2,
                                              border: '1px solid',
                                              borderColor: 'divider',
                                              borderLeft: '5px solid',
                                              borderLeftColor: rowVisual.borderLeftColor,
                                              backgroundColor: rowVisual.backgroundColor,
                                              '&:hover': {
                                                backgroundColor: rowVisual.hoverColor,
                                              },
                                            }}
                                          >
                                            <Stack
                                              direction={{ xs: 'column', md: 'row' }}
                                              justifyContent="space-between"
                                              alignItems={{ xs: 'stretch', md: 'center' }}
                                              spacing={1.25}
                                            >
                                              <Stack direction="row" spacing={1} alignItems="center">
                                                <Tooltip title={movimentoIcon.label}>
                                                  <Chip
                                                    icon={movimentoIcon.icon}
                                                    label=""
                                                    size="small"
                                                    color={movimentoIcon.color as any}
                                                    sx={{
                                                      width: 36,
                                                      '& .MuiChip-label': {
                                                        display: 'none',
                                                      },
                                                      '& .MuiChip-icon': {
                                                        marginLeft: 0,
                                                        marginRight: 0,
                                                      },
                                                    }}
                                                  />
                                                </Tooltip>

                                                <Box sx={{ minWidth: 0 }}>
                                                  <Typography fontWeight={900} noWrap title={item.descricao}>
                                                    {item.descricao}
                                                  </Typography>

                                                  <Typography variant="caption" color="text.secondary">
                                                    {campoDataLabel(dataCampo)}: {formatarData(dataPrincipal)} ·{' '}
                                                    Ref.: {getReferencia(item)} · {origemLabel(item.origem)}
                                                  </Typography>
                                                </Box>
                                              </Stack>

                                              <Stack
                                                direction="row"
                                                spacing={1}
                                                alignItems="center"
                                                justifyContent={{ xs: 'space-between', md: 'flex-end' }}
                                              >
                                                <Chip
                                                  label={item.status}
                                                  size="small"
                                                  variant="outlined"
                                                  color={statusChipColor(item.status) as any}
                                                />

                                                <Typography
                                                  fontWeight={950}
                                                  color={
                                                    item.movimento === 'Entrada' || item.movimento === 'Estorno'
                                                      ? 'success.main'
                                                      : 'error.main'
                                                  }
                                                  whiteSpace="nowrap"
                                                >
                                                  {item.movimento === 'Entrada' || item.movimento === 'Estorno'
                                                    ? '+'
                                                    : '-'}
                                                  {formatarValor(item.valor)}
                                                </Typography>

                                                {!movimentoExcluido(item) && (
                                                  <Tooltip title="Editar movimento">
                                                    <IconButton
                                                      component={RouterLink}
                                                      to={`/movimentos/${item.idcontasapagar}/editar`}
                                                      color="primary"
                                                      size="small"
                                                    >
                                                      <EditIcon />
                                                    </IconButton>
                                                  </Tooltip>
                                                )}
                                              </Stack>
                                            </Stack>
                                          </Paper>
                                        );
                                      })}
                                    </Stack>
                                  </Collapse>
                                </Paper>
                              );
                            })}
                          </Stack>
                        </Collapse>
                      </Paper>
                    );
                  })}
                </Stack>
              </Collapse>
            </Paper>
          );
        })}
      </Stack>
    );
  }

  return (
    <Box>
      <Stack
        direction={{ xs: 'column', md: 'row' }}
        justifyContent="space-between"
        alignItems={{ xs: 'stretch', md: 'center' }}
        spacing={2}
        marginBottom={{ xs: 3, md: 4 }}
      >
        <Box>
          <Chip
            icon={<SwapHorizIcon />}
            label="Central de movimentos"
            color="primary"
            variant="outlined"
            sx={{ marginBottom: 1.25, fontWeight: 700 }}
          />

          <Typography variant="h4" fontWeight={950}>
            Movimentos
          </Typography>

          <Typography color="text.secondary" sx={{ marginTop: 0.5 }}>
            Consulte, filtre e edite os lançamentos financeiros.
          </Typography>
        </Box>

        <Button
          component={RouterLink}
          to="/movimentos/novo"
          variant="contained"
          startIcon={<AddIcon />}
          sx={{
            minHeight: 48,
            borderRadius: 3,
            px: 2.5,
            boxShadow: 3,
          }}
        >
          Novo movimento
        </Button>
      </Stack>

      {erro && (
        <Alert severity="error" sx={{ marginBottom: 2.5 }}>
          {erro}
        </Alert>
      )}

      {sucesso && (
        <Alert severity="success" sx={{ marginBottom: 2.5 }}>
          {sucesso}
        </Alert>
      )}

      <Box
        display="grid"
        gridTemplateColumns={{
          xs: '1fr',
          md: 'repeat(6, 1fr)',
        }}
        gap={{ xs: 2, md: 2.5 }}
        marginBottom={{ xs: 2.5, md: 3 }}
      >
        <Card>
          <CardContent>
            <Typography variant="body2" color="text.secondary">
              Registros encontrados
            </Typography>
            <Typography variant="h5" fontWeight={950}>
              {summary.quantidade}
            </Typography>
          </CardContent>
        </Card>

        <Card>
          <CardContent>
            <Typography variant="body2" color="text.secondary">
              Entradas
            </Typography>
            <Typography variant="h5" fontWeight={950} color="success.main">
              {formatarValor(summary.totalEntradas)}
            </Typography>
          </CardContent>
        </Card>

        <Card>
          <CardContent>
            <Typography variant="body2" color="text.secondary">
              Saídas
            </Typography>
            <Typography variant="h5" fontWeight={950} color="error.main">
              {formatarValor(summary.totalSaidas + summary.totalSangrias)}
            </Typography>
          </CardContent>
        </Card>

        <Card>
          <CardContent>
            <Typography variant="body2" color="text.secondary">
              Saldo filtrado
            </Typography>
            <Typography
              variant="h5"
              fontWeight={950}
              color={summary.saldo >= 0 ? 'success.main' : 'error.main'}
            >
              {formatarValor(summary.saldo)}
            </Typography>
          </CardContent>
        </Card>

        <Card>
          <CardContent>
            <Typography variant="body2" color="text.secondary">
              Em aberto
            </Typography>
            <Typography variant="h5" fontWeight={950} color="warning.main">
              {formatarValor(summary.totalAberto)}
            </Typography>
          </CardContent>
        </Card>

        <Card>
          <CardContent>
            <Typography variant="body2" color="text.secondary">
              Baixados
            </Typography>
            <Typography variant="h5" fontWeight={950} color="info.main">
              {formatarValor(summary.totalBaixado)}
            </Typography>
          </CardContent>
        </Card>
      </Box>

      <Card sx={{ marginBottom: { xs: 2.5, md: 3 } }}>
        <CardContent sx={{ padding: { xs: 2, md: 3 } }}>
          <Stack
            direction="row"
            spacing={1}
            alignItems="center"
            marginBottom={2.5}
          >
            <FilterAltIcon color="primary" />
            <Typography variant="h6" fontWeight={900}>
              Filtros
            </Typography>

            <Chip
              label={`${filtrosAtivos} ativo(s)`}
              size="small"
              variant="outlined"
            />
          </Stack>

          <Box
            display="grid"
            gridTemplateColumns={{
              xs: '1fr',
              md: 'repeat(4, 1fr)',
            }}
            gap={{ xs: 2, md: 2.25 }}
          >
            <TextField
              label="Buscar"
              value={busca}
              onChange={(event) => setBusca(event.target.value)}
              placeholder="Descrição, observação, banco, cliente..."
              fullWidth
            />

            <TextField
              select
              label="Campo de data"
              value={dataCampo}
              onChange={(event) => setDataCampo(event.target.value as DataCampo)}
              fullWidth
            >
              <MenuItem value="datavencimento">Data de vencimento</MenuItem>
              <MenuItem value="dataentrada">Data de entrada</MenuItem>
              <MenuItem value="databaixa">Data de baixa</MenuItem>
              <MenuItem value="insert_date">Data de cadastro</MenuItem>
              <MenuItem value="update_date">Data de atualização</MenuItem>
              <MenuItem value="deleted_at">Data de exclusão</MenuItem>
            </TextField>

            <TextField
              label="Data inicial"
              type="date"
              value={dataInicio}
              onChange={(event) => setDataInicio(event.target.value)}
              InputLabelProps={{ shrink: true }}
              fullWidth
            />

            <TextField
              label="Data final"
              type="date"
              value={dataFim}
              onChange={(event) => setDataFim(event.target.value)}
              InputLabelProps={{ shrink: true }}
              fullWidth
            />

            <TextField
              select
              label="Movimento"
              value={movimento}
              onChange={(event) => setMovimento(event.target.value as MovimentoTipo | '')}
              fullWidth
            >
              <MenuItem value="">Todos</MenuItem>
              <MenuItem value="Entrada">Entrada</MenuItem>
              <MenuItem value="Saida">Saída</MenuItem>
              <MenuItem value="Sangria">Sangria</MenuItem>
              <MenuItem value="Estorno">Estorno</MenuItem>
            </TextField>

            <TextField
              select
              label="Situação"
              value={status}
              onChange={(event) => setStatus(event.target.value as MovimentoStatus | '')}
              fullWidth
            >
              <MenuItem value="">Todas</MenuItem>
              <MenuItem value="Pago">Pago</MenuItem>
              <MenuItem value="A pagar">A pagar</MenuItem>
              <MenuItem value="Recebido">Recebido</MenuItem>
              <MenuItem value="A receber">A receber</MenuItem>
            </TextField>

            <TextField
              select
              label="Banco/Carteira"
              value={idBanco}
              onChange={(event) =>
                setIdBanco(event.target.value === '' ? '' : Number(event.target.value))
              }
              disabled={loadingRefs}
              fullWidth
            >
              <MenuItem value="">Todos</MenuItem>
              {bancos.map((banco) => (
                <MenuItem key={banco.id} value={banco.id}>
                  {banco.descricao}
                </MenuItem>
              ))}
            </TextField>

            <TextField
              select
              label="Centro de custo"
              value={idCentroCusto}
              onChange={(event) =>
                setIdCentroCusto(event.target.value === '' ? '' : Number(event.target.value))
              }
              disabled={loadingRefs}
              fullWidth
            >
              <MenuItem value="">Todos</MenuItem>
              {centrosCusto.map((centro) => (
                <MenuItem key={centro.id} value={centro.id}>
                  {centro.descricao}
                </MenuItem>
              ))}
            </TextField>

            <TextField
              select
              label="Cliente"
              value={idCliente}
              onChange={(event) =>
                setIdCliente(event.target.value === '' ? '' : Number(event.target.value))
              }
              disabled={loadingRefs}
              fullWidth
            >
              <MenuItem value="">Todos</MenuItem>
              {clientes.map((cliente) => (
                <MenuItem key={cliente.id} value={cliente.id}>
                  {cliente.nome}
                </MenuItem>
              ))}
            </TextField>

            <TextField
              select
              label="Referência"
              value={referenciaTipo}
              onChange={(event) => setReferenciaTipo(event.target.value)}
              fullWidth
            >
              <MenuItem value="">Todas</MenuItem>
              <MenuItem value="cliente">Com cliente</MenuItem>
              <MenuItem value="banco">Com banco referência</MenuItem>
              <MenuItem value="sem_referencia">Sem referência</MenuItem>
            </TextField>

            <TextField
              label="Competência"
              type="month"
              value={competencia}
              onChange={(event) => setCompetencia(event.target.value)}
              InputLabelProps={{ shrink: true }}
              fullWidth
            />

            <TextField
              select
              label="Origem"
              value={origem}
              onChange={(event) => setOrigem(event.target.value)}
              fullWidth
            >
              <MenuItem value="">Todas</MenuItem>
              <MenuItem value="manual">Manual</MenuItem>
              <MenuItem value="parcelamento">Parcelamento</MenuItem>
              <MenuItem value="movimento_fixo">Movimento fixo</MenuItem>
              <MenuItem value="quitacao">Quitação</MenuItem>
              <MenuItem value="ajuste_saldo">Ajuste de saldo</MenuItem>
            </TextField>

            <TextField
              select
              label="Saldo processado"
              value={saldoProcessado}
              onChange={(event) =>
                setSaldoProcessado(event.target.value === '' ? '' : Number(event.target.value))
              }
              fullWidth
            >
              <MenuItem value="">Todos</MenuItem>
              <MenuItem value={1}>Sim</MenuItem>
              <MenuItem value={0}>Não</MenuItem>
            </TextField>

            <TextField
              select
              label="Excluídos"
              value={incluirExcluidos}
              onChange={(event) =>
                setIncluirExcluidos(event.target.value === '' ? '' : Number(event.target.value))
              }
              fullWidth
            >
              <MenuItem value="">Somente ativos</MenuItem>
              <MenuItem value={1}>Incluir excluídos</MenuItem>
            </TextField>
          </Box>

          <Stack
            direction={{ xs: 'column', sm: 'row' }}
            spacing={1.5}
            justifyContent="flex-end"
            marginTop={2.5}
          >
            <Button
              variant="outlined"
              startIcon={<RestartAltIcon />}
              onClick={limparFiltros}
            >
              Limpar
            </Button>

            <Button
              variant="contained"
              startIcon={<SearchIcon />}
              onClick={aplicarFiltros}
              disabled={loading}
            >
              Aplicar filtros
            </Button>
          </Stack>
        </CardContent>
      </Card>

      <Stack
        direction="row"
        flexWrap="wrap"
        spacing={1}
        useFlexGap
        marginBottom={1.5}
      >
        <Chip size="small" label="Compensado" color="success" variant="outlined" />
        <Chip size="small" label="Vencido em aberto" color="error" variant="outlined" />
        <Chip size="small" label="Próximo do vencimento" color="warning" variant="outlined" />
        <Chip size="small" label="Excluído" color="default" variant="outlined" />
      </Stack>

      <Stack
        direction={{ xs: 'column', sm: 'row' }}
        justifyContent="space-between"
        alignItems={{ xs: 'stretch', sm: 'center' }}
        spacing={1.5}
        marginBottom={1.5}
      >
        <Box>
          <Typography variant="h6" fontWeight={900}>
            Resultado
          </Typography>
          <Typography variant="body2" color="text.secondary">
            Alterne entre a tabela detalhada e o extrato agrupado por dia, banco e centro.
          </Typography>
        </Box>

        <ToggleButtonGroup
          exclusive
          size="small"
          value={modoVisualizacao}
          onChange={(_, novoModo) => mudarModoVisualizacao(novoModo)}
        >
          <ToggleButton value="tabela">
            <Stack direction="row" spacing={0.75} alignItems="center">
              <TableRowsIcon fontSize="small" />
              <span>Tabela</span>
            </Stack>
          </ToggleButton>

          <ToggleButton value="agrupado">
            <Stack direction="row" spacing={0.75} alignItems="center">
              <ViewAgendaIcon fontSize="small" />
              <span>Extrato</span>
            </Stack>
          </ToggleButton>
        </ToggleButtonGroup>
      </Stack>

      {totalMaiorQueLimiteAgrupado && (
        <Alert severity="warning" sx={{ marginBottom: 1.5 }}>
          Exibindo os primeiros {LIMITE_AGRUPADO} movimentos do filtro no modo extrato.
          Refine o período para uma análise completa.
        </Alert>
      )}

      <Card>
        <CardContent sx={{ padding: 0 }}>
          {loading ? (
            <Box padding={3} display="flex" alignItems="center" gap={2}>
              <CircularProgress size={22} />
              <Typography>Carregando movimentos...</Typography>
            </Box>
          ) : modoVisualizacao === 'agrupado' ? (
            renderExtratoAgrupado()
          ) : movimentos.length === 0 ? (
            <Box padding={3}>
              <Typography fontWeight={800}>
                Nenhum movimento encontrado.
              </Typography>
              <Typography color="text.secondary" marginTop={0.5}>
                Ajuste os filtros ou cadastre um novo movimento.
              </Typography>
            </Box>
          ) : isMobile ? (
            <Stack divider={<Divider />}>
              {movimentos.map((item) => {
                const dataPrincipal = getDataPrincipal(item, dataCampo);
                const rowVisual = getMovimentoRowVisual(item);
                const movimentoIcon = getMovimentoIconVisual(item.movimento);

                return (
                  <Box
                    key={item.idcontasapagar}
                    sx={{
                      padding: 2,
                      backgroundColor: rowVisual.backgroundColor,
                      borderLeft: '5px solid',
                      borderLeftColor: rowVisual.borderLeftColor,
                      '&:hover': {
                        backgroundColor: rowVisual.hoverColor,
                      },
                    }}
                  >
                    <Stack spacing={1.25}>
                      <Stack
                        direction="row"
                        justifyContent="space-between"
                        alignItems="flex-start"
                        spacing={2}
                      >
                        <Box sx={{ minWidth: 0 }}>
                          <Stack direction="row" alignItems="center" spacing={1}>
                            <Tooltip title={movimentoIcon.label}>
                              <Chip
                                icon={movimentoIcon.icon}
                                label=""
                                size="small"
                                color={movimentoIcon.color as any}
                                sx={{
                                  width: 36,
                                  '& .MuiChip-label': {
                                    display: 'none',
                                  },
                                  '& .MuiChip-icon': {
                                    marginLeft: 0,
                                    marginRight: 0,
                                  },
                                }}
                              />
                            </Tooltip>

                            <Typography fontWeight={900}>
                              {item.descricao}
                            </Typography>
                          </Stack>

                          <Typography variant="body2" color="text.secondary">
                            {campoDataLabel(dataCampo)}: {formatarData(dataPrincipal)}
                          </Typography>
                        </Box>

                        <Typography
                          fontWeight={950}
                          color={
                            item.movimento === 'Entrada' || item.movimento === 'Estorno'
                              ? 'success.main'
                              : 'text.primary'
                          }
                          whiteSpace="nowrap"
                        >
                          {formatarValor(item.valor)}
                        </Typography>
                      </Stack>

                      <Stack direction="row" flexWrap="wrap" spacing={1} useFlexGap>
                        <Chip
                          label={item.movimento}
                          size="small"
                          color={movimentoChipColor(item.movimento) as any}
                        />

                        <Chip
                          label={item.status}
                          size="small"
                          variant="outlined"
                          color={statusChipColor(item.status) as any}
                        />

                        <Chip
                          label={`${item.parcela}/${item.parcelas}`}
                          size="small"
                          variant="outlined"
                        />

                        <Chip
                          label={origemLabel(item.origem)}
                          size="small"
                          color={origemChipColor(item.origem) as any}
                          variant="outlined"
                        />

                        <Chip
                          label={saldoProcessadoLabel(item.saldo_processado)}
                          size="small"
                          color={saldoProcessadoColor(item.saldo_processado) as any}
                          variant={Number(item.saldo_processado) === 1 ? 'filled' : 'outlined'}
                        />

                        {movimentoExcluido(item) && (
                          <Chip
                            label="Excluído"
                            size="small"
                            color="error"
                            variant="outlined"
                          />
                        )}
                      </Stack>

                      <Typography variant="body2" color="text.secondary">
                        Banco: <strong>{item.banco_descricao || '-'}</strong>
                      </Typography>

                      <Typography variant="body2" color="text.secondary">
                        Centro: <strong>{item.centro_custo_descricao || '-'}</strong>
                      </Typography>

                      <Typography variant="body2" color="text.secondary">
                        Referência: <strong>{getReferencia(item)}</strong>
                      </Typography>

                      <Typography variant="body2" color="text.secondary">
                        Competência: <strong>{item.competencia || '-'}</strong>
                      </Typography>

                      <Typography variant="body2" color="text.secondary">
                        Origem: <strong>{origemLabel(item.origem)}</strong>
                      </Typography>

                      <Box display="flex" justifyContent="flex-end">
                        <Button
                          component={RouterLink}
                          to={`/movimentos/${item.idcontasapagar}/editar`}
                          variant="outlined"
                          size="small"
                          startIcon={<EditIcon />}
                        >
                          Editar
                        </Button>
                      </Box>
                    </Stack>
                  </Box>
                );
              })}
            </Stack>
          ) : (
            <TableContainer
              sx={{
                overflowX: 'auto',
              }}
            >
              <Table
                size="small"
                sx={{
                  minWidth: 1720,
                  '& th': {
                    whiteSpace: 'nowrap',
                    fontWeight: 900,
                    backgroundColor: 'rgba(15,23,42,0.04)',
                  },
                  '& td': {
                    whiteSpace: 'nowrap',
                  },
                }}
              >
                <TableHead>
                  <TableRow>
                    <TableCell sx={{ minWidth: 70 }} align="center">Tipo</TableCell>
                    <TableCell sx={{ minWidth: 260 }}>Descrição</TableCell>
                    <TableCell sx={{ minWidth: 120 }}>Entrada</TableCell>
                    <TableCell sx={{ minWidth: 130 }}>Vencimento</TableCell>
                    <TableCell sx={{ minWidth: 120 }}>Baixa</TableCell>
                    <TableCell sx={{ minWidth: 120 }} align="right">Valor</TableCell>
                    <TableCell sx={{ minWidth: 90 }} align="center">Parcela</TableCell>
                    <TableCell sx={{ minWidth: 95 }} align="center">Parcelas</TableCell>
                    <TableCell sx={{ minWidth: 130 }}>Situação</TableCell>
                    <TableCell sx={{ minWidth: 150 }}>Movimento</TableCell>
                    <TableCell sx={{ minWidth: 130 }}>Competência</TableCell>
                    <TableCell sx={{ minWidth: 150 }}>Origem</TableCell>
                    <TableCell sx={{ minWidth: 150 }}>Saldo</TableCell>
                    <TableCell sx={{ minWidth: 180 }}>Centro de custo</TableCell>
                    <TableCell sx={{ minWidth: 180 }}>Banco</TableCell>
                    <TableCell sx={{ minWidth: 180 }}>Cliente</TableCell>
                    <TableCell sx={{ minWidth: 180 }}>Banco ref.</TableCell>
                    <TableCell sx={{ minWidth: 220 }}>Observação</TableCell>
                    <TableCell sx={{ minWidth: 130 }}>Exclusão</TableCell>
                    <TableCell sx={{ minWidth: 90 }} align="center">Ações</TableCell>
                  </TableRow>
                </TableHead>

                <TableBody>
                  {movimentos.map((item) => {
                    const dataPrincipal = getDataPrincipal(item, dataCampo);
                    const rowVisual = getMovimentoRowVisual(item);
                    const movimentoIcon = getMovimentoIconVisual(item.movimento);

                    return (
                      <TableRow
                        key={item.idcontasapagar}
                        hover
                        sx={{
                          backgroundColor: rowVisual.backgroundColor,
                          borderLeft: '5px solid',
                          borderLeftColor: rowVisual.borderLeftColor,
                          '&:hover': {
                            backgroundColor: rowVisual.hoverColor,
                          },
                          '&:last-child td': {
                            borderBottom: 0,
                          },
                        }}
                      >
                        <TableCell align="center">
                          <Tooltip title={movimentoIcon.label}>
                            <Chip
                              icon={movimentoIcon.icon}
                              label=""
                              size="small"
                              color={movimentoIcon.color as any}
                              sx={{
                                width: 38,
                                '& .MuiChip-label': {
                                  display: 'none',
                                },
                                '& .MuiChip-icon': {
                                  marginLeft: 0,
                                  marginRight: 0,
                                },
                              }}
                            />
                          </Tooltip>
                        </TableCell>

                        <TableCell>
                          <Box sx={{ maxWidth: 260 }}>
                            <Typography fontWeight={800} noWrap title={item.descricao}>
                              {item.descricao}
                            </Typography>
                          </Box>
                        </TableCell>

                        <TableCell>
                          {formatarData(item.dataentrada)}
                        </TableCell>

                        <TableCell>
                          {formatarData(item.datavencimento)}
                        </TableCell>

                        <TableCell>
                          {formatarData(item.databaixa)}
                        </TableCell>

                        <TableCell align="right">
                          <Typography
                            fontWeight={950}
                            color={
                              item.movimento === 'Entrada' || item.movimento === 'Estorno'
                                ? 'success.main'
                                : 'text.primary'
                            }
                          >
                            {formatarValor(item.valor)}
                          </Typography>
                        </TableCell>

                        <TableCell align="center">
                          {item.parcela}
                        </TableCell>

                        <TableCell align="center">
                          {item.parcelas}
                        </TableCell>

                        <TableCell>
                          <Chip
                            label={item.status}
                            size="small"
                            variant="outlined"
                            color={statusChipColor(item.status) as any}
                          />
                        </TableCell>

                        <TableCell>
                          <Chip
                            label={item.movimento}
                            size="small"
                            color={movimentoChipColor(item.movimento) as any}
                          />
                        </TableCell>

                        <TableCell>
                          {item.competencia || '-'}
                        </TableCell>

                        <TableCell>
                          <Chip
                            label={origemLabel(item.origem)}
                            size="small"
                            color={origemChipColor(item.origem) as any}
                            variant="outlined"
                          />
                        </TableCell>

                        <TableCell>
                          <Chip
                            label={saldoProcessadoLabel(item.saldo_processado)}
                            size="small"
                            color={saldoProcessadoColor(item.saldo_processado) as any}
                            variant={Number(item.saldo_processado) === 1 ? 'filled' : 'outlined'}
                          />
                        </TableCell>

                        <TableCell>
                          <Typography variant="body2" noWrap title={item.centro_custo_descricao || '-'}>
                            {item.centro_custo_descricao || '-'}
                          </Typography>
                        </TableCell>

                        <TableCell>
                          <Typography variant="body2" noWrap title={item.banco_descricao || '-'}>
                            {item.banco_descricao || '-'}
                          </Typography>
                        </TableCell>

                        <TableCell>
                          <Typography variant="body2" noWrap title={item.cliente_nome || '-'}>
                            {item.cliente_nome || '-'}
                          </Typography>
                        </TableCell>

                        <TableCell>
                          <Typography variant="body2" noWrap title={item.banco_referencia_descricao || '-'}>
                            {item.banco_referencia_descricao || '-'}
                          </Typography>
                        </TableCell>

                        <TableCell>
                          <Box sx={{ maxWidth: 220 }}>
                            <Typography variant="body2" noWrap title={item.observacao || '-'}>
                              {item.observacao || '-'}
                            </Typography>
                          </Box>
                        </TableCell>

                        <TableCell>
                          {formatarData(item.deleted_at)}
                        </TableCell>

                        <TableCell align="center">
                          <Stack
                            direction="row"
                            spacing={0.5}
                            alignItems="center"
                            justifyContent="center"
                          >
                            {!movimentoExcluido(item) && (
                              <>
                                <Tooltip title="Editar movimento">
                                  <IconButton
                                    component={RouterLink}
                                    to={`/movimentos/${item.idcontasapagar}/editar`}
                                    color="primary"
                                    size="small"
                                  >
                                    <EditIcon />
                                  </IconButton>
                                </Tooltip>

                                <Tooltip title="Excluir movimento">
                                  <IconButton
                                    color="error"
                                    size="small"
                                    onClick={() => handleDeletarMovimento(item)}
                                  >
                                    <DeleteIcon />
                                  </IconButton>
                                </Tooltip>
                              </>
                            )}
                          </Stack>
                        </TableCell>

                      </TableRow>
                    );
                  })}
                </TableBody>
              </Table>
            </TableContainer>
          )}
        </CardContent>
      </Card>

      {modoVisualizacao === 'tabela' && pagination.totalPages > 1 && (
        <Stack alignItems="center" marginTop={3}>
          <Pagination
            page={pagination.page}
            count={pagination.totalPages}
            color="primary"
            onChange={(_, novaPagina) => {
              setPage(novaPagina);
              carregarMovimentos(novaPagina);
            }}
          />
        </Stack>
      )}

      <Paper
        elevation={0}
        sx={{
          marginTop: 2,
          padding: 2,
          border: '1px solid',
          borderColor: 'divider',
          borderRadius: 3,
          backgroundColor: 'rgba(255,255,255,0.65)',
        }}
      >
        <Typography variant="body2" color="text.secondary">
          {modoVisualizacao === 'agrupado' ? (
            <>
              Exibindo <strong>{movimentos.length}</strong> movimento(s) no extrato agrupado,
              de um total de <strong>{pagination.total}</strong> registro(s) filtrado(s).
            </>
          ) : (
            <>
              Exibindo página {pagination.page} de {pagination.totalPages}, total de{' '}
              <strong>{pagination.total}</strong> registro(s).
            </>
          )}
        </Typography>
      </Paper>
    </Box>
  );
}