レスポンシブ・ナビバー
ロゴ・メニュー・CTAを横並びに表示するナビバー。画面が狭くなるとハンバーガーボタンに切り替わり、タップで全幅ドロワーメニューがふわりと展開します。
ライブデモ
コード
HTML
<!-- 幅に応じて横並びメニュー⇄ハンバーガー+ドロワーを切り替えるレスポンシブ・ナビバー -->
<div class="nnr-frame" id="nnrFrame">
<header class="nnr-head">
<a class="nnr-logo" href="#" onclick="return false"><span class="nnr-logo__mark">◆</span>Arcadia</a>
<nav class="nnr-nav" aria-label="メインナビゲーション">
<a href="#" onclick="return false" aria-current="page">ホーム</a>
<a href="#" onclick="return false">プロダクト</a>
<a href="#" onclick="return false">料金</a>
<a href="#" onclick="return false">導入事例</a>
<a href="#" onclick="return false">会社情報</a>
</nav>
<div class="nnr-actions">
<a class="nnr-cta" href="#" onclick="return false">無料で始める</a>
<button class="nnr-burger" id="nnrBurger" type="button" aria-label="メニューを開く" aria-expanded="false" aria-controls="nnrDrawer">
<span></span><span></span><span></span>
</button>
</div>
</header>
<div class="nnr-overlay" id="nnrOverlay" aria-hidden="true"></div>
<nav class="nnr-drawer" id="nnrDrawer" aria-label="モバイルメニュー" aria-hidden="true">
<a href="#" onclick="return false" style="--i:0" aria-current="page">ホーム</a>
<a href="#" onclick="return false" style="--i:1">プロダクト</a>
<a href="#" onclick="return false" style="--i:2">料金</a>
<a href="#" onclick="return false" style="--i:3">導入事例</a>
<a href="#" onclick="return false" style="--i:4">会社情報</a>
<a class="nnr-drawer__cta" href="#" onclick="return false" style="--i:5">無料で始める</a>
</nav>
<div class="nnr-stage">
<p class="nnr-hint">画面幅が広いと横並びメニュー、狭くなるとハンバーガー→ドロワーに切り替わります。<br><small>(このプレビュー幅に応じて自動的に表示が変わります)</small></p>
</div>
</div>
CSS
* { box-sizing: border-box; }
body { margin: 0; display: block; background: #f7faf9; font-family: "Hiragino Sans", "Segoe UI", system-ui, sans-serif; }
/* ルート: width:100% + height:100vh でカード/モーダルどちらの枠にも隙間なく収まる */
.nnr-frame { position: relative; width: 100%; height: 100vh; overflow: hidden; background: #f7faf9; }
.nnr-head {
position: relative; z-index: 20;
display: flex; align-items: center; gap: 18px;
height: 62px; padding: 0 22px;
background: #fff; border-bottom: 1px solid #e3ece9;
}
.nnr-logo { display: flex; align-items: center; gap: 7px; font-size: 18px; font-weight: 800; color: #0f2b25; text-decoration: none; letter-spacing: -.01em; flex-shrink: 0; }
.nnr-logo__mark { color: #0d9488; font-size: 15px; }
.nnr-nav { display: flex; align-items: center; gap: 4px; }
.nnr-nav a {
position: relative; font-size: 13.5px; font-weight: 600; color: #3f5852;
text-decoration: none; padding: 8px 12px; border-radius: 8px; white-space: nowrap;
transition: background .18s ease, color .18s ease;
}
.nnr-nav a:hover { background: #eef7f5; color: #0d9488; }
.nnr-nav a[aria-current="page"] { color: #0d9488; }
.nnr-nav a[aria-current="page"]::after {
content: ""; position: absolute; left: 12px; right: 12px; bottom: 3px; height: 2px;
background: #0d9488; border-radius: 2px;
}
.nnr-actions { margin-left: auto; display: flex; align-items: center; gap: 14px; }
.nnr-cta {
font-size: 13px; font-weight: 700; color: #fff; text-decoration: none; white-space: nowrap;
padding: 9px 18px; border-radius: 999px;
background: linear-gradient(120deg, #0d9488, #059669);
transition: filter .15s ease, transform .15s ease;
}
.nnr-cta:hover { filter: brightness(1.08); transform: translateY(-1px); }
/* ハンバーガー:3本線 → X へモーフ。狭幅でのみ表示 */
.nnr-burger { display: none; width: 38px; height: 38px; position: relative; background: none; border: none; cursor: pointer; padding: 0; flex-shrink: 0; }
.nnr-burger span {
position: absolute; left: 8px; right: 8px; height: 2px; background: #12312b; border-radius: 2px;
transition: transform .3s ease, opacity .2s ease;
}
.nnr-burger span:nth-child(1) { top: 13px; }
.nnr-burger span:nth-child(2) { top: 18px; }
.nnr-burger span:nth-child(3) { top: 23px; }
.nnr-frame.is-open .nnr-burger span:nth-child(1) { transform: translateY(5px) rotate(45deg); }
.nnr-frame.is-open .nnr-burger span:nth-child(2) { opacity: 0; }
.nnr-frame.is-open .nnr-burger span:nth-child(3) { transform: translateY(-5px) rotate(-45deg); }
/* ドロワー:ヘッダー直下からフルワイドで展開 */
.nnr-overlay {
position: absolute; inset: 62px 0 0 0; z-index: 15;
background: rgba(10, 30, 25, .28); opacity: 0; pointer-events: none;
transition: opacity .25s ease;
}
.nnr-frame.is-open .nnr-overlay { opacity: 1; pointer-events: auto; }
.nnr-drawer {
position: absolute; top: 62px; left: 0; right: 0; z-index: 18;
display: flex; flex-direction: column; gap: 2px;
padding: 10px; background: #fff; border-bottom: 1px solid #e3ece9;
box-shadow: 0 20px 40px rgba(10, 40, 32, .14);
transform: translateY(-8px); opacity: 0; pointer-events: none;
transition: transform .25s ease, opacity .2s ease;
}
.nnr-frame.is-open .nnr-drawer { transform: translateY(0); opacity: 1; pointer-events: auto; }
.nnr-drawer a {
--d: calc(var(--i, 0) * 45ms);
font-size: 14px; font-weight: 600; color: #1c3a33; text-decoration: none;
padding: 12px 14px; border-radius: 9px;
opacity: 0; transform: translateY(-6px);
transition: background .18s ease, opacity .3s ease var(--d), transform .3s ease var(--d);
}
.nnr-frame.is-open .nnr-drawer a { opacity: 1; transform: translateY(0); }
.nnr-drawer a:hover { background: #eef7f5; }
.nnr-drawer a[aria-current="page"] { color: #0d9488; }
.nnr-drawer__cta { margin-top: 6px; text-align: center; color: #fff !important; background: linear-gradient(120deg, #0d9488, #059669); }
.nnr-stage { display: grid; place-content: center; height: calc(100% - 62px); text-align: center; padding: 24px; }
.nnr-hint { color: #4b6961; font-size: 13.5px; line-height: 1.8; max-width: 380px; margin: 0; }
.nnr-hint small { color: #7c948c; }
@media (max-width: 680px) {
.nnr-nav, .nnr-cta { display: none; }
.nnr-burger { display: block; }
}
@media (prefers-reduced-motion: reduce) {
.nnr-drawer, .nnr-drawer a, .nnr-overlay, .nnr-burger span, .nnr-cta { transition: none; }
}
JavaScript
// ハンバーガー⇄ドロワーの開閉。狭幅の時だけ自動デモも実演し、実操作が来たら止まる(null安全)
(() => {
const frame = document.getElementById('nnrFrame');
const burger = document.getElementById('nnrBurger');
const overlay = document.getElementById('nnrOverlay');
const drawer = document.getElementById('nnrDrawer');
if (!frame || !burger) return;
const set = (open) => {
frame.classList.toggle('is-open', open);
burger.setAttribute('aria-expanded', open ? 'true' : 'false');
if (overlay) overlay.setAttribute('aria-hidden', open ? 'false' : 'true');
if (drawer) drawer.setAttribute('aria-hidden', open ? 'false' : 'true');
};
let auto = !matchMedia('(prefers-reduced-motion: reduce)').matches;
burger.addEventListener('click', () => { auto = false; set(!frame.classList.contains('is-open')); });
if (overlay) overlay.addEventListener('click', () => { auto = false; set(false); });
if (drawer) drawer.querySelectorAll('a').forEach((a) => a.addEventListener('click', () => { auto = false; set(false); }));
const isMobile = () => getComputedStyle(burger).display !== 'none';
if (auto) {
let open = false;
const tick = () => {
if (!auto || !isMobile()) return;
open = !open;
set(open);
setTimeout(tick, open ? 2200 : 1400);
};
setTimeout(tick, 1000);
}
})();
🤖 AIエージェント用プロンプト
このままコピーしてAIに貼り付け「追加する場所」だけ書き換えればOK
あなたは熟練のフロントエンドエンジニアです。私のWebサイトに「レスポンシブ・ナビバー」の効果を追加してください。
# 追加してほしい効果
レスポンシブ・ナビバー(ヘッダー & ナビ)
ロゴ・メニュー・CTAを横並びに表示するナビバー。画面が狭くなるとハンバーガーボタンに切り替わり、タップで全幅ドロワーメニューがふわりと展開します。
# 追加する場所
👉【ここに対象箇所を記入:例「トップのヒーローセクション」「お問い合わせボタン」「記事カードの一覧」など】
# 参考実装(この見た目・挙動を再現してください)
【HTML】
<!-- 幅に応じて横並びメニュー⇄ハンバーガー+ドロワーを切り替えるレスポンシブ・ナビバー -->
<div class="nnr-frame" id="nnrFrame">
<header class="nnr-head">
<a class="nnr-logo" href="#" onclick="return false"><span class="nnr-logo__mark">◆</span>Arcadia</a>
<nav class="nnr-nav" aria-label="メインナビゲーション">
<a href="#" onclick="return false" aria-current="page">ホーム</a>
<a href="#" onclick="return false">プロダクト</a>
<a href="#" onclick="return false">料金</a>
<a href="#" onclick="return false">導入事例</a>
<a href="#" onclick="return false">会社情報</a>
</nav>
<div class="nnr-actions">
<a class="nnr-cta" href="#" onclick="return false">無料で始める</a>
<button class="nnr-burger" id="nnrBurger" type="button" aria-label="メニューを開く" aria-expanded="false" aria-controls="nnrDrawer">
<span></span><span></span><span></span>
</button>
</div>
</header>
<div class="nnr-overlay" id="nnrOverlay" aria-hidden="true"></div>
<nav class="nnr-drawer" id="nnrDrawer" aria-label="モバイルメニュー" aria-hidden="true">
<a href="#" onclick="return false" style="--i:0" aria-current="page">ホーム</a>
<a href="#" onclick="return false" style="--i:1">プロダクト</a>
<a href="#" onclick="return false" style="--i:2">料金</a>
<a href="#" onclick="return false" style="--i:3">導入事例</a>
<a href="#" onclick="return false" style="--i:4">会社情報</a>
<a class="nnr-drawer__cta" href="#" onclick="return false" style="--i:5">無料で始める</a>
</nav>
<div class="nnr-stage">
<p class="nnr-hint">画面幅が広いと横並びメニュー、狭くなるとハンバーガー→ドロワーに切り替わります。<br><small>(このプレビュー幅に応じて自動的に表示が変わります)</small></p>
</div>
</div>
【CSS】
* { box-sizing: border-box; }
body { margin: 0; display: block; background: #f7faf9; font-family: "Hiragino Sans", "Segoe UI", system-ui, sans-serif; }
/* ルート: width:100% + height:100vh でカード/モーダルどちらの枠にも隙間なく収まる */
.nnr-frame { position: relative; width: 100%; height: 100vh; overflow: hidden; background: #f7faf9; }
.nnr-head {
position: relative; z-index: 20;
display: flex; align-items: center; gap: 18px;
height: 62px; padding: 0 22px;
background: #fff; border-bottom: 1px solid #e3ece9;
}
.nnr-logo { display: flex; align-items: center; gap: 7px; font-size: 18px; font-weight: 800; color: #0f2b25; text-decoration: none; letter-spacing: -.01em; flex-shrink: 0; }
.nnr-logo__mark { color: #0d9488; font-size: 15px; }
.nnr-nav { display: flex; align-items: center; gap: 4px; }
.nnr-nav a {
position: relative; font-size: 13.5px; font-weight: 600; color: #3f5852;
text-decoration: none; padding: 8px 12px; border-radius: 8px; white-space: nowrap;
transition: background .18s ease, color .18s ease;
}
.nnr-nav a:hover { background: #eef7f5; color: #0d9488; }
.nnr-nav a[aria-current="page"] { color: #0d9488; }
.nnr-nav a[aria-current="page"]::after {
content: ""; position: absolute; left: 12px; right: 12px; bottom: 3px; height: 2px;
background: #0d9488; border-radius: 2px;
}
.nnr-actions { margin-left: auto; display: flex; align-items: center; gap: 14px; }
.nnr-cta {
font-size: 13px; font-weight: 700; color: #fff; text-decoration: none; white-space: nowrap;
padding: 9px 18px; border-radius: 999px;
background: linear-gradient(120deg, #0d9488, #059669);
transition: filter .15s ease, transform .15s ease;
}
.nnr-cta:hover { filter: brightness(1.08); transform: translateY(-1px); }
/* ハンバーガー:3本線 → X へモーフ。狭幅でのみ表示 */
.nnr-burger { display: none; width: 38px; height: 38px; position: relative; background: none; border: none; cursor: pointer; padding: 0; flex-shrink: 0; }
.nnr-burger span {
position: absolute; left: 8px; right: 8px; height: 2px; background: #12312b; border-radius: 2px;
transition: transform .3s ease, opacity .2s ease;
}
.nnr-burger span:nth-child(1) { top: 13px; }
.nnr-burger span:nth-child(2) { top: 18px; }
.nnr-burger span:nth-child(3) { top: 23px; }
.nnr-frame.is-open .nnr-burger span:nth-child(1) { transform: translateY(5px) rotate(45deg); }
.nnr-frame.is-open .nnr-burger span:nth-child(2) { opacity: 0; }
.nnr-frame.is-open .nnr-burger span:nth-child(3) { transform: translateY(-5px) rotate(-45deg); }
/* ドロワー:ヘッダー直下からフルワイドで展開 */
.nnr-overlay {
position: absolute; inset: 62px 0 0 0; z-index: 15;
background: rgba(10, 30, 25, .28); opacity: 0; pointer-events: none;
transition: opacity .25s ease;
}
.nnr-frame.is-open .nnr-overlay { opacity: 1; pointer-events: auto; }
.nnr-drawer {
position: absolute; top: 62px; left: 0; right: 0; z-index: 18;
display: flex; flex-direction: column; gap: 2px;
padding: 10px; background: #fff; border-bottom: 1px solid #e3ece9;
box-shadow: 0 20px 40px rgba(10, 40, 32, .14);
transform: translateY(-8px); opacity: 0; pointer-events: none;
transition: transform .25s ease, opacity .2s ease;
}
.nnr-frame.is-open .nnr-drawer { transform: translateY(0); opacity: 1; pointer-events: auto; }
.nnr-drawer a {
--d: calc(var(--i, 0) * 45ms);
font-size: 14px; font-weight: 600; color: #1c3a33; text-decoration: none;
padding: 12px 14px; border-radius: 9px;
opacity: 0; transform: translateY(-6px);
transition: background .18s ease, opacity .3s ease var(--d), transform .3s ease var(--d);
}
.nnr-frame.is-open .nnr-drawer a { opacity: 1; transform: translateY(0); }
.nnr-drawer a:hover { background: #eef7f5; }
.nnr-drawer a[aria-current="page"] { color: #0d9488; }
.nnr-drawer__cta { margin-top: 6px; text-align: center; color: #fff !important; background: linear-gradient(120deg, #0d9488, #059669); }
.nnr-stage { display: grid; place-content: center; height: calc(100% - 62px); text-align: center; padding: 24px; }
.nnr-hint { color: #4b6961; font-size: 13.5px; line-height: 1.8; max-width: 380px; margin: 0; }
.nnr-hint small { color: #7c948c; }
@media (max-width: 680px) {
.nnr-nav, .nnr-cta { display: none; }
.nnr-burger { display: block; }
}
@media (prefers-reduced-motion: reduce) {
.nnr-drawer, .nnr-drawer a, .nnr-overlay, .nnr-burger span, .nnr-cta { transition: none; }
}
【JavaScript】
// ハンバーガー⇄ドロワーの開閉。狭幅の時だけ自動デモも実演し、実操作が来たら止まる(null安全)
(() => {
const frame = document.getElementById('nnrFrame');
const burger = document.getElementById('nnrBurger');
const overlay = document.getElementById('nnrOverlay');
const drawer = document.getElementById('nnrDrawer');
if (!frame || !burger) return;
const set = (open) => {
frame.classList.toggle('is-open', open);
burger.setAttribute('aria-expanded', open ? 'true' : 'false');
if (overlay) overlay.setAttribute('aria-hidden', open ? 'false' : 'true');
if (drawer) drawer.setAttribute('aria-hidden', open ? 'false' : 'true');
};
let auto = !matchMedia('(prefers-reduced-motion: reduce)').matches;
burger.addEventListener('click', () => { auto = false; set(!frame.classList.contains('is-open')); });
if (overlay) overlay.addEventListener('click', () => { auto = false; set(false); });
if (drawer) drawer.querySelectorAll('a').forEach((a) => a.addEventListener('click', () => { auto = false; set(false); }));
const isMobile = () => getComputedStyle(burger).display !== 'none';
if (auto) {
let open = false;
const tick = () => {
if (!auto || !isMobile()) return;
open = !open;
set(open);
setTimeout(tick, open ? 2200 : 1400);
};
setTimeout(tick, 1000);
}
})();
# 外部ライブラリ
なし(追加ライブラリ不要)
# 守ってほしいこと
- 既存のHTML構造・レイアウト・デザインを壊さないこと。必要に応じてクラス名・色・サイズを私のサイトに合わせて調整してよい。
- クラス名やidが既存と衝突しないよう、必要なら接頭辞で名前空間を分けること。
- レスポンシブ対応と prefers-reduced-motion への配慮を入れること。
- 私のサイトのフレームワーク(React / Vue / 素のHTML など)に合わせて実装すること。不明な場合は素のHTML/CSS/JSで提示し、組み込み手順も説明すること。
- 変更後の確認手順も簡潔に教えてください。