Menu

z-index w CSS: kolejność warstw i stacking context

z-index decyduje, który z nachodzących na siebie elementów jest rysowany na wierzchu. Dowiedz się, na jakich elementach działa, jak konteksty nakładania grupują elementy tak, że z-index 9999 wciąż może przegrać, co tworzy kontekst nakładania i jak naprawić z-index, który nie działa.

Na tej stronie są działające edytory: edytuj, uruchamiaj i od razu zobacz wynik.

Co robi z-index

Gdy elementy na siebie nachodzą, z-index decyduje, który jest rysowany z przodu. Wygrywa wyższa liczba. Działa na elementach pozycjonowanych (dowolne position oprócz static) oraz na elementach flex i grid:

Bez z-index elementy występujące później w HTML są rysowane na wcześniejszych, więc C zakryłby B, a B zakryłby A. Wartości z-index odwracają tę kolejność: A jest z przodu, potem C, potem B.

Wartości

WartośćZnaczenie
auto (domyślna)Układany na poziomie 0 razem z rodzeństwem, nie tworzy kontekstu nakładania
0Poziom 0, ale tworzy kontekst nakładania
Dodatnia liczba całkowitaPrzed niższymi wartościami
Ujemna liczba całkowitaZa poziomem 0, a także za treścią rodzica, jeśli to rodzic tworzy kontekst nakładania

Prawidłowe są tylko liczby całkowite: z-index: 1.5 jest ignorowane.

Dlaczego z-index 9999 może przegrać: konteksty nakładania

Wartości z-index nie są porównywane w obrębie całej strony. Elementy są grupowane w konteksty nakładania (stacking contexts), a z-index ustala kolejność tylko wewnątrz tego samego kontekstu. Sam kontekst jest potem umieszczany jako jedna warstwa, według z-index elementu, który go utworzył.

Poniżej niebieskie menu rozwijane ma z-index: 9999, ale znajduje się w nagłówku z z-index: 1. Zielony baner, rodzeństwo tego nagłówka, ma z-index: 2. Cała warstwa nagłówka, razem z menu, leży pod banerem:

Kliknij przycisk. Przy z-index: auto nagłówek przestaje tworzyć kontekst nakładania, więc 9999 menu jest porównywane bezpośrednio z 2 banera i menu wychodzi na wierzch. Podniesienie menu do 99999 nigdy by nie pomogło.

Co tworzy kontekst nakładania

Każda z tych właściwości zamienia element we własny kontekst nakładania, zamykając w nim z-index wszystkiego, co jest w środku:

WłaściwośćWarunek
position: relative lub absoluteZ z-index innym niż auto
position: fixed lub stickyZawsze
Element flex lub gridZ z-index innym niż auto
opacityMniejsze niż 1
transform, scale, rotate, translateDowolna wartość inna niż none
filter, backdrop-filterDowolna wartość inna niż none
isolationisolate
mix-blend-modeDowolna wartość inna niż normal
will-changeGdy wskazuje którąś z powyższych właściwości
containlayout lub paint (oraz strict, content)

Zaskakujące są opacity i transform: dodanie rodzicowi efektu zanikania albo animacji przy najechaniu może nagle schować jego menu rozwijane za następną sekcję.

z-index: 10 tooltipa powinien umieścić go nad następną kolumną. Ale opacity: 0.99 robi z pierwszej kolumny kontekst nakładania z z-index auto (poziom 0), a druga kolumna występuje później w HTML na tym samym poziomie, więc jest malowana na całej pierwszej kolumnie, razem z tooltipem. Usuń linię z opacity, a tooltip znów będzie z przodu.

Ujemny z-index

Ujemny z-index umieszcza element za jego rodzeństwem. Jeśli rodzic nie tworzy kontekstu nakładania, element może trafić nawet za tło rodzica, co często zaskakuje. isolation: isolate na rodzicu tworzy kontekst bez żadnego innego efektu wizualnego i zatrzymuje ujemne dziecko w środku:

Bez isolation bursztynowa ramka spada za szare tło samego przycisku, więc widać tylko jej krawędź. Z isolation: isolate ramka zostaje w kontekście nakładania przycisku: nad jego tłem, pod jego tekstem.

Skala z-index

Zamiast podbijać liczby, wybierz kilka nazwanych warstw dla całej strony:

:root {
  --z-dropdown: 10;
  --z-sticky: 20;
  --z-overlay: 30;
  --z-modal: 40;
  --z-toast: 50;
}
.modal { position: fixed; z-index: var(--z-modal); }

Większość błędów z warstwami to błędy kontekstów nakładania, a nie liczb, więc mała skala plus isolation: isolate na komponentach, które wewnętrznie używają z-index, rozwiązuje bardzo wiele. z-index potrzebuje pozycjonowania, żeby działać; strona o position to omawia.

Częste błędy

  • z-index na elemencie static. Dodaj position: relative (albo zrób z niego element flex lub grid).
  • Podbijanie do 9999. Jeśli rodzic tworzy kontekst nakładania poniżej konkurenta, żadna wartość dziecka nie wygra. Znajdź ten kontekst.
  • Nowe opacity, transform lub filter na rodzicu, które nagle zamyka w nim menu rozwijane.
  • Wartości dziesiętne. z-index: 1.5 jest nieprawidłowe.
  • Oczekiwanie, że z-index: 0 i auto działają tak samo. 0 tworzy kontekst nakładania; auto nie.
  • Okna modalne w głęboko zagnieżdżonych komponentach. Renderuj je blisko końca <body> (albo użyj górnej warstwy elementu <dialog>), żeby żaden kontekst przodka nie mógł ich uwięzić.

Najczęściej zadawane pytania

Co robi z-index?

Ustala kolejność nakładania elementów, które na siebie nachodzą: wyższa wartość jest rysowana przed niższą w obrębie tego samego kontekstu nakładania. Wartość domyślna to auto, a wartości są liczbami całkowitymi, także ujemnymi.

Dlaczego mój z-index nie działa?

Albo element nie jest pozycjonowany (z-index wymaga position innego niż static albo elementu flex lub grid), albo znajduje się w rodzicu, który tworzy kontekst nakładania o niższej kolejności. Dziecko nigdy nie wzniesie się ponad element, pod którym leży jego kontekst nakładania, bez względu na własny z-index.

Co to jest kontekst nakładania (stacking context)?

Grupa elementów nakładanych razem jako jedna warstwa. Wewnątrz niej dzieci są ułożone według swojego z-index; na zewnątrz cała grupa jest umieszczana według z-index elementu, który ją utworzył.

Co tworzy kontekst nakładania?

Między innymi: element główny, element pozycjonowany z z-index innym niż auto, position: fixed lub sticky, element flex lub grid z z-index, opacity mniejsze niż 1, transform, filter, isolation: isolate oraz will-change wskazujące te właściwości.

Czy z-index działa bez position?

Nie na zwykłych elementach blokowych i inline: position: static go ignoruje. Działa natomiast na elementach flex i grid bez żadnego position.

Ilustracja języków programowania w Coddy

Ucz się programowania z Coddy

ZACZNIJ