HTML&CSS スクロールすると項目が固定される表の作り方

2018-04-06

HTMLで表を書くと、ページ内に表全体がギュッを収まるようになっています。

そうなると、大きな表は見づらくなってしまう事も。

ここでは、表全体をスクロールで表示しつつ、見出しや項目だけは固定される表の作り方をまとめています。

\項目をタップするとジャンプできます/

見出し固定のスクロール表

最初に1つ注意点。

ここで作る見出し固定の表は、CSSプロパティ「position: sticky」とHTMLタグ「thead」を使用しています。

最新ブラウザではおおむね対応されていますが、バージョンが古いなど非対応ブラウザでは正常に固定できません。

2019年4月時点での大手ブラウザの対応状況はこちら。

MEMO
	【thead】【sticky】
Firefox	○		○
Chrome	○		○
Safari	○		○※プレフィックス必須
Eedge	○		○
IE	×		○

ということで、完成形はこちらになります。

余白、背景色は適当につけているので、お好みで変更してくださいね。

見出しA見出しB見出しC見出しD見出しE見出しF
見出しA内容1内容2内容3内容4内容5内容6
見出しB内容1内容2内容3内容4内容5内容6
見出しC内容1内容2内容3内容4内容5内容6
見出しD内容1内容2内容3内容4内容5内容6
見出しE内容1内容2内容3内容4内容5内容6

ここからは、この見出し固定の表の作り方を見ていきましょう。

下準備

HTMLで普通に表を書き、CSSで「table」のデフォルトの隙間を消しておきます。

ついでにマス(セル)に罫線やpaddingをつけておくと見やすくなります。

HTML

<table>
<tr><th></th><th></th><th></th><th></th></tr>
<tr><th></th><td></td><td></td><td></td></tr>
<tr><th></th><td></td><td></td><td></td></tr>
<tr><th></th><td></td><td></td><td></td></tr>
</table>
CSS

table{
/*tableの余白リセット*/
  border-collapse: collapse;
  border-spacing: 0;
}
/*表の罫線*/
table,td,th{
 border: 1px #eee solid;
}
/*セルの余白*/
td,th{
  padding: 10px;
}

①表をスクロールできるようにする

デフォルトだと、表は画面内に収まるようになってるので、スクロールできるようにします。

スクロールする表を作るには、HTMLで普通に書いた表をdivで囲み、class名をつけて以下を指定します。

HTML

<div class="sample">
<table>
<tr><th></th><th></th><th></th><th></th></tr>
<tr><th></th><td></td><td></td><td></td></tr>
<tr><th></th><td></td><td></td><td></td></tr>
<tr><th></th><td></td><td></td><td></td></tr>
</table>
</div>

CSS

.sample{
  overflow: auto;
  white-space: nowrap;
}
見出しA見出しB見出しC見出しD見出しE見出しF
見出しA内容1内容2内容3内容4内容5内容6
見出しB内容1内容2内容3内容4内容5内容6
見出しC内容1内容2内容3内容4内容5内容6

これでスクロールできる表になりました。

②見出しを固定する

このままだと見出しも一緒にスクロールしてしまうので、見出しだけ固定します。

上の見出しを固定する

まず上の見出しを固定します。

HTMLファイルで固定したい見出しの行を「thead」タグで囲みます。

HTML

<div class="sample">
<table>
<thead>
<tr><th></th><th></th><th></th><th></th></tr>
</thead>
<tr><th></th><td></td><td></td><td></td></tr>
<tr><th></th><td></td><td></td><td></td></tr>
<tr><th></th><td></td><td></td><td></td></tr>
</table>
</div>

MEMO「thead」タグの仲間には「tbody」「tfoot」といったタグもあります。
「thead」=見出しの行
「tbody」=中身の行
「tfoot」=一番下の行
と囲むイメージですが、「tbody」「tfoot」タグは ブラウザによって挙動が違うようなので、ここでは割愛します。

つぎに「thead」タグで囲んだ見出しに、CSSで「position: sticky」と「top: 0」を指定して固定します。

「position: sticky」がSafariでも動作するように、プレフィックス(-webkit-sticky)も追加します。

CSS

/*上の見出しを固定*/
.sample thead th{
  position: sticky;
  position: -webkit-sticky;
  top: 0;
  z-index: 1;
}

固定だけではスクロールした時に文字が重なってしまうので「z-index」で表示の優先順位をつけています。

「z-index」のデフォルト値は「0」で、上に表示したいものにより大きな数字をつけます。

また、背景色をつけることでも重なりを防ぐことができます。
その場合は「background」で背景色を指定します。

これで上の見出し固定は完了です。

左側の見出しを固定する

左側の見出しを固定するには、見出しタグに「position: sticky」と固定位置、そして表示優先順位の「z-index」を指定すればOKです。

CSS

/*タテの見出しを固定*/
.sample th{
  position: sticky;
  position: -webkit-sticky;
  left: 0;
  z-index: 2;
}

③角の交点マスの対応

見出しは固定できましたが、左上のマスは空っぽなので、スクロールすると内容が入ってしまいます。

見栄えがよくないので、マスの中身を見えないように隠します。

ここでは背景色を記事の背景色と同じに変更して、「z-index」で優先的に表示させる事で対応しています。

CSS

/*左上のマス*/
.sample thead th:nth-of-type(1){
  background: #fff;
  z-index: 5;
}

④左上の枠線とチラ見えする隙間を消す

これでおおよそ完成ですが、もう一手間。

表に枠線を指定していると、表の外側に隙間ができてスクロールした文字がチラ見えする事があります。

表の線を全て消すと手っ取り早いですが、上と左側の枠線だけを消すこともできます。

その場合は、線に濃い色をつけると浮いてしまうので、薄めの色を指定するといいかなと思います。

CSS

/*線を全て消すとき*/
.sample table,
.sample td,
.sample th{
  border: 0;
}
/*外側の線だけを消すとき*/
.sample table{
  border: 0;
}
.sample td, .sample th{
  border: 1px #eee solid;
}
.sample th{
  border-left: 0;
}
.sample thead th{
  border-top: 0;
}

完成ソース

ということで、完成ソースはこちら!

CSS

/*スクロールさせる*/
.sample{
  overflow: auto;
  white-space: nowrap;
}
/*上の見出しを固定*/
.sample thead th{
  position: sticky;
  position: -webkit-sticky;/*Safari用プレフィックス*/
  top: 0;
  background: #9dd;
  z-index: 1;
}
/*タテの見出しを固定*/
.sample th{
  position: sticky;
  position: -webkit-sticky;
  left: 0;
  background: #fbcfcf;
  z-index: 2;
}
/*左上のマス*/
.sample thead th:nth-of-type(1){
  background: #fff;
  z-index: 5;
}
/*外側の線だけを消すとき*/
.sample table{
  border: 0;
}
.sample td, .sample th{
  border: 1px #eee solid;
}
.sample th{
  border-left: 0;
}
.sample thead th{
  border-top: 0;
}
/*1行おきに色をつける*/
.sample table tr:nth-child(odd) td{
  background: #fffee4;
}
見出しA見出しB見出しC見出しD見出しE見出しF
見出しA内容1内容2内容3内容4内容5内容6
見出しB内容1内容2内容3内容4内容5内容6
見出しC内容1内容2内容3内容4内容5内容6
見出しD内容1内容2内容3内容4内容5内容6
見出しE内容1内容2内容3内容4内容5内容6

背景色や余白を変えてアレンジもできます。

表の装飾の書き方は、こちらでまとめているので、参考にしてみてくださいね。