タブメニュー デザイン見本
タブをクリック(またはホバー)して表示内容を切り替えるタブメニューの実装デモ。コピーしてすぐに使えるHTML・CSS・JSのコードを掲載しています。
① クリック — タブをクリックで表示を切り替える
Tab 1 の内容です。
クリックでタブを切り替えてください。
Tab 2 の内容です。
テキストや画像を自由に配置できます。
Tab 3 の内容です。
複数の情報を整理して表示できます。
選択中のタブ: Tab 1
<div class="tab-container">
<ul>
<li class="selected" data-id="tab-1">Tab 1</li>
<li data-id="tab-2">Tab 2</li>
<li data-id="tab-3">Tab 3</li>
</ul>
<div class="tab-content selected" id="tab-1">
タブ1のコンテンツです。
</div>
<div class="tab-content" id="tab-2">
タブ2のコンテンツです。
</div>
<div class="tab-content" id="tab-3">
タブ3のコンテンツです。
</div>
</div>
.tab-container ul {
margin: 0;
padding: 0;
list-style: none;
display: flex;
}
.tab-container ul li {
width: 100%;
padding: 10px 16px;
text-align: center;
cursor: pointer;
border-bottom: 3px solid transparent;
transition: border-color 0.2s, color 0.2s;
}
.tab-container ul li.selected {
color: #2563eb;
border-bottom-color: #2563eb;
font-weight: 700;
}
.tab-container ul li:not(.selected):hover {
opacity: 0.6;
}
.tab-content {
display: none;
padding: 20px;
border: 1px solid #e2e8f0;
border-top: none;
}
.tab-content.selected {
display: block;
}
const tabItems = document.querySelectorAll('.tab-container ul li');
const tabContents = document.querySelectorAll('.tab-container .tab-content');
tabItems.forEach(item => {
item.addEventListener('click', () => {
tabItems.forEach(t => t.classList.remove('selected'));
tabContents.forEach(c => c.classList.remove('selected'));
item.classList.add('selected');
document.getElementById(item.dataset.id).classList.add('selected');
});
});
タブのコンテンツは初期状態で display: none にしておき、selected クラスが付いたものだけ display: block で表示します。タブをクリックすると、まず全タブと全コンテンツから selected を除去し、クリックされたタブと data-id に対応するコンテンツにだけ selected を付与します。このパターンは1つの要素しか表示しない「排他制御」の基本形で、モーダルやアコーディオンにも応用できます。
② ホバー — マウスホバーで表示を切り替える
Tab 1 の内容です。
タブにマウスを乗せて切り替えてください。
Tab 2 の内容です。
Tab 3 の内容です。
ホバー中のタブ: Tab 1
<div class="tab-container">
<ul>
<li class="selected" data-id="tab-1">Tab 1</li>
<li data-id="tab-2">Tab 2</li>
<li data-id="tab-3">Tab 3</li>
</ul>
<div class="tab-content selected" id="tab-1">
タブ1のコンテンツです。
</div>
<div class="tab-content" id="tab-2">
タブ2のコンテンツです。
</div>
<div class="tab-content" id="tab-3">
タブ3のコンテンツです。
</div>
</div>
.tab-container ul {
margin: 0;
padding: 0;
list-style: none;
display: flex;
}
.tab-container ul li {
width: 100%;
padding: 10px 16px;
text-align: center;
cursor: pointer;
border-bottom: 3px solid transparent;
transition: border-color 0.2s, color 0.2s;
}
.tab-container ul li.selected {
color: #2563eb;
border-bottom-color: #2563eb;
font-weight: 700;
}
.tab-content {
display: none;
padding: 20px;
border: 1px solid #e2e8f0;
border-top: none;
}
.tab-content.selected {
display: block;
}
const tabItems = document.querySelectorAll('.tab-container ul li');
const tabContents = document.querySelectorAll('.tab-container .tab-content');
tabItems.forEach(item => {
item.addEventListener('mouseover', () => {
tabItems.forEach(t => t.classList.remove('selected'));
tabContents.forEach(c => c.classList.remove('selected'));
item.classList.add('selected');
document.getElementById(item.dataset.id).classList.add('selected');
});
});
click の代わりに mouseover イベントを使うだけで、マウスを乗せた瞬間にタブが切り替わります。mouseover はカーソルが要素の上に来るたびに発火します。なお、子要素があると子要素からの移動でも発火する場合があるため、子要素を持つ複雑な構造の場合は mouseenter イベントの使用も検討してください。
③ レスポンシブ — 画面サイズで縦横レイアウトを自動調整する
Tab 1 の内容です。
PC幅では横並び、SP幅では縦並びに切り替わります。
Tab 2 の内容です。
Tab 3 の内容です。
表示モード: PC幅(481px超)
<div class="tab-container">
<ul>
<li class="selected" data-id="tab-1">Tab 1</li>
<li data-id="tab-2">Tab 2</li>
<li data-id="tab-3">Tab 3</li>
</ul>
<div class="tab-content selected" id="tab-1">
タブ1のコンテンツです。
</div>
<div class="tab-content" id="tab-2">
タブ2のコンテンツです。
</div>
<div class="tab-content" id="tab-3">
タブ3のコンテンツです。
</div>
</div>
.tab-container ul {
margin: 0;
padding: 0;
list-style: none;
display: flex;
}
.tab-container ul li {
width: 100%;
padding: 10px 16px;
text-align: center;
cursor: pointer;
border-bottom: 3px solid transparent;
transition: border-color 0.2s, color 0.2s;
}
.tab-container ul li.selected {
color: #2563eb;
border-bottom-color: #2563eb;
font-weight: 700;
}
.tab-container ul li:not(.selected):hover {
opacity: 0.6;
}
.tab-content {
display: none;
padding: 20px;
border: 1px solid #e2e8f0;
border-top: none;
}
.tab-content.selected {
display: block;
}
@media (max-width: 600px) {
.tab-container ul {
flex-direction: column;
}
.tab-container ul li {
border-bottom: 1px solid #e2e8f0;
border-left: 3px solid transparent;
text-align: left;
}
.tab-container ul li.selected {
color: #2563eb;
border-left-color: #2563eb;
border-bottom-color: #e2e8f0;
}
.tab-content {
border-top: 1px solid #e2e8f0;
}
}
const tabItems = document.querySelectorAll('.tab-container ul li');
const tabContents = document.querySelectorAll('.tab-container .tab-content');
tabItems.forEach(item => {
item.addEventListener('click', () => {
tabItems.forEach(t => t.classList.remove('selected'));
tabContents.forEach(c => c.classList.remove('selected'));
item.classList.add('selected');
document.getElementById(item.dataset.id).classList.add('selected');
});
});
タブの横並びは display: flex で実現しています。@media (max-width: 600px) の中で flex-direction: column に切り替えると、タブが縦積みに変わります。あわせてアクティブ表示のインジケーターを border-bottom から border-left に変えることで、縦並びでも選択状態が視覚的にわかりやすくなります。JSのロジックはクリック版と同じため、変更は不要です。

当サイトで公開しているWebデザインやUIの実装例は、一覧として以下記事に纏めています。

