Ustawienia powiadomień faktur cyklicznych
This commit is contained in:
@@ -187,6 +187,18 @@ include '../../header-invoice.php';
|
||||
<label class="form-label small text-uppercase text-muted fw-bold">Email kontaktowy</label>
|
||||
<input type="email" class="form-control" value="ksiegowosc@abclogistics.pl">
|
||||
</div>
|
||||
<div class="mb-3">
|
||||
<label class="form-label small text-uppercase text-muted fw-bold">Wysyłka faktur e-mail</label>
|
||||
<div class="form-check form-switch mb-2">
|
||||
<input class="form-check-input" type="checkbox" id="autoEmail" checked>
|
||||
<label class="form-check-label" for="autoEmail">Automatyczna wysyłka wg profilu:</label>
|
||||
</div>
|
||||
<select class="form-select form-select-sm">
|
||||
<option value="1">Profil: Standardowy (Termin 30 dni)</option>
|
||||
<option value="2">Profil: Szybki (Termin 3 dni)</option>
|
||||
<option value="3">Profil: Tylko przypomnienia po terminie</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="mb-3">
|
||||
<label class="form-label small text-uppercase text-muted fw-bold">Numer SMS</label>
|
||||
<input type="text" class="form-control" placeholder="+48 ...">
|
||||
|
||||
@@ -0,0 +1,324 @@
|
||||
<?php
|
||||
$enablePrototypeComments = true;
|
||||
include '../../header-invoice.php';
|
||||
?>
|
||||
|
||||
<div class="container-fluid flex-grow-1 container-p-y">
|
||||
<h4 class="py-3 mb-4">
|
||||
<span class="text-muted fw-light">Sprzedaż / Ustawienia /</span> Powiadomienia e-mail (Faktury cykliczne)
|
||||
</h4>
|
||||
|
||||
<div class="row">
|
||||
<!-- Lewa Kolumna: Konfigurator -->
|
||||
<div class="col-lg-5 mb-4 mb-lg-0">
|
||||
|
||||
<!-- Wybór Profilu -->
|
||||
<div class="card mb-4">
|
||||
<div class="card-header border-bottom d-flex justify-content-between align-items-center">
|
||||
<h5 class="card-title mb-0">Wybierz Profil Powiadomień</h5>
|
||||
<div class="d-flex gap-2">
|
||||
<button class="btn btn-sm btn-label-danger"><i class="bx bx-trash me-1"></i> Usuń profil</button>
|
||||
<button class="btn btn-sm btn-primary"><i class="bx bx-plus me-1"></i> Nowy profil</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card-body pt-4">
|
||||
<div class="mb-3">
|
||||
<label class="form-label">Aktualny profil</label>
|
||||
<select class="form-select select2" id="profile-select">
|
||||
<option value="1">Standardowy (Termin 30 dni)</option>
|
||||
<option value="2">Szybki (Termin 3 dni)</option>
|
||||
<option value="3">Tylko przypomnienia po terminie</option>
|
||||
</select>
|
||||
<div class="form-text">Zmiany wprowadzane poniżej zapiszą się dla wybranego profilu.</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Harmonogram wysyłki -->
|
||||
<div class="card mb-4">
|
||||
<div class="card-header border-bottom d-flex justify-content-between align-items-center">
|
||||
<h5 class="card-title mb-0">Harmonogram wysyłki</h5>
|
||||
<button class="btn btn-sm btn-label-primary" data-bs-toggle="modal" data-bs-target="#modalRule"><i class="bx bx-plus me-1"></i> Dodaj regułę</button>
|
||||
</div>
|
||||
<div class="card-body pt-4">
|
||||
<ul class="list-group list-group-flush mb-0">
|
||||
<li class="list-group-item d-flex justify-content-between align-items-center px-0 pt-0 pb-3" style="cursor: pointer;">
|
||||
<div class="d-flex align-items-center gap-2">
|
||||
<span class="badge bg-label-success p-2"><i class="bx bx-check"></i></span>
|
||||
<div>
|
||||
<h6 class="mb-0">Wystawienie faktury</h6>
|
||||
<small class="text-muted">Natychmiast (W dniu dokumentu)</small>
|
||||
</div>
|
||||
</div>
|
||||
<button class="btn btn-icon btn-sm text-secondary" data-bs-toggle="modal" data-bs-target="#modalRule"><i class="bx bx-edit"></i></button>
|
||||
</li>
|
||||
<li class="list-group-item d-flex justify-content-between align-items-center px-3 py-3 rounded border border-primary bg-label-primary mb-2 mt-2" style="cursor: pointer;">
|
||||
<div class="d-flex align-items-center gap-2">
|
||||
<span class="badge bg-primary p-2 text-white"><i class="bx bx-time"></i></span>
|
||||
<div>
|
||||
<h6 class="mb-0 text-primary fw-bold">Przypomnienie przed terminem</h6>
|
||||
<small class="text-primary">14 dni przed upływem terminu</small>
|
||||
</div>
|
||||
</div>
|
||||
<button class="btn btn-icon btn-sm text-primary" data-bs-toggle="modal" data-bs-target="#modalRule"><i class="bx bx-edit"></i></button>
|
||||
</li>
|
||||
<li class="list-group-item d-flex justify-content-between align-items-center px-0 py-3" style="cursor: pointer;">
|
||||
<div class="d-flex align-items-center gap-2">
|
||||
<span class="badge bg-label-warning p-2"><i class="bx bx-error"></i></span>
|
||||
<div>
|
||||
<h6 class="mb-0">Przypomnienie przed terminem</h6>
|
||||
<small class="text-muted">3 dni przed upływem terminu</small>
|
||||
</div>
|
||||
</div>
|
||||
<button class="btn btn-icon btn-sm text-secondary" data-bs-toggle="modal" data-bs-target="#modalRule"><i class="bx bx-edit"></i></button>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Treść wiadomości -->
|
||||
<div class="card border border-primary">
|
||||
<div class="card-header border-bottom bg-label-primary">
|
||||
<h5 class="card-title mb-0 text-primary">Treść wiadomości <span class="fw-normal fs-6 d-block mt-1">Edytujesz: <strong>Przypomnienie przed terminem (14 dni)</strong></span></h5>
|
||||
</div>
|
||||
<div class="card-body pt-4">
|
||||
|
||||
<div class="mb-3">
|
||||
<label class="form-label">Temat e-maila</label>
|
||||
<input type="text" id="email-subject" class="form-control" value="Przypomnienie: Zbliża się termin płatności faktury {NUMER_FAKTURY}">
|
||||
<div class="form-text">Zmienne: {NUMER_FAKTURY}, {NAZWA_KLIENTA}</div>
|
||||
</div>
|
||||
|
||||
<div class="mb-3">
|
||||
<label class="form-label">Nagłówek powitania</label>
|
||||
<input type="text" id="email-heading" class="form-control" value="Cześć {IMIE_NABYWCY},">
|
||||
</div>
|
||||
|
||||
<div class="mb-3">
|
||||
<label class="form-label">Główna treść wiadomości</label>
|
||||
<textarea id="email-body" class="form-control" rows="4">Przypominamy, że za 14 dni upływa termin płatności za Twoją ostatnią fakturę. W załączniku przesyłamy plik PDF z dokumentem. Będziemy wdzięczni za terminową wpłatę.</textarea>
|
||||
</div>
|
||||
|
||||
<div class="mb-0">
|
||||
<label class="form-label">Podpis / Stopka</label>
|
||||
<input type="text" id="email-footer" class="form-control" value="Pozdrawiamy serdecznie,\nZespół TwojaFirma">
|
||||
</div>
|
||||
|
||||
<!-- Zmienne do kliknięcia -->
|
||||
<div class="mt-4 pt-3 border-top">
|
||||
<small class="text-muted text-uppercase fw-bold d-block mb-2">Dostępne zmienne (kliknij, aby wstawić)</small>
|
||||
<div class="d-flex flex-wrap gap-2" id="variable-badges">
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{NUMER_FAKTURY}">+ {NUMER_FAKTURY}</span>
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{NAZWA_KLIENTA}">+ {NAZWA_KLIENTA}</span>
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{IMIE_NABYWCY}">+ {IMIE_NABYWCY}</span>
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{KWOTA_BRUTTO}">+ {KWOTA_BRUTTO}</span>
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{TERMIN_PLATNOSCI}">+ {TERMIN_PLATNOSCI}</span>
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{POZOSTALO_DNI_DO_TERMINU}">+ {POZOSTALO_DNI_DO_TERMINU}</span>
|
||||
<span class="badge bg-label-primary" style="cursor: pointer;" data-var="{LINK_DO_OPLATY}">+ {LINK_DO_OPLATY}</span>
|
||||
</div>
|
||||
<div class="form-text mt-2">Tag zostanie wstawiony w polu, w którym ostatnio pisałeś.</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<!-- Prawa Kolumna: Podgląd Live -->
|
||||
<div class="col-lg-7">
|
||||
<div class="card h-100" style="background-color: #f8f9fa;">
|
||||
<div class="card-header border-bottom bg-white d-flex justify-content-between align-items-center">
|
||||
<div>
|
||||
<small class="text-muted d-block mb-1">Podgląd na żywo</small>
|
||||
<h6 class="mb-0">Temat: <span id="preview-subject" class="fw-normal">Przypomnienie: Zbliża się termin płatności faktury FV/2026/08/12</span></h6>
|
||||
</div>
|
||||
<span class="badge bg-label-secondary">Wersja Desktop</span>
|
||||
</div>
|
||||
|
||||
<!-- Email Canvas -->
|
||||
<div class="card-body d-flex justify-content-center align-items-start pt-5 pb-5 overflow-auto" style="min-height: 600px;">
|
||||
|
||||
<div class="email-container bg-white rounded shadow-sm" style="width: 100%; max-width: 600px; overflow: hidden; font-family: Arial, sans-serif;">
|
||||
|
||||
<!-- Email Header Logo -->
|
||||
<div class="bg-primary text-center py-4 text-white">
|
||||
<h3 class="mb-0 fw-bold text-white"><i class="bx bxl-sketch fs-2 align-middle mb-1 me-1"></i> TwojaFirma</h3>
|
||||
</div>
|
||||
|
||||
<!-- Email Content Container -->
|
||||
<div class="p-4 p-md-5">
|
||||
|
||||
<h4 id="preview-heading" class="fw-bold mb-3" style="color: #333;">Cześć Jan,</h4>
|
||||
|
||||
<p id="preview-body" style="color: #555; line-height: 1.6; margin-bottom: 30px;">
|
||||
Przypominamy, że za 14 dni upływa termin płatności za Twoją ostatnią fakturę. W załączniku przesyłamy plik PDF z dokumentem. Będziemy wdzięczni za terminową wpłatę.
|
||||
</p>
|
||||
|
||||
<!-- ZABLOKOWANY MODUŁ Z FAKTURĄ (LOCKED SUMMARY TABLE) -->
|
||||
<div class="invoice-summary border rounded bg-lighter p-4 mb-4 text-center">
|
||||
<small class="text-muted fw-bold d-block mb-2 text-uppercase">Szczegóły Faktury</small>
|
||||
<h3 class="mb-2 text-primary">1 845,00 PLN</h3>
|
||||
<p class="mb-0 text-muted">Termin: <strong>15.08.2026</strong></p>
|
||||
|
||||
<hr class="my-3">
|
||||
|
||||
<div class="d-flex justify-content-between align-items-center mb-2 text-start">
|
||||
<span class="text-muted">Numer:</span>
|
||||
<span class="fw-medium">FV/2026/08/12</span>
|
||||
</div>
|
||||
<div class="d-flex justify-content-between align-items-center mb-3 text-start">
|
||||
<span class="text-muted">Do zapłaty:</span>
|
||||
<span class="fw-medium text-danger">1 845,00 PLN</span>
|
||||
</div>
|
||||
|
||||
<a href="#" class="btn btn-primary w-100 mt-2" style="padding: 10px 20px; text-decoration: none; display: inline-block;">
|
||||
Zobacz dokument i opłać online
|
||||
</a>
|
||||
</div>
|
||||
<!-- END LOCKED MODULE -->
|
||||
|
||||
<p id="preview-footer" style="color: #777; margin-top: 30px; font-size: 0.95em;">
|
||||
Pozdrawiamy serdecznie,<br>Zespół TwojaFirma
|
||||
</p>
|
||||
|
||||
</div>
|
||||
|
||||
<!-- Email Footer App Info -->
|
||||
<div class="bg-lighter text-center py-3">
|
||||
<small class="text-muted">Wiadomość wygenerowana automatycznie przez system Magico ERP.</small>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<!-- Modal: Dodaj Regułę -->
|
||||
<div class="modal fade" id="modalRule" tabindex="-1" aria-hidden="true">
|
||||
<div class="modal-dialog modal-dialog-centered" role="document">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<h5 class="modal-title" id="modalRuleTitle">Konfiguracja reguły wysyłki</h5>
|
||||
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<div class="row">
|
||||
<div class="col mb-3">
|
||||
<label class="form-label">Wydarzenie początkowe (Wyzwalacz)</label>
|
||||
<select class="form-select">
|
||||
<option value="issue">Wystawienie nowej faktury</option>
|
||||
<option value="due">Termin płatności faktury</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row g-2">
|
||||
<div class="col mb-0">
|
||||
<label class="form-label">Kiedy wysłać e-mail?</label>
|
||||
<select class="form-select">
|
||||
<option value="0">Dokładnie w tym dniu</option>
|
||||
<option value="before">Przed wydarzeniem</option>
|
||||
<option value="after">Po wydarzeniu</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="col mb-0">
|
||||
<label class="form-label">Ile dni?</label>
|
||||
<input type="number" class="form-control" value="0">
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button type="button" class="btn btn-label-secondary" data-bs-dismiss="modal">Anuluj</button>
|
||||
<button type="button" class="btn btn-primary" data-bs-dismiss="modal">Zapisz regułę</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
|
||||
// Inputs
|
||||
const inputSubject = document.getElementById('email-subject');
|
||||
const inputHeading = document.getElementById('email-heading');
|
||||
const inputBody = document.getElementById('email-body');
|
||||
const inputFooter = document.getElementById('email-footer');
|
||||
|
||||
// Previews
|
||||
const previewSubject = document.getElementById('preview-subject');
|
||||
const previewHeading = document.getElementById('preview-heading');
|
||||
const previewBody = document.getElementById('preview-body');
|
||||
const previewFooter = document.getElementById('preview-footer');
|
||||
|
||||
// Mocks for variables
|
||||
const mockVars = {
|
||||
'{NUMER_FAKTURY}': 'FV/2026/08/12',
|
||||
'{NAZWA_KLIENTA}': 'ABC Logistics',
|
||||
'{IMIE_NABYWCY}': 'Jan',
|
||||
'{KWOTA_BRUTTO}': '1 845,00 PLN',
|
||||
'{TERMIN_PLATNOSCI}': '15.08.2026',
|
||||
'{POZOSTALO_DNI_DO_TERMINU}': '14',
|
||||
'{LINK_DO_OPLATY}': 'https://magico.pl/pay/123'
|
||||
};
|
||||
|
||||
function replaceVariables(text) {
|
||||
let result = text;
|
||||
for (const [key, value] of Object.entries(mockVars)) {
|
||||
result = result.replace(new RegExp(key, 'g'), value);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
function updatePreview() {
|
||||
previewSubject.innerText = replaceVariables(inputSubject.value);
|
||||
previewHeading.innerText = replaceVariables(inputHeading.value);
|
||||
|
||||
// Preserve line breaks in body
|
||||
const bodyText = replaceVariables(inputBody.value);
|
||||
previewBody.innerHTML = bodyText.replace(/\n/g, '<br>');
|
||||
|
||||
// Preserve line breaks in footer
|
||||
const footerText = replaceVariables(inputFooter.value);
|
||||
previewFooter.innerHTML = footerText.replace(/\n/g, '<br>');
|
||||
}
|
||||
|
||||
// Event Listeners
|
||||
inputSubject.addEventListener('input', updatePreview);
|
||||
inputHeading.addEventListener('input', updatePreview);
|
||||
inputBody.addEventListener('input', updatePreview);
|
||||
inputFooter.addEventListener('input', updatePreview);
|
||||
|
||||
// Initial render
|
||||
updatePreview();
|
||||
|
||||
// Variable insertion logic
|
||||
let lastFocusedInput = inputBody; // default
|
||||
const allInputs = [inputSubject, inputHeading, inputBody, inputFooter];
|
||||
|
||||
allInputs.forEach(input => {
|
||||
input.addEventListener('focus', function() {
|
||||
lastFocusedInput = this;
|
||||
});
|
||||
});
|
||||
|
||||
document.querySelectorAll('#variable-badges .badge').forEach(badge => {
|
||||
badge.addEventListener('click', function() {
|
||||
const varText = this.getAttribute('data-var');
|
||||
if (lastFocusedInput) {
|
||||
const start = lastFocusedInput.selectionStart;
|
||||
const end = lastFocusedInput.selectionEnd;
|
||||
const text = lastFocusedInput.value;
|
||||
lastFocusedInput.value = text.substring(0, start) + varText + text.substring(end);
|
||||
lastFocusedInput.selectionStart = lastFocusedInput.selectionEnd = start + varText.length;
|
||||
lastFocusedInput.focus();
|
||||
updatePreview();
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
</script>
|
||||
|
||||
<?php include '../../footer.php'; ?>
|
||||
@@ -156,7 +156,7 @@ $currentPage = basename($_SERVER['PHP_SELF']);
|
||||
</li>
|
||||
|
||||
<li
|
||||
class="menu-item <?php echo ($currentPage == 'sys-export.php' || $currentPage == 'sys-dictionaries.php' || $currentPage == 'sys-settings.php' || $currentPage == 'sys-logs.php') ? 'active open' : ''; ?>">
|
||||
class="menu-item <?php echo ($currentPage == 'sys-export.php' || $currentPage == 'sys-dictionaries.php' || $currentPage == 'sys-settings.php' || $currentPage == 'app-settings-notifications.php' || $currentPage == 'sys-logs.php') ? 'active open' : ''; ?>">
|
||||
<a href="javascript:void(0);" class="menu-link menu-toggle">
|
||||
<i class="menu-icon tf-icons bx bx-cog"></i>
|
||||
<div class="text-truncate" data-i18n="System">System</div>
|
||||
@@ -177,6 +177,11 @@ $currentPage = basename($_SERVER['PHP_SELF']);
|
||||
<div class="text-truncate" data-i18n="Ustawienia">Ustawienia</div>
|
||||
</a>
|
||||
</li>
|
||||
<li class="menu-item <?php echo ($currentPage == 'app-settings-notifications.php') ? 'active' : ''; ?>">
|
||||
<a href="app-settings-notifications.php" class="menu-link">
|
||||
<div class="text-truncate" data-i18n="Powiadomienia (Cykliczne)">Powiadomienia (Cykliczne)</div>
|
||||
</a>
|
||||
</li>
|
||||
<li class="menu-item <?php echo ($currentPage == 'sys-logs.php') ? 'active' : ''; ?>">
|
||||
<a href="sys-logs.php" class="menu-link">
|
||||
<div class="text-truncate" data-i18n="Logi zdarzeń">Logi zdarzeń</div>
|
||||
|
||||
Reference in New Issue
Block a user