Every Declaration Just Onceの例

同じ定義は書かないCSSの簡単な例とその書き方に対する覚え書きを残しておく。同じ定義を書かないようにしていくと、CSSプリプロセッサーはおろか、セレクターのネストもなくて良いのかと感じてくる。もしかするとCSSの着地点はここなのかと洗脳されつつある。もはや第三者の目で見ることができなくなったので、他の人の意見も聞いてみたい。

.foo {
  border: 1px solid red;
  margin: 0 auto;
  width: 40rem;
}

.bar {
  border: 1px solid green;
  margin: 0 auto;
  width: 40rem;
}

.baz {
  border: 1px solid blue;
  margin: 0 auto;
  width: 40rem;
}

このような共通する定義を持つセレクターは以下のように書かれる。

.foo,
.bar,
.baz {
  margin: 0 auto;
}

.foo,
.bar,
.baz {
  width: 40rem;
}

.foo {
  border: 1px solid red;
}

.bar {
  border: 1px solid green;
}

.baz {
  border: 1px solid blue;
}

まずは定義ごとというのがポイントだ。

.foo,
.bar,
.baz {
  margin: 0 auto;
}

.foo,
.bar,
.baz {
  width: 40rem;
}

このようにまとめられそうなブロックでもあえて分割する。そうしておくことによって、後にmargin: 0 autoだけ使うクラスを追加したい時に分割し直す手間が省ける。こういった後のメンテナンス性を考えた場合、先頭に定義をわかりやすくしたクラスを追加するのも悪くなかった。

.centering,
.foo,
.bar,
.baz {
  margin: 0 auto;
}

こうしておくと,\n\.fooで置換を行えるようになる。しかし使いもしないセレクターが書かれているのは無駄が多い気がしたのでやめてしまった。ただし、そのブロックがどういう定義のためのブロックなのかをわかりやすくできるので、すこし規模が大きくなると助かるかもしれない。その場合は後にツールで削除してやると良さそうだ。

またどこまで定義を分けるかというのもちょっと悩む。例えばborderショートカット・プロパティーなどだ。上記例だと以下のようにも書くことができ、定義をなるべく重複しないようにとするとこのように書くべきようにも思える。

.foo,
.bar,
.baz {
  border-style: solid;
}

.foo,
.bar,
.baz {
  border-width: 1px;
}

.foo {
  border-color: red;
}

.bar {
  border-color: green;
}

.baz {
  border-color: blue;
}

さすがに冗長すぎる印象だ。どこまで分割するかの線引きはもうちょっと考える必要があるだろう。


この書き方は、今まで良い解とされていたOOCSSのようなアプローチとは真逆で、悪いアプローチとされていた物理的な装飾を基準としたアプローチに近い。そのためOOCSSどっぷりだった人達には違和感しかない。

作業としては、どのような装飾を加えるか決まったら、そのプロパティー等で検索し、既にあったらそこにセレクターを追加、なかったらブロックを追加と、非常に単純化されたものだけで済む。ルールそのものが単純なこと、書き方の説明としても簡単で済むこと、間違えて重複する定義を追加しても致命的ではないこと、差分がわかりやすいことなど開発中の利点は多い。

一方でコンポーネント単位での確認というような地道な作業、つまりテストとは相性が悪い。逆に言うと定義ごとに分けることによってコード上で確認できるようにしたとも言えるかもしれない。ブラウザーの実装の不行き届きやバグへの対処に確認が必要な現状だと絵空事に近いので、ワークフローが大幅に省力化するわけではなさそうだ。