メインコンテンツまでスキップ

BEM

1. BEM là gì?

BEM cũng giống FLOCSS được dùng để quy định tên class trong CSS.
Tuy nhiên nó là 1 quy chế khác, có thể kết hợp với FLOCSS để làm cho source code thêm phong phú.
BEM là chữ viết tắt của Block, Element, Modifier.

2. Tại sao dùng BEM?

Ví dụ .image.text là các lớp mà chúng ta thường sử dụng.
Khi sử dụng các lớp phổ biến như .image.text, rất có khả năng phần bạn đã tạo sẽ bị ảnh hưởng bởi các phong cách do người khác (ở các phần khác) tạo ra trước đó.
BEM là một phương pháp để CSS không bị ảnh hưởng hoặc trùng lặp, giảm thời gian suy nghĩ tên class, làm việc thống nhất theo nhóm.
Điều này tốt cho việc phát triển dự án.

3. Sử dụng BEM như thế nào?

Trên đây là một ví dụ tổng quan.
Bạn sẽ thấy có 2 khối giống nhau nên ta coi đây là một component (tên lớp phải bắt đầu bằng tiền tố c-).

  • Tên class cho block là c-imgtxt
  • Trong block c-imgtxt có 2 phần tử con, tên class của chúng phải kế thừa tên lớp từ c-imgtxt theo cấu trúc: c-imgtxt__***, ví dụ: c-imgtxt__imagec-imgtxt__text
  • Block 2 chỉ khác block 1 ở màu chữ, để chỉnh sửa định dạng màu chữ cho block 2, ta thêm class mới ngang hàng với class c-imgtxt__text nơi cần sửa đổi.
    Có thể hiểu định dạng của lớp mới này ghi đè lên định dạng của lớp c-imgtxt__text cũ, tên lớp này mới phải kế thừa tên lớp c-imgtxt__text theo cấu trúc: c-imgtxt__text--***, ví dụ: c-imgtxt__text--red

Tên class theo quy tắc BEM bao gồm ba loại:

  1. Block (là một thực thể độc lập có ý nghĩa riêng), ví dụ: c-imgtxt trong ví dụ tổng quan.
  2. Element (là phần tử con của phần tử Block), ví dụ: c-imgtxt__img, c-imgtxt__text trong ví dụ tổng quan.
  3. Modifier (là hình thức, hành vi hoặc trạng thái của Block/Element), ví dụ: c-imgtxt__text--red trong ví dụ tổng quan.

3.1. Block

Ví dụ trên có một block có viền bao quanh, bên trái là img, bên phải là text
=> Coi nó là một block và đặt tên class cho nó, ví dụ: .c-sample (tiền tố c- của flocss).

Quy tắc đặt tên cho BlockHTMLCSS
Tên block có thể bao gồm các chữ cái Latinh, chữ số và dấu gạch ngang. Để tạo một lớp CSS, có thể thêm tiền tố flocss(c-, p-...) vào tên class:
.block, .c-block
Bất kỳ nút DOM nào cũng có thể là một block.
<div class="block">...</div>
- Chỉ sử dụng bộ chọn tên class
- Không dùng tên thẻ hoặc id
- Không phụ thuộc vào các block/element khác trên cùng trang
.block { color: #042; }

3.2. Element

Trong block c-sample có 2 thành phần con là imgtext, nên tên lớp của chúng phải kế thừa tên lớp c-sample theo cấu trúc: c-sample__***, ví dụ: c-sample__img, c-sample__text

Quy tắc đặt tên cho ElementHTMLCSS
Tên element có thể bao gồm các chữ cái Latin, chữ số, dấu gạch ngang và dấu gạch dưới. Lớp CSS được hình thành dưới dạng tên block cộng với hai dấu gạch dưới cộng với tên element: .block__elemBất kỳ nút DOM nào trong một block đều có thể là một element
<div class="block">...<span class="block__elem"></span></div>
- Chỉ sử dụng bộ chọn tên class
- Không dùng tên thẻ hoặc id
- Không phụ thuộc vào các block/element khác trên cùng trang
Good
.block__elem {color: #042;}
Bad
.block .block__elem { color: #042; } div.block__elem { color: #042; }

3.3 Modifier

Tiêu đề DummyDummy chỉ có chút khác biệt về màu sắc của đường viền bên trái.
Vì vậy, chúng ta sẽ tạo các class anh em của class gốc c-title1 để sửa đổi màu của đường viền bên trái.
Class anh em sẽ được tạo ra theo cấu trúc c-title1--***, ví dụ: c-title1--yellow, c-title1--red.
Style của những class mới này sẽ được ghi đè lên style cũ.

Quy tắc đặt tên cho ModifierHTMLCSS
Modifier có thể bao gồm các chữ cái Latin, chữ số, dấu gạch ngang và dấu gạch dưới.
Lớp CSS được hình thành dưới dạng tên của block/element cộng với hai dấu gạch ngang: .block--mod, .block__elem--mod.
Dấu cách trong các từ bổ nghĩa phức tạp được thay thế bằng dấu gạch ngang: .block--color-black, .block__elem--color-red.
Modifier là một tên class bổ sung mà bạn thêm vào nút DOM block/element. Chỉ thêm các lớp modifier vào các block/element cần sửa đổi và giữ nguyên lớp ban đầu:
Good
<div class="block block--mod">…</div><div class="block block--size-big block--shadow-yes">...</div>
Bad
<div class="block--mod">…</div>
Modifier cho block:
.block--hidden { }
Để thay đổi các element dựa trên modifier cấp block:
.block--mod .block__elem { }
Modifier cho element:
.block__elem--mod { }

3.4. Common mistake

<!--Ví dụ đặt tên Class-->
<div class="c-sample">
<div class="c-sample__img">
<img class="c-sample__img__img1" alt="img" src="/">
</div>
<div class="c-sample__text">
<p class="c-sample__text__text1">title title title</p>
</div>
</div>

Đính kèm Class vào tất cả các thẻ.
Cách đặt tên này vẫn dùng được, nhưng với mục đích bảo trì và sửa chữa trang web, bạn chỉ nên đính kèm các Class vào các thẻ cần thiết.

<!--Ví dụ đặt tên sai cách-->
<div class="c-list">
<div class="c-list__card">
<div class="c-list__card__info"> <!--Sai-->
<div class="c-list__card__info__img"> <!--Sai-->
<img alt="img" src="/">
</div>
<div class="c-list__card__info__text"> <!--Sai-->
title title title
</div>
</div>
</div>
</div>

<!--Ví dụ đặt tên đúng cách-->
<div class="c-list">
<div class="c-list__card">
<div class="c-list__info">
<div class="c-list__img">
<img alt="img" src="/">
</div>
<div class="c-list__text">
title title title
</div>
</div>
</div>
</div>

Lưu ý

  • Không cần đặt tên tất cả các Class con có kèm theo Class chính.
  • Tránh đặt tên Class quá dài và đặt tên lồng nhiều Class cha.