(function($, document, window, viewport) {
    'use strict';

    // PLUGIN CLASS
    // ============
    const AjaxFilterPluginClass = {

        replacedContainerSelector: '.et-product-list-filter-collapse-content-mobile',
        applyFilterButtonsSelector: '.et-ajax-filter-apply',
        directLinkParentSelectors: '.et-product-list-filter-sort, .et-product-list-filter-productsperpage, .et-product-list-filter-layout',

        /**
         * @this {PluginBase & AjaxFilterPluginClass}
         * @param {HTMLElement} element
         * @param {Object} options
         */
        init: function(element, options) {
            /**
             * How Ajax Filter works:
             * - Render the regular filters.
             * - Prevent any links from actually navigating
             * - Instead call those links via AJAX request (with parameter etAjaxFilter=1, which will result in a reduced DOM being returned)
             * - From that result DOM extract the new filters + apply filters button.
             * - On click on the apply filters button, the actual navigation happens (to the last clicked filter URL)
             * - Price filters work differently - they are triggered from within evo.redirectToNewPriceRange
             */
            if(this.$el.hasClass('et-ajax-filter-initialized')) {
                return;
            }
            this.registerPriceFilterFunction();
            this.$el.addClass('et-ajax-filter-initialized');
            this.$el.find('.et-product-list-filter-wrapper').on('click', 'a:not(.et-ajax-filter-apply)', {}, (event) => {
                // Safety to only do anything if the apply filters button is visible
                let $applyFiltersButton = this.$el.find(this.applyFilterButtonsSelector);
                if(!$applyFiltersButton.length || !$applyFiltersButton.is(':visible')) {
                    return;
                }
                let $target = $(event.target);
                if($target.parents(this.directLinkParentSelectors).length) {
                    // Never prevent links for sorting, products per page, layout, etc.
                    return;
                }
                event.preventDefault(); // stop default navigation
                let url = $target.closest('a').attr('href');
                this.updateFromUrl(url, $applyFiltersButton);
            });
        },

        updateFromUrl: function(url, $button) {
            let $targetContainer = this.$el.find(this.replacedContainerSelector);
            $button.addClass('et-ajax-filter-loading disabled');
            $button.prop('disabled', true);
            fetch(url, {
                method: "POST",
                headers: {
                    'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8'
                },
                body: 'etAjaxFilter=1&isAjax=1'
            }).then((response) => {
                response.text().then((result) => {
                    let $result = $(result);
                    let $newFilters = $result.find(this.replacedContainerSelector);
                    $targetContainer.replaceWith($newFilters);
                    $.evo.initPriceSlider($targetContainer, false);
                });
            });
        },

        registerPriceFilterFunction: function() {
            /*
             * Depending on the current display status, this function either redirects the user to the target url or updates these filters with the given URL.
             * It is used by evo.redirectToNewPriceRange, if it exists.
             */
            window.etUpdatePriceFilterUrl = (url) => {
                let $applyFiltersButton = this.$el.find(this.applyFilterButtonsSelector);
                if(!$applyFiltersButton.length || !$applyFiltersButton.is(':visible')) {
                    // Trigger default behavior
                    window.location.href = url;
                } else {
                    // Use our own logic
                    this.updateFromUrl(url, $applyFiltersButton);
                }
            }
        }
    };

    // REGISTER AND ADD THE PLUGIN
    // ===========================
    if (!window.easytemplate && !window.easytemplate.PluginManager) {
        throw Error('Cannot initialize Easytemplate Plugin. plugin-manager.js has to be loaded first!');
    }

    /** @type {PluginManager} manager */
    const manager = window.easytemplate.PluginManager;
    manager.addPlugin('[data-et-ajax-filter]', AjaxFilterPluginClass, 'etAjaxFilterPlugin');

    // Re-Init on content load (i.e. pagination)
    $(document).on('evo:loaded.evo.content', () => {
        let $ajaxFilterWrapper = $('[data-et-ajax-filter]');
        if(!$ajaxFilterWrapper.hasClass('et-ajax-filter-initialized')) {
            manager.reinitialize('etAjaxFilterPlugin');
        }
    });
})(jQuery, document, window, ResponsiveBootstrapToolkit);