Сітка товарів з можливістю фільтрації

13

Від автора: макет чуйною сітки товарів з дружньою до сенсорних екранів галереєю на основі Flickity і функцією фільтрації на основі Isotope.

Сітка товарів з можливістю фільтрації

Сітка товарів з можливістю фільтраціїСітка товарів з можливістю фільтрації

Наш проект це чуйний макет сітки товарів на основі Isotope, де кожен елемент сітки це Flickity слайдер картинок. Товари, додані в кошик позначені маленької іконкою візки. Фільтр товарів працює на основі Isotope filter. Для того, щоб зробити макет адаптивним, застосовуються медіа запити. (Зверніть увагу, що IE9 не підтримує анімацію)

Використання Flickity від David DeSandro можливо за ліцензією GNU GPL license v3. Якщо ви плануєте використовувати даний ресурс у комерційних цілях, будь ласка, детально ознайомтеся з ліцензією Flickity.

HTML

Filter:
All
Jackets
Shirts
Dresses
Trousers
Shoes

Shopping cart
0

Сітка товарів з можливістю фільтрації

Сітка товарів з можливістю фільтрації
Сітка товарів з можливістю фільтрації
Сітка товарів з можливістю фільтрації

Miriam Classic

Miriam
$79

Add to cart

CSS

/* Сітка товарів */
.grid {
position: relative;
overflow: hidden;
max-width: 1300px;
margin: 0 auto;
padding: 1.5 em 0 8em;
text-align: center;
}
/* Завантажувач */
.grid__loader {
display: none;
margin: 3em auto 0;
}
.grid—loading .grid__loader {
display: block;
}
/* Clearfix */
.grid:after {
content: «;
display: block;
clear: both;
}
/* Grid елементи */
.grid__sizer,
.grid__item {
position: relative;
float: left;
width: 20%;
padding: .75em;
}
.no-touch .grid__sizer,
.no-touch .grid__item {
padding: .75em .75em 1.25 em;
}
.grid—loading .grid__item {
visibility: hidden;
}
.grid__item—size-a {
width: 40%;
}
/* Галерея */
.slider {
padding: 0;
border-radius: 5px;
background: #24252a;
}
.no-touch .slider {
padding: 0 0 1.25 em;
}
.slider__item {
width: 100%;
padding: 1em;
}
.slider__item img {
width: 100%;
}
/* Flickity точки сторінок */
.slider .flickity-page-dots {
bottom: 20px;
opacity: 0;
-webkit-transition: opacity .3s;
transition: opacity .3s;
}
.no-touch .slider:hover .flickity-page-dots {
opacity: 1;
}
.slider .flickity-page-dots .dot {
background: #131417;
}
/* мета інформація про товар */
.meta {
position: relative;
margin: 10px 0 0;
padding: 0 60px 0 0;
text-align: left;
}
.meta__brand {
font-size: .85em;
font-weight: bold;
display: block;
color: #595b64;
}
.meta__title {
font-size: .95em;
font-weight: bold;
margin: 0;
padding: .4em 0 .1em;
}
.meta__price {
font-size: .95em;
font-weight: bold;
position: absolute;
top: .45em;
right: .25em;
color: #595b64;
}
/* Стилі для кнопок/ * /
.action {
font-family: Avenir, ‘Helvetica Neue’, ‘Lato’, ‘Segoe UI’, Helvetica, Arial, sans-serif;
font-size: 1.05 em;
position: relative;
overflow: hidden;
margin: 0;
padding: .25em;
cursor: pointer;
color: #fff;
border: none;
background: none;
}
.action:focus {
outline: none;
}
.action—button {
color: #5c5edc;
}
.no-touch .action—button:hover {
color: #fff;
outline: none;
}
.text-hidden {
position: absolute;
top: 200%;
}
/* Кнопка додати в корзину */
.action—buy {
position: absolute;
top: 0;
right: 0;
padding: 1.85 em 2.35 em;
-webkit-transition: opacity .3s, -webkit-transform .3s;
transition: opacity .3s, transform .3s;
-webkit-transform: translate3d(-5px, 0, 0);
transform: translate3d(-5px, 0, 0);
}
.no-touch .action—buy {
opacity: 0;
}
.no-touch .grid__item:hover .action—buy {
opacity: 1;
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
/* Фіксована нижня панель */
.bar {
position: fixed;
z-index: 100;
bottom: 0;
left: 0;
width: 100%;
padding: 1.75 em 5em;
text-align: center;
background: #191a1b;
-webkit-transform: translate3d(0, 0, 0);
/* Fix for Chrome flicker on Mac …party like we’re in 2012! */
}
.flexbox .filter {
display: -webkit-flex;
display: flex;
-webkit-align-items: center;
align-items: center;
-webkit-justify-content: center;
justify-content: center;
}
/* Фільтр */
.filter__label {
font-size: .85em;
display: inline-block;
margin: 0 2%;
font-weight: bold;
color: #393A3F;
}
.filter__item {
font-weight: bold;
margin: 0 2%;
padding: .1em;
vertical-align: middle;
color: #a3a3b3;
border-bottom: 2px solid transparent;
}
.filter__item—selected {
color: #5c5edc;
border-color: #5c5edc;
}
.filter__item .icon {
font-size: 1.75 em;
display: none;
}
/* Кошик */
.cart {
font-size: 1.5 em;
position: absolute;
top: 0;
right: 0;
overflow: hidden;
height: 100%;
padding: 0 1.195 em;
cursor: pointer;
color: #abacae;
border: none;
background-color: #131415;
}
.no-touch .cart:focus,
.no-touch .cart:hover {
color: #fff;
outline: none;
}
.cart—animate .cart__icon {
-webkit-animation: cartAnim .4s forwards;
animation: cartAnim .4s forwards;
}
@-webkit-keyframes cartAnim {
50% {
opacity: 0;
-webkit-transform: translate3d(50px, 0, 0);
transform: translate3d(50px, 0, 0);
}
51% {
opacity: 0;
-webkit-transform: translate3d(-50px, 0, 0);
transform: translate3d(-50px, 0, 0);
}
100% {
opacity: 1;
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
}
@keyframes cartAnim {
50% {
opacity: 0;
-webkit-transform: translate3d(50px, 0, 0);
transform: translate3d(50px, 0, 0);
}
51% {
opacity: 0;
-webkit-transform: translate3d(-50px, 0, 0);
transform: translate3d(-50px, 0, 0);
}
100% {
opacity: 1;
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
}
.cart__count {
font-size: 9px;
font-weight: bold;
line-height: 15px;
position: absolute;
top: 50%;
right: 20px;
width: 15px;
height: 15px;
margin: -16px 0 0 0;
text-align: center;
color: #fff;
border-radius: 50%;
background: #5c5edc;
}
.cart—animate .cart__count {
-webkit-animation: countAnim .4s forwards;
animation: countAnim .4s forwards;
}
@-webkit-keyframes countAnim {
50% {
opacity: 0;
-webkit-transform: translate3d(0, 80px, 0);
transform: translate3d(0, 80px, 0);
}
51% {
opacity: 0;
-webkit-transform: translate3d(0, -80px, 0);
transform: translate3d(0, -80px, 0);
}
100% {
opacity: 1;
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
}
@keyframes countAnim {
50% {
opacity: 0;
-webkit-transform: translate3d(0, 80px, 0);
transform: translate3d(0, 80px, 0);
}
51% {
opacity: 0;
-webkit-transform: translate3d(0, -80px, 0);
transform: translate3d(0, -80px, 0);
}
100% {
opacity: 1;
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
}
/* Зміна розміру елементів, сітки на маленьких екранах */
@media screen and (max-width: 65em) {
.grid__sizer,
.grid__item,
.grid__item—size-a {
width: 33.333%;
}
}
@media screen and (max-width: 50em) {
.grid__sizer,
.grid__item,
.grid__item—size-a {
width: 50%;
}
.bar {
padding-left: 0;
text-align: left;
}
}
@media screen and (max-width: 40em) {
.bar {
padding: .5em 4.5 em .5em 0;
}
.flexbox .filter {
-webkit-justify-content: space-around;
justify-content: space-around;
}
.filter__item {
height: 100%;
padding: .5em .1em;
border: none;
}
.filter__item .icon {
display: inline-block;
}
.filter__label,
.action__text {
display: none;
}
.cart {
padding: 0 1em;
}
}
@media screen and (max-width: 25em) {
.grid {
max-width: 75%;
}
.grid__loader {
margin: 0 auto;
}
.grid__sizer,
.grid__item,
.grid__item—size-a {
width: 100%;
}
.action—buy {
font-size: 1.5 em;
padding: 1.15 em 1.5 em;
-webkit-tap-highlight-color: transparent;
}
}

JavaScript

/**
* main.js
* http://www.codrops.com
*
* Licensed under the MIT license.
* http://www.opensource.org/licenses/mit-license.php
*
* Copyright 2015, Codrops
* http://www.codrops.com
*/
;(function(window) {
‘use strict’;
var support = { animations : Modernizr.cssanimations },
animEndEventNames = { ‘WebkitAnimation’ : ‘webkitAnimationEnd’, ‘OAnimation’ : ‘oAnimationEnd’, ‘msAnimation’ : ‘MSAnimationEnd’, ‘animation’ : ‘animationend’ },
animEndEventName = animEndEventNames[ Modernizr.prefixed( ‘animation’ ) ],
onEndAnimation = function( el, callback ) {
var onEndCallbackFn = function( ev ) {
if( support.animations ) {
if( ev.target != this ) return;
this.removeEventListener( animEndEventName, onEndCallbackFn );
}
if( callback && typeof callback === ‘function’ ) { callback.call(); }
};
if( support.animations ) {
el.addEventListener. ( animEndEventName, onEndCallbackFn );
}
else {
onEndCallbackFn();
}
};
// Ресурс http://www.sberry.me/articles/javascript-event-throttling-debouncing
function throttle(fn, delay) {
var allowSample = true;
return function(e) {
if (allowSample) {
allowSample = false;
setTimeout(function() { allowSample = true; }, delay);
fn(e);
}
};
}
// слайдери — flickity
var sliders = [].slice.call(document.querySelectorAll(‘.slider’)),
// масив для збереження примірників flickity
flkties = [],
// grid елементи
grid = document.querySelector(‘.grid’),
// isotope об’єкт
iso,
// filter контролери
filterCtrls = [].slice.call(document.querySelectorAll(‘.filter > button’)),
// кошик
cart = document.querySelector(‘.cart’),
cartItems = cart.querySelector(‘.cart__count’);
function init() {
// предзагрузочные зображення
imagesLoaded(grid, function() {
initFlickity();
initIsotope();
initEvents();
classie.remove(grid, ‘grid—loading’);
});
}
function initFlickity() {
sliders.forEach(function(slider){
var flkty = new Flickity(slider, {
prevNextButtons: false,
wrapAround: true,
cellAlign: ‘left’,
contain: true,
resize: false
});
// збереження об’єктів flickity
flkties.push(flkty);
});
}
function initIsotope() {
iso = new Isotope( grid, {
isResizeBound: false,
itemSelector: ‘.grid__item’,
percentPosition: true,
masonry: {
// використовуємо зовнішню ширину grid-sizer для columnWidth
columnWidth: ‘.grid__sizer’
},
transitionDuration: ‘0.6 s’
});
}
function initEvents() {
filterCtrls.forEach(function(filterCtrl) {
filterCtrl.addEventListener. (‘click’, function() {
classie.remove(filterCtrl.parentNode.querySelector(‘.filter__item—selected’), ‘filter__item—selected’);
classie.add(filterCtrl, ‘filter__item—selected’);
iso.arrange({
filter: filterCtrl.getAttribute(‘data-filter’)
});
recalcFlickities();
iso.layout();
});
});
// зміна розміру вікна / перерахунок розмірів макетів flickity і isotope
window.addEventListener. (‘resize’, throttle(function(ev) {
recalcFlickities()
iso.layout();
}, 50));
// додати в кошик
[].slice.call(grid.querySelectorAll(‘.grid__item’)).forEach(function(item) {
item.querySelector(‘.action—buy’).addEventListener. (‘click’, addToCart);
});
}
function addToCart() {
classie.add(cart, ‘cart—animate’);
setTimeout(function() {cartItems.innerHTML = Number(cartItems.innerHTML) + 1;}, 200);
onEndAnimation(cartItems, function() {
classie.remove(cart, ‘cart—animate’);
});
}
function recalcFlickities() {
for(var i = 0, len = flkties.length; i < len; ++i) {
flkties.resize();
}
}
init();
})(window);

Подивитися проект на Github