cssresponsifcontainer-queriesMahir6 mnt baca

Container Queries

Responsif berbasis lebar komponen, bukan layar: @container dan container-type.

Masalah yang diselesaikan

Media query merespons lebar layar. Tapi komponen yang sama bisa tampil di tempat berbeda: kartu produk di sidebar sempit vs di konten lebar. Dengan media query, kartu tidak tahu ia sedang sempit atau lebar, ia hanya tahu ukuran layar. Hasilnya: kartu di sidebar 300px tetap memakai gaya desktop karena layarnya 1400px.

Container queries menyelesaikan ini: komponen merespons lebar wadahnya sendiri.

Menyiapkan container

Langkah 1: daftarkan wadah sebagai container.

css
.daftar-produk {
  container-type: inline-size; /* jadilah container! */
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
  gap: 16px;
}

Langkah 2: tulis query terhadap container, bukan viewport.

css
/* Kartu tahu lebar wadahnya sendiri */
@container (max-width: 400px) {
  .kartu {
    flex-direction: column;
    text-align: center;
  }
}

Contoh lengkap: kartu adaptif

css
/* Wadah kartu = container */
.pembungkus-kartu {
  container-type: inline-size;
}

/* Dasar: kartu horizontal (untuk wadah lebar) */
.kartu {
  display: flex;
  gap: 16px;
  padding: 16px;
  border: 1px solid #e2e8f0;
  border-radius: 12px;
}

.kartu img {
  width: 120px;
  height: 120px;
  object-fit: cover;
  border-radius: 8px;
}

/* Kalau wadahnya sempit: kartu vertikal */
@container (max-width: 420px) {
  .kartu {
    flex-direction: column;
  }

  .kartu img {
    width: 100%;
    height: 180px;
  }
}

Kartu yang sama: horizontal di konten utama (lebar), vertikal di sidebar (sempit). Tanpa JavaScript, tanpa duplikasi class.

Kapan memakai container queries?

  • Design system / komponen reusable yang dipakai di banyak tempat.
  • Dashboard dengan panel yang bisa di-resize.
  • Sidebar vs konten utama.

Kapan tetap media query? Untuk perubahan level halaman (navigasi jadi hamburger, layout kolom jadi satu). Aturan praktis: halaman = media query, komponen = container query.

Catatan teknis: container-type: inline-size membuat lebar wadah tidak lagi dipengaruhi kontennya (size containment). Ini biasanya yang diinginkan, tapi waspadai bila wadah mengandalkan konten untuk menentukan ukuran. Dukungan browser: semua modern sejak 2023.

Tips profesional

  • Beri nama container bila ada lebih dari satu: container-name: kartu; lalu @container kartu (max-width: 400px).
  • Container queries + web components = komponen yang benar-benar mandiri.
  • Jangan sarangkan container terlalu dalam; satu-dua level cukup.

Pola siap salin: kartu dua mode

css
.pembungkus { container-type: inline-size; }

.kartu {
  display: grid;
  grid-template-columns: 120px 1fr;
  gap: 16px;
}

@container (max-width: 380px) {
  .kartu { grid-template-columns: 1fr; }
  .kartu img { height: 160px; }
}

Kartu horizontal di ruang lebar, vertikal di ruang sempit. Satu komponen, dua penampilan, nol JavaScript.

Rangkuman

Container queries = media query untuk komponen: container-type: inline-size pada wadah, @container (kondisi) untuk aturan. Komponen reusable yang cerdas tanpa JavaScript.

Live Playground
export default function App(): JSX.Element {
  return <h1>Hello world</h1>
}

Edit kode di kiri, preview kanan ter-update otomatis.

Tantangan

Buktikan Container Query

Container query adalah fitur yang membedakan komponen biasa dari komponen cerdas. Pahami dengan eksperimen langsung.

Di playground:

  1. Amati: kartu di sidebar sempit otomatis vertikal, kartu di konten lebar tetap horizontal, padahal layarnya sama. Tulis di komentar kenapa media query tidak bisa melakukan ini.
  2. Ubah breakpoint container dari 300px menjadi 500px, amati kartu mana yang berubah.
  3. Coba hapus container-type: inline-size, amati query berhenti bekerja. Jelaskan di komentar kenapa baris itu wajib.
<!doctype html>
<html>
<head>
<meta charset="utf-8" />
<link rel="stylesheet" href="styles.css" />
</head>
<body>
<h1>Halo CSS</h1>
<p>Edit styles.css dan lihat hasilnya.</p>
</body>
</html>