もはやスマホ表示を考えないwebサイトは新規制作やリニューアルではほぼない今日、どんなに横に長いテーブルでもレスポンシブでどうするか考える必要があります。
PCで組むだけなら何も考えずに済むのですが、スマホの縦長の画面で如何にユーザビリティを落とさず横長になりがちなテーブルを表示させることができるか、いくつかtableコーディングのパターンを用意してみました。
Contents
- 縦に積むテーブルレスポンシブ
- 横並びを縦並びにするテーブルレスポンシブ
- 疑似要素で見出しを用意するテーブルレスポンシブ
- content:attr() で見出しを表現するテーブルレスポンシブ
- spanで見出しを表現するテーブルレスポンシブ
- スクロールで表示させるテーブルレスポンシブ
縦に積むテーブルレスポンシブ
PC
SP
ごくごく一般的なテーブルパターンですね。
ソース上は上から順番に要素が並んでいるので、それらをblock要素に指定して横幅100%等にすれば
簡単に縦積みのSPに適したレイアウトにすることができます。
2列のみだと以下のように会社概要などに使われている構成です。
内容が余程長かったり見づらくならない限り、そのまま横幅を縮める形でも問題ないでしょう。
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | <table class="tbl-r02"> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr class="last"> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> </table> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 | p { font-size: 16px; font-weight: bold; text-align: center; margin: 60px auto 40px; } table { margin: 20px auto; } .tbl-r02 th { background: #e9727e; border: solid 1px #ccc; color: #fff; padding: 10px; } .tbl-r02 td { border: solid 1px #ccc; padding: 10px; } @media screen and (max-width: 640px) { .last td:last-child { border-bottom: solid 1px #ccc; width: 100%; } .tbl-r02 { width: 80%; } .tbl-r02 th, .tbl-r02 td { border-bottom: none; display: block; width: 100%; } } |
横並びを縦並びにするテーブルレスポンシブ
PC
SP
料金表、成分表など…横に長く並ぶ表示のテーブルで、縦にしても問題ないような場合はスマホでは縦並びにすることで解決できます。
ただ、この方法は高さ指定をする必要があり、テキスト量の差がある場合などは少し手間がかかるかもしれません。
trをtheadとtbody以下に格納してfloatで横並びにして、中身はblockにすることで縦並びにしています。
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | <table class="tbl-r03"> <thead> <tr> <th>見出し01(th)</th> <th>見出し02(th)</th> <th>見出し03(th)</th> <th>見出し04(th)</th> </tr> </thead> <tbody> <tr> <td>内容(コンテンツ)上</td> <td>内容(コンテンツ)上</td> <td>内容(コンテンツ)上</td> <td>内容(コンテンツ)上</td> </tr> <tr class="last"> <td>内容(コンテンツ)下</td> <td>内容(コンテンツ)下</td> <td>内容(コンテンツ)下</td> <td>内容(コンテンツ)下</td> </tr> </tbody> </table> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 | p { font-size: 16px; font-weight: bold; text-align: center; margin: 60px auto 40px; } th { background: #e9727e; border: solid 1px #ccc; color: #fff; padding: 10px; } td { border: solid 1px #ccc; padding: 10px; } @media screen and (max-width: 640px) { .tbl-r03 { width: 90%; } .tbl-r03 tr { display: block; float: left; } .tbl-r03 tr td, .tbl-r03 tr th { border-left: none; display: block; height: 50px; } .tbl-r03 thead { display: block; float: left; width: 30%; } .tbl-r03 thead tr { width: 100%; } .tbl-r03 tbody { display: block; float: left; width: 70%; } .tbl-r03 tbody tr { width: 50%; } .tbl-r03 tr td + td { border-left: none; } .tbl-r03 tbody td:last-child { border-bottom: solid 1px #ccc; } } |
疑似要素で見出しを用意するテーブルレスポンシブ
PC
SP
こちらも横長だけれど内容が長いなどで縦積みのレイアウトにしたい場合のtableで使えるパターンです。
thを全部スマホでは非表示にして消してしまい、各trの一番初めのtd要素に:before疑似要素でthを偽装します。
border分が疑似要素の横幅100%と合わなかったりするようなので少々力業です。
borderを使用しないデザインであれば問題なく実装できそうです。
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 | <table class="tbl-r04"> <tr class="thead"> <th>見出し01(th)</th> <th>見出し02(th)</th> <th>見出し03(th)</th> <th>見出し04(th)</th> </tr> <tr> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr class="last"> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> </table> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 | //PCのデフォルトスタイルは割愛します @media screen and (max-width: 640px) { .tbl-r04 { width: 80%; } .tbl-r04 .thead { display: none; } .tbl-r04 tr, .tbl-r04 td{ display: block; width: 100%; position: relative; } .tbl-r04 td:first-child:before { content: "見出し:before"; background: #e9727e; box-sizing: border-box; color: #fff; font-weight: bold; height: 40px; padding: 10px; position: absolute; top: -41px; left: -0.2%; display: block; width: 100.5%; } .tbl-r04 tr { margin-bottom: 40px; } } |
content:attr() で見出しを表現するテーブルレスポンシブ
PC
SP
縦にも横にも結構重要な見出し系が設定されているtableをレスポンシブするパターンです。
スマホの際にはPCで表示されていた見出し部分を非表示にし、縦に積まれていた見出しを一番上に。
そして非表示にした要素はtdに仕込んでいたdata-labelをcontentプロパティで呼び出して表示します。
表の内容によっては意味合いを崩さないレイアウトにできるかどうか判断する必要がありますが
結構使えるのではないかと思います!
content:attr() は他のことでも使用できそうです。
参考:【 content:attr() 】CSSでタグのdata属性やtitle属性を取得して表示する
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | <table class="tbl-r05"> <tr class="thead"> <th></th> <th>見出し01(th)</th> <th>見出し02(th)</th> <th>見出し03(th)</th> <th>見出し04(th)</th> </tr> <tr> <td>A</td> <td data-label="見出し01">内容(コンテンツ)</td> <td data-label="見出し02">内容(コンテンツ)</td> <td data-label="見出し03">内容(コンテンツ)</td> <td data-label="見出し04">内容(コンテンツ)</td> </tr> <tr> <td>B</td> <td data-label="見出し01">内容(コンテンツ)</td> <td data-label="見出し02">内容(コンテンツ)</td> <td data-label="見出し03">内容(コンテンツ)</td> <td data-label="見出し04">内容(コンテンツ)</td> </tr> <tr> <td>C</td> <td data-label="見出し01">内容(コンテンツ)</td> <td data-label="見出し02">内容(コンテンツ)</td> <td data-label="見出し03">内容(コンテンツ)</td> <td data-label="見出し04">内容(コンテンツ)</td> </tr> <tr class="last"> <td>D</td> <td data-label="見出し01">内容(コンテンツ)</td> <td data-label="見出し02">内容(コンテンツ)</td> <td data-label="見出し03">内容(コンテンツ)</td> <td data-label="見出し04">内容(コンテンツ)</td> </tr> </table> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 | //PCのデフォルトスタイルは割愛します .tbl-r05 td:first-child { background: #fbf5f5; } @media screen and (max-width: 640px) { .tbl-r05 { width: 80%; } .tbl-r05 .thead { display: none; } .tbl-r05 tr { width: 100%; } .tbl-r05 td { display: block; text-align: right; width: 100%; } .tbl-r05 td:first-child { background: #e9727e; color: #fff; font-weight: bold; text-align: center; } .tbl-r05 td:before { content: attr(data-label); float: left; font-weight: bold; margin-right: 10px; } } |
spanで見出しを表現するテーブルレスポンシブ
PC
SP
これは旅行会社系のテーブルのコーディングの際に数回使用したことがあり、
見出し部分が「料金」「日付」~になるようなイメージです。
こちらもCで表示されている見出しを非表示にしてしまうところまでは同様で、
逆にtdにspanタグで入れておいた見出しのテキストをSPの時に表示することで
tableの内容を保った形でレスポンシブを実現する方法です。
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 | <table class="tbl-r06"> <tr class="thead"> <th>見出し01(th)</th> <th>見出し02(th)</th> <th>見出し03(th)</th> <th>見出し04(th)</th> </tr> <tr> <td><span class="sp">見出し01:</span>内容(コンテンツ)</td> <td><span class="sp">見出し02:</span>内容(コンテンツ)</td> <td><span class="sp">見出し03:</span>内容(コンテンツ)</td> <td><span class="sp">見出し04:</span>内容(コンテンツ)内容(コンテンツ)</td> </tr> <tr> <td><span class="sp">見出し01:</span>内容(コンテンツ)</td> <td><span class="sp">見出し02:</span>内容(コンテンツ)</td> <td><span class="sp">見出し03:</span>内容(コンテンツ)</td> <td><span class="sp">見出し04:</span>内容(コンテンツ)内容(コンテンツ)</td> </tr> <tr> <td><span class="sp">見出し01:</span>内容(コンテンツ)</td> <td><span class="sp">見出し02:</span>内容(コンテンツ)</td> <td><span class="sp">見出し03:</span>内容(コンテンツ)</td> <td><span class="sp">見出し04:</span>内容(コンテンツ)内容(コンテンツ)</td> </tr> <tr class="last"> <td><span class="sp">見出し01:</span>内容(コンテンツ)</td> <td><span class="sp">見出し02:</span>内容(コンテンツ)</td> <td><span class="sp">見出し03:</span>内容(コンテンツ)</td> <td><span class="sp">見出し04:</span>内容(コンテンツ)内容(コンテンツ)</td> </tr> </table> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | //PCのデフォルトスタイルは割愛します .tbl-r06 tr:nth-child(even) { background: #fbf5f5; } .tbl-r06 td { border: none; } .tbl-r06 .last { border-bottom: solid 1px #ccc; } @media screen and (max-width: 640px) { .tbl-r06 { width: 80%; } .tbl-r06 .thead { display: none; } .tbl-r06 td { display: inline-block; } .tbl-r06 span { font-weight: bold; } .tbl-r06 .last { border-bottom: none; } } |
スクロールで表示させるテーブルレスポンシブ
SP
最後は、どうしても横長のままが見やすい!
というときにスマホはスクロールで見せる方法です。
今までの方法で見やすくするのもよいのですが、あまりに縦に長くなる場合や
レスポンシブさせることにこだわりすぎることもあるので
純粋にスクロールさせたほうが良いパターンも想定に入れておきましょう。
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | <div class="scroll"> <table class="tbl-r07"> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <th>見出し02(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <th>見出し03(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> </table> </div> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | @media screen and (max-width: 640px) { .scroll { overflow-x: auto; } .tbl-r07 { min-width: 640px; margin: 0 10px 50px; } .tbl-r07 td { border-top: solid 1px #ccc; border-bottom: solid 1px #ccc; } } |
+α tableのセルの間の余白をつける
tableでセル間にmarginをあけることもできます。
が、セルの【左右】【上下】のセットでの指定のみが可能です。
上下左右別々のmarginを指定することはできないのでデザインの際は要注意ですね。
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 | <table class="tbl-m01"> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr class="last"> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> </table> <table class="tbl-m01 m02"> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> <tr class="last"> <th>見出し01(th)</th> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> <td>内容(コンテンツ)</td> </tr> </table> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | .tbl-m01 { border-collapse: separate; border-spacing: 5px; } .tbl-m01.m02 { border-spacing: 10px 0; margin: 0 auto 100px; } .tbl-m01.m02 th { border: none; } .tbl-m01.m02 td { background: #fbf5f5; border: none; } @media screen and (max-width: 640px) { .tbl-m01 th { width: 20%; } .tbl-m01 td { border-bottom: solid 1px #ccc; width: 25%; } } |
以上、すべてのパターンをまとめたデモページは以下よりご覧頂けます。
demo
なんでも縦に直せばOKというわけではないテーブルのレスポンシブ対応。
よーくテーブルの内容を理解して、どのようなレイアウトが良いか判断できるとよいですね。
■参考記事
CSSだけでレスポンシブ対応のtableを実装してみた
CSSで出来るレスポンシブ対応を考えた table レイアウト