data-* / hidden / tabindex
| 対応: | HTML5(2014) |
|---|
『data-*』『hidden』『tabindex』はほぼすべてのHTML要素に指定できるグローバル属性です。『data-*』はJavaScriptで使うカスタムデータの埋め込み、『hidden』は要素の非表示、『tabindex』はキーボードのTabキーによるフォーカス順序の制御に使用します。
構文
<!-- data-* カスタムデータ属性 --> <div data-user-id="123" data-role="admin">...</div> <!-- hidden 要素を非表示にする --> <p hidden>この段落は非表示です。</p> <!-- tabindex フォーカス順序の制御 --> <div tabindex="0">フォーカス可能な要素</div> <input tabindex="1" type="text"> <input tabindex="-1" type="text"><!-- フォーカスをスキップ -->
属性一覧
| 属性 | 概要 |
|---|---|
| data-* | 任意のカスタムデータを要素に埋め込みます。『data-』に続けて自由な名前を付けられます。JavaScriptの『dataset』プロパティで読み書きできます。 |
| hidden | 要素を非表示にします。値なしのブール属性で、指定するだけで要素が見えなくなります。CSSの『display: none』と同様の効果です。 |
| tabindex | Tabキーによるフォーカスの順序を数値で指定します。『0』で自然な順序でフォーカス可能になり、『-1』でフォーカスをスキップします。 |
tabindexの値一覧
| 値 | 概要 |
|---|---|
| 正の整数(1, 2, 3...) | 数値の小さい順にフォーカスされます。自然な順序を乱すため、通常は使用しません。 |
| 0 | DOMの順序でフォーカスされます。本来フォーカスできない要素(divなど)をフォーカス可能にする際に使用します。 |
| -1 | Tabキーではフォーカスされなくなります。JavaScriptで『.focus()』を呼べば手動でフォーカスできます。 |
サンプルコード
sample_data_hidden_tabindex.html
<!-- data-*にデータを埋め込む -->
<ul id="product-list">
<li data-product-id="101" data-price="1500">商品A</li>
<li data-product-id="102" data-price="2800">商品B</li>
</ul>
<!-- hiddenで初期状態を非表示にする -->
<div id="detail-panel" hidden>
<p>詳細情報がここに表示されます。</p>
</div>
<button onclick="document.getElementById('detail-panel').hidden = false;">
詳細を表示する
</button>
<!-- tabindex="0": div要素をキーボードフォーカス可能にする -->
<div tabindex="0"
style="padding: 8px; border: 2px solid #ccc; display: inline-block;"
onkeydown="if(event.key==='Enter'||event.key===' ') alert('選択されました');">
Tabキーでフォーカスできる要素
</div>
<!-- tabindex="-1": JSで手動フォーカスさせる(Tabではスキップ) -->
<div id="modal-close" tabindex="-1"
style="padding: 8px; background: #eee;">
モーダルの閉じるボタン(TabではスキップされJSからfocus()で使う)
</div>
<button onclick="document.getElementById('modal-close').focus();">
閉じるにフォーカス
</button>
sample_data_hidden_tabindex.js
// data-*属性をJavaScriptで読み取る
var items = document.querySelectorAll('#product-list li');
items.forEach(function(item) {
var id = item.dataset.productId; // data-product-id → dataset.productId
var price = item.dataset.price;
console.log('ID: ' + id + ' 価格: ' + price + '円');
});
// data-*属性をJavaScriptで書き込む
var firstItem = document.querySelector('#product-list li');
firstItem.dataset.inStock = 'true'; // data-in-stock="true" が追加される
実行結果
ページ読み込み時は「詳細を表示する」ボタンのみ表示されます。ボタンをクリックすると、『hidden』属性が外れて詳細パネルが表示されます。
概要
『data-*』属性はHTMLとJavaScriptのデータ受け渡しによく使われます。JavaScriptでは『dataset』プロパティを使ってアクセスでき、属性名のハイフン区切り(例: 『data-product-id』)はキャメルケース(例: 『dataset.productId』)に自動変換されます。
『hidden』属性はCSSの『display: none』と同じ効果ですが、HTMLの属性として記述できるため、JavaScriptで『要素.hidden = true/false』と書くだけで表示・非表示を切り替えられて便利です。ただし、CSSで『display: flex』などを指定している要素に対しては『hidden』が上書きされる場合があるため、注意が必要です。
『tabindex』はアクセシビリティ向上のために使用します。正の整数を使ったフォーカス順序の制御は、DOMの自然な順序を乱してスクリーンリーダーの利用者を混乱させる可能性があるため、基本的には避けてください。『tabindex="0"』と『tabindex="-1"』の2種類で大半のユースケースに対応できます。
対応ブラウザ
22 以降 ○
21 以前 ×
Android Browser
62 以降 ○
61 以前 ×※ バージョン情報は MDN に基づいています。
JavaScriptとの連携
『data-*』属性はJavaScriptから簡単に読み書きでき、DOMと状態管理を連携させる際に非常に役立ちます。
<!-- data-* 属性でデータを埋め込む -->
<ul id="product-list">
<li data-product-id="101" data-price="2980" data-stock="5">
商品A - ¥2,980
<button class="add-to-cart">カートに追加</button>
</li>
<li data-product-id="102" data-price="4500" data-stock="0">
商品B - ¥4,500
<button class="add-to-cart" disabled>在庫なし</button>
</li>
</ul>
<script>
var buttons = document.querySelectorAll('.add-to-cart');
buttons.forEach(function(btn) {
btn.addEventListener('click', function() {
var item = btn.closest('li');
// dataset プロパティで data-* 属性にアクセス
// data-product-id → dataset.productId(camelCaseに変換される)
var id = item.dataset.productId;
var price = parseInt(item.dataset.price, 10);
var stock = parseInt(item.dataset.stock, 10);
if (stock > 0) {
console.log('カートに追加: ID=' + id + ', 価格=' + price);
// data-stock を更新する
item.dataset.stock = stock - 1;
}
});
});
</script>
tabindexの実践的な使い方
『tabindex』はキーボードナビゲーションの順序を制御します。アクセシビリティに大きく影響するため、正しい使い方を理解することが重要です。
| 値 | 効果 | 推奨度 |
|---|---|---|
| tabindex="0" | デフォルトのタブ順序に追加(HTMLの順序に従う)。div等の非フォーカス要素をフォーカス可能にする | 推奨 |
| tabindex="-1" | Tabキーの順序から除外(JSからfocus()で直接フォーカスは可能) | 推奨 |
| tabindex="1以上" | 正の値で順序を指定(推奨されない。管理が複雑になりバグの元になる) | 非推奨 |
<!-- tabindex="0" で非インタラクティブな要素をキーボード操作可能にする -->
<div tabindex="0" role="button" id="customBtn"
style="padding: 8px 16px; background: #4488ff; color: white; cursor: pointer; border-radius: 4px;">
カスタムボタン
</div>
<!-- tabindex="-1" でモーダルの最初の要素にフォーカスを移動する -->
<div id="modal" role="dialog" aria-modal="true" aria-label="確認ダイアログ">
<h2 tabindex="-1" id="modal-heading">本当に削除しますか?</h2>
<button>はい</button>
<button>いいえ</button>
</div>
<script>
// モーダルを開いたとき、tabindex="-1"の要素に直接フォーカスを移す
function openModal() {
var heading = document.getElementById('modal-heading');
heading.focus(); // tabindex="-1"があるのでfocus()できる
}
</script>
記事の間違いや著作権の侵害等ございましたらお手数ですがこちらまでご連絡頂ければ幸いです。