HTML テーブルは、行と列を含む表形式のデータを表示するために使用されます。<table>
を使用するかどうかは、表示するコンテンツとそのコンテンツに対するユーザーのニーズに基づいて判断する必要があります。データの提示、比較、並べ替え、計算、相互参照が行われている場合は、<table>
がおそらく正しい選択です。サムネイル画像の大きなグループなど、表以外のコンテンツをきれいにレイアウトしたいだけの場合は、表は適していません。代わりに、画像のリストを作成し、CSS によるグリッドのスタイルを設定します。
このセクションでは、テーブルを構成するすべての要素と、表形式のデータを表示する際に考慮すべきユーザー補助機能とユーザビリティ機能について説明します。Learn HTML は基本的に CSS に関するものではありません。CSS の学習に特化したコースもありますが、テーブル固有の CSS プロパティをいくつか取り上げます。
テーブル要素を順番に並べる
<table>
タグは、すべてのテーブル要素を含むテーブルのコンテンツをラップします。<table>
の暗黙的な ARIA ロールは table
です。支援技術は、この要素が行と列に配置されたデータを含むテーブル構造であることを認識しています。テーブルが選択状態を保持する場合、2 次元ナビゲーションを備えている場合、またはユーザーがセルの順序を変更できる場合は、role="grid"
を設定します。grid
の行を展開または折りたたむことができる場合は、代わりに role="treegrid"
を使用します。
<table>
には、テーブルのヘッダー(<thead>
)、テーブル本文(<tbody>
)、必要に応じてテーブルのフッター(<tfoot>
)があります。これらはそれぞれ、テーブルの行(<tr>
)で構成されます。行にはテーブル ヘッダー(<th>
)とテーブルデータ(<td>
)のセルが含まれ、そのセルにすべてのデータが含まれます。
DOM では、その前に、テーブル キャプション(<caption>
)と列グループ(<colgroup>
)という 2 つの追加機能があります。<colgroup>
に span
属性があるかどうかによって、ネストされたテーブル列(<col>
)要素が含まれる場合があります。
このテーブルの子は次の順序で並べられます。
<caption>
要素<colgroup>
要素<thead>
要素<tbody>
要素<tfoot>
要素
ここでは、<table>
要素の子要素(すべて省略可能ですが推奨)について説明した後、行、表見出しのセル、表データのセルを確認します。<colgroup>
が最後に取り上げられます。
表の説明
ネイティブのセマンティック要素である <caption>
は、テーブルに名前を付けるために推奨されるメソッドです。<caption>
は、プログラムに関連付けられた説明的なテーブルタイトルを指定します。これは、デフォルトですべてのユーザーが表示して利用できます。
<caption>
要素は、<table>
要素内でネストされる最初の要素にする必要があります。これを含めると、すべてのユーザーは周囲のテキストを読むことなく、テーブルの目的をすぐに知ることができます。また、<table>
で aria-label
または aria-labelledby
を使用して、わかりやすい名前をキャプションとして指定することもできます。<caption>
要素に要素固有の属性はありません。
キャプションは表の外に表示されます。字幕の場所は CSS の caption-side
プロパティで設定できます。これは、サポートが終了した align
属性を使用するよりもおすすめの方法です。これにより、字幕を上下に設定できます。inline-start
と inline-end
での左右のポジショニングはまだ完全にはサポートされていません。上部はデフォルトのブラウザ表示です。
データテーブルには、ヘッダーとキャプションが明確で、その内容が簡単にわかるシンプルなものにしてください。すべてのユーザーが同じ認知能力を持っているわけではありません。表が「要点を述べている」場合や解釈が必要な場合は、テーブルの要点または機能の概要を簡潔に記載します。要約がどこに配置されるかは、要約の長さと複雑さによって異なります。簡潔な場合は、字幕の内部テキストとして使用します。長い場合はキャプションを要約し、表の前の段落に要約を記述して、2 つを aria-describedby
属性に関連付けます。また、表を <figure>
に入れ、要約を <figcaption>
に入れるという方法もあります。
データ セクション
テーブルのコンテンツは、0 個以上の表ヘッダー(<thead>
)、表の本文(<tbody>
)、表のフッター(<tfoot>
)という最大 3 つのセクションで構成されます。いずれも省略可能で、それぞれ 0 個以上がサポートされています。
これらの要素は、表のアクセシビリティを妨げませんが、ユーザビリティの点では有用です。スタイルフックを提供します。たとえば、ヘッダーのコンテンツをスティッキーに、<tbody>
のコンテンツをスクロールさせることができます。これら 3 つの要素のいずれかにネストされていない行は、暗黙的に <tbody>
にラップされます。3 つはすべて同じ暗黙的ロール rowgroup
を共有します。これら 3 つの要素のいずれも、要素固有の属性を持ちません。
現状:
<table>
<caption>MLW Students</caption>
<thead></thead>
<tbody></tbody>
<tfoot></tfoot>
</table>
もともと <tfoot>
要素は、アクセシビリティ上の理由から <thead>
の直後と <tbody>
の前に配置するように指定されていました。以前のコードベースでは、このような直感的でないソースの順序に遭遇することがあります。
テーブルの内容
テーブルは、テーブルのヘッダー、本文、フッターに分割できますが、テーブルにテーブルの行、セル、コンテンツが含まれていなければ、これらはいずれも実際には機能しません。表の各行 <tr>
には 1 つ以上のセルが含まれます。セルがヘッダーセルの場合は、<th>
を使用します。
それ以外の場合は、<td>
を使用します。
ユーザー エージェント スタイルシートでは通常、<th>
の表ヘッダーのセルに、中央揃えで太字で表示されます。これらのデフォルトのスタイルとすべてのスタイルは、個々のセル、行、さらには <table>
で使用可能だった非推奨の属性ではなく、CSS で制御するのが最適です。
これまでは、セル間やセル内、枠線、テキストの配置にパディングを追加する属性が存在していました。セルのコンテンツと隣接するセルの境界の間のスペースを定義する Cellpadding と cellpacing は、それぞれ CSS の border-collapse プロパティと border-spacing プロパティを使用して設定する必要があります。border-collapse: collapse
が設定されている場合、Border-spacing
は無効になります。border-collapse: separate;
が設定されている場合、empty-cells: hide;
を使用して空のセルを完全に非表示にできます。表のスタイル設定について詳しくは、テーブル関連の CSS スタイルのインタラクティブなスライド資料をご覧ください。
この例では、いくつかの機能をわかりやすくするために、表と個々のセルに CSS で枠線を追加しました。
この例には、キャプション、表の見出し、表の本文があります。ヘッダーには 1 行に 3 つのヘッダー <th>
セルが含まれているため、3 つの列が作成されます。本文には 3 行のデータが含まれます。最初のセルは行のヘッダーセルであるため、<td>
ではなく <th>
を使用します。
<th>
セルには、columnheader または rowheader の暗黙的な ARIA ロールがあるセマンティックな意味があります。列挙した scope
属性の値に応じて、テーブルセルの列または行のヘッダーとしてセルを定義します。scope
が明示的に設定されていない場合、ブラウザはデフォルトで col
または row
になります。セマンティック マークアップを使用しているため、1956
セルには Year と Lou Minious の 2 つのヘッダーがあります。この関連付けから、「1956」は「Lou Minious」の卒業年であることがわかります。この例ではテーブル全体を見ることができるため、関連付けが視覚的にわかります。<th>
を使用すると、ヘッダーの列または行がビューの外にスクロールされても関連付けが行われます。<th scope="col">Year</th>
と <th scope="row">Lou Minious</th>
を明示的に設定することもできますが、このようなシンプルなテーブルでは、列挙されたデフォルト値が機能します。scope
の他の値として、rowgroup
や colgroup
があります。これらは複雑なテーブルで役立ちます。
セルの結合
MS Excel、Google スプレッドシート、Numbers と同様に、複数のセルを 1 つのセルに結合できます。これは HTML で行われます。
colspan
属性は、1 つの行内で 2 つ以上の隣接するセルを結合するために使用します。rowspan
属性は、一番上の行のセルに配置される複数の行にわたってセルを結合するために使用します。
この例では、表のヘッダーに 2 つの行が含まれています。最初のヘッダー行には 4 列にわたる 3 つのセルがあり、中央のセルには colspan="2"
があります。これにより、隣接する 2 つのセルが結合されます。最初と最後のセルには rowspan="2"
が含まれます。これにより、セルが隣接する行の直下にあるセルと結合されます。
表のヘッダーの 2 行目には 2 つのセルがあります。これらは 2 行目の 2 列目と 3 列のセルです。 最初の行の最初と最後の列のセルは 2 行にわたるため、最初または最後の列のセルは宣言されていません。
1 つのセルが、scope
属性だけでは設定できない関連付けを持つ複数のヘッダー セルによって定義される場合は、headers
属性と、関連するヘッダーのスペース区切りリストを含めます。この例はより複雑なテーブルであるため、scope
属性を使用してヘッダーのスコープを明示的に定義します。さらにわかりやすくするために、各セルに headers
属性を追加しました。
このような単純なユースケースでは headers
属性は必要ないかもしれませんが、テーブルの複雑さが増すにつれ、この属性をツールバーに含めることが重要です。ヘッダーまたはセルが結合されている表や、2 階層を超える列ヘッダーまたは行ヘッダーがある表など、複雑な構造を持つ表では、関連付けられたヘッダー セルを明示的に識別する必要があります。このような複雑なテーブルでは、各データセルを対応する各ヘッダーセルに明示的に関連付け、headers
属性の値として、関連付けられたすべてのヘッダーのスペース区切りの id
値のリストを使用します。
headers
属性は <td>
要素でより一般的に使用されますが、<th>
でも有効です。
とはいえ、複雑なテーブル構造は、スクリーン リーダーのユーザーだけでなく、すべてのユーザーが理解するのは難しいものです。認知的にもスクリーン リーダーのサポートの観点からも、スコープやヘッダーを追加しなくても、スパンセルがほとんどないか、まったくないシンプルな表は、より簡単に理解できます。管理も簡単です。
テーブルのスタイル設定
簡単に説明した 2 つの比較的わかりにくい要素は、列グループの <colgroup>
要素と、その唯一の子孫である空の <col>
列要素です。<colgroup>
要素は、テーブル内の列のグループまたは <col>
要素を定義するために使用されます。
列グループを使用する場合、<table>
内の <caption>
の直後とテーブルデータの前にネストする必要があります。複数の列にまたがる場合は、span
属性を使用します。
通常、表の内容の概要は次のとおりです。含める必要のある要素は <table>
と <caption>
です。
<table>
<caption>Table Caption</caption>
<colgroup>
<col/>
</colgroup>
<thead>...
<colgroup>
と <col>
のいずれも、テーブルを利用しやすくするという意味ではセマンティックな意味を持ちませんが、CSS による列の幅の設定など、列のスタイルを限定できます。
<col>
スタイルは、そのスタイルをオーバーライドする <td>
または <th>
スタイルがなければ、列のスタイルを設定します。たとえば、<colspan>
を使用してテーブルの一部の行のセルを結合する場合、すべての行の 8 番目の子を選択する tr > *:nth-child(8)
などのセレクタで、8 列目が完全にハイライト表示されたり、複数の行の 8 列目がハイライト表示されたりすることはありませんが、結合先の行または列のセルに応じて 9 列目と 10 列目のセルがわずかにハイライト表示されます。
残念ながら、サポートされているプロパティは限られており、スタイルはセルに継承されません。また、ターゲット セルで <col>
要素を使用するには、:has()
リレーショナル セレクタを含む複雑なセレクタを使用する必要があります。
<table>
と <colgroup>
の両方に背景色が設定されている場合、<colgroup>
の background-color
が上部になります。描画の順序は、テーブルレイヤのスキーマに示すように、テーブル、列グループ、列、行グループ、行、最上層のセルからなります。<td>
要素と <th>
要素は <colgroup>
要素または <col>
要素の子孫ではないため、そのスタイルは継承されません。
テーブルをストライプ化するには、CSS 構造セレクタが便利です。たとえば、tbody tr:nth-of-type(odd) {background-color: rgba(0 0 0 / 0.1);}
は、テーブルの本体の奇数行に半透明の黒を追加し、<colgroup>
に設定されている背景エフェクトが透けて見えるようにします。
テーブルはデフォルトではレスポンシブではありません。デフォルトでは、コンテンツに合わせてサイズが設定されます。テーブル レイアウトのスタイル設定をさまざまなデバイスで効果的に機能させるには、追加の手段が必要です。テーブル要素の CSS 表示プロパティを変更する場合は、ARIA role
属性を含めます。これは冗長に思われるかもしれませんが、一部のブラウザでは CSS display
プロパティがユーザー補助ツリーに影響することがあります。
データの提示
テーブル要素には、支援技術で使用されるセマンティックな意味があり、「失われる」ことなく行や列を移動できます。<table>
要素は表示には使用しないでください。リストの上に見出しが必要な場合は、ヘッダーとリストを使用します。コンテンツを多くの列に配置する場合は、複数列レイアウトを使用します。コンテンツをグリッドに配置する場合は、CSS グリッドを使用します。データにのみテーブルを使用します。次のように考えてください。会議でプレゼンテーションするためにスプレッドシートが必要な場合は、<table>
を使用します。
Keynote や PowerPoint などのプレゼンテーション ソフトウェアの機能を使用する場合は、説明リストが必要になります。
表の列の並べ替えは JavaScript の範囲ですが、ヘッダーをマークアップして列が並べ替え可能であることをユーザーに知らせることは、HTML の範囲です。
表の列が並べ替え可能であること、昇順、降順、並べ替えなしを示すアイコンが表示されていることをユーザーに知らせます。現在並べ替えられている列には、並べ替え方向の列挙値を持つ aria-sort 属性が含まれている必要があります。<caption>
は、aria-live と動的に更新されスクリーン リーダーのユーザーに表示されるスパンを介して、並べ替え順の更新を丁寧にアナウンスできます。ヘッダーのコンテンツをクリックすると列を並べ替えることができるため、ヘッダーのコンテンツは <button>
である必要があります。
表形式のデータを提示しない場合は、<table>
を使用しないでください。プレゼンテーションに表を使用する場合は、role="none"
を設定します。
多くのデベロッパーはフォームの配置にテーブルを使用しますが、その必要はありません。ただし、HTML フォームについては知っておく必要があります。それについては次に説明します。
理解度をチェックする
テーブルに関する知識をテストします。
見出しのセルをマークアップするために使用する要素はどれですか。
<header>
<caption>
<th>
表のあるレイアウトに適した情報はどれですか。
<dl>
のほうが適しています。<ul>
のほうが適しています。