add order fulfillment type selection and optimize checkout UI, and update docker container naming conventions

This commit is contained in:
Alaguraj0361 2026-04-08 12:27:23 +05:30
parent 467181c4af
commit ed6e69e191

View File

@ -84,11 +84,6 @@
<input type="hidden" name="fulfilment_type" id="hidden_fulfilment_type" value="delivery"/> <input type="hidden" name="fulfilment_type" id="hidden_fulfilment_type" value="delivery"/>
<div class="section-header"><i class="fa fa-clock-o me-2"></i>Preferred Greeting / Timing</div>
<div class="mb-4">
<input type="datetime-local" name="delivery_time" id="delivery_time_input" class="form-control form-control-lg border-0 bg-light" required="required"/>
</div>
<div id="uber_message" class="alert d-none my-3" role="alert"></div> <div id="uber_message" class="alert d-none my-3" role="alert"></div>
<div id="contact_info_header" class="section-header mt-4"><i class="fa fa-user me-2"></i>Contact Details</div> <div id="contact_info_header" class="section-header mt-4"><i class="fa fa-user me-2"></i>Contact Details</div>
</xpath> </xpath>
@ -106,9 +101,106 @@
function initUnifiedForm() { function initUnifiedForm() {
const hiddenType = document.getElementById('hidden_fulfilment_type'); const hiddenType = document.getElementById('hidden_fulfilment_type');
const msgDiv = document.getElementById('uber_message'); const msgDiv = document.getElementById('uber_message');
const submitBtn = document.querySelector('button[type="submit"]') || document.querySelector('.btn-primary'); const submitBtn = document.querySelector('button[type="submit"]') || document.querySelector('.btn-primary') || document.querySelector('.s_website_form_send');
let debounceTimer; let debounceTimer;
// Force Name, Email, and Phone to be required
['name', 'email', 'phone'].forEach(fieldName => {
const input = document.querySelector(`form.checkout_autoformat [name="${fieldName}"]`);
if (input) input.setAttribute('required', 'required');
});
// 1. Add prominent red required icons to labels
document.querySelectorAll('form.checkout_autoformat .control-label, form.checkout_autoformat label').forEach(label => {
const inputId = label.getAttribute('for');
const input = inputId ? document.getElementById(inputId) : label.closest('.mb-3')?.querySelector('input, select');
if (input &amp;&amp; input.hasAttribute('required') &amp;&amp; !label.querySelector('.fa-asterisk')) {
label.innerHTML += ' <i class="fa fa-asterisk text-danger" style="font-size: 7px; vertical-align: top; margin-left: 2px;"></i>';
}
});
// 2. Clear error state on input change (Real-time update)
document.querySelectorAll('form.checkout_autoformat input, form.checkout_autoformat select').forEach(input => {
const handler = function() {
const val = this.value ? this.value.trim() : "";
// Check if the field is actually filled (0 is valid for select if it's not the placeholder)
const isFilled = val &amp;&amp; val !== "0" &amp;&amp; val !== "";
if (isFilled) {
this.classList.remove('is-invalid');
this.style.borderColor = '';
// Update the summary error list dynamically
const form = this.closest('form');
const errorDiv = document.getElementById('chennora_val_error');
if (errorDiv) {
const stillInvalid = form.querySelectorAll('.is-invalid');
if (stillInvalid.length === 0) {
errorDiv.style.display = 'none';
} else {
let missingNames = [];
stillInvalid.forEach(inv => {
const l = form.querySelector(`label[for="${inv.name}"]`) || inv.closest('.mb-3')?.querySelector('label');
missingNames.push(l ? l.textContent.replace('*', '').trim() : inv.name);
});
errorDiv.innerHTML = `<strong>Missing Required Fields:</strong><br/>${missingNames.join(', ')}`;
}
}
}
};
input.addEventListener('input', handler);
input.addEventListener('change', handler);
});
// 3. Custom Validation on Submit
if (submitBtn) {
submitBtn.addEventListener('click', function(e) {
const form = document.querySelector('form.checkout_autoformat');
if (!form) return;
// Reset errors before checking
let missingFields = [];
const requiredInputs = form.querySelectorAll('input[required]:not([type="hidden"]), select[required]');
requiredInputs.forEach(input => {
// Skip hidden fields (from pickup/delivery toggle or company hide)
const container = input.closest('div[class*="col-"], .mb-3');
if (container &amp;&amp; container.style.display === 'none') return;
if (input.name === 'company_name' || input.name === 'vat') return;
const val = input.value ? input.value.trim() : "";
const isMissing = !val || val === "0" || val === "";
if (isMissing) {
const label = form.querySelector(`label[for="${input.name}"]`) || input.closest('.mb-3')?.querySelector('label');
const fieldName = label ? label.textContent.replace('*', '').trim() : input.name;
missingFields.push(fieldName);
input.classList.add('is-invalid');
input.style.borderColor = '#dc3545';
} else {
input.classList.remove('is-invalid');
input.style.borderColor = '';
}
});
if (missingFields.length > 0) {
e.preventDefault();
e.stopPropagation();
let errorDiv = document.getElementById('chennora_val_error');
if (!errorDiv) {
errorDiv = document.createElement('div');
errorDiv.id = 'chennora_val_error';
errorDiv.className = 'alert alert-danger mt-3 animated fadeIn';
form.insertBefore(errorDiv, form.firstChild);
}
errorDiv.style.display = 'block';
errorDiv.innerHTML = `<strong>Missing Required Fields:</strong><br/>${missingFields.join(', ')}`;
errorDiv.scrollIntoView({ behavior: 'smooth', block: 'center' });
}
});
}
function getAddressContainers() { function getAddressContainers() {
const addressNames = ['street', 'street2', 'city', 'zip', 'country_id', 'state_id']; const addressNames = ['street', 'street2', 'city', 'zip', 'country_id', 'state_id'];
let containers = []; let containers = [];
@ -143,11 +235,19 @@
containers.forEach(c => c.style.display = 'none'); containers.forEach(c => c.style.display = 'none');
if (addrHeader) addrHeader.style.display = 'none'; if (addrHeader) addrHeader.style.display = 'none';
if (msgDiv) msgDiv.style.display = 'none'; if (msgDiv) msgDiv.style.display = 'none';
if (submitBtn) submitBtn.disabled = false; // Remove required for pickup
containers.forEach(c => {
c.querySelectorAll('input, select').forEach(i => i.removeAttribute('required'));
});
} else { } else {
containers.forEach(c => c.style.display = ''); containers.forEach(c => c.style.display = '');
if (addrHeader) addrHeader.style.display = ''; if (addrHeader) addrHeader.style.display = '';
if (msgDiv) msgDiv.style.display = ''; if (msgDiv) msgDiv.style.display = '';
// Restore required
['street', 'city', 'zip', 'country_id', 'state_id'].forEach(name => {
const i = document.querySelector(`[name="${name}"]`);
if (i) i.setAttribute('required', 'required');
});
checkUber(); checkUber();
} }
}; };