diff --git a/assets/css/styles.css b/assets/css/styles.css
index 2082053..cc049e0 100644
--- a/assets/css/styles.css
+++ b/assets/css/styles.css
@@ -2017,10 +2017,6 @@ select {
bottom: 100%;
}
-.left-0 {
- left: 0px;
-}
-
.left-2 {
left: 0.5rem;
}
@@ -2777,6 +2773,11 @@ html {
background-color: rgb(89 10 12/var(--tw-bg-opacity));
}
+.hover\:bg-stone-300:hover {
+ --tw-bg-opacity: 1;
+ background-color: rgb(214 211 209/var(--tw-bg-opacity));
+}
+
.hover\:bg-stone-500:hover {
--tw-bg-opacity: 1;
background-color: rgb(120 113 108/var(--tw-bg-opacity));
@@ -2787,21 +2788,6 @@ html {
background-color: rgb(87 83 78/var(--tw-bg-opacity));
}
-.hover\:bg-stone-100:hover {
- --tw-bg-opacity: 1;
- background-color: rgb(245 245 244/var(--tw-bg-opacity));
-}
-
-.hover\:bg-stone-200:hover {
- --tw-bg-opacity: 1;
- background-color: rgb(231 229 228/var(--tw-bg-opacity));
-}
-
-.hover\:bg-stone-300:hover {
- --tw-bg-opacity: 1;
- background-color: rgb(214 211 209/var(--tw-bg-opacity));
-}
-
.hover\:text-white:hover {
--tw-text-opacity: 1;
color: rgb(255 255 255/var(--tw-text-opacity));
diff --git a/autocart_assets/css/filter-panel.css b/autocart_assets/css/filter-panel.css
index 43a558d..be92b3e 100644
--- a/autocart_assets/css/filter-panel.css
+++ b/autocart_assets/css/filter-panel.css
@@ -209,7 +209,7 @@ li.mdc-list-item:hover {
#slide-out-filters{
transition: 300ms ease-in-out;
- translate: -100%;
+ /* translate: -100%; */
}
@@ -238,4 +238,12 @@ li.mdc-list-item:hover {
.sticky-container{
position: static;
}
+/*
+ #applied-filters-container{
+ position: fixed;
+ bottom: 0px;
+ z-index: 50;
+ width: 100%;
+ right: 0;
+ } */
}
\ No newline at end of file
diff --git a/autocart_assets/js/FinanceForm.js b/autocart_assets/js/FinanceForm.js
index 6c94fda..9bf1c3e 100644
--- a/autocart_assets/js/FinanceForm.js
+++ b/autocart_assets/js/FinanceForm.js
@@ -1,523 +1,555 @@
class FinanceForm {
- constructor(vehicle,appointmentForm, notifyParentCallback) {
- this.notifyParentCallback = notifyParentCallback;
- this.inputs = [
- 'loanTerm',
- 'intRate',
- 'downPayment',
- 'tradeValue',
- 'paymentFrequency',
- 'rate',
- 'customRateValue',
- ];
- this.modalDiv = null;
- this.name = 'financeForm';
- this.appointmentForm = appointmentForm;
- this.frequencyMap = {
- 12: 'Monthly',
- 26: 'Bi-Weekly',
- 52: 'Weekly',
- };
-
- this.vehicle = vehicle;
-
- // Default values
- this.loanTerm = 12;
- this.intRate = 7.99;
- this.downPayment = 0;
- this.tradeValue = 0;
- this.paymentFrequency = 26;
-
- // Check if values exist in localStorage, and if so, override default values
- const storedValues =
- JSON.parse(localStorage.getItem(`autocart_${this.name}`)) || {};
- if (storedValues) {
- this.loanTerm = parseInt(storedValues.loanTerm) || this.loanTerm;
- this.intRate = parseFloat(storedValues.customRateValue) || this.intRate;
- this.downPayment = parseInt(storedValues.downPayment) || this.downPayment;
- this.tradeValue = parseInt(storedValues.tradeValue) || this.tradeValue;
- this.paymentFrequency =
- parseInt(storedValues.paymentFrequency) || this.paymentFrequency;
- }
-
- // Calculate other values based on the provided vehicle and overridden inputs
- let amount = parseFloat(this.vehicle.advertise_price) || 0;
- let months = parseFloat(this.loanTerm) || 0;
- let down = parseFloat(this.downPayment) || 0;
- let trade = parseFloat(this.tradeValue) || 0;
- let totalDown = down + trade;
- let annInterest = parseFloat(this.intRate) || 0;
- let monInt = annInterest / 1200;
- let financeTotal = amount - totalDown;
- let numberOfPayments = months / (12 / this.paymentFrequency);
-
- // Fix calculation for total cost of credit
- let interest = financeTotal * monInt * numberOfPayments;
- this.totalCostOfCredit = interest.toFixed(2);
-
- this.totalObligation = (
- financeTotal + parseFloat(this.totalCostOfCredit)
- ).toFixed(2);
-
- this.payment =
- (
- (monInt + monInt / (Math.pow(1 + monInt, months) - 1)) *
- (amount - (totalDown || 0))
- ).toFixed(2) /
- (this.paymentFrequency / 12);
-
- // Notify parent callback with the updated values
- this.notifyParentCallback(this);
-
- // Initialize the form
- this.initForm();
- this.initializeFormInputs();
- }
-
- generateLoanTermOptions(vehicleAge) {
- const defaultOptions = [
- { year: 2, terms: [12, 24, 36, 48, 60, 72, 84, 96] },
- { year: 5, terms: [12, 24, 36, 48, 60, 72, 84] },
- { year: 7, terms: [12, 24, 36, 48, 60, 72] },
- { year: 8, terms: [12, 24, 36, 48, 60] },
- { year: 10, terms: [12, 24, 36, 48] }
+ constructor(vehicle,appointmentForm, notifyParentCallback) {
+ this.notifyParentCallback = notifyParentCallback;
+ this.inputs = [
+ 'loanTerm',
+ 'intRate',
+ 'downPayment',
+ 'tradeValue',
+ 'paymentFrequency',
+ 'rate',
+ 'customRateValue',
];
+ this.modalDiv = null;
+ this.name = 'financeForm';
+ this.appointmentForm = appointmentForm;
+ this.frequencyMap = {
+ 12: 'Monthly',
+ 26: 'Bi-Weekly',
+ 52: 'Weekly',
+ };
- const selectedOptions = defaultOptions.find(option => vehicleAge <= option.year);
-
- if (selectedOptions) {
- const optionsHTML = selectedOptions.terms.map(term => `${term} Month Term `).join('\n');
- return optionsHTML;
- } else {
- return '';
+ if (!vehicle.advertise_price) {
+ vehicle['advertise_price'] = 0;
+ this.inputs.push('advertise_price')
}
- }
-
-
- initForm() {
- // console.log('initForm')
- this.modalDiv = document.createElement('div');
- const currentYear = new Date().getFullYear();
- const vehicleYear = this.vehicle.year;
- const vehicleAge = currentYear - vehicleYear;
- const loanTermOptions = this.generateLoanTermOptions(vehicleAge);
- // const modalDiv = document.createElement('div');
- this.modalDiv.innerHTML = `
-
-
-
-
-
-
-
-
-
-
-
-
-
Let’s Structure a Deal That Works For You
-
- We understand that purchasing a vehicle is a big decision, so we want you to be paying a price that you’re comfortable with.
- Let’s structure a deal that works for you below:
-
-
-
- Finance Option
-
- ${this.payment} / ${this.frequencyMap[this.paymentFrequency]}
-
- ${this.intRate} % APR for ${this.loanTerm} Months
-
-
-
+
+
+
+
+
Let’s Structure a Deal That Works For You
+
+
+ We understand that purchasing a vehicle is a big decision, so we want you to be paying a price that you’re comfortable with.
+ Let’s structure a deal that works for you below:
+
+
+
- if (!optionValues.includes(selectedValue)) {
- const closestValue = optionValues.reduce((a, b) => Math.abs(b - selectedValue) < Math.abs(a - selectedValue) ? b : a);
- inputElement.value = closestValue;
- }
- }
- inputElement.dispatchEvent(new Event('input'));
- }
- }
- this.updateView();
- }
-
- calculatePayments() {
- var vehiclePrice = this.vehicle.advertise_price;
- this.loanTerm = document.getElementById('loanTerm').value;
- this.paymentFrequency = document.getElementById('paymentFrequency').value;
- this.intRate = document.getElementById('rate').value == 'default-rate'
- ? 7.99
- : document.getElementById('customRateValue').value;
- this.downPayment = document.getElementById('downPayment').value;
- this.tradeValue = document.getElementById('tradeValue').value;
- var amount = parseFloat(vehiclePrice) || 0,
- months = parseFloat(this.loanTerm) || 0,
- down = parseFloat(this.downPayment) || 0,
- trade = parseFloat(this.tradeValue) || 0,
- totalDown = down + trade,
- annInterest = parseFloat(this.intRate) || 0,
- monInt = annInterest / 1200;
- var financeTotal = amount - totalDown;
- var numberOfPayments = months / (12 / this.paymentFrequency);
-
- var monthlyPayment =
- (
- (monInt + monInt / (Math.pow(1 + monInt, months) - 1)) *
- (amount - (totalDown || 0))
- ).toFixed(2) /
- (this.paymentFrequency / 12);
- this.totalCostOfCredit = (
- monthlyPayment * numberOfPayments -
- financeTotal
- ).toFixed(2);
- this.totalObligation = (
- parseFloat(this.totalCostOfCredit) + parseFloat(financeTotal)
- ).toFixed(2);
- this.payment =
- (
- (monInt + monInt / (Math.pow(1 + monInt, months) - 1)) *
- (amount - (totalDown || 0))
- ).toFixed(2) /
- (this.paymentFrequency / 12);
-
- this.updateView();
- }
-
- updateView() {
- ['default-rate', 'custom-rate'].forEach((el) => {
- document.getElementById(el)?.classList?.add('hidden');
- });
- if(document.getElementById('rate')){
- document
- .getElementById(document.getElementById('rate').value)
- .classList.remove('hidden');
- }
-
-
- if (document.querySelectorAll('.loanTermSpan').length) {
- document.querySelectorAll('.loanTermSpan').forEach((el) => {
- el.innerHTML = `${this.loanTerm}`;
- });
- }
-
- if (document.querySelectorAll('.rateSpan').length) {
- document.querySelectorAll('.rateSpan').forEach((el) => {
- el.innerHTML = `${this.intRate}`;
- });
- }
-
- if (document.querySelectorAll('.paymentSpan').length) {
- document.querySelectorAll('.paymentSpan').forEach((el) => {
- el.innerHTML = (Number(this.payment) || 0).toLocaleString('en-CA', {
- style: 'currency',
- currency: 'CAD',
- });
- });
- }
-
- if (document.querySelectorAll('.paymentFrequencySpan').length) {
- document.querySelectorAll('.paymentFrequencySpan').forEach((el) => {
- el.innerHTML = this.frequencyMap[this.paymentFrequency];
- });
- }
-
- if (document.querySelectorAll('.totalCostOfCreditSpan').length) {
- document.querySelectorAll('.totalCostOfCreditSpan').forEach((el) => {
- el.innerHTML = (Number(this.totalCostOfCredit) || 0).toLocaleString(
- 'en-CA',
- { style: 'currency', currency: 'CAD' }
- );
- });
- }
-
- if (document.querySelectorAll('.totalObligationSpan').length) {
- document.querySelectorAll('.totalObligationSpan').forEach((el) => {
- el.innerHTML = (Number(this.totalObligation) || 0).toLocaleString(
- 'en-CA',
- { style: 'currency', currency: 'CAD' }
- );
- });
- }
- }
-
- goToNextTab() {
- let tab1 = document.querySelector('[data-tab="tab1"]');
- let tab2 = document.querySelector('[data-tab="tab2"]');
- let backButton = document.getElementById('next-step');
-
- if (tab1 && tab2 && backButton) {
- if (tab1.classList.contains('active')) {
- // Switch to tab2 and update button text to "Back"
- tab2.click();
- backButton.innerText = 'Back';
- } else if (tab2.classList.contains('active')) {
- // Switch to tab1 and update button text to "Next step"
- tab1.click();
- backButton.innerText = 'Next step';
- }
- }
- }
-
- initializeTabNavigation(modalDiv) {
- const tabLinks = modalDiv.querySelectorAll('.tab-link');
- const tabContents = modalDiv.querySelectorAll('.tab-content');
- let nextStepButton = modalDiv.querySelector('#next-step');
- if (nextStepButton) {
- nextStepButton.addEventListener('click', this.goToNextTab.bind(this));
- }
- tabLinks.forEach(function (tabLink) {
- tabLink.addEventListener('click', function (event) {
- event.preventDefault();
-
- tabLinks.forEach(function (link) {
- link.classList.remove('active', 'bg-gray-600', 'text-white');
- });
- tabContents.forEach(function (content) {
- content.classList.add('hidden');
- });
-
- const targetTab = this.getAttribute('data-tab');
- this.classList.add('active', 'bg-gray-600', 'text-white');
-
- let backButtonTexts = { tab1: 'Next Step', tab2: 'Back To Options' };
- nextStepButton.innerText = backButtonTexts[targetTab];
- modalDiv
- .querySelector(`.tab-content[data-content="${targetTab}"]`)
- .classList.remove('hidden');
- });
- });
- }
-
- initializeFormEventListeners(modalDiv) {
-
-
- this.inputs.forEach((id) => {
- const inputElement = modalDiv.querySelector(`#${id}`);
- if (inputElement) {
- inputElement.addEventListener('input', () => {
- this.calculatePayments();
- this.saveFormValues(); // Save form values whenever an input changes
- });
- }
- });
- }
-
- saveFormValues() {
+
+
+
+
+
+
Vehicle Price
+
+
+ Vehicle Price
+
+ ${this.vehicle.advertise_price.toLocaleString('en-CA', { style: 'currency', currency: 'CAD', minimumFractionDigits: 0, maximumFractionDigits: 0 })}
+
+
+
+
+
+
+
+
+
+ Finance Total
+
+ ${this.vehicle.advertise_price.toLocaleString('en-CA', { style: 'currency', currency: 'CAD', minimumFractionDigits: 0, maximumFractionDigits: 0 })}
+
+
+
+
+
+
Finance Payment
+
+
+ Loan Term
+
+ ${this.loanTerm} Months
+
+
+
+ Program Rate
+
+ 7.99 %
+
+
+
+ Frequency
+
+ ${this.frequencyMap[this.paymentFrequency]}
+
+
+
+
+
+
+
Total
+
+
+ Total Cost of Credit
+
+ ${this.totalCostOfCredit.toLocaleString('en-CA', { style: 'currency', currency: 'CAD', minimumFractionDigits: 0, maximumFractionDigits: 0 })}
+
+
+
+ Total Obligation
+
+ ${this.totalObligation.toLocaleString('en-CA', { style: 'currency', currency: 'CAD', minimumFractionDigits: 0, maximumFractionDigits: 0 })}
+
+
+
+
+
+
+
+
+
+ ${(Number(this.payment) || 0).toLocaleString('en-CA', { style: 'currency', currency: 'CAD' })}
+ /
+ ${this.frequencyMap[this.paymentFrequency]}
+
+
+
+
Next Step
+
+
+
+
+ `;
+
+ const formContainer = this.modalDiv.querySelector(
+ '#appointmentFormContainer'
+ );
+
+ formContainer.appendChild(this.appointmentForm.initForm());
- const formValues = {};
-
- this.inputs.forEach((input) => {
- const inputElement = document.getElementById(input);
- if (inputElement) {
- formValues[input] = inputElement.value;
- }
- });
-
- if (formValues['rate'] == 'default-rate') {
- formValues['customRateValue'] = 7.99;
+ this.initializeTabNavigation(this.modalDiv);
+ this.initializeFormEventListeners(this.modalDiv);
+ return this.modalDiv;
}
-
- localStorage.setItem(`autocart_${this.name}`, JSON.stringify(formValues));
+
+ // initializeFormInputs() {
+ // const storedValues = JSON.parse(localStorage.getItem(`autocart_${this.name}`)) || {};
+ // // const mergedValues = { ...this.defaultValues, ...storedValues };
+ // console.log(storedValues);
+ // for (const key in storedValues) {
+ // console.log(key);
+
+ // const inputElement = document.getElementById(key);
+ // if (inputElement) {
+ // inputElement.value = storedValues[key];
+ // }
+ // }
+ // this.updateView()
+ // }
+
+ initializeFormInputs() {
+ const storedValues = JSON.parse(localStorage.getItem(`autocart_${this.name}`)) || {};
+ const selectElements = document.querySelectorAll('select');
+
+ for (const key in storedValues) {
+ const inputElement = document.getElementById(key);
+ if (inputElement) {
+ inputElement.value = storedValues[key];
+ if (inputElement.tagName.toLowerCase() === 'select') {
+ const optionValues = Array.from(inputElement.options).map(option => option.value);
+ const selectedValue = storedValues[key];
+
+ if (!optionValues.includes(selectedValue)) {
+ const closestValue = optionValues.reduce((a, b) => Math.abs(b - selectedValue) < Math.abs(a - selectedValue) ? b : a);
+ inputElement.value = closestValue;
+ }
+ }
+ inputElement.dispatchEvent(new Event('input'));
+ }
+ }
+ this.updateView();
+}
+
+ calculatePayments() {
+
+ var vehiclePrice = this.vehicle.advertise_price;
+ if(this.inputs.includes('advertise_price')){
+ vehiclePrice = document.getElementById('advertise_price').value;
+ }
+ this.loanTerm = document.getElementById('loanTerm').value;
+ this.paymentFrequency = document.getElementById('paymentFrequency').value;
+ this.intRate = document.getElementById('rate').value == 'default-rate'
+ ? 7.99
+ : document.getElementById('customRateValue').value;
+ this.downPayment = document.getElementById('downPayment').value;
+ this.tradeValue = document.getElementById('tradeValue').value;
+ var amount = parseFloat(vehiclePrice) || 0,
+ months = parseFloat(this.loanTerm) || 0,
+ down = parseFloat(this.downPayment) || 0,
+ trade = parseFloat(this.tradeValue) || 0,
+ totalDown = down + trade,
+ annInterest = parseFloat(this.intRate) || 0,
+ monInt = annInterest / 1200;
+ var financeTotal = amount - totalDown;
+ var numberOfPayments = months / (12 / this.paymentFrequency);
+
+ var monthlyPayment =
+ (
+ (monInt + monInt / (Math.pow(1 + monInt, months) - 1)) *
+ (amount - (totalDown || 0))
+ ).toFixed(2) /
+ (this.paymentFrequency / 12);
+ this.totalCostOfCredit = (
+ monthlyPayment * numberOfPayments -
+ financeTotal
+ ).toFixed(2);
+ this.totalObligation = (
+ parseFloat(this.totalCostOfCredit) + parseFloat(financeTotal)
+ ).toFixed(2);
+ this.payment =
+ (
+ (monInt + monInt / (Math.pow(1 + monInt, months) - 1)) *
+ (amount - (totalDown || 0))
+ ).toFixed(2) /
+ (this.paymentFrequency / 12);
+
+ this.updateView();
+ }
+
+ updateView() {
+ ['default-rate', 'custom-rate'].forEach((el) => {
+ document.getElementById(el)?.classList?.add('hidden');
+ });
+ if(document.getElementById('rate')){
+ document.getElementById(document.getElementById('rate').value)
+ .classList.remove('hidden');
+ }
+
+
+ if (document.querySelectorAll('.loanTermSpan').length) {
+ document.querySelectorAll('.loanTermSpan').forEach((el) => {
+ el.innerHTML = `${this.loanTerm}`;
+ });
+ }
+
+ if (document.querySelectorAll('.rateSpan').length) {
+ document.querySelectorAll('.rateSpan').forEach((el) => {
+ el.innerHTML = `${this.intRate}`;
+ });
+ }
+
+ if (document.querySelectorAll('.paymentSpan').length) {
+ document.querySelectorAll('.paymentSpan').forEach((el) => {
+ el.innerHTML = (Number(this.payment) || 0).toLocaleString('en-CA', {
+ style: 'currency',
+ currency: 'CAD',
+ });
+ });
+ }
+
+ if (document.querySelectorAll('.paymentFrequencySpan').length) {
+ document.querySelectorAll('.paymentFrequencySpan').forEach((el) => {
+ el.innerHTML = this.frequencyMap[this.paymentFrequency];
+ });
+ }
+
+ if (document.querySelectorAll('.totalCostOfCreditSpan').length) {
+ document.querySelectorAll('.totalCostOfCreditSpan').forEach((el) => {
+ el.innerHTML = (Number(this.totalCostOfCredit) || 0).toLocaleString(
+ 'en-CA',
+ { style: 'currency', currency: 'CAD' }
+ );
+ });
+ }
+
+ if (document.querySelectorAll('.advertisePriceSpan').length) {
+ document.querySelectorAll('.advertisePriceSpan').forEach((el) => {
+ el.innerHTML = (Number(document.getElementById('advertise_price').value) || 0).toLocaleString(
+ 'en-CA',
+ { style: 'currency', currency: 'CAD' }
+ );
+ });
+ }
+
+
+
+ if (document.querySelectorAll('.totalObligationSpan').length) {
+ document.querySelectorAll('.totalObligationSpan').forEach((el) => {
+ el.innerHTML = (Number(this.totalObligation) || 0).toLocaleString(
+ 'en-CA',
+ { style: 'currency', currency: 'CAD' }
+ );
+ });
}
}
-
\ No newline at end of file
+
+ goToNextTab() {
+ let tab1 = document.querySelector('[data-tab="tab1"]');
+ let tab2 = document.querySelector('[data-tab="tab2"]');
+ let backButton = document.getElementById('next-step');
+
+ if (tab1 && tab2 && backButton) {
+ if (tab1.classList.contains('active')) {
+ // Switch to tab2 and update button text to "Back"
+ tab2.click();
+ backButton.innerText = 'Back';
+ } else if (tab2.classList.contains('active')) {
+ // Switch to tab1 and update button text to "Next step"
+ tab1.click();
+ backButton.innerText = 'Next step';
+ }
+ }
+ }
+
+ initializeTabNavigation(modalDiv) {
+ const tabLinks = modalDiv.querySelectorAll('.tab-link');
+ const tabContents = modalDiv.querySelectorAll('.tab-content');
+ let nextStepButton = modalDiv.querySelector('#next-step');
+ if (nextStepButton) {
+ nextStepButton.addEventListener('click', this.goToNextTab.bind(this));
+ }
+ tabLinks.forEach(function (tabLink) {
+ tabLink.addEventListener('click', function (event) {
+ event.preventDefault();
+
+ tabLinks.forEach(function (link) {
+ link.classList.remove('active', 'bg-gray-600', 'text-white');
+ });
+ tabContents.forEach(function (content) {
+ content.classList.add('hidden');
+ });
+
+ const targetTab = this.getAttribute('data-tab');
+ this.classList.add('active', 'bg-gray-600', 'text-white');
+
+ let backButtonTexts = { tab1: 'Next Step', tab2: 'Back To Options' };
+ nextStepButton.innerText = backButtonTexts[targetTab];
+ modalDiv
+ .querySelector(`.tab-content[data-content="${targetTab}"]`)
+ .classList.remove('hidden');
+ });
+ });
+ }
+
+ initializeFormEventListeners(modalDiv) {
+
+
+ this.inputs.forEach((id) => {
+ const inputElement = modalDiv.querySelector(`#${id}`);
+ if (inputElement) {
+ inputElement.addEventListener('input', () => {
+ this.calculatePayments();
+ this.saveFormValues(); // Save form values whenever an input changes
+ });
+ }
+ });
+ }
+
+ saveFormValues() {
+
+ const formValues = {};
+
+ this.inputs.forEach((input) => {
+ const inputElement = document.getElementById(input);
+ if (inputElement) {
+ formValues[input] = inputElement.value;
+ }
+ });
+
+ if (formValues['rate'] == 'default-rate') {
+ formValues['customRateValue'] = 7.99;
+ }
+
+ localStorage.setItem(`autocart_${this.name}`, JSON.stringify(formValues));
+ }
+}
diff --git a/autocart_assets/js/index.js b/autocart_assets/js/index.js
index 95e147c..b707a9e 100644
--- a/autocart_assets/js/index.js
+++ b/autocart_assets/js/index.js
@@ -10,329 +10,296 @@ let shouldUpdateFilters = true;
let modelFilter = [];
let makeFilters;
function sendReq() {
- var formData = {
- action: 'handle_autocart_form',
- minPrice: price.getValueStart(),
- maxPrice: price.getValue(),
- minKilometres: kilometres.getValueStart(),
- maxKilometres: kilometres.getValue(),
- minYear: year.getValueStart(),
- maxYear: year.getValue(),
- autocart_nonce: jQuery('#autocart_nonce').val(),
- };
- const vehiclesContainer = document.querySelector('.vehicles-container');
- // vehiclesContainer.textContent = 'Loading...';
- // Add skeleton cards to the vehicles container
- for (let i = 0; i < 6; i++) {
- const skeletonCard = createSkeletonCard();
- vehiclesContainer.appendChild(skeletonCard);
- }
+ var formData = {
+ 'action': 'handle_autocart_form',
+ 'minPrice': price.getValueStart(),
+ 'maxPrice': price.getValue(),
+ 'minKilometres': kilometres.getValueStart(),
+ 'maxKilometres': kilometres.getValue(),
+ 'minYear': year.getValueStart(),
+ 'maxYear': year.getValue(),
+ 'autocart_nonce': jQuery('#autocart_nonce').val(),
+ };
+ const vehiclesContainer = document.querySelector('.vehicles-container');
+ // vehiclesContainer.textContent = 'Loading...';
+ // Add skeleton cards to the vehicles container
+ for (let i = 0; i < 6; i++) {
+ const skeletonCard = createSkeletonCard();
+ vehiclesContainer.appendChild(skeletonCard);
+ }
- const filtersContainer = document.querySelector('.make-container');
- for (let i = 0; i < 2; i++) {
- const skeletonListItem = createSkeletonListItem();
- filtersContainer.appendChild(skeletonListItem);
- }
- // Add skeleton list item to the filters container
- // const skeletonListItem = createSkeletonListItem();
- // filtersContainer.appendChild(skeletonListItem);
+ const filtersContainer = document.querySelector('.make-container');
+ for (let i = 0; i < 2; i++) {
+ const skeletonListItem = createSkeletonListItem();
+ filtersContainer.appendChild(skeletonListItem);
+ }
+ // Add skeleton list item to the filters container
+ // const skeletonListItem = createSkeletonListItem();
+ // filtersContainer.appendChild(skeletonListItem);
- jQuery.ajax({
- type: 'POST',
- url: ajax_object.ajax_url,
- data: formData,
- success: function (response) {
- const vehicles = response.data.vehicles;
- if (dataStore) {
- dataStore.unsubscribeAll();
- }
+ jQuery.ajax({
+ type: 'POST',
+ url: ajax_object.ajax_url,
+ data: formData,
+ success: function (response) {
+ const vehicles = response.data.vehicles;
+ if (dataStore) {
+ dataStore.unsubscribeAll();
+ }
- // Initialize new data store
- dataStore.vehicles = vehicles;
- filterManager = new FilterManager(dataStore);
- appliedFilters = new AppliedFilters(dataStore, filterManager);
+
+ // Initialize new data store
+ dataStore.vehicles = vehicles;
+ filterManager = new FilterManager(dataStore);
+ appliedFilters = new AppliedFilters(dataStore, filterManager);
- // filterManager = new FilterManager(dataStore);
- // appliedFilters = new AppliedFilters(dataStore, filterManager);
+ // filterManager = new FilterManager(dataStore);
+ // appliedFilters = new AppliedFilters(dataStore, filterManager);
+
+ shouldUpdateFilters = true;
+ dataStore.subscribe(filteredVehicles => {
+ console.log('dataStore has been changed')
+ handleSuccess(filteredVehicles);
+ });
- shouldUpdateFilters = true;
- dataStore.subscribe((filteredVehicles) => {
- console.log('dataStore has been changed');
- handleSuccess(filteredVehicles);
- });
-
- dataStore.notifySubscribers(vehicles);
- },
- error: function (xhr, status, error) {
- console.log(xhr.responseText);
- console.log('Status: ' + status);
- console.log('Error: ' + error);
- jQuery('#inventory-search__search-button').text('Error');
- },
- });
+ dataStore.notifySubscribers(vehicles);
+ },
+ error: function (xhr, status, error) {
+ console.log(xhr.responseText);
+ console.log('Status: ' + status);
+ console.log('Error: ' + error);
+ jQuery("#inventory-search__search-button").text("Error");
+ }
+ });
}
function handleSuccess(vehicles, updateFilters = shouldUpdateFilters) {
- if (updateFilters) {
- createMakeList(vehicles);
- createBodyTypeList(vehicles);
- createTransmissionList(vehicles);
- createExteriorList(vehicles);
- }
- const vehiclesContainer = document.querySelector('.vehicles-container');
- vehiclesContainer.innerHTML = '';
+ if(updateFilters){
+ createMakeList(vehicles);
+ createBodyTypeList(vehicles);
+ createTransmissionList(vehicles);
+ createExteriorList(vehicles);
+ }
+ const vehiclesContainer = document.querySelector('.vehicles-container');
+ vehiclesContainer.innerHTML = '';
+
+ vehicles.forEach(vehicleData => {
+ const vehicle = new VehicleThumbnail(vehicleData);
+ // vehiclesContainer.appendChild(vehicle.generateCardHTML());
+ vehiclesContainer.appendChild(vehicle.generateCardElement());
- vehicles.forEach((vehicleData) => {
- const vehicle = new VehicleThumbnail(vehicleData);
- // vehiclesContainer.appendChild(vehicle.generateCardHTML());
- vehiclesContainer.appendChild(vehicle.generateCardElement());
- });
-}
-
-function createMakeList(vehicles) {
- const makeContainer = document.querySelector('.make-container');
- makeContainer.innerHTML = '';
-
- const makeCounts = vehicles.reduce((acc, vehicle) => {
- const { make } = vehicle;
- acc[make] = (acc[make] || 0) + 1;
- return acc;
- }, {});
- let makeValue = document.querySelector('#autocart-make-field').value;
- // if(makeValue){
- // console.log('makeValue',makeValue);
- // // dataStore.addFilter('make', makeValue);
- // }
- makeFilters = Object.entries(makeCounts).map(([make, count]) => {
- return filterManager.createMakeFilter(
- {
- text: make,
- checked: makeValue.toLowerCase() === make.toLowerCase(),
- count,
- models: fetchAvailableModels(vehicles, make),
- },
- dataStore
- );
- });
- makeFilters.sort((a, b) => a.value.localeCompare(b.value));
- makeFilters.forEach((make) => {
- makeContainer.appendChild(make.generateCardHTML());
- make.subscribe((m) => initModelContainer(m));
- });
-}
-
-function createBodyTypeList(vehicles) {
- const bodyTypeContainer = document.querySelector('.body-type-container');
- bodyTypeContainer.innerHTML = '';
-
- const bodyType = vehicles.reduce((acc, vehicle) => {
- const { body_type } = vehicle;
- acc[body_type] = (acc[body_type] || 0) + 1;
- return acc;
- }, {});
-
- filterManager.resetList('body_type');
-
- bodyTypeFilters = Object.entries(bodyType).map(([body_type, count]) =>
- filterManager.createBodyTypeFilter({ text: body_type, count }, dataStore)
- );
- bodyTypeFilters.sort((a, b) => a.value.localeCompare(b.value));
- bodyTypeFilters.forEach((body_type) => {
- bodyTypeContainer.appendChild(body_type.initCheckbox());
- // body_type.subscribe(m=> iniBodyTypeContainer(m))
- });
-}
-
-function createTransmissionList(vehicles) {
- const transmissionContainer = document.querySelector(
- '.transmission-container'
- );
-
- transmissionContainer.innerHTML = '';
-
- const transmission = vehicles.reduce((acc, vehicle) => {
- const { transmission_type } = vehicle;
- acc[transmission_type] = (acc[transmission_type] || 0) + 1;
- return acc;
- }, {});
-
- filterManager.resetList('transmission_type');
- transmissionFilters = Object.entries(transmission).map(
- ([transmission_type, count]) =>
- filterManager.createTransmissionFilter(
- { text: transmission_type, count },
- dataStore
- )
- );
- transmissionFilters.sort((a, b) => a.value.localeCompare(b.value));
- transmissionFilters.forEach((transmission) => {
- transmissionContainer.appendChild(transmission.initCheckbox());
- });
-}
-
-function createExteriorList(vehicles) {
- console.log(vehicles);
- const exteriorContainer = document.querySelector('.exterior-color');
- exteriorContainer.innerHTML = '';
- const exterior = vehicles.reduce((acc, vehicle) => {
- const { exterior_color } = vehicle;
- acc[exterior_color] = (acc[exterior_color] || 0) + 1;
- return acc;
- }, {});
- filterManager.resetList('exterior_color');
-
- exteriorFilters = Object.entries(exterior).map(([exterior_color, count]) =>
- filterManager.createExteriorFilter(
- { text: exterior_color, count },
- dataStore
- )
- );
- exteriorFilters.sort((a, b) => a.value.localeCompare(b.value));
-
- exteriorFilters.forEach((exterior) => {
- exteriorContainer.appendChild(exterior.initCheckbox());
- });
-}
-
-function initModelContainer(make) {
- let list = [
- ...new Set(
- filterManager.makeFilters
- .filter((m) => m.checked == true)
- .map((m) => m.models)
- .flat()
- ),
- ];
-
- const modelContainer = document.querySelector('.model-container');
- if (list.length === 0) {
- modelContainer.innerHTML = 'Please Select a Make
';
- } else if (list && list.length > 0) {
- modelContainer.innerHTML = '';
- list.sort((a, b) => a.value.localeCompare(b.value));
- list.forEach((model) => {
- modelContainer.appendChild(model.initCheckbox());
});
- } else {
- modelContainer.innerHTML = 'No models available
';
- }
+
+
}
-function initTrimContainer(model) {
- let list = [
- ...new Set(
- filterManager.modelFilters
- .filter((m) => m.checked == true)
- .map((m) => m.trims)
- .flat()
- ),
- ];
+function createMakeList(vehicles){
- // const uniqueArray = [...new Set(array)];
- const trimContainer = document.querySelector('.trim-container');
+ const makeContainer = document.querySelector('.make-container');
+ makeContainer.innerHTML = '';
- if (list.length === 0) {
- trimContainer.innerHTML = 'Please Select a Model
';
- } else if (list && list.length > 0) {
- trimContainer.innerHTML = '';
- list.sort((a, b) => a.value.localeCompare(b.value));
- list.forEach((trim) => {
- trimContainer.appendChild(trim.initCheckbox());
+ const makeCounts = vehicles.reduce((acc, vehicle) => {
+ const { make } = vehicle;
+ acc[make] = (acc[make] || 0) + 1;
+ return acc;
+ }, {});
+ let makeValue = document.querySelector('#autocart-make-field').value;
+ // if(makeValue){
+ // console.log('makeValue',makeValue);
+ // // dataStore.addFilter('make', makeValue);
+ // }
+ makeFilters = Object.entries(makeCounts).map(([make, count]) => {
+
+ return filterManager.createMakeFilter({
+ text: make,
+ checked: makeValue.toLowerCase() === make.toLowerCase(),
+ count,
+ models: fetchAvailableModels(vehicles, make)
+ }, dataStore);
});
- } else {
- trimContainer.innerHTML = 'No trims available
';
- }
+ makeFilters.sort((a, b) => a.value.localeCompare(b.value));
+ makeFilters.forEach(make => {
+
+ makeContainer.appendChild(make.generateCardHTML());
+ make.subscribe(m=> initModelContainer(m))
+ });
+}
+
+function createBodyTypeList(vehicles){
+ const bodyTypeContainer = document.querySelector('.body-type-container');
+ bodyTypeContainer.innerHTML = '';
+
+ const bodyType = vehicles.reduce((acc, vehicle) => {
+ const { body_type } = vehicle;
+ acc[body_type] = (acc[body_type] || 0) + 1;
+ return acc;
+ }, {});
+
+ filterManager.resetList('body_type');
+
+
+ bodyTypeFilters = Object.entries(bodyType).map(([body_type, count]) => filterManager.createBodyTypeFilter({ text: body_type, count}, dataStore));
+ bodyTypeFilters.sort((a, b) => a.value.localeCompare(b.value));
+ bodyTypeFilters.forEach(body_type => {
+ bodyTypeContainer.appendChild(body_type.initCheckbox());
+ // body_type.subscribe(m=> iniBodyTypeContainer(m))
+ });
+}
+
+function createTransmissionList(vehicles){
+ const transmissionContainer = document.querySelector('.transmission-container');
+
+ transmissionContainer.innerHTML = '';
+
+ const transmission = vehicles.reduce((acc, vehicle) => {
+ const { transmission_type } = vehicle;
+ acc[transmission_type] = (acc[transmission_type] || 0) + 1;
+ return acc;
+ }, {});
+
+ filterManager.resetList('transmission_type');
+ transmissionFilters = Object.entries(transmission).map(([transmission_type, count]) => filterManager.createTransmissionFilter({ text: transmission_type, count}, dataStore));
+ transmissionFilters.sort((a, b) => a.value.localeCompare(b.value));
+ transmissionFilters.forEach(transmission => {
+ transmissionContainer.appendChild(transmission.initCheckbox());
+ });
+}
+
+function createExteriorList(vehicles){
+ console.log(vehicles);
+ const exteriorContainer = document.querySelector('.exterior-color');
+ exteriorContainer.innerHTML = '';
+ const exterior = vehicles.reduce((acc, vehicle) => {
+ const { exterior_color } = vehicle;
+ acc[exterior_color] = (acc[exterior_color] || 0) + 1;
+ return acc;
+ }, {});
+ filterManager.resetList('exterior_color');
+
+ exteriorFilters = Object.entries(exterior).map(([exterior_color, count]) => filterManager.createExteriorFilter({ text: exterior_color, count}, dataStore));
+ exteriorFilters.sort((a, b) => a.value.localeCompare(b.value));
+
+ exteriorFilters.forEach(exterior => {
+ exteriorContainer.appendChild(exterior.initCheckbox());
+ });
+}
+
+
+function initModelContainer(make){
+ let list = [...new Set(filterManager.makeFilters.filter(m=>m.checked == true).map(m=>m.models).flat())];
+
+ const modelContainer = document.querySelector('.model-container');
+ if (list.length === 0) {
+ modelContainer.innerHTML = 'Please Select a Make
';
+ } else if (list && list.length > 0) {
+ modelContainer.innerHTML = '';
+ list.sort((a, b) => a.value.localeCompare(b.value));
+ list.forEach(model => {
+ modelContainer.appendChild(model.initCheckbox());
+ });
+ } else {
+ modelContainer.innerHTML = 'No models available
';
+ }
+}
+
+function initTrimContainer(model){
+ let list = [...new Set(filterManager.modelFilters.filter(m=>m.checked == true).map(m=>m.trims).flat())];
+
+ // const uniqueArray = [...new Set(array)];
+ const trimContainer = document.querySelector('.trim-container');
+
+ if (list.length === 0) {
+ trimContainer.innerHTML = 'Please Select a Model
';
+ } else if (list && list.length > 0) {
+ trimContainer.innerHTML = '';
+ list.sort((a, b) => a.value.localeCompare(b.value));
+ list.forEach(trim => {
+ trimContainer.appendChild(trim.initCheckbox());
+ });
+ } else {
+ trimContainer.innerHTML = 'No trims available
';
+ }
}
function fetchAvailableModels(vehicles, make) {
- const filteredModels = vehicles
- .filter((vehicle) => vehicle.make === make)
- .map((vehicle) => vehicle.model);
- // Count occurrences of each model
- const modelCounts = filteredModels.reduce((acc, model) => {
- acc[model] = (acc[model] || 0) + 1;
- return acc;
- }, {});
+ const filteredModels = vehicles
+ .filter(vehicle => vehicle.make === make)
+ .map(vehicle => vehicle.model);
+ // Count occurrences of each model
+ const modelCounts = filteredModels.reduce((acc, model) => {
+ acc[model] = (acc[model] || 0) + 1;
+ return acc;
+ }, {});
- // Convert to an array of objects
- const modelsArray = Object.entries(modelCounts).map(([model, count]) => ({
- model,
- count,
- }));
- modelsArray.map((m) => (m['trims'] = fetchAvailableTrim(vehicles, m.model)));
- return modelsArray;
+ // Convert to an array of objects
+ const modelsArray = Object.entries(modelCounts).map(([model, count]) => ({ model, count }));
+ modelsArray.map(m=>m['trims'] = fetchAvailableTrim(vehicles, m.model))
+ return modelsArray;
}
-function fetchAvailableTrim(vehicles, modelName) {
- const filteredVehicles = vehicles.filter(
- (vehicle) => vehicle.model === modelName
- );
- const trimCount = filteredVehicles.reduce((result, vehicle) => {
- vehicle.trim.forEach((trim) => {
- const existingTrim = result.find((item) => item.text === trim);
- if (existingTrim) {
- existingTrim.count += 1;
- } else {
- result.push({ text: trim, count: 1 });
- }
- });
- return result;
- }, []);
- return trimCount;
+function fetchAvailableTrim(vehicles, modelName){
+ const filteredVehicles = vehicles.filter(vehicle => vehicle.model === modelName);
+ const trimCount = filteredVehicles.reduce((result, vehicle) => {
+ vehicle.trim.forEach(trim => {
+ const existingTrim = result.find(item => item.text === trim);
+ if (existingTrim) {
+ existingTrim.count += 1;
+ } else {
+ result.push({ text: trim, count: 1 });
+ }
+ });
+ return result;
+ }, []);
+ return trimCount;
}
-function updateModel(models) {
- console.log('updateModel', models);
+function updateModel(models){
+ console.log('updateModel', models)
}
+
+
function debounce(func, delay) {
- let timeout;
- return function () {
- const context = this;
- const args = arguments;
- clearTimeout(timeout);
- timeout = setTimeout(() => func.apply(context, args), delay);
- };
+ let timeout;
+ return function () {
+ const context = this;
+ const args = arguments;
+ clearTimeout(timeout);
+ timeout = setTimeout(() => func.apply(context, args), delay);
+ };
}
function updatePrice() {
- const min = price.getValueStart();
- const max = price.getValue();
- const formattedMin = '$' + min.toLocaleString();
- const formattedMax = '$' + max.toLocaleString();
- document.getElementById(
- 'priceRange'
- ).textContent = `${formattedMin} to ${formattedMax}`;
- debouncedSendReq();
+ const min = price.getValueStart();
+ const max = price.getValue();
+ const formattedMin = '$' + min.toLocaleString();
+ const formattedMax = '$' + max.toLocaleString();
+ document.getElementById('priceRange').textContent = `${formattedMin} to ${formattedMax}`;
+ debouncedSendReq();
}
function updateYear() {
- const min = year.getValueStart();
- const max = year.getValue();
- document.getElementById('yearRange').textContent = `${min} to ${max}`;
- debouncedSendReq();
+ const min = year.getValueStart();
+ const max = year.getValue();
+ document.getElementById('yearRange').textContent = `${min} to ${max}`;
+ debouncedSendReq();
}
function updateMileage() {
- const min = kilometres.getValueStart();
- const max = kilometres.getValue();
- document.getElementById('KilometresRange').textContent = `${min} to ${max}`;
- debouncedSendReq();
+ const min = kilometres.getValueStart();
+ const max = kilometres.getValue();
+ document.getElementById('KilometresRange').textContent = `${min} to ${max}`;
+ debouncedSendReq();
}
// Create debounced versions of sendReq
const debouncedSendReq = debounce(sendReq, 300);
function createSkeletonCard() {
- const skeletonCard = document.createElement('div');
- skeletonCard.classList.add(
- 'bg-red-200',
- 'rounded-lg',
- 'shadow-md',
- 'animate-pulse'
- );
-
- const innerHTML = `
+ const skeletonCard = document.createElement('div');
+ skeletonCard.classList.add('bg-red-200', 'rounded-lg', 'shadow-md', 'animate-pulse');
+
+ const innerHTML = `
@@ -342,23 +309,18 @@ function createSkeletonCard() {
`;
+
+ skeletonCard.innerHTML = innerHTML;
+
+ return skeletonCard;
+ }
- skeletonCard.innerHTML = innerHTML;
-
- return skeletonCard;
-}
function createSkeletonListItem() {
- const listItem = document.createElement('li');
- listItem.classList.add(
- 'w-full',
- 'bg-custom-red',
- 'rounded-lg',
- 'shadow-md',
- 'animate-pulse'
- );
+ const listItem = document.createElement('li');
+ listItem.classList.add('w-full', 'bg-custom-red', 'rounded-lg', 'shadow-md', 'animate-pulse');
- const innerHTML = `
+ const innerHTML = `
@@ -366,7 +328,7 @@ function createSkeletonListItem() {
`;
- listItem.innerHTML = innerHTML;
+ listItem.innerHTML = innerHTML;
- return listItem;
-}
+ return listItem;
+}
\ No newline at end of file
diff --git a/autocart_assets/templates/autocart-results.php b/autocart_assets/templates/autocart-results.php
index aabd59d..cba0a96 100644
--- a/autocart_assets/templates/autocart-results.php
+++ b/autocart_assets/templates/autocart-results.php
@@ -34,6 +34,8 @@ $response = get_transient("autocart_response");