CSS Grid Layoutをガッツリ使った所感

  • 183
    いいね
  • 0
    コメント

CSS Grid Layout Moduleはレイアウトを構築できる新しいCSSの仕様です。従来はfloatやFlexbox( display: flex )で対応していたようなレイアウトを効率的に構築できます。

2017年4月にリニューアルした私の個人プロジェクト「Beautifl - Flash Gallery🌈」でCSS Grid Layoutをガシガシ使ったので、所感をお伝えします。一般公開されている事例でCSS Grid Layoutを使っているサイトを見かけないので、ベンチマークとして見てもらえたら幸いです。

Beautifl - Flash Gallery

Beautifl - Flash Galleryは2009年に公開したサイト🌏。従来はIE 7対応をベースに構築してましたが、リニューアルでは脱jQuery🌀の方針のもと、Vue.jsやCSS Grid Layoutを導入。WAI-ARIAや部分的にHTTP/2対応もしてます。

CSS Grid Layoutの所感

CSS Grid Layoutの良かった点

  • floatやFlexboxだとDOMが入れ子構造となりがちだが、CSS Grid Layoutだと入れ子構造を使わずに構築できる
  • DOM構造の自由度が上がるので、モバイル・デスクトップのレスポンシブに対応しやすい
  • 動的に画面が変化するSPA(Single Page Application)やRIA(Rich Internet Application)の構築が楽になる

Beautiflのサイトはいろんなレイアウトに変化しますがCSS Grid Layoutが役立ちました。

CSS Grid Layoutの困った点

  • 最新ブラウザしか使えない
  • IEとEdgeは古い仕様で実装されているので、工夫が必要
  • 検索エンジンのインデックス収集に支障ないか不安
  • Polyfillはイマイチ信用できない
  • レイアウトの切り替わりにアニメーションを付けられない

CSS Grid Layoutは便利なので、SPAなど必要な場面でもっと普及して欲しいと思っています💭 しかし、古いブラウザ、特にIE 11の存在はビジネス🏢としてやってる立場では無視できません。IE 11🐒は今やウェブ業界の足かせと思っているコーダーは多いでしょうが、記事「各Windows OSでのInternet Explorerのサポート終了時期 - @IT」によるとIE 11は2025年まで生き延びているはずです💀

ただ実は古い仕様とはいえ、IEがCSS Grid Layoutに対応しているのは救いです😇

背景

CSS Grid Layoutのオススメの入門記事

CSS Grid Layoutの解説記事は次がわかりやすいでしょう。私はCodeGridで学びました。Webクリエイターボックスの記事は図版入りでわかりやすいですね。

対応環境

CSS Grid Layoutが対応しているのは、最新のブラウザのみ(参照「Can I use...」)。2017年3月に足並みを揃えたように各種ブラウザが一斉に対応しました。

  • Chrome 57 (2017年3月)
  • Firefox 52 (2017年3月)
  • Safari 10.1 (2017年3月)
  • iOS Safari 10.3 (2017年3月)
  • Internet Explorer 10 (2012年9月)
  • Edge 12 (2015年1月)

一般的なサイトでは動作対象ブラウザを「IE 11以上、Chrome最新版、Firefox最新版」としているサイトも多いでしょう。IEとEdgeが先行して実装してていたおかげで、比較的導入しやすい土台が揃っています。

spec.png

CSS Grid Layoutで困った点へのアプローチを紹介

シンプルな例でクロスブラウザ対応を考える

まずはCSS Grid Layoutの説明。CSS Grid Layoutでは、レイアウトを格子状に考えます。どの格子に要素を割り当てるか、という考え方で使います。

まずはレイアウトを区切ります。

Web 1920 – 10.png

CSSでは次のように書きます。1frという単位は可変するところに指定します。

.my-grid {
  display: grid;
  grid-template-columns: 200px 1fr;
  grid-template-rows: 50px 1fr 50px;
}

ヘッダーやサイドバー、メインコンテンツ、フッターの4要素を割り当てます。

Web 1920 – 2.png

CSSでは次のように指定します。


header {
  grid-column-start: 1;
  grid-column-end: 3;
  grid-row: 1;
}

aside {
  grid-column: 1;
  grid-row-start: 2;
  grid-row-end: 4;
}

main {
  grid-column: 2;
  grid-row: 2;
}

footer {
  grid-column: 2;
  grid-row: 3;
}

次のURLでサンプルを公開しているので、アクセスしてみてください。

▶ 標準仕様のみ対応版のデモ
https://ics-creative.github.io/170414_css_grid/dist/1.html

ChromeやSafari、Firefoxなど最新のブラウザーでは期待通りに表示されています。

sample_01_modern.jpg

これでめでたく完成。と思いきやIE 11やEdge 15(Creators Update適用済)で見てみましょう。

CSS Grid Layoutのサンプル1

はい、全滅ですね🙅

IEとEdgeを対応させる

IE 11やEdge 15ではベンダープレフィックスが必要です。次はコードの一部ですが、-ms-を付与したCSSのコードです。

.my-grid {
  display: -ms-grid;
  display: grid;
  -ms-grid-columns: 200px 1fr;
  grid-template-columns: 200px 1fr;
  -ms-grid-rows: 50px 1fr 50px;
  grid-template-rows: 50px 1fr 50px;
}
header {
  -ms-grid-column: 1;
  grid-column-start: 1;
  grid-column-end: 3;
  -ms-grid-row: 1;
  grid-row: 1;
}

ちなみにベンダープレフィックスを手動で付与するのは人類がなすべきことではありません。Autoprefixerという文明の利器を使いましょう。Autoprefixerは @tonkotsuboy_com の記事「CSSベンダープレフィックス-webkit-を今この瞬間に辞める為のAutoprefixerの導入とお薦め設定」が参考になります。

さぁ、これでIE 11やEdge 15で見てみます。

▶ AutoPrefixer対応版
https://ics-creative.github.io/170414_css_grid/dist/2.html

CSS Grid Layoutのサンプル2

まだ微妙・・・😝 ヘッダーが横一行になっていなかったり、サイドバーが行二列に突き抜けていません。背景の赤色が見えています。

ベンダープレフィックスを付けるだけでは十分とは言えない

実はIE 11やEdge 15はCSS Grid Layoutが使えるとは言え、古い仕様(Grid Layout | W3C Working Draft 7 April 2011)でブラウザに実装されています。標準のCSS Grid Layoutと古い仕様では次のような違いがあります

  • 使えるプロパティーが少ない
  • Autoprefixerで変換しきれないプロパティーがある
  • 片方にはあって、片方にない仕様がある

レイアウト崩れの原因は行・列の結合部分に関する部分です。ここに古い仕様と標準仕様の違いがあります。

標準の仕様では、格子状の分割線①から③まで指定するという方法です。

header {
  grid-column-start: 1;
  grid-column-end: 3;
  grid-row: 1;
}

対してIE 11やEdge 15の仕様は①からセルをいくつ結合するかという指定です。

header {
  -ms-grid-column: 1;
  -ms-grid-column-span: 2; /* MS対策(手動) */
  -ms-grid-row: 1;
}

標準仕様ではgrid-column-endで、古い仕様は-ms-grid-column-spanで、仕様自体が異なっています。そのため、Autoprefixerではこの変換は解消できません。ここは自分でコードを書き足して対応します。

header {
  -ms-grid-column: 1;
      grid-column-start: 1;
  grid-column-end: 3;
  -ms-grid-column-span: 2; /* MS対策(手動) */
  -ms-grid-row: 1;
      grid-row: 1;
}

▶ IEとEdgeの対応コード追加
https://ics-creative.github.io/170414_css_grid/dist/3.html

やっと、期待通りに表示できるようになりました🙆

CSS Grid Layoutのサンプル3

SASSのmixinを用意して対処した

簡単に対処するには、SASSで次のmixinを使うといいでしょう。これとAutoprefixerを組み合わせると、無事にクロスブラウザ対応ができます。

/** CSS Grid Layoutで複数の行を指定するmixin */
@mixin create-grid-column-span($start, $end) {
  grid-column-start: $start;
  grid-column-end: $end;
  -ms-grid-column-span: $end - $start;
}

/** CSS Grid Layoutで複数の列を指定するmixin */
@mixin create-grid-row-span($start, $end) {
  grid-row-start: $start;
  grid-row-end: $end;
  -ms-grid-row-span: $end - $start;
}

/* 使用例 */
header {
  @include create-grid-column-span(1, 3);
  grid-row: 1;
}

完成品のサンプルはこちらになります。SASSのmixinと、Autoprefixerのあわせ技で対応しています。

▶ 完成品のサンプル
https://ics-creative.github.io/170414_css_grid/dist/

ソースコードはGitHubで公開しているので、よかったら使ってくださいませ。Yarn🐈などコマンドラインが必要になるので、そういうのが得意なフロントエンドエンジニアの向けです😎

https://github.com/ics-creative/170414_css_grid

検索エンジンのインデックス収集に支障がないか不安

IE 11、Edge 15まで含め様々なブラウザに対応できたので安心してましたが、落とし穴がありました💥 検索エンジンでインデックスされるように、Google Search ConsoleのFetch as Googleに送信すると・・・

google-search-console.jpg

CSS Grid Layoutを使った部分が解釈されずレンダリングされてしまいました😜 検索エンジンにはレイアウトが崩れたまま解析されてそうで、不安が大いに残ります。検索流入に影響があるかは経過を眺めながら分析していこうと思います📉。

なお、後述のPolyfillを入れると検索エンジンでレンダリングされましたが、いろんな問題があったため導入を諦めました。

あてにならないPolyfill

Polyfillを探して実験的に試しました。試したのはGitHubで公開されている次のリンクのものです。

FremyCompany/css-grid-polyfill: A working implementation of css grids for current browsers.

Polyfillを入れるとJavaScriptによって一応CSS Grid Layoutが解釈されるようになります。が、次のような課題がありました🆖

  • id属性が付与されまくる
  • overflowの解釈・スクロールバーの発生有無が想定と異なった
  • CSS Grid Layoutとはあまり関係ない部分のレイアウトが崩れた
  • PolyfillのJSライブラリの容量がでかい(78 KB)
  • IE 11とEdge 15にも、Polyfillが効いてしまう(エンバグが発生)

じっくり取り組んだり、他のPolyfillを探せば解決できたかもしれません。ただ、Polyfillを使わず、最新のブラウザが普及するのを待つ方が本質的だと考え、採用を見送りました。

まとめ

CSS Grid Layoutが利用できる最新ブラウザが十分に浸透するまで数ヶ月かかりますが、採用するサイトは今後増えてくるでしょう。DOMの要素の順番や親子構造とレイアウトを分離できるのがCSS Grid Layoutの利点なので、適材適所として選択肢の1つに入れておくといいでしょう📕

冒頭で紹介した「Beautifl - Flash Gallery」には技術的に新しく取り組んだ箇所が他にもあります。リニューアルの話は続編記事「脱jQueryのためにしたこと - Qiita」へと続きます。