V4 quotation print
This commit is contained in:
parent
f4f4d49502
commit
4ce50d5774
115
index.php
115
index.php
@ -3751,6 +3751,7 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
});
|
||||
}
|
||||
|
||||
const companySettings = <?= json_encode($data['settings']) ?>;
|
||||
const invoiceType = '<?= in_array($page, ["sales", "quotations"]) ? "sale" : ($page === "purchases" ? "purchase" : "") ?>';
|
||||
initInvoiceForm('productSearchInput', 'searchSuggestions', 'invoiceItemsTableBody', 'grandTotal', 'subtotal', 'totalVat');
|
||||
initInvoiceForm('editProductSearchInput', 'editSearchSuggestions', 'editInvoiceItemsTableBody', 'edit_grandTotal', 'edit_subtotal', 'edit_totalVat');
|
||||
@ -3818,21 +3819,54 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
`;
|
||||
});
|
||||
|
||||
// Company Logo and Header Construction
|
||||
const logoUrl = companySettings.company_logo || '';
|
||||
const logoImg = logoUrl ? `<img src="${logoUrl}" alt="Logo" class="invoice-logo mb-3">` : '';
|
||||
const companyName = companySettings.company_name || 'Accounting System';
|
||||
const companyAddress = (companySettings.company_address || '').replace(/\n/g, '<br>');
|
||||
const companyVat = companySettings.vat_number ? `<p class="text-muted small mb-0">VAT: ${companySettings.vat_number}</p>` : '';
|
||||
const companyPhone = companySettings.company_phone ? `<p class="text-muted small mb-0">Tel: ${companySettings.company_phone}</p>` : '';
|
||||
|
||||
// Quotation Header Construction
|
||||
const quotDate = data.quotation_date;
|
||||
const quotValid = data.valid_until || 'N/A';
|
||||
const quotNo = 'QUO-' + data.id.toString().padStart(5, '0');
|
||||
const customerName = data.customer_name || 'Walk-in Customer';
|
||||
const statusBadge = `<span class="badge ${data.status === 'converted' ? 'bg-success' : 'bg-secondary'}">${data.status.toUpperCase()}</span>`;
|
||||
|
||||
content.innerHTML = `
|
||||
<div class="p-5">
|
||||
<div class="d-flex justify-content-between mb-4 border-bottom pb-3">
|
||||
<div>
|
||||
<h3 class="text-primary fw-bold">QUOTATION</h3>
|
||||
<p class="mb-0"><strong>No:</strong> QUO-${data.id.toString().padStart(5, '0')}</p>
|
||||
<p class="mb-0"><strong>Date:</strong> ${data.quotation_date}</p>
|
||||
<p class="mb-0"><strong>Valid Until:</strong> ${data.valid_until || 'N/A'}</p>
|
||||
</div>
|
||||
<div class="text-end">
|
||||
<h4 class="fw-bold">${data.customer_name || 'Walk-in Customer'}</h4>
|
||||
<p class="mb-0">Status: <span class="badge ${data.status === 'converted' ? 'bg-success' : 'bg-secondary'}">${data.status.toUpperCase()}</span></p>
|
||||
<div class="invoice-header mb-4">
|
||||
<div class="row align-items-center">
|
||||
<div class="col-6">
|
||||
${logoImg}
|
||||
<h3 class="mb-1 fw-bold">${companyName}</h3>
|
||||
<p class="text-muted small mb-0">${companyAddress}</p>
|
||||
${companyVat}
|
||||
${companyPhone}
|
||||
</div>
|
||||
<div class="col-6 text-end">
|
||||
<h1 class="invoice-title fw-bold mb-0 text-uppercase">Quotation</h1>
|
||||
<div class="mt-2">${statusBadge}</div>
|
||||
<div class="mt-3">
|
||||
<p class="mb-0 fs-5">No: <strong class="text-primary">${quotNo}</strong></p>
|
||||
<p class="mb-0">Date: <span class="fw-bold">${quotDate}</span></p>
|
||||
<p class="mb-0">Valid Until: <span class="fw-bold">${quotValid}</span></p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<table class="table table-bordered table-striped">
|
||||
|
||||
<div class="row mb-4 g-3">
|
||||
<div class="col-6">
|
||||
<div class="invoice-info-card">
|
||||
<p class="text-muted small text-uppercase fw-bold mb-2 border-bottom pb-1">To</p>
|
||||
<h5 class="mb-1 fw-bold">${customerName}</h5>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<table class="table table-bordered table-formal">
|
||||
<thead class="bg-dark text-white">
|
||||
<tr>
|
||||
<th>#</th>
|
||||
@ -3859,10 +3893,11 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
</tr>
|
||||
</tfoot>
|
||||
</table>
|
||||
|
||||
<div class="mt-5 pt-3 border-top">
|
||||
<div class="row">
|
||||
<div class="col-6">
|
||||
<p class="small text-muted">Terms & Conditions:</p>
|
||||
<p class="small text-muted text-uppercase fw-bold">Terms & Conditions:</p>
|
||||
<ul class="small text-muted">
|
||||
<li>Quotation is valid until the date mentioned above.</li>
|
||||
<li>Prices are inclusive of VAT where applicable.</li>
|
||||
@ -3873,6 +3908,9 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="mt-4 text-center">
|
||||
<p class="text-muted x-small mb-0">Generated by ${companyName}</p>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
||||
@ -3899,7 +3937,6 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
editBtn.onclick = function() {
|
||||
const editModal = new bootstrap.Modal(document.getElementById('editQuotationModal'));
|
||||
modal.hide();
|
||||
// Trigger the existing edit button click logic or manually populate
|
||||
const originalEditBtn = document.querySelector(`.edit-quotation-btn[data-json*='"id":${data.id},']`) ||
|
||||
document.querySelector(`.edit-quotation-btn[data-json*='"id":${data.id}']`);
|
||||
if (originalEditBtn) originalEditBtn.click();
|
||||
@ -4387,11 +4424,29 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
table:not(.table-formal), .bg-light:not(.invoice-info-card):not(.p-3), .modal-backdrop { display: none !important; }
|
||||
body { background: white !important; margin: 0 !important; padding: 0 !important; }
|
||||
.main-content { margin: 0 !important; padding: 0 !important; background: white !important; }
|
||||
.modal { position: absolute !important; left: 0 !important; top: 0 !important; margin: 0 !important; padding: 0 !important; overflow: visible !important; display: block !important; visibility: visible !important; background: white !important; }
|
||||
#viewInvoiceModal { display: block !important; background: white !important; }
|
||||
#viewInvoiceModal .modal-dialog { max-width: 100% !important; width: 100% !important; margin: 0 !important; padding: 0 !important; }
|
||||
#viewInvoiceModal .modal-content { border: none !important; box-shadow: none !important; background: white !important; }
|
||||
#viewInvoiceModal .modal-body { padding: 0 !important; margin: 0 !important; background: white !important; }
|
||||
|
||||
/* Hide all modals by default */
|
||||
.modal { display: none !important; }
|
||||
|
||||
/* Show ONLY the active modal */
|
||||
.modal.show {
|
||||
position: absolute !important;
|
||||
left: 0 !important;
|
||||
top: 0 !important;
|
||||
margin: 0 !important;
|
||||
padding: 0 !important;
|
||||
overflow: visible !important;
|
||||
display: block !important;
|
||||
visibility: visible !important;
|
||||
background: white !important;
|
||||
width: 100% !important;
|
||||
height: 100% !important;
|
||||
}
|
||||
|
||||
.modal.show .modal-dialog { max-width: 100% !important; width: 100% !important; margin: 0 !important; padding: 0 !important; }
|
||||
.modal.show .modal-content { border: none !important; box-shadow: none !important; background: white !important; }
|
||||
.modal.show .modal-body { padding: 0 !important; margin: 0 !important; background: white !important; }
|
||||
|
||||
.table-bordered th, .table-bordered td { border: 1px solid #dee2e6 !important; }
|
||||
.bg-light { background-color: #f8f9fa !important; -webkit-print-color-adjust: exact; }
|
||||
.text-primary { color: #0d6efd !important; -webkit-print-color-adjust: exact; }
|
||||
@ -4399,7 +4454,7 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
|
||||
/* Ensure the modal is the only thing visible */
|
||||
body > *:not(.main-content):not(.modal) { display: none !important; }
|
||||
.main-content > *:not(#viewInvoiceModal):not(.modal) { display: none !important; }
|
||||
.main-content > *:not(.modal) { display: none !important; }
|
||||
}
|
||||
.invoice-logo { max-height: 80px; width: auto; }
|
||||
.invoice-header { border-bottom: 2px solid #333; padding-bottom: 20px; }
|
||||
@ -5099,27 +5154,7 @@ document.addEventListener('DOMContentLoaded', function() {
|
||||
});
|
||||
</script>
|
||||
|
||||
<style>
|
||||
@media print {
|
||||
.no-print, .sidebar, .topbar, .card, .btn, .modal-header, .modal-footer, .d-print-none, .table-responsive,
|
||||
table:not(.table-formal), .bg-light:not(.invoice-info-card):not(.p-3), .modal-backdrop { display: none !important; }
|
||||
body { background: white !important; margin: 0 !important; padding: 0 !important; }
|
||||
.main-content { margin: 0 !important; padding: 0 !important; background: white !important; }
|
||||
.modal { position: absolute !important; left: 0 !important; top: 0 !important; margin: 0 !important; padding: 0 !important; overflow: visible !important; display: block !important; visibility: visible !important; background: white !important; }
|
||||
#viewInvoiceModal { display: block !important; background: white !important; }
|
||||
#viewInvoiceModal .modal-dialog { max-width: 100% !important; width: 100% !important; margin: 0 !important; padding: 0 !important; }
|
||||
#viewInvoiceModal .modal-content { border: none !important; box-shadow: none !important; background: white !important; }
|
||||
#viewInvoiceModal .modal-body { padding: 0 !important; margin: 0 !important; background: white !important; }
|
||||
.table-bordered th, .table-bordered td { border: 1px solid #dee2e6 !important; }
|
||||
.bg-light { background-color: #f8f9fa !important; -webkit-print-color-adjust: exact; }
|
||||
.text-primary { color: #0d6efd !important; -webkit-print-color-adjust: exact; }
|
||||
.badge { border: 1px solid #000; color: #000 !important; }
|
||||
|
||||
/* Ensure the modal is the only thing visible */
|
||||
body > *:not(.main-content):not(.modal) { display: none !important; }
|
||||
.main-content > *:not(#viewInvoiceModal):not(.modal) { display: none !important; }
|
||||
}
|
||||
</style>
|
||||
|
||||
|
||||
<script>
|
||||
window.printItemBarcode = function(sku, name, price) {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user