dsg
Copy This
import {
    getDiscoverData
} from "./api/discover.js";
import store from "./store.js";

var $ = Dom7;

// let activeTab = \'all\';
let lastSearchText = \'\';
let controller; // To store the current AbortController

var searchResultsStore = store.getters.getSearchResults;

$(document).on(\'page:afterin\', \'.page[data-name="search"]\', async function (e) {
    $(\'#discover-search\').focus();
})

// event listener for tab change
$(document).on(\'click\', \'.discovery-wrap .tab-link\', async function (e) {
    const type = this.getAttribute(\'data-type\')
    activeTab = type
})

function debounce(func, delay) {
    let timer;
    return function (...args) {
        clearTimeout(timer);
        timer = setTimeout(() => func.apply(this, args), delay);
    };
}

function addLoaderToTabs() {
    const eventsContainer = document.querySelector(\'#events-results .list ul\');
    const usersContainer = document.querySelector(\'#users_vehicles-results .list ul\');
    const venuesContainer = document.querySelector(\'#venues-results .list ul\');
    const topContainer = document.querySelector(\'#top-results .list\');

    const loader = `
    <div style="padding-block: .5rem;">
        <div class="infinite-scroll-preloader">
            <div class="preloader"></div>
        </div>
    </div>`;

    eventsContainer.innerHTML = loader;
    usersContainer.innerHTML = loader;
    venuesContainer.innerHTML = loader;
    topContainer.innerHTML = loader;
}

const debouncedSearch = debounce(async function () {
    const search = $(this).val().trim();

    if (search.length < 3 || search === lastSearchText) {
        return;
    }

    lastSearchText = search;

    // Abort the previous request if it\'s still ongoing
    if (controller) {
        controller.abort();
    }

    // Create a new AbortController for the current request
    controller = new AbortController();
    const signal = controller.signal;

    addLoaderToTabs();
    try {
        const searchResults = await getDiscoverData(search, \'all\', 1, signal);
        store.dispatch(\'setSearchResults\', searchResults);
    } catch (error) {
        if (error.name === \'AbortError\') {
            console.log(\'Fetch aborted\');
        } else {
            console.error(\'Error fetching search results:\', error);
        }
    }
}, 300); // Adjust the delay (in milliseconds) as needed

$(document).on(\'change input paste\', \'#discover-search\', debouncedSearch);

// Function to render a list of items in the DOM
function renderList(container, items, renderItem) {
    container.innerHTML = \'\';

    const noResultsMessage = \'<li><strong>No results found</strong></li>\';

    if (!items || items.length === 0) {
        container.innerHTML = noResultsMessage;
        return;
    }

    // Render each item
    items.forEach(item => {
        const li = document.createElement(\'li\');
        li.innerHTML = renderItem(item);
        container.appendChild(li);
    });
}

// Function to render the search results
function renderSearchResults(searchResults) {
    const eventsContainer = document.querySelector(\'#events-results .list ul\');
    const usersContainer = document.querySelector(\'#users_vehicles-results .list ul\');
    const venuesContainer = document.querySelector(\'#venues-results .list ul\');
    const topContainer = document.querySelector(\'#top-results .list\');

    // Ensure containers are cleared before rendering
    eventsContainer.innerHTML = \'\';
    usersContainer.innerHTML = \'\';
    venuesContainer.innerHTML = \'\';
    topContainer.innerHTML = \'\';

    // Render events
    if (searchResults.events) {
        renderList(eventsContainer, searchResults.events.data, event => `
            <a class="item-link search-result item-content" href="/discover-view-event/${event.id}">
                <div class="item-media">
                    <div class="image-square image-rounded" style="background-image:url(\'${event.thumbnail}\')"></div>
                </div>
                <div class="item-inner">
                    <div class="item-title">${event.name}</div>
                </div>
            </a>
        `);
    }

    // Render users
    if (searchResults.users) {
        renderList(usersContainer, searchResults.users.data, (user) => {
            const userLink = user.type == \'user\' ? \'/profile-view/\' + user.id : \'/profile-garage-vehicle-view/\' + user.id;
            let contentText;

            if (user.type == \'user\') {
                contentText = `${user.name} (${user.username})`;
            }

            if (user.type == \'vehicle\') {
                contentText = `${user.name}\'s <b>${user.meta.make} ${user.meta.model}</b>`;
            }

            return `
                <a class="item-link search-result item-content" href="${userLink}">
                    <div class="item-media">
                        <div class="image-square image-rounded" style="background-image:url(\'${user.thumbnail || \'assets/img/profile-placeholder.jpg\'}\')"></div>
                    </div>
                    <div class="item-inner">
                        <div class="item-title">${contentText}</div>
                    </div>
                </a>`
        });
    }

    // Render venues
    if (searchResults.venues) {
        renderList(venuesContainer, searchResults.venues.data, venue => `
            <a class="item-link search-result item-content" href="/discover-view-venue/${venue.id}">
                <div class="item-media">
                    <div class="image-square image-rounded" style="background-image:url(\'${venue.thumbnail}\')"></div>
                </div>
                <div class="item-inner">
                    <div class="item-title">${venue.name} - ${venue.venue_location}</div>
                </div>
            </a>
        `);
    }

    // Render top results
    let hasTopResults = false;

    if (searchResults.top_results) {
        if (searchResults.top_results.events && searchResults.top_results.events.length > 0) {
            hasTopResults = true;
            const eventSubList = document.createElement(\'ul\');
            const heading = document.createElement(\'h2\');

            heading.innerHTML = \'Trending Events\';
            heading.classList.add(\'section-title\', \'mt-3\', \'mb-2\');
            topContainer.appendChild(heading);
            topContainer.appendChild(eventSubList);

            renderList(eventSubList, searchResults.top_results.events, event => `
                <a class="item-link search-result item-content" href="/discover-view-event/${event.id}">
                    <div class="item-media">
                        <div class="image-square image-rounded" style="background-image:url(\'${event.thumbnail}\')"></div>
                    </div>
                    <div class="item-inner">
                        <div class="item-title">${event.name}</div>
                    </div>
                </a>
            `);
        }

        if (searchResults.top_results.users && searchResults.top_results.users.length > 0) {
            hasTopResults = true;

            const userSubList = document.createElement(\'ul\');
            const heading = document.createElement(\'h2\');

            heading.innerHTML = \'Trending Users\';
            heading.classList.add(\'section-title\', \'mt-3\', \'mb-2\');
            topContainer.appendChild(heading);
            topContainer.appendChild(userSubList);

            renderList(userSubList, searchResults.top_results.users, (user) => {
                const userLink = user.type == \'user\' ? \'/profile-view/\' + user.id : \'/profile-garage-vehicle-view/\' + user.id;
                let contentText;

                if (user.type == \'user\') {
                    contentText = `${user.name} (${user.username})`;
                }

                if (user.type == \'vehicle\') {
                    contentText = `${user.name}\'s <b>${user.meta.make} ${user.meta.model}</b>`;
                }

                return `
                <a class="item-link search-result item-content" href="${userLink}">
                    <div class="item-media">
                        <div class="image-square image-rounded" style="background-image:url(\'${user.thumbnail || \'assets/img/profile-placeholder.jpg\'}\')"></div>
                    </div>
                    <div class="item-inner">
                        <div class="item-title">${contentText}</div>
                    </div>
                </a>`
            });
        }

        if (searchResults.top_results.venues && searchResults.top_results.venues.length > 0) {
            hasTopResults = true;

            const venueSubList = document.createElement(\'ul\');
            const heading = document.createElement(\'h2\');

            heading.innerHTML = \'Trending Venues\';
            heading.classList.add(\'section-title\', \'mt-3\', \'mb-2\');

            topContainer.appendChild(heading);
            topContainer.appendChild(venueSubList);

            renderList(venueSubList, searchResults.top_results.venues, venue => `
                <a class="item-link search-result item-content" href="/discover-view-venue/${venue.id}">
                    <div class="item-media">
                        <div class="image-square image-rounded" style="background-image:url(\'${venue.thumbnail}\')"></div>
                    </div>
                    <div class="item-inner">
                        <div class="item-title">${venue.name} - ${venue.venue_location}</div>
                    </div>
                </a>
            `);
        }
    }

    if (!hasTopResults) {
        topContainer.innerHTML = \'<div><strong>No top results found</strong></div>\';
    }
}

searchResultsStore.onUpdated((results) => {
    renderSearchResults(results);
});
Add JS Function Name