🤔
Split BEMというCSS設計を考えてみた。
修正 (2019/09/14)
--
はクラスの命名規約的に NG だったため Modifier のプレフィックスを-
に修正。
(合わせて Element のプレフィックスを_
に修正)
id 名/class 名に使用できる文字の種類
TL;DR
BEM のクラス名は冗長になりがちなので、html が読みづらくなる。
※さらにpostcss-nestingとも相性が良くない。。。
そこで、BEM の利点を活かしつつ html が読みやすくなるような CSS 設計を考えてみた。
そもそも BEM とは
・Block
:サイトを構成するパーツのこと
・Element
:Block
を構成するパーツの 1 つ 1 つのこと
・Modifier
:Block
とElement
のバリエーションや状態の変化のためのクラス
の 3 つの構成要素からなる CSS 設計手法のこと。
参考:BEM によるフロントエンドの設計 - 基本概念とルール | CodeGrid
BEM のデメリット
クラス名が冗長になりがちなため、html が読みづらい。。。(Block がネストされると尚更)
html
<!-- BEM -->
<div class="block--Modifier">
<div class="block__element"></div>
</div>
<div class="block">
<div class="block__element--Modifier"></div>
</div>
Split BEM
Block
, Element
, Modifier
の 3 つの構成要素の考え方は BEM と同じですが、クラス名が冗長にならないように、BEM をベースにクラスの命名規則とセレクタの指定方法を変更した。
Block
- BEM と同じ
html
<!-- BEM -->
<div class="block"></div>
<!-- Split BEM -->
<div class="block"></div>
css
/* BEM */
.block {}
/* Split BEM */
.block {}
Element
- クラス名のプレフィックスに
_
を付ける。 -
Block
の子要素となるようにする。 - 可能な限り子セレクタ
>
を使う。
html
<!-- BEM -->
<div class="block">
<div class="block__element"></div>
</div>
<!-- Split BEM -->
<div class="block">
<div class="_element"></div>
</div>
css
/* BEM */
.block__element {}
/* Split BEM */
.block > ._element {}
Modifier
- クラス名のプレフィックスに
-
を付ける。 -
Block
またはElement
とセットで使用する(Modifier クラス単体で使用しない。)
html
<!-- BEM -->
<div class="block--modifier">
<div class="block__element"></div>
</div>
<div class="block">
<div class="block__element--modifier"></div>
</div>
<!-- Split BEM -->
<div class="block --modifier">
<div class="_element"></div>
</div>
<div class="block">
<div class="_element -modifier"></div>
</div>
css
/* BEM */
.block--modifier {}
.block__element--modifier {}
/* Split BEM */
.block.-modifier {}
.block > ._element.-modifier {}
Example
html
<header class="header">
<div class="_inner">
<h1 class="_title">
Title
<h1>
<nav class="_menu menu">
<ul class="_list">
<li class="_item">
<a href="#" class="_link">メニュー1</a>
</li>
<li class="__item">
<a href="#" class="_link -outer">メニュー2</a>
</li>
</ul>
</nav>
</div>
</header>
css
.header {}
.header > ._inner {}
.header > ._inner > ._title {}
.header > ._inner > ._menu {}
.menu {}
.menu > ._list {}
.menu > ._list > ._item {}
.menu > ._list > ._item > ._link{}
.menu > ._list > ._item > ._link.-outer{}
まとめ
BEM に慣れた人が、Block
、Element
、Modifier
の考え方、命名のノウハウを活かしつつ可読性高くなるといいなと。
似たような設計にrscssがあるが、こっちはそれぞれの命名が BEM と違うので混乱しそう。
使ってみて規約の追加、修正があれば加筆してきます。
Discussion