diff --git a/app/Views/administrator/events/event_charges.php b/app/Views/administrator/events/event_charges.php
index 8b659b9..fcf2652 100644
--- a/app/Views/administrator/events/event_charges.php
+++ b/app/Views/administrator/events/event_charges.php
@@ -181,8 +181,7 @@
Add non-school participant
-
After adding participants, click Submit to save them to the database.
- Enrolled students are saved when you click Submit. Non-school participants are saved immediately and will then appear in all browsers.
@@ -290,8 +289,14 @@
($charge['external_parent_lastname'] ?? '')
);
$externalParentPhone = $charge['external_parent_phone'] ?? '';
+ $externalParentEmail = $charge['external_parent_email'] ?? '';
$standardParentName = trim($charge['parent_firstname'] . ' ' . $charge['parent_lastname']);
$parentColumnName = $externalParentLabel ?: ($standardParentName ?: '—');
+ $externalInfoValue = trim(implode(' ', array_filter([
+ $externalParentPhone,
+ $externalParentEmail,
+ $externalNote,
+ ])));
?>
= esc($parentColumnName) ?> |
@@ -300,10 +305,14 @@
= esc($externalNote) ?>
|
-
+ |
= esc($externalParentPhone) ?>
-
+
+
+ = esc($externalParentEmail) ?>
+
+
—
|
@@ -524,186 +533,11 @@ function loadStudentsWithCharges() {
loadStudentsWithCharges();
}
- const $externalHidden = $('#externalParticipantsHidden');
const $externalSaveButton = $('#externalParticipantSave');
- const storageKey = 'eventChargesExternalParticipants';
- let externalDrafts = [];
- let editingKey = null;
-
- const escapeHtml = (value) => {
- const s = String(value ?? '');
- return s.replace(/&/g, '&')
- .replace(//g, '>')
- .replace(/"/g, '"')
- .replace(/'/g, ''');
- };
-
- function buildExternalRow(entry) {
- const key = entry.key;
- const isPaid = !!entry.paid;
- const waiverSigned = !!entry.waiverSigned;
- const firstEsc = escapeHtml(entry.firstname);
- const lastEsc = escapeHtml(entry.lastname);
- const noteEsc = escapeHtml(entry.note);
- const parentFirstEsc = escapeHtml(entry.parentFirstname);
- const parentLastEsc = escapeHtml(entry.parentLastname);
- const parentPhoneEsc = escapeHtml(entry.parentPhone);
- const parentEmailEsc = escapeHtml(entry.parentEmail);
- const label = (firstEsc || lastEsc)
- ? `${firstEsc || ''} ${lastEsc || ''}`.trim()
- : 'Unnamed participant';
- const parentLabel = (parentFirstEsc || parentLastEsc)
- ? `
Parent: ${parentFirstEsc} ${parentLastEsc}
`
- : '';
- const phoneLabel = parentPhoneEsc
- ? `
${parentPhoneEsc}
`
- : '';
- const parentNameForRow = entry.parentDisplayName || '—';
- const amountDisplay = ((entry.eventAmount ?? 0) || 0.0).toFixed(2);
-
- const $wrapper = $(`
-
-
-
-
-
-
-
-
-
-
-
- `);
- $externalHidden.append($wrapper);
-
- const $tableBody = $(`#eventTable_${entry.eventId} tbody`);
- if (!$tableBody.length) {
- return;
- }
- const createdDisplay = new Date().toLocaleString();
- const $previewRow = $(`
-
- | — |
- ${escapeHtml(parentNameForRow)} |
-
- ${label}
- ${noteEsc ? ` ${noteEsc} ` : ''}
- |
-
- ${phoneLabel}
- ${phoneLabel ? '' : '—'}
- |
- External |
- $${amountDisplay} |
- ${createdDisplay} |
-
-
-
- ${waiverSigned ? 'Signed' : 'Unsigned'}
-
- |
-
- ${isPaid ? 'Paid' : 'Unpaid'}
- |
-
-
-
- Paid
-
- |
-
-
-
- |
-
- `);
- $tableBody.append($previewRow);
- applyActiveSort($tableBody.closest('table').get(0));
- }
-
- function persistDrafts() {
- localStorage.setItem(storageKey, JSON.stringify(externalDrafts));
- }
-
- function saveExternalDraft(entry) {
- entry.key = entry.key ?? `${Date.now()}_${Math.random().toString(36).slice(2)}`;
- entry.paid = !!entry.paid;
- entry.waiverSigned = !!entry.waiverSigned;
- removeExternalEntryFromDom(entry.key);
- externalDrafts = externalDrafts.filter((existing) => existing.key !== entry.key);
- externalDrafts.push(entry);
- persistDrafts();
- buildExternalRow(entry);
- }
-
- function removeExternalEntryFromDom(key) {
- $(`tr.external-preview[data-key="${key}"]`).remove();
- $externalHidden.find(`div[data-key="${key}"]`).remove();
- }
-
- function removeDraft(key) {
- externalDrafts = externalDrafts.filter((entry) => entry.key !== key);
- persistDrafts();
- }
-
- function loadDrafts() {
- const raw = localStorage.getItem(storageKey);
- if (!raw) {
- return;
- }
- try {
- const saved = JSON.parse(raw);
- if (!Array.isArray(saved)) {
- return;
- }
- externalDrafts = saved;
- const currentEvent = $('#event_id').val();
- externalDrafts.forEach((entry) => {
- if (String(entry.eventId) === String(currentEvent)) {
- buildExternalRow(entry);
- }
- });
- } catch (e) {
- console.error('Failed to load external drafts', e);
- }
- }
-
- function getDraftByKey(key) {
- return externalDrafts.find((entry) => entry.key === key);
- }
-
- function openExternalModalForEntry(key) {
- const entry = getDraftByKey(key);
- if (!entry) {
- return;
- }
- editingKey = key;
- $externalSaveButton.text('Save');
- $('#modalExternalFirstName').val(entry.firstname);
- $('#modalExternalLastName').val(entry.lastname);
- $('#modalExternalNote').val(entry.note);
- $('#modalParentFirstName').val(entry.parentFirstname);
- $('#modalParentLastName').val(entry.parentLastname);
- $('#modalParentPhone').val(entry.parentPhone);
- $('#modalParentEmail').val(entry.parentEmail);
- if (modalInstance) {
- modalInstance.show();
- }
- }
const modalElement = document.getElementById('externalParticipantModal');
const modalInstance = modalElement ? new bootstrap.Modal(modalElement) : null;
- if (modalElement) {
- modalElement.addEventListener('hidden.bs.modal', () => {
- editingKey = null;
- $externalSaveButton.text('Add to list');
- });
- }
+
function clearModalInputs() {
$('#modalExternalFirstName').val('');
$('#modalExternalLastName').val('');
@@ -714,6 +548,46 @@ function loadStudentsWithCharges() {
$('#modalParentEmail').val('');
}
+ function appendHiddenField(form, name, value) {
+ const input = document.createElement('input');
+ input.type = 'hidden';
+ input.name = name;
+ input.value = value;
+ form.appendChild(input);
+ }
+
+ function escapeHtml(value) {
+ const s = String(value ?? '');
+ return s.replace(/&/g, '&')
+ .replace(//g, '>')
+ .replace(/"/g, '"')
+ .replace(/'/g, ''');
+ }
+
+ function submitExternalParticipant(payload) {
+ const form = document.createElement('form');
+ form.method = 'post';
+ form.action = '= site_url('payment/event_charges') ?>';
+
+ appendHiddenField(form, '= csrf_token() ?>', '= csrf_hash() ?>');
+ appendHiddenField(form, 'school_year', '= esc($school_year) ?>');
+ appendHiddenField(form, 'semester', '= esc($semester) ?>');
+ appendHiddenField(form, 'event_id', payload.eventId);
+ appendHiddenField(form, 'external_participants[new][firstname]', payload.firstname);
+ appendHiddenField(form, 'external_participants[new][lastname]', payload.lastname);
+ appendHiddenField(form, 'external_participants[new][note]', payload.note);
+ appendHiddenField(form, 'external_participants[new][parent_firstname]', payload.parentFirstname);
+ appendHiddenField(form, 'external_participants[new][parent_lastname]', payload.parentLastname);
+ appendHiddenField(form, 'external_participants[new][parent_phone]', payload.parentPhone);
+ appendHiddenField(form, 'external_participants[new][parent_email]', payload.parentEmail);
+ appendHiddenField(form, 'external_participants[new][waiver_signed]', '0');
+ appendHiddenField(form, 'external_participants[new][paid]', '0');
+
+ document.body.appendChild(form);
+ form.submit();
+ }
+
function getSortValue(row, columnIndex, sortType) {
const cell = row.children[columnIndex];
if (!cell) {
@@ -910,7 +784,6 @@ function loadStudentsWithCharges() {
alert('Select an event before adding a non-school participant.');
return;
}
- const eventAmount = parseFloat($('#event_id option:selected').data('amount')) || 0;
const explicitParentName = `${parentFirst} ${parentLast}`.trim();
if (!explicitParentName) {
alert('Please enter the external kid parent name.');
@@ -920,9 +793,7 @@ function loadStudentsWithCharges() {
alert('Please enter the external kid parent email.');
return;
}
- const parentName = explicitParentName;
- const draftEntry = editingKey ? getDraftByKey(editingKey) : null;
- const entry = {
+ submitExternalParticipant({
firstname: firstName,
lastname: lastName,
note: note,
@@ -930,91 +801,10 @@ function loadStudentsWithCharges() {
parentLastname: parentLast,
parentPhone: parentPhone,
parentEmail: parentEmail,
- eventId: (draftEntry && draftEntry.eventId) ? draftEntry.eventId : eventId,
- eventAmount: (draftEntry && draftEntry.eventAmount) ? draftEntry.eventAmount : eventAmount,
- parentDisplayName: (draftEntry && draftEntry.parentDisplayName) ? draftEntry.parentDisplayName : parentName,
- waiverSigned: (draftEntry && typeof draftEntry.waiverSigned !== 'undefined') ? !!draftEntry.waiverSigned : false,
- paid: (draftEntry && typeof draftEntry.paid !== 'undefined') ? !!draftEntry.paid : false,
- };
- if (editingKey) {
- entry.key = editingKey;
- }
- saveExternalDraft(entry);
- editingKey = null;
- $externalSaveButton.text('Add to list');
+ eventId: eventId
+ });
clearModalInputs();
- if (modalInstance) {
- modalInstance.hide();
- }
});
-
- $(document).on('click', '.remove-external-participant', function() {
- const $entry = $(this).closest('[data-key]');
- const key = $entry.data('key');
- removeExternalEntryFromDom(key);
- if (key) {
- removeDraft(key);
- }
- });
- $(document).on('click', '.edit-external-participant', function() {
- const key = $(this).data('key');
- if (key) {
- openExternalModalForEntry(key);
- }
- });
- $(document).on('change', '.external-paid-toggle', function() {
- const key = $(this).data('key');
- const paid = !!this.checked;
- if (!key) {
- return;
- }
- const entry = getDraftByKey(key);
- if (entry) {
- entry.paid = paid;
- persistDrafts();
- }
- $externalHidden
- .find(`div[data-key="${key}"] input[name="external_participants[${key}][paid]"]`)
- .val(paid ? '1' : '0');
- const $badge = $(`tr.external-preview[data-key="${key}"] .external-paid-badge`);
- if (paid) {
- $badge.removeClass('bg-danger').addClass('bg-success').text('Paid');
- } else {
- $badge.removeClass('bg-success').addClass('bg-danger').text('Unpaid');
- }
- const $row = $(`tr.external-preview[data-key="${key}"]`);
- $row.children().eq(8).attr('data-sort-value', paid ? 'paid' : 'unpaid');
- $row.children().eq(9).attr('data-sort-value', paid ? 'paid' : 'unpaid');
- applyActiveSort($row.closest('table').get(0));
- });
- $(document).on('change', '.external-waiver-toggle', function() {
- const key = $(this).data('key');
- const signed = !!this.checked;
- if (!key) {
- return;
- }
- const entry = getDraftByKey(key);
- if (entry) {
- entry.waiverSigned = signed;
- persistDrafts();
- }
- $externalHidden
- .find(`div[data-key="${key}"] input[name="external_participants[${key}][waiver_signed]"]`)
- .val(signed ? '1' : '0');
- const $label = $(`tr.external-preview[data-key="${key}"] .external-waiver-label`);
- if (signed) {
- $label.text('Signed');
- } else {
- $label.text('Unsigned');
- }
- const $row = $(`tr.external-preview[data-key="${key}"]`);
- $row.children().eq(7).attr('data-sort-value', signed ? 'signed' : 'unsigned');
- applyActiveSort($row.closest('table').get(0));
- });
- $('#event-participant-form').on('submit', function() {
- localStorage.removeItem(storageKey);
- });
- loadDrafts();
});
= $this->endSection() ?>