Product filtering (filter)

Verze:

22. 09. 2022

Zodpovědná osoba:

Dominik Šlechta

Latte / Html

{form filter}

    <div class="filter">

        <div class="filter__content --content --flex">

            <div class="filter__toggler js--toggler button button--brand" data-target="#filterWrap">{$web['FILTER_TOGGLER']}</div>

            <div class="filter__box --flex" id="filterWrap">
                <div class="filter__label">{$web['FILTER_BY_PRICE']}</div>

                <div n:class="'filter__item filter__item--price', ('cena'|expand) ? 'filter__item--expanded'">
                    <div class="filter__value filter__value--left"
                         id="priceSlider-left">
                        <input id="priceSlider_input_from" class="filter__input" value="{$minMaxValues['cena_min']}"><span
                                id="priceSlider_left_unit">{$web["JS_CONFIG_CURRENCY"]|noescape}</span>
                    </div>
                    <div id="priceSlider"></div>
                    <div class="filter__value filter__value--right"
                         id="priceSlider-right">
                        <input id="priceSlider_input_to" class="filter__input" value="{$minMaxValues['cena_max']}"><span
                                id="priceSlider_right_unit">{$web["JS_CONFIG_CURRENCY"]|noescape}</span>
                    </div>
                </div>


                <div class="filter__nav --flex-inline">
                    <span class="filter__label">{$web['FILTER_SORT_BY']}</span>

                    <ul class="filter__tabs tabs tabs--big">
                        <li class="tabs__item {$ord == 'doporucene' || $ord == NULL ? 'tabs__item--selected'}">
                            <a class="tabs__link" href="{link sortingRecommended}" data-tab="1">{$web['FILTER_BY_RECOMMENDED']}</a>
                        </li>
                        <li class="tabs__item {$ord == 'nejlevnejsi' ? 'tabs__item--selected'}">
                            <a class="tabs__link" href="{link sortingCheap}" data-tab="2">{$web['FILTER_BY_LOWEST_PRICE']}</a>
                        </li>
                        <li class="tabs__item {$ord == 'nejdrazsi' ? 'tabs__item--selected'}">
                            <a class="tabs__link" href="{link sortingExpensive}" data-tab="3">{$web['FILTER_BY_HIGHEST_PRICE']}</a>
                        </li>
                    </ul>
                </div>

            </div>






            <div class="--hide">
                {foreach $form->components as $component}
                    {if ($component instanceof Nette\Forms\Container) === false && $component->getOption('autoset') === true}
                        {input $component}
                    {/if}
                {/foreach}

                {input ord}
                {input send}
            </div>
        </div>
    </div>

{/form}

CSS / SCSS

/* Filter */

.filter {
	background: $color__gray-light;
	
	
	/* Plugin part */
	
	.noUi-connect {
		background: #32404E;
	}
	
	.noUi-horizontal {
		height: 8px;
	}
	
	.noUi-target {
		background: $color__gray;
		border-radius: 0px;
		border: none;
		width: 300px;
		max-width: 100%;
		margin: 0 17px;
	}
	
	.noUi-handle {
		width: 20px;
		height: 20px;
		background: $color__primary;
		position: absolute;
		border: none;
		border-radius: 50%;
		box-shadow: none;
		left: 20px;
		
		&::before, &::after {
			content: none;
		}
	}
}

.filter__item {
	display: flex;
	align-items: center;
	
	margin: 10px 0px;
	
	@include media($large) {
		margin: 10px 30px;
	}
}


.filter__toggler {
	display: flex;
	width: 100%;
	@include media($large) {
		display: none;
	}
}


.filter__box {
	max-height: 0px;
	overflow: hidden;
	transition: max-height 0.3s ease-in-out;
	overflow-x: auto;
	@include media($large) {
		max-height: none;
		display: flex;
	}
}


.filter__value {
	width: 105px;
	height: 45px;
	display: flex;
	align-items: center;
	justify-content: center;
	background: #fff;
	border: 2px solid $color__gray;
	font-size: 1.5rem;
	padding: 5px 10px;
}

.filter__input {
	min-width: 0px;
	max-width: 100%;
	font-size: 1.5rem;
	text-align: right;
}


.filter__tabs {
	margin-left: auto;
}

.filter__nav {
	
	
	@include media($large) {
		margin-left: auto;
	}
}

.filter__label {
	font-size: 1.8rem;
	padding: 10px 0;
	display: flex;
	justify-content: space-between;
	align-items: center;
	cursor: pointer;
	
	margin-right: 15px;
	
}

JavaScript - js-filter-settings.latte

In addition to this setup, you also need to have a sliderInit.js file in webpack.mix.js

document.addEventListener('DOMContentLoaded', function () {

        /* Price slider */

        if (document.getElementById("priceSlider") !== null) {
            createSlider('priceSlider', 'slider_cena_min', 'slider_cena_max', 'cena_min', 'cena_max', '{$web["JS_CONFIG_CURRENCY"]|noescape}', _currency);
        }

        document.querySelectorAll(".js--onchange-submit").forEach((item) => {
            item.addEventListener('change', function (e) {
                document.getElementById('filter_submit').click();
            })
        })

    });