Apa fungsi z-index
Saat elemen saling tumpang tindih, z-index menentukan mana yang digambar di depan. Angka yang lebih tinggi menang. Property ini berfungsi pada elemen yang diposisikan (position apa pun selain static) dan pada item flex dan grid:
Tanpa z-index, elemen yang muncul belakangan di HTML digambar di atas elemen sebelumnya, jadi C akan menutupi B dan B akan menutupi A. Nilai z-index membalik urutan itu: A berada paling depan, lalu C, lalu B.
Nilai
| Nilai | Arti |
|---|---|
auto (default) | Ditumpuk di level 0 bersama saudara-saudaranya, dan tidak membuat stacking context |
0 | Level 0, tetapi membuat stacking context |
| Bilangan bulat positif | Di depan nilai yang lebih rendah |
| Bilangan bulat negatif | Di belakang level 0, dan di belakang isi elemen induk kalau elemen induk itu yang membentuk stacking context |
Hanya bilangan bulat yang valid: z-index: 1.5 diabaikan.
Kenapa z-index 9999 bisa kalah: stacking context
Nilai z-index tidak dibandingkan di seluruh halaman. Elemen dikelompokkan ke dalam stacking context, dan z-index hanya mengurutkan elemen di dalam context yang sama. Context itu sendiri kemudian ditempatkan sebagai satu lapisan, memakai z-index dari elemen yang membuatnya.
Di bawah, dropdown biru punya z-index: 9999, tetapi berada di dalam header dengan z-index: 1. Banner hijau, saudara dari header itu, punya z-index: 2. Seluruh lapisan header, termasuk dropdown-nya, berada di bawah banner:
Tekan tombolnya. Dengan z-index: auto, header tidak lagi membentuk stacking context, jadi nilai 9999 milik dropdown dibandingkan langsung dengan nilai 2 milik banner, dan dropdown-nya maju ke depan. Menaikkan dropdown ke 99999 tidak akan pernah membantu.
Apa yang membuat stacking context
Salah satu dari hal-hal berikut mengubah elemen menjadi stacking context sendiri, yang mengurung z-index semua elemen di dalamnya:
| Property | Kondisi |
|---|---|
position: relative atau absolute | Dengan z-index selain auto |
position: fixed atau sticky | Selalu |
| Item flex atau grid | Dengan z-index selain auto |
opacity | Di bawah 1 |
transform, scale, rotate, translate | Nilai apa pun selain none |
filter, backdrop-filter | Nilai apa pun selain none |
isolation | isolate |
mix-blend-mode | Nilai apa pun selain normal |
will-change | Menyebutkan salah satu property di atas |
contain | layout atau paint (dan strict, content) |
Yang mengejutkan adalah opacity dan transform: menambahkan efek fade atau animasi hover pada elemen induk bisa tiba-tiba menaruh dropdown-nya di belakang bagian berikutnya.
z-index: 10 pada tooltip seharusnya menaruhnya di atas kolom berikutnya. Tetapi opacity: 0.99 membuat kolom pertama menjadi stacking context dengan z-index auto (level 0), dan kolom kedua muncul belakangan di HTML pada level yang sama, jadi kolom kedua digambar di atas seluruh kolom pertama, termasuk tooltip-nya. Hapus baris opacity, dan tooltip-nya kembali berada di depan.
z-index negatif
z-index negatif menaruh elemen di belakang saudara-saudaranya. Kalau elemen induknya tidak membentuk stacking context, elemen itu bahkan bisa pindah ke belakang background elemen induk, hal yang sering mengejutkan. isolation: isolate pada elemen induk membuat context tanpa efek visual lain dan menjaga child negatif tetap di dalamnya:
Tanpa isolation, bingkai kuning jatuh ke belakang background abu-abu milik tombol itu sendiri, jadi hanya tepinya yang terlihat. Dengan isolation: isolate, bingkainya tetap di dalam stacking context tombol: di atas background-nya, di bawah teksnya.
Skala z-index
Pilih beberapa lapisan bernama untuk seluruh situs, alih-alih terus menaikkan angka:
:root {
--z-dropdown: 10;
--z-sticky: 20;
--z-overlay: 30;
--z-modal: 40;
--z-toast: 50;
}
.modal { position: fixed; z-index: var(--z-modal); }
Sebagian besar bug lapisan adalah bug stacking context, bukan bug angka, jadi skala kecil ditambah isolation: isolate pada komponen yang memakai z-index di dalamnya sudah sangat membantu. z-index butuh pemosisian agar berfungsi, dan halaman position membahasnya.
Kesalahan yang sering terjadi
- z-index pada elemen static. Tambahkan
position: relative(atau jadikan elemen itu item flex atau grid). - Terus menaikkan sampai 9999. Kalau elemen induk membentuk stacking context di bawah elemen pesaingnya, nilai child berapa pun tidak bisa menang. Cari context-nya.
opacity,transform, ataufilterbaru pada elemen induk yang tiba-tiba mengurung dropdown-nya.- Nilai desimal.
z-index: 1.5tidak valid. - Mengira
z-index: 0danautoberperilaku sama.0membuat stacking context, sedangkanautotidak. - Modal di dalam komponen yang bertingkat dalam. Render modal di dekat akhir
<body>(atau pakai top layer milik elemen<dialog>), supaya tidak ada context ancestor yang bisa mengurungnya.
Pertanyaan yang sering diajukan
Apa fungsi z-index?
Property ini mengatur urutan tumpukan elemen yang saling tumpang tindih: nilai yang lebih tinggi digambar di depan nilai yang lebih rendah di dalam stacking context yang sama. Default-nya adalah auto, dan nilainya berupa bilangan bulat, termasuk bilangan negatif.
Kenapa z-index-ku tidak berfungsi?
Bisa karena elemennya tidak diposisikan (z-index butuh position selain static, atau elemen itu child flex atau grid), atau karena elemen itu berada di dalam elemen induk yang membentuk stacking context dengan urutan yang lebih rendah. Sebuah child tidak akan pernah bisa naik di atas elemen yang berada di atas stacking context-nya, berapa pun z-index miliknya sendiri.
Apa itu stacking context?
Sekelompok elemen yang ditumpuk bersama sebagai satu lapisan. Di dalamnya, child diurutkan berdasarkan z-index masing-masing. Di luarnya, seluruh kelompok ditempatkan berdasarkan z-index elemen yang membuatnya.
Apa yang membuat stacking context?
Di antaranya: elemen root, elemen terposisi dengan z-index selain auto, position: fixed atau sticky, child flex atau grid dengan z-index, opacity di bawah 1, transform, filter, isolation: isolate, dan will-change pada property-property tersebut.
Apakah z-index berfungsi tanpa position?
Tidak pada elemen blok atau inline biasa: position: static mengabaikannya. Tetapi z-index berfungsi pada item flex dan item grid tanpa position apa pun.