Styling Komponen — React

React komponen-based, tapi CSS sifatnya GLOBAL secara default — class .btn di file A bisa nabrak class .btn di file B. Perang specificity, override…

Ada dua cara dasar memberi gaya ke komponen React: className, yang menunjuk ke class di file CSS, dan style, yang menerima object JavaScript berisi gaya untuk satu elemen. Bayangin lemari baju. className itu menyebut nama setelan yang sudah disiapkan di lemari (file CSS): "pakai setelan badge-success". style itu menempelkan satu detail langsung ke satu baju, tanpa lewat lemari. Dan karena komponen itu function, kamu bisa memilih setelannya dari prop, kayak memilih baju sesuai cuaca.

🧪 Tebakan cepat: di JSX kamu menulis <div style="color: red">Halo</div>, persis seperti di HTML. Teksnya jadi merah, atau React menolak? Tebak dulu, jawabannya ada di bagian "Inline style: object, bukan string".

className, bukan class

Di HTML kamu menulis class="...". Di JSX, atributnya className, karena class adalah kata kunci JavaScript untuk membuat class.

/* Badge.css */
.badge-success { background: #dcfce7; color: #166534; }
.badge-error   { background: #fee2e2; color: #991b1b; }
import "./Badge.css"

function App() {
  return <span className="badge-success">Berhasil</span>
}

Inline style: object, bukan string

function App() {
  return (
    <div id="box" style={{ backgroundColor: "skyblue", padding: "20px" }}>
      Kotak Biru
    </div>
  )
}
Di file CSS Di style={{ }}
background-color: skyblue; backgroundColor: "skyblue"
padding: 20px; padding: "20px"
font-size: 24px; fontSize: "24px"
color: red; color: "red"

Kalau style diberi string seperti style="color: red", React menolak merender dan melempar error: style harus berupa object, bukan string. Itu jawaban tebakannya. Versi yang benar: style={{ color: "red" }}.

Kelas yang berubah sesuai prop

function Badge({ type, children }) {
  return (
    <span className={type === "success" ? "badge-success" : "badge-error"}>
      {children}
    </span>
  )
}

function App() {
  return <Badge type="success">Berhasil</Badge>
}

Hasil render-nya: <span class="badge-success">Berhasil</span>, hijau. Ganti jadi type="error", dan hasilnya <span class="badge-error">, merah.

Kalau ada bagian class yang tetap, gabungkan dengan template literal: className={`badge ${aktif ? "badge-aktif" : ""}`}.

📌 Cara lain di project besar

Class di file CSS biasa berlaku global: .badge di dua file berbeda bisa saling timpa. Dua cara populer mengatasinya, dan dua-duanya tetap lewat className:

⚠️ Jebakan yang sering ketemu

TL;DR: Di JSX, atribut class ditulis className, dan class-nya didefinisikan di file CSS. Inline style adalah object di dalam kurung kurawal ganda: style={{ backgroundColor: "skyblue", padding: "20px" }}, nama properti camelCase, nilai string dengan satuan, bukan string CSS seperti "color: red" (React melempar error). Class yang bergantung prop dihitung dengan ekspresi: className={type === "success" ? "badge-success" : "badge-error"}. Inline style gak bisa :hover atau @media, jadi gaya seperti itu masuk class. Project besar sering memakai CSS Modules atau Tailwind, tetap lewat className.

Yang akan kamu pelajari