2025-04-02 14:14:37 -03:00
{% extends "base.html" %}
2025-02-19 14:27:14 -03:00
2025-04-03 10:30:48 -03:00
{% block title %}Home{% endblock %}
2025-02-19 14:27:14 -03:00
{% block content %}
2025-04-02 17:22:48 -03:00
< div class = "row g-4" >
2025-04-02 14:14:37 -03:00
< div class = "col-12" >
2025-04-02 21:20:48 -03:00
< div class = "welcome-header" >
< h2 class = "mb-2" > Olá, {{ nome_usuario }}!< / h2 >
< h4 class = "text-muted" >
{{ data_atual }}
< / h4 >
< / div >
2025-04-02 14:14:37 -03:00
< / div >
2025-04-03 13:48:09 -03:00
<!-- Cards de Estatísticas -->
2025-04-02 14:14:37 -03:00
< div class = "col-md-6 col-lg-3" >
2025-04-03 13:48:09 -03:00
< div class = "stats-card blue" >
< div class = "title" > Total de Militantes< / div >
< div class = "value" > {{ total_militantes }}< / div >
< a href = "{{ url_for('listar_militantes') }}" class = "link" >
Ver detalhes < i class = "fas fa-arrow-right" > < / i >
< / a >
< div class = "icon" >
< i class = "fas fa-users" > < / i >
2025-04-02 14:14:37 -03:00
< / div >
< / div >
< / div >
< div class = "col-md-6 col-lg-3" >
2025-04-03 13:48:09 -03:00
< div class = "stats-card green" >
< div class = "title" > Total de Cotas< / div >
< div class = "value" > R$ {{ total_cotas }}< / div >
< a href = "{{ url_for('listar_cotas') }}" class = "link" >
Ver detalhes < i class = "fas fa-arrow-right" > < / i >
< / a >
< div class = "icon" >
< i class = "fas fa-dollar-sign" > < / i >
2025-04-02 14:14:37 -03:00
< / div >
< / div >
< / div >
< div class = "col-md-6 col-lg-3" >
2025-04-03 13:48:09 -03:00
< div class = "stats-card cyan" >
< div class = "title" > Materiais Vendidos< / div >
< div class = "value" > {{ total_materiais }}< / div >
< a href = "{{ url_for('listar_materiais') }}" class = "link" >
Ver detalhes < i class = "fas fa-arrow-right" > < / i >
< / a >
< div class = "icon" >
< i class = "fas fa-book" > < / i >
2025-04-02 14:14:37 -03:00
< / div >
< / div >
< / div >
< div class = "col-md-6 col-lg-3" >
2025-04-03 13:48:09 -03:00
< div class = "stats-card yellow" >
< div class = "title" > Assinaturas Ativas< / div >
< div class = "value" > {{ total_assinaturas }}< / div >
< a href = "{{ url_for('listar_assinaturas') }}" class = "link" >
Ver detalhes < i class = "fas fa-arrow-right" > < / i >
< / a >
< div class = "icon" >
< i class = "fas fa-newspaper" > < / i >
2025-04-02 14:14:37 -03:00
< / div >
< / div >
< / div >
< / div >
< div class = "row mt-4" >
<!-- Últimos Militantes -->
< div class = "col-md-6 mb-4" >
< div class = "card h-100" >
2025-04-02 21:20:48 -03:00
< div class = "card-header" >
2025-04-03 13:48:09 -03:00
< h5 class = "card-title" >
< i class = "fas fa-user-plus" > < / i > Últimos Militantes Cadastrados
2025-04-02 14:14:37 -03:00
< / h5 >
< / div >
2025-04-03 13:48:09 -03:00
< div class = "card-body p-0" >
2025-04-02 14:14:37 -03:00
{% if ultimos_militantes %}
< div class = "list-group list-group-flush" >
{% for militante in ultimos_militantes %}
2025-04-03 13:48:09 -03:00
< div class = "list-group-item" onclick = "window.location='{{ url_for('editar_militante', id=militante.id) }}'" >
< div class = "militante-info" >
2025-04-02 14:14:37 -03:00
< h6 class = "mb-1" > {{ militante.nome }}< / h6 >
2025-04-03 13:48:09 -03:00
< small > {{ militante.email }}< / small >
2025-04-02 14:14:37 -03:00
< / div >
2025-04-03 13:48:09 -03:00
< i class = "fas fa-chevron-right text-muted" > < / i >
< / div >
2025-03-24 14:50:42 -03:00
{% endfor %}
2025-04-02 14:14:37 -03:00
< / div >
{% else %}
2025-04-03 13:48:09 -03:00
< p class = "text-muted m-3" > Nenhum militante cadastrado recentemente.< / p >
2025-03-24 14:50:42 -03:00
{% endif %}
2025-04-02 14:14:37 -03:00
< / div >
< / div >
< / div >
<!-- Últimos Pagamentos -->
< div class = "col-md-6 mb-4" >
< div class = "card h-100" >
2025-04-03 13:48:09 -03:00
< div class = "card-header" >
< h5 class = "card-title" >
< i class = "fas fa-money-bill-wave" > < / i > Últimos Pagamentos
2025-04-02 14:14:37 -03:00
< / h5 >
< / div >
2025-04-03 13:48:09 -03:00
< div class = "card-body p-0" >
2025-04-02 14:14:37 -03:00
{% if ultimos_pagamentos %}
< div class = "list-group list-group-flush" >
{% for pagamento in ultimos_pagamentos %}
2025-04-03 13:55:31 -03:00
< div class = "list-group-item" style = "cursor: pointer" onclick = "carregarDadosPagamento({{ pagamento.id }})" >
2025-04-03 13:48:09 -03:00
< div class = "militante-info" >
2025-04-02 14:14:37 -03:00
< h6 class = "mb-1" > {{ pagamento.militante.nome }}< / h6 >
2025-04-03 13:48:09 -03:00
< small > {{ pagamento.data_pagamento.strftime('%d/%m/%Y') }}< / small >
2025-04-03 10:30:48 -03:00
< / div >
2025-04-03 13:55:31 -03:00
< div class = "d-flex align-items-center gap-2" >
< span class = "badge bg-success" > R$ {{ "%.2f"|format(pagamento.valor) }}< / span >
< div class = "dropdown" >
< button class = "btn btn-link text-secondary p-0" type = "button" data-bs-toggle = "dropdown" >
< i class = "fas fa-ellipsis-v" > < / i >
< / button >
< ul class = "dropdown-menu dropdown-menu-end" >
< li >
< a class = "dropdown-item" href = "#" onclick = "event.stopPropagation(); carregarDadosPagamento({{ pagamento.id }})" >
< i class = "fas fa-edit me-2" > < / i > Editar
< / a >
< / li >
< li >
< a class = "dropdown-item text-danger" href = "#" onclick = "event.stopPropagation(); confirmarExclusao({{ pagamento.id }}, 'pagamentos')" >
< i class = "fas fa-trash me-2" > < / i > Excluir
< / a >
< / li >
< / ul >
< / div >
< / div >
2025-04-03 10:30:48 -03:00
< / div >
2025-04-02 14:14:37 -03:00
{% endfor %}
2025-04-03 10:30:48 -03:00
< / div >
2025-04-02 14:14:37 -03:00
{% else %}
2025-04-03 13:48:09 -03:00
< p class = "text-muted m-3" > Nenhum pagamento registrado recentemente.< / p >
2025-04-02 14:14:37 -03:00
{% endif %}
2025-03-24 14:50:42 -03:00
< / div >
2025-02-19 14:27:14 -03:00
< / div >
< / div >
< / div >
2025-04-02 21:20:48 -03:00
2025-04-02 21:33:56 -03:00
<!-- Modal de Detalhes do Militante -->
2025-04-03 13:48:09 -03:00
< div class = "modal fade" id = "militanteModal" tabindex = "-1" >
2025-04-02 21:33:56 -03:00
< div class = "modal-dialog modal-dialog-centered" >
< div class = "modal-content" >
< div class = "modal-header" >
2025-04-03 13:48:09 -03:00
< h5 class = "modal-title" >
< i class = "fas fa-user me-2" > < / i > Detalhes do Militante
< / h5 >
2025-04-02 21:33:56 -03:00
< button type = "button" class = "btn-close" data-bs-dismiss = "modal" aria-label = "Fechar" > < / button >
< / div >
< div class = "modal-body" >
< div class = "mb-3" >
< label class = "fw-bold" > Nome:< / label >
< p id = "militanteNome" class = "mb-2" > < / p >
< / div >
< div class = "mb-3" >
< label class = "fw-bold" > CPF:< / label >
< p id = "militanteCPF" class = "mb-2" > < / p >
< / div >
< div class = "mb-3" >
< label class = "fw-bold" > Email:< / label >
< p id = "militanteEmail" class = "mb-2" > < / p >
< / div >
< div class = "mb-3" >
< label class = "fw-bold" > Telefone:< / label >
< p id = "militanteTelefone" class = "mb-2" > < / p >
< / div >
< div class = "mb-3" >
< label class = "fw-bold" > Endereço:< / label >
< p id = "militanteEndereco" class = "mb-2" > < / p >
< / div >
< div class = "mb-3" >
< label class = "fw-bold" > Status:< / label >
< p id = "militanteFiliado" class = "mb-2" > < / p >
< / div >
< / div >
< div class = "modal-footer" >
2025-04-03 13:48:09 -03:00
< button type = "button" class = "btn btn-primary" data-bs-toggle = "modal" data-bs-target = "#modalEditarMilitante" >
< i class = "fas fa-edit me-2" > < / i > Editar
< / button >
< button type = "button" class = "btn btn-danger" data-bs-toggle = "modal" data-bs-target = "#deleteModal" >
< i class = "fas fa-trash me-2" > < / i > Excluir
< / button >
< button type = "button" class = "btn btn-secondary" data-bs-dismiss = "modal" > Cancelar< / button >
< / div >
< / div >
< / div >
< / div >
<!-- Modal de Edição -->
< div class = "modal fade" id = "modalEditarMilitante" tabindex = "-1" >
< div class = "modal-dialog modal-lg modal-dialog-centered" >
< div class = "modal-content" >
< div class = "modal-header" >
< h5 class = "modal-title" >
< i class = "fas fa-user-edit me-2" > < / i > Editar Militante
< / h5 >
< button type = "button" class = "btn-close" data-bs-dismiss = "modal" > < / button >
< / div >
< div class = "modal-body" >
< form id = "formEditarMilitante" method = "post" >
< div class = "row" >
< div class = "col-md-6 mb-3" >
< label for = "editNome" class = "form-label" > Nome:< / label >
< input type = "text" class = "form-control" id = "editNome" name = "nome" required >
< / div >
< div class = "col-md-6 mb-3" >
< label for = "editCpf" class = "form-label" > CPF:< / label >
< input type = "text" class = "form-control" id = "editCpf" name = "cpf" required >
< / div >
< / div >
< div class = "row" >
< div class = "col-md-6 mb-3" >
< label for = "editEmail" class = "form-label" > Email:< / label >
< input type = "email" class = "form-control" id = "editEmail" name = "email" required >
< / div >
< div class = "col-md-6 mb-3" >
< label for = "editTelefone" class = "form-label" > Telefone:< / label >
< input type = "text" class = "form-control" id = "editTelefone" name = "telefone" >
< / div >
< / div >
< div class = "mb-3" >
< label for = "editEndereco" class = "form-label" > Endereço:< / label >
< input type = "text" class = "form-control" id = "editEndereco" name = "endereco" >
< / div >
< div class = "mb-3 form-check" >
< input type = "checkbox" class = "form-check-input" id = "editFiliado" name = "filiado" >
< label class = "form-check-label" for = "editFiliado" > Filiado< / label >
< / div >
< / form >
< / div >
< div class = "modal-footer" >
< button type = "button" class = "btn btn-secondary" data-bs-dismiss = "modal" > Cancelar< / button >
< button type = "submit" form = "formEditarMilitante" class = "btn btn-success" >
< i class = "fas fa-save me-2" > < / i > Salvar
2025-04-02 21:33:56 -03:00
< / button >
< / div >
< / div >
< / div >
< / div >
2025-04-03 13:55:31 -03:00
<!-- Modal de Edição de Pagamento -->
< div class = "modal fade" id = "modalEditarPagamento" tabindex = "-1" >
< div class = "modal-dialog modal-dialog-centered" >
< div class = "modal-content" >
< div class = "modal-header" >
< h5 class = "modal-title" >
< i class = "fas fa-money-bill-wave me-2" > < / i > Editar Pagamento
< / h5 >
< button type = "button" class = "btn-close" data-bs-dismiss = "modal" > < / button >
< / div >
< div class = "modal-body" >
< form id = "formEditarPagamento" method = "post" >
< input type = "hidden" id = "editPagamentoId" name = "id" >
< div class = "mb-3" >
< label for = "editValor" class = "form-label" > Valor< / label >
< div class = "input-group" >
< span class = "input-group-text" > R$< / span >
< input type = "number" step = "0.01" class = "form-control" id = "editValor" name = "valor" required >
< / div >
< / div >
< div class = "mb-3" >
< label for = "editDataPagamento" class = "form-label" > Data do Pagamento< / label >
< input type = "date" class = "form-control" id = "editDataPagamento" name = "data_pagamento" required >
< / div >
< div class = "mb-3" >
< label for = "editTipoPagamento" class = "form-label" > Tipo de Pagamento< / label >
< select class = "form-select" id = "editTipoPagamento" name = "tipo_pagamento" required >
{% for tipo in tipos_pagamento %}
< option value = "{{ tipo.id }}" > {{ tipo.nome }}< / option >
{% endfor %}
< / select >
< / div >
< div class = "mb-3" >
< label for = "editObservacao" class = "form-label" > Observação< / label >
< textarea class = "form-control" id = "editObservacao" name = "observacao" rows = "3" > < / textarea >
< / div >
< / form >
< / div >
< div class = "modal-footer" >
< button type = "button" class = "btn btn-secondary" data-bs-dismiss = "modal" >
< i class = "fas fa-times me-2" > < / i > Cancelar
< / button >
< button type = "submit" form = "formEditarPagamento" class = "btn btn-primary" >
< i class = "fas fa-save me-2" > < / i > Salvar Alterações
< / button >
< / div >
< / div >
< / div >
< / div >
<!-- Modal de Confirmação de Exclusão -->
2025-04-03 13:48:09 -03:00
< div class = "modal fade" id = "deleteModal" tabindex = "-1" >
2025-04-02 21:33:56 -03:00
< div class = "modal-dialog modal-dialog-centered" >
< div class = "modal-content" >
< div class = "modal-header" >
2025-04-03 13:55:31 -03:00
< h5 class = "modal-title" >
< i class = "fas fa-exclamation-triangle me-2" > < / i > Confirmar Exclusão
< / h5 >
2025-04-03 13:48:09 -03:00
< button type = "button" class = "btn-close" data-bs-dismiss = "modal" > < / button >
2025-04-02 21:33:56 -03:00
< / div >
< div class = "modal-body" >
2025-04-03 13:55:31 -03:00
< < < < < < < HEAD
2025-04-03 13:48:09 -03:00
< p > Tem certeza que deseja excluir este militante?< / p >
< p class = "text-danger" > Esta ação não pode ser desfeita.< / p >
2025-04-02 21:33:56 -03:00
< / div >
< div class = "modal-footer" >
2025-04-03 13:48:09 -03:00
< button type = "button" class = "btn btn-secondary" data-bs-dismiss = "modal" > Cancelar< / button >
< button type = "button" class = "btn btn-danger" id = "confirmDelete" >
2025-04-03 13:55:31 -03:00
=======
< p > Tem certeza que deseja excluir este item?< / p >
< p class = "text-danger" > < small > Esta ação não pode ser desfeita.< / small > < / p >
< / div >
< div class = "modal-footer" >
< button type = "button" class = "btn btn-secondary" data-bs-dismiss = "modal" >
< i class = "fas fa-times me-2" > < / i > Cancelar
< / button >
< button type = "button" class = "btn btn-danger" id = "btnConfirmarExclusao" >
>>>>>>> 324660d (refactor: melhorias na interface e funcionalidades - Atualização do layout do dashboard com Bootstrap 5 - Remoção do template editar_pagamento.html (integrado ao modal) - Melhorias no template home.html com cards estatísticos - Ajustes nos estilos e responsividade - Correções nas rotas e conexões do banco de dados - Implementação do modal de edição de pagamentos - Adição de efeitos hover e melhorias visuais)
2025-04-03 13:48:09 -03:00
< i class = "fas fa-trash me-2" > < / i > Excluir
< / button >
2025-04-02 21:33:56 -03:00
< / div >
< / div >
< / div >
< / div >
2025-04-03 13:48:09 -03:00
{% endblock %}
2025-04-02 21:33:56 -03:00
2025-04-03 13:48:09 -03:00
{% block scripts %}
< script >
// Função para formatar CPF
function formatCPF(cpf) {
return cpf.replace(/(\d{3})(\d{3})(\d{3})(\d{2})/, "$1.$2.$3-$4");
2025-04-02 21:33:56 -03:00
}
2025-04-03 13:48:09 -03:00
// Função para formatar telefone
function formatPhone(phone) {
return phone.replace(/(\d{2})(\d{5})(\d{4})/, "($1) $2-$3");
}
2025-04-02 21:33:56 -03:00
2025-04-03 13:48:09 -03:00
// Função para carregar detalhes do militante
function loadMilitanteDetails(id) {
fetch(`/api/militante/${id}`)
.then(response => response.json())
.then(data => {
document.getElementById('militanteNome').textContent = data.nome;
document.getElementById('militanteCPF').textContent = formatCPF(data.cpf);
document.getElementById('militanteEmail').textContent = data.email;
document.getElementById('militanteTelefone').textContent = formatPhone(data.telefone);
document.getElementById('militanteEndereco').textContent = data.endereco;
document.getElementById('militanteFiliado').textContent = data.filiado ? 'Filiado' : 'Não Filiado';
// Preencher formulário de edição
document.getElementById('editNome').value = data.nome;
document.getElementById('editCpf').value = data.cpf;
document.getElementById('editEmail').value = data.email;
document.getElementById('editTelefone').value = data.telefone;
document.getElementById('editEndereco').value = data.endereco;
document.getElementById('editFiliado').checked = data.filiado;
});
}
2025-04-02 21:33:56 -03:00
2025-04-03 13:48:09 -03:00
// Função para excluir militante
function deleteMilitante(id) {
fetch(`/api/militante/${id}`, {
method: 'DELETE',
headers: {
'Content-Type': 'application/json'
}
})
.then(response => response.json())
.then(data => {
if (data.success) {
window.location.reload();
} else {
alert('Erro ao excluir militante: ' + data.message);
}
});
}
2025-04-02 21:33:56 -03:00
2025-04-03 13:48:09 -03:00
// Event listeners
document.addEventListener('DOMContentLoaded', function() {
// Máscara para CPF
const cpfInput = document.getElementById('editCpf');
cpfInput.addEventListener('input', function(e) {
let value = e.target.value.replace(/\D/g, '');
if (value.length > 11) value = value.slice(0, 11);
e.target.value = formatCPF(value);
});
2025-04-02 21:33:56 -03:00
2025-04-03 13:48:09 -03:00
// Máscara para telefone
const phoneInput = document.getElementById('editTelefone');
phoneInput.addEventListener('input', function(e) {
let value = e.target.value.replace(/\D/g, '');
if (value.length > 11) value = value.slice(0, 11);
e.target.value = formatPhone(value);
});
2025-04-02 21:33:56 -03:00
2025-04-03 13:48:09 -03:00
// Submit do formulário de edição
const formEditar = document.getElementById('formEditarMilitante');
formEditar.addEventListener('submit', function(e) {
2025-04-02 21:33:56 -03:00
e.preventDefault();
2025-04-03 13:48:09 -03:00
const formData = new FormData(formEditar);
const data = Object.fromEntries(formData.entries());
fetch('/api/militante/' + data.id, {
method: 'PUT',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify(data)
})
.then(response => response.json())
.then(data => {
if (data.success) {
window.location.reload();
} else {
alert('Erro ao editar militante: ' + data.message);
}
});
});
// Confirmação de exclusão
const confirmDelete = document.getElementById('confirmDelete');
confirmDelete.addEventListener('click', function() {
const id = this.dataset.militanteId;
deleteMilitante(id);
2025-04-02 21:33:56 -03:00
});
});
2025-04-03 13:55:31 -03:00
< < < < < < < HEAD
=======
// Função para carregar dados do pagamento no modal
function carregarDadosPagamento(id) {
fetch(`/api/pagamentos/${id}`)
.then(response => response.json())
.then(data => {
document.getElementById('editPagamentoId').value = data.id;
document.getElementById('editValor').value = data.valor;
document.getElementById('editDataPagamento').value = data.data_pagamento;
document.getElementById('editTipoPagamento').value = data.tipo_pagamento_id;
document.getElementById('editObservacao').value = data.observacao || '';
// Abre o modal
new bootstrap.Modal(document.getElementById('modalEditarPagamento')).show();
})
.catch(error => {
console.error('Erro ao carregar dados:', error);
alert('Erro ao carregar dados do pagamento');
});
}
// Função para salvar alterações do pagamento
document.getElementById('formEditarPagamento').addEventListener('submit', function(e) {
e.preventDefault();
const id = document.getElementById('editPagamentoId').value;
const formData = new FormData(this);
fetch(`/api/pagamentos/${id}`, {
method: 'PUT',
body: formData
})
.then(response => response.json())
.then(data => {
if (data.success) {
// Fecha o modal
bootstrap.Modal.getInstance(document.getElementById('modalEditarPagamento')).hide();
// Recarrega a página
location.reload();
} else {
alert('Erro ao salvar alterações: ' + data.message);
}
})
.catch(error => {
console.error('Erro ao salvar:', error);
alert('Erro ao salvar alterações');
});
});
// Configuração do modal de exclusão
let itemParaExcluir = null;
let tipoItem = null;
function confirmarExclusao(id, tipo) {
itemParaExcluir = id;
tipoItem = tipo;
new bootstrap.Modal(document.getElementById('deleteModal')).show();
}
document.getElementById('btnConfirmarExclusao').addEventListener('click', function() {
if (!itemParaExcluir || !tipoItem) return;
fetch(`/api/${tipoItem}/${itemParaExcluir}`, {
method: 'DELETE'
})
.then(response => response.json())
.then(data => {
if (data.success) {
location.reload();
} else {
alert('Erro ao excluir: ' + data.message);
}
})
.catch(error => {
console.error('Erro ao excluir:', error);
alert('Erro ao excluir item');
});
});
});
>>>>>>> 324660d (refactor: melhorias na interface e funcionalidades - Atualização do layout do dashboard com Bootstrap 5 - Remoção do template editar_pagamento.html (integrado ao modal) - Melhorias no template home.html com cards estatísticos - Ajustes nos estilos e responsividade - Correções nas rotas e conexões do banco de dados - Implementação do modal de edição de pagamentos - Adição de efeitos hover e melhorias visuais)
2025-04-02 21:33:56 -03:00
< / script >
2025-02-19 14:27:14 -03:00
{% endblock %}