Actualizar contabilidad.html

This commit is contained in:
2026-08-02 13:30:50 +00:00
parent 43b2d13b37
commit 4a6c2bebe8

View File

@@ -145,7 +145,8 @@
<div id="budgetModal" class="fixed inset-0 bg-slate-900/75 hidden z-[100] flex items-center justify-center backdrop-blur-sm p-4"> <div id="budgetModal" class="fixed inset-0 bg-slate-900/75 hidden z-[100] flex items-center justify-center backdrop-blur-sm p-4">
<div class="bg-white rounded-[2rem] w-full max-w-3xl flex flex-col max-h-[90vh] shadow-2xl"> <div class="bg-white rounded-[2rem] w-full max-w-3xl flex flex-col max-h-[90vh] shadow-2xl">
<div class="p-6 border-b border-slate-100 flex justify-between items-center"> <div class="p-6 border-b border-slate-100 flex justify-between items-center">
<h3 class="font-black text-xl text-slate-800">Nuevo Presupuesto</h3> <h3 id="budgetModalTitle" class="font-black text-xl text-slate-800">Nuevo Presupuesto</h3>
<input type="hidden" id="editBudgetId" value="">
<button onclick="document.getElementById('budgetModal').classList.add('hidden')" class="p-2 bg-slate-100 rounded-full text-slate-500 hover:text-red-500"><i data-lucide="x" class="w-5 h-5"></i></button> <button onclick="document.getElementById('budgetModal').classList.add('hidden')" class="p-2 bg-slate-100 rounded-full text-slate-500 hover:text-red-500"><i data-lucide="x" class="w-5 h-5"></i></button>
</div> </div>
<div class="p-6 overflow-y-auto no-scrollbar flex-1 space-y-4"> <div class="p-6 overflow-y-auto no-scrollbar flex-1 space-y-4">
@@ -596,8 +597,9 @@
actions = `<button onclick="openConvertModal(${b.id})" class="bg-emerald-500 text-white px-4 py-2 rounded-xl font-black text-[10px] uppercase tracking-widest shadow-md hover:bg-emerald-600 transition-all active:scale-95">Crear Servicio</button>`; actions = `<button onclick="openConvertModal(${b.id})" class="bg-emerald-500 text-white px-4 py-2 rounded-xl font-black text-[10px] uppercase tracking-widest shadow-md hover:bg-emerald-600 transition-all active:scale-95">Crear Servicio</button>`;
} }
// Botones fijos (PDF y Borrar) // Botones fijos (Editar, PDF y Borrar)
let utilityButtons = ` let utilityButtons = `
<button onclick="editBudget(${b.id})" class="text-slate-400 hover:text-emerald-500 p-2 transition-colors" title="Editar Presupuesto"><i data-lucide="edit" class="w-5 h-5"></i></button>
<button onclick="generatePDF(${b.id})" class="text-slate-400 hover:text-blue-600 p-2 transition-colors" title="Descargar PDF"><i data-lucide="file-text" class="w-5 h-5"></i></button> <button onclick="generatePDF(${b.id})" class="text-slate-400 hover:text-blue-600 p-2 transition-colors" title="Descargar PDF"><i data-lucide="file-text" class="w-5 h-5"></i></button>
<button onclick="deleteBudget(${b.id}, '${b.status}', ${isAnulado})" class="text-slate-300 hover:text-red-500 p-2 transition-colors" title="Borrar"><i data-lucide="trash-2" class="w-5 h-5"></i></button> <button onclick="deleteBudget(${b.id}, '${b.status}', ${isAnulado})" class="text-slate-300 hover:text-red-500 p-2 transition-colors" title="Borrar"><i data-lucide="trash-2" class="w-5 h-5"></i></button>
`; `;
@@ -727,6 +729,8 @@
} }
function openBudgetModal() { function openBudgetModal() {
document.getElementById('editBudgetId').value = "";
document.getElementById('budgetModalTitle').innerText = "Nuevo Presupuesto";
document.getElementById('bPhone').value = ""; document.getElementById('bName').value = ""; document.getElementById('bAddress').value = ""; document.getElementById('bPhone').value = ""; document.getElementById('bName').value = ""; document.getElementById('bAddress').value = "";
document.getElementById('budgetLines').innerHTML = ""; document.getElementById('budgetLines').innerHTML = "";
addBudgetLine(); addBudgetLine();
@@ -734,6 +738,51 @@
document.getElementById('budgetModal').classList.remove('hidden'); document.getElementById('budgetModal').classList.remove('hidden');
} }
function editBudget(id) {
const budget = myBudgets.find(b => b.id === id);
if (!budget) return;
document.getElementById('editBudgetId').value = id;
document.getElementById('budgetModalTitle').innerText = "Editar Presupuesto #" + id;
document.getElementById('bPhone').value = budget.client_phone || "";
document.getElementById('bName').value = budget.client_name || "";
document.getElementById('bAddress').value = budget.client_address || "";
document.getElementById('budgetLines').innerHTML = "";
if (budget.items && budget.items.length > 0) {
budget.items.forEach((item, index) => {
const lineId = Date.now() + index; // ID único para la línea
const artOptions = myArticles.map(a => `<option value="${a.name}|${a.price}">${a.name} (${a.price}€)</option>`).join("");
const html = `
<div class="flex flex-col md:flex-row gap-2 items-center bg-white p-2 rounded-xl border border-slate-100 shadow-sm" id="bl-${lineId}">
<select onchange="applyArticleToLine(${lineId}, this.value)" class="w-full md:w-1/3 border border-slate-200 rounded px-2 py-1.5 text-xs outline-none">
<option value="">Elegir catálogo...</option>${artOptions}
</select>
<input type="text" class="b-concept w-full border border-slate-200 rounded px-2 py-1.5 text-xs font-bold outline-none" placeholder="Concepto manual..." value="${item.concept}">
<div class="flex items-center gap-2 w-full md:w-auto">
<input type="number" class="b-qty w-16 border border-slate-200 rounded px-2 py-1.5 text-xs text-center outline-none" value="${item.qty}" oninput="calcBudget()">
<div class="relative w-24">
<input type="number" class="b-price w-full border border-slate-200 rounded pl-2 pr-6 py-1.5 text-xs text-right outline-none" value="${item.price}" oninput="calcBudget()">
<span class="absolute right-2 top-1.5 text-xs text-slate-400">€</span>
</div>
<button onclick="document.getElementById('bl-${lineId}').remove(); calcBudget();" class="text-red-400 hover:text-red-600 p-1"><i data-lucide="trash" class="w-4 h-4"></i></button>
</div>
</div>
`;
document.getElementById('budgetLines').insertAdjacentHTML('beforeend', html);
});
} else {
addBudgetLine();
}
calcBudget();
document.getElementById('budgetModal').classList.remove('hidden');
lucide.createIcons();
}
async function searchClientByPhone() { async function searchClientByPhone() {
const phone = document.getElementById('bPhone').value; const phone = document.getElementById('bPhone').value;
if(!phone || phone.length < 9) return; if(!phone || phone.length < 9) return;
@@ -815,10 +864,17 @@
const payload = { client_phone: phone, client_name: name, client_address: document.getElementById('bAddress').value, items, subtotal: sub, tax, total: tot }; const payload = { client_phone: phone, client_name: name, client_address: document.getElementById('bAddress').value, items, subtotal: sub, tax, total: tot };
const editId = document.getElementById('editBudgetId').value;
if (editId) {
await fetch(`${API_URL}/budgets/${editId}`, { method: 'PUT', headers: { "Content-Type": "application/json", "Authorization": `Bearer ${localStorage.getItem("token")}` }, body: JSON.stringify(payload) });
showToast("Presupuesto actualizado");
} else {
await fetch(`${API_URL}/budgets`, { method: 'POST', headers: { "Content-Type": "application/json", "Authorization": `Bearer ${localStorage.getItem("token")}` }, body: JSON.stringify(payload) }); await fetch(`${API_URL}/budgets`, { method: 'POST', headers: { "Content-Type": "application/json", "Authorization": `Bearer ${localStorage.getItem("token")}` }, body: JSON.stringify(payload) });
showToast("Presupuesto guardado");
}
document.getElementById('budgetModal').classList.add('hidden'); document.getElementById('budgetModal').classList.add('hidden');
showToast("Presupuesto guardado");
loadBudgets(); loadBudgets();
} }