Strona główna / Wiedza / Blog / Jak tworzyć galerie filtrów (masonry)
Porady

Jak tworzyć galerie filtrów (masonry)

Tomek BoguckiTomek BoguckiSEO APP Developer 09.09.2026 14 min czytania
Grafika wpisu icomSEO: Jak tworzyć galerie filtrów (masonry) (Porady)

Masonry to technika układu, która pozwala elementom o różnych wysokościach układać się jak cegły w murze, wypełniając luki bez sztywnych rzędów. Dzięki temu galerie wyglądają naturalnie i mieszczą więcej treści na tej samej przestrzeni. W tym przewodniku krok po kroku zbudujesz elastyczną galerię z przyciskami filtrowania kategorii, działającą szybko, dostępnie i bez bolesnych niespodzianek przy rozbudowie. Pokażę wariant bez bibliotek oraz wariant z popularnymi narzędziami.

Fundamenty galerii filtrów i układów masonry

Jak działa układ kaskadowy w praktyce

Idea jest prosta: elementy o rozmaitej wysokości układają się kolumnami, bez wymuszania równej wysokości wierszy. Różnica względem tradycyjnej siatki polega na tym, że najbliższa wolna przestrzeń pod danym kafelkiem zostaje wypełniona kolejnym elementem. To sprawia, że wrażenie wizualne jest lekkie, a powierzchnia ekranu wykorzystana maksymalnie.

Technicznie można to osiągnąć kilkoma sposobami: układem kolumnowym (CSS columns), siatką grid z obliczaniem rozpiętości wierszy skryptem, albo dedykowaną biblioteką działającą jak silnik układu. Wybór zależy od potrzeb interakcji, zgodności przeglądarek oraz budżetu utrzymaniowego projektu.

Jeśli zdjęcia doczytują się z opóźnieniem, warto pamiętać o mechanizmach, które po załadowaniu obrazka wymuszą ponowne ułożenie kafelków. Bez tego mogą powstawać dziury, bo początkowo przeglądarka nie zna rzeczywistej wysokości elementów.

Kiedy wybrać masonry, a kiedy równe wiersze

Układ kaskadowy najlepiej sprawdza się, gdy treści mają zróżnicowaną wysokość: portfolio fotograficzne, moodboardy, katalogi inspiracji. Gdy priorytetem jest czytelna kolumna tekstu lub równa siatka kart produktowych, klasyczny układ o stałej wysokości bywa bardziej przewidywalny i prostszy do kontrolowania.

W praktyce warto zadać sobie pytania:

  • Czy wysokość elementów jest mocno różna i zmienna w czasie (np. opisy, dynamiczne tagi)?
  • Czy potrzebne są animacje podczas filtrowania i sortowania?
  • Czy krytyczna jest wydajność na urządzeniach mobilnych?
  • Jakie są oczekiwania względem SEO, dostępności i zgodności z przeglądarkami?

Projekt danych: kategorie, tagi i metadane

Filtrowanie opiera się o system klasyfikacji. Najprościej przyjąć schemat: każdy element ma jedną lub wiele kategorii (np. natura, architektura, ludzie), przechowywanych jako klasy lub atrybuty danych. Przyciski filtrów wskazują, którą kategorię wyświetlić, a logika ukrywa pozostałe.

Warto od razu zdecydować, czy potrzebujemy jednego filtra naraz, czy kombinacji wielu (AND/OR). Jednowymiarowe filtrowanie jest prostsze i tańsze wydajnościowo, ale wielowymiarowe (np. kategoria + kolor + format) zwiększa elastyczność, kosztem złożoności implementacji i testów.

Dobrym nawykiem jest opisanie danych atrybutami: data-category, data-tags, data-date. To ułatwia sortowanie i filtrację bez konieczności parsowania tekstów. Z góry zaplanuj także fallback: co pokazujemy, gdy filtr nie zwróci żadnego elementu (np. komunikat i przycisk reset).

Struktura HTML i style bazowe bez bibliotek

Minimalny szkielet znacznika

Podstawowy układ zawiera pasek filtrów i kontener galerii. Pasek ma przyciski (li lub button), każdy z atrybutem data-filter. Kontener galerii zawiera elementy (np. article lub div), każdy z klasami i/lub atrybutami data opisującymi kategorię. Wpisz wyraźne etykiety tekstowe dla przycisków: to ułatwia zrozumienie i wspiera dostępność.

Dla elementów galerii przygotuj wewnętrzną strukturę: obrazek, tytuł, krótką notkę, ewentualnie tagi. Upewnij się, że obrazy mają określone wymiary (atrybuty width i height lub style), by ograniczyć przeskoki układu podczas ładowania.

Style bazowe i przygotowanie zmiennych

Ustal system odstępów i kolory zapisywane jako zmienne (np. w preprocesorze lub na poziomie root). Zdefiniuj styl przycisków z dwoma stanami: aktywny i nieaktywny. Elementy ukryte przez filtr otrzymają klasę visually-hidden lub style display: none: ważne, aby sposób ukrycia był spójny z mechanizmem przebudowy układu.

Jeśli zależy Ci na lekkiej implementacji, zastosuj cienie i zaokrąglenia subtelnie. Zbyt wiele dekoracji potrafi zaburzyć wizualny rytm kafelków i obniża szybkość renderowania, szczególnie przy dużej liczbie elementów.

Układ kolumnowy bez skryptu (CSS columns)

Najłatwiejszy wariant bez dodatkowych bibliotek to kolumny: kontenerowi ustawiasz wielokolumnowy układ, a elementy „spływają” jedna pod drugą. Zaletą jest prostota, wadą: ograniczona kontrola kolejności czy animacji podczas filtrowania. Ponadto elementy rozkładają się w pierwszej kolejności kolumnami, co może skutkować nieintuicyjnym porządkiem przy czytnikach ekranu.

Stosując kolumny, pamiętaj o odstępach między elementami (column-gap) i o tym, by każdy kafelek miał wewnętrzne marginesy. W filtrach ustaw przełączanie klas ukrywających elementy; przeglądarka sama „zawija” sąsiednie, jednak nie zawsze da się uzyskać płynną animację.

Siatka grid z obliczaniem rozpiętości

Jeśli chcesz większej kontroli, użyj siatki i sztuczki z automatycznym wierszem jako jednostką wysokości. Każdemu elementowi przypisujesz rozpiętość wierszy na podstawie jego wysokości mierzonej skryptem. Dzięki temu osiągasz pełen efekt masonry z precyzyjnymi przerwami i przewidywalną kolejnością źródła. To rozwiązanie bywa stabilniejsze wizualnie i lepiej współgra z filtrami, bo to Ty decydujesz o przebudowie układu.

Pamiętaj, aby trzymać stały rytm kolumn (np. 2–5 w zależności od szerokości ekranu) i spójny gutter. Siatka dobrze wspiera responsywne przełamania, w których zmieniasz liczbę kolumn.

Responsywne dopasowanie i odstępy

Ustal punkty przełamań, w których zmienia się liczba kolumn: na małych ekranach 1–2, na średnich 3, na szerokich 4–6. Rozważ dynamiczne skalowanie odstępów, aby na gęstych układach nie „połknąć” zbyt wiele przestrzeni. Zachowaj czytelną hierarchię i trzymanie baseline’u w opisach, aby uniknąć „pływającego” wrażenia.

W kontekście obrazów zastosuj techniki oszczędzające transfer: formaty nowej generacji (AVIF, WebP) i srcset dla różnych gęstości pikseli. To wspiera responsywność i skraca czas do pełnego wyrenderowania.

Stany interakcji filtrów

Przyciski filtrów powinny mieć wyraźny stan: aktywny (podświetlenie, pogrubienie), hover i focus. Dla spójności wprowadź klasę is-active dodawaną do aktualnego filtra. Dla użytkowników klawiatury zadbaj o widoczny focus ring. Gdy filtr nic nie zwróci, pokaż komunikat oraz element resetujący filtr, aby nie „uwięzić” użytkownika w pustym stanie.

Filtry i interakcja: czysty JavaScript

Atrybuty danych i logika filtrowania

Najprościej działać na atrybutach data. Każdy kafelek ma data-category z listą wartości rozdzielonych spacją. Przycisk filtra ma data-filter określający pojedynczą kategorię albo specjalną wartość all. Kliknięcie porównuje filtr z listą kategorii w elemencie i przełącza stan widoczności. Dla wielokrotnego wyboru przechowuj aktywne filtry w tablicy i przeliczaj dopasowanie w logice AND lub OR.

Warto trzymać referencje do elementów galerii i filtrów, aby unikać kosztownych selektorów w pętli. Dodawaj lub usuwaj klasy kontrolujące widoczność bez dotykania stylów inline: czystsze i prostsze do nadpisania.

Przebudowa układu po filtrze

Po każdej zmianie widoczności trzeba odświeżyć układ, aby uniknąć luk. Jeśli używasz wariantu kolumnowego, przeglądarka zwykle poradzi sobie sama. Jeśli korzystasz z siatki z wyliczaniem rozpiętości, wywołaj funkcję obliczającą wysokość i przypisz odpowiedni span. Dobrze jest dodać opóźnienie rzędu kilkunastu milisekund po załadowaniu obrazów (lub nasłuch na zdarzenie). Dzięki temu unikniesz migotania i niepotrzebnych przebudów.

Unikaj reflow w pętli: mierz rozmiary zbiorczo, a style zapisuj partiami. Rozważ requestAnimationFrame przy animacjach i throttle/debounce przy zdarzeniach przewijania i zmiany rozmiaru okna. To znacząco poprawia optymalizacja i płynność działania.

Lazy loading i obserwacja wczytywania

Obrazy oznacz atrybutem loading=lazy oraz rozważ Intersection Observer do doładowywania treści w momencie, gdy zbliżają się do widoku. Po doczytaniu obrazu zaktualizuj obliczoną wysokość i odśwież układ. Warto też zapewnić rezerwę miejsca stosunkiem szerokości do wysokości, żeby galeria nie „podskakiwała”.

Dla długich list dodaj paginację lub nieskończone przewijanie. Pamiętaj jednak o możliwości powrotu do poprzedniego miejsca (zachowanie scrolla i filtrów w adresie, np. poprzez parametry zapytania), tak aby użytkownik mógł udostępnić link do konkretnego widoku.

Klawiatura, ARIA i czytelność

Przyciski filtrów powinny być elementami nativnymi (button), a nie pseudo-linkami bez roli. Dodaj atrybut aria-pressed dla stanów włącz/wyłącz. Obszar wyników warto poprzedzić „żywym regionem” informującym o liczbie trafień: użytkownicy czytników ekranu zyskają natychmiastową informację zwrotną. Rozważ skróty klawiaturowe do szybkiego przełączania kategorii, ale tylko jako uzupełnienie, nie zamiast standardowej nawigacji.

Zadbaj o kontrast tekstu, odpowiednią wysokość linii i rozmiar tap targetów. Struktura DOM powinna odzwierciedlać logikę: filtry, potem wyniki. Nie mieszaj porządku wizualnego z kolejnością w źródle bez ważnej potrzeby.

Wariant z bibliotekami: Masonry i Isotope

Kiedy sięgnąć po sprawdzone narzędzia

Biblioteki rozwiązują skomplikowane przypadki: animowane przejścia, inteligentne rozmieszczanie, przeliczanie wymiarów po załadowaniu obrazów. Jeśli chcesz szybko mieć dopracowane efekty, to dobry wybór. W zamian akceptujesz dodatkowy ciężar skryptów i pewien narzut na utrzymanie.

Popularne wybory to klasyczny silnik masonry albo pakiet, który łączy układ i filtrowanie, jak Isotope. Dają płynne animacje, sortowanie i bogate API do finezyjnego sterowania zachowaniem poszczególnych elementów.

Włączanie i inicjalizacja

W praktyce podłączasz skrypty z CDN lub paczki i inicjalizujesz na kontenerze galerii. Określasz selektor elementów, odstępy, liczbę kolumn i opcje animacji. Przy ładowaniu obrazów dodaj pomocnika, który po zakończeniu dociągania wymusi relayout. Następnie definiujesz callbacki dla zdarzeń filtrów i sortowania.

Jeżeli korzystasz z bundlera, rozważ podział kodu i ładowanie warunkowe: galeria to element ciężki, więc dobrze, by reszta strony nie czekała, jeśli użytkownik nie wchodzi w sekcję z kafelkami. To prosta droga do poprawy metryk wydajnościowych.

Obsługa filtrów i sortowania

W bibliotekach filtr to zwykle przekazanie funkcji testującej element lub podanie selektora CSS dopasowującego daną kategorię. Sortowanie może bazować na tekście tytułu, dacie, rozmiarze miniatury lub niestandardowej metryce. Zachowaj konsekwentny język: jeżeli przycisk mówi „Najnowsze”, zadbaj, aby sortowanie faktycznie opierało się na dacie publikacji, a nie na przypadkowym atrybucie.

Pamiętaj, by aktualny stan (filtr, sortowanie) odzwierciedlić wizualnie i w adresie. Dzięki temu użytkownik odświeży stronę lub wklei link i trafi do tego samego widoku.

Wydajność, pamięć i adaptacja

Przy dużych zbiorach elementów animacje mogą być kosztowne. Wtedy rozważ wyłączanie przejść przy masowych zmianach, a włączanie tylko przy pojedynczych interakcjach. Przechowuj referencje do instancji biblioteki i niszcz je tam, gdzie sekcja znika (np. w nawigacji SPA), aby uniknąć wycieków pamięci. Zwróć uwagę na wymiary obrazów: zmniejszaj je do sensownych rozmiarów miniatur.

Dodaj monitorowanie błędów i metryk. Jeśli zauważysz spadki klatek podczas przewijania, sprawdź, czy nie robisz nadmiernych obliczeń w handlerach zdarzeń. Często ratunkiem jest proste throttle i mniejsza liczba przeliczeń na sekundę.

Testowanie, utrzymanie i jakość

Plan testów funkcjonalnych

Przygotuj listę scenariuszy: przełączanie pojedynczego filtra, kombinacja filtrów, powrót do widoku „Wszystkie”, sortowanie rosnące i malejące, puste wyniki, zniknięcie i pojawienie się nowych elementów, zachowanie po zmianie rozmiaru okna. Do każdego scenariusza dopisz oczekiwane rezultaty, by łatwiej odtwarzać i diagnozować błędy.

W testach mobilnych sprawdź dotyk, przewijanie i momenty przypadkowych tapnięć. Symuluj słabe łącze i małą ilość pamięci urządzenia. To tam najczęściej wychodzą na jaw realne problemy użytkowników.

Jakość wizualna i ruch

Animacje powinny być lekkie: krótkie, przewidywalne i użyteczne. Zamiast przesadnych transformacji lepiej delikatnie zmienić położenie i krycie elementów. Wspieraj redukcję ruchu: gdy system użytkownika zgłasza prefers-reduced-motion, przełącz na prostsze przejścia lub całkowicie je wyłącz. Zachowaj spójność prędkości i krzywych easingu.

Przetestuj kontrasty i czytelność miniatur przy różnych tłach. Zadbaj o warianty dla trybu ciemnego: rozważ inne obramowania i cienie, aby uniknąć zlewających się krawędzi.

Dostępność i semantyka

Używaj poprawnych elementów interfejsu: rzeczywiste przyciski, listy dla grup filtrów, nagłówki sekcji. Dodaj aria-controls i aria-live tam, gdzie to ma sens. Upewnij się, że kolejność focusu odzwierciedla kolejność wizualną, a skróty klawiaturowe nie kolidują z systemowymi.

Teksty alternatywne obrazów powinny mówić, co jest na zdjęciu, a nie powtarzać tytuł kolekcji. Jeżeli obraz pełni funkcję dekoracyjną, oznacz go jako takie, by czytniki ekranu nie traciły czasu na zbędne informacje. To realnie poprawia dostępność interfejsu.

Wydajność i metryki

Monitoruj koszt renderowania: ilość węzłów DOM, czas layoutu i malowania. Zadbaj o minimalną liczbę warstw z akceleracją i rozsądne użycie cieni. Przy ogromnych listach rozważ wirtualizację, czyli renderowanie jedynie widocznych elementów. W statycznych generatorach stron uprzednio buduj układy i kompresuj zasoby.

Na etapie CI ustaw lintery i proste testy E2E: kliknięcie filtrów, oczekiwanie na przeliczenie układu, asercja liczby widocznych kafelków. Automatyzacja wychwyci regresje, zanim trafią na produkcję.

Praktyczny plan wdrożenia krok po kroku

Planowanie i makieta

Najpierw zaprojektuj, ile kolumn chcesz na kluczowych rozdzielczościach, jakie odstępy między kafelkami i gdzie pojawi się panel filtrów. Ustal listę kategorii, nazwy przycisków i zachowanie trybu „Wszystkie”. Zrób prostą makietę z 10–15 przykładowymi elementami o różnych wysokościach, aby wcześnie zweryfikować rytm i hierarchię wizualną.

Uzgodnij z zespołem nazewnictwo klas i atrybutów, by uniknąć chaosu w czasie rozbudowy. Dobrym pomysłem jest prefiks dla modułu, np. gal-, aby nazwy nie zderzały się z innymi komponentami na stronie.

Implementacja HTML i stylów

Stwórz pasek filtrów z przyciskami i atrybutami data-filter. Dodaj kontener galerii i kafelki z data-category zawierającymi listę kategorii. Zaimplementuj układ: wybierz kolumny dla prostoty lub siatkę z rozpiętością wierszy dla większej kontroli. Ustal odstępy i stany interakcji. Przygotuj klasy utility: hidden, is-active, is-animating, aby spójnie zarządzać stanami.

Dodaj obrazom atrybuty rozmiarów i formaty wielorozdzielczościowe. Zadbaj o podpisy, aby kontekst był zrozumiały nawet bez obrazka. Włącz mechanizmy oszczędzania transferu i przygotuj się na wolne sieci.

Logika filtrów i przebudowa

Załóż słuchacze kliknięć na przyciskach filtrów. Po aktywacji określ, które kafelki spełniają warunek, dodaj/usuń klasę ukrywającą i wywołaj przebudowę układu. Dla sortowania zastosuj porównywanie wartości atrybutów i przełączanie kolejności w DOM albo wsparcie biblioteki, jeśli ją wdrożysz.

Przy pierwszym uruchomieniu zmierz wysokości elementów i zapisz wynik. Po każdym załadowaniu obrazka przelicz wysokość i zaktualizuj rozpiętość wierszy. Zmiany grupuj, aby uniknąć migotania i przeciążeń. Pamiętaj o obsłudze resetu filtrów i o komunikacie „Brak wyników”.

Wariant z bibliotekami

Jeśli wybierasz biblioteki, zainicjalizuj układ, podpinając się pod gotowe zdarzenia i API. Podłącz przyciski filtrów, podstawiając selektory kategorii. Dla sortowania zdefiniuj własne klucze na podstawie atrybutów. Włącz tryb bez animacji dla masowych zmian, a w pozostałych przypadkach korzystaj z subtelnych przejść.

Regularnie testuj na realnych urządzeniach. W razie problemów z płynnością zmniejsz liczbę elementów na stronę, zoptymalizuj obrazy, wyłącz zbędne dekoracje i sprawdź, które operacje najczęściej wymuszają kosztowny reflow.

Utrzymanie i rozwój

Zadbaj o dokumentację komponentu: schemat klas, dostępne atrybuty, przykładowe konfiguracje. Dodaj checklistę publikacyjną: zoptymalizowane grafiki, aktualne zależności, testy filtrów i sortowania, walidacja dostępności. Przy kolejnych iteracjach trzymaj się zasad semantyki i modularności, aby unikać efektu „kuli śnieżnej”.

Wyznacz budżet wydajnościowy: maksymalny rozmiar JS i stylów, limity liczby elementów renderowanych jednocześnie. Pomiary i raporty automatyzuj: tylko wtedy utrzymasz stabilną jakość w dłuższym horyzoncie.

Najczęstsze pułapki i jak ich uniknąć

  • Niespójne dane kategorii: ujednolicaj nazwy i testuj case-sensitivity.
  • Brak miejsca rezerwowego dla obrazów: zawsze ustaw proporcje, by nie psuć układu.
  • „Skaczące” animacje: stosuj transform i opacity zamiast kosztownych właściwości układu.
  • Nieczytelny stan aktywnego filtra: wyraźna wizualna informacja to podstawa.
  • Przegrzanie CPU na mobilnych: throttle/debounce i mądre planowanie przebudów.
  • Zapominanie o czytnikach ekranu: semantyka, aria-pressed, live regiony.

Podsumowując wybór narzędzi: prostsze projekty wygrywają na minimalizmie i czystych stylach. Bardziej złożone aplikacje docenią gotowe API i animacje bibliotek, o ile kontrolujesz koszt skryptów i dbasz o CSS zgodny z ich wymaganiami. W obu podejściach kluczem jest przewidywalna logika filtry, czysty DOM oraz świadome wykorzystanie JavaScript tak, by zachować równowagę między efektem wizualnym a realnymi potrzebami użytkownika.

Masz podobny problem na swojej stronie?

Podaj adres strony i e-mail. Sprawdzimy ją bezpłatnie i odpiszemy z konkretnymi wnioskami.

Administratorem danych jest icomSEO Sp. z o.o. z siedzibą w Lublinie. Dane przetwarzamy, aby odpowiedzieć na zgłoszenie. Więcej w Polityce prywatności.

Tomek Bogucki
O autorze

Tomek Bogucki

SEO APP Developer · 964 artykuły

Tomek Bogucki tworzy treści dla bloga icomSEO: praktyczne poradniki o SEO, reklamie i marketingu internetowym.

Podobne artykuły

Współpraca, która napędza sukces

Zadzwoń