Navbar
Navbar Is a Layout Shell
A navbar is not just a row of links. In production it carries navigation, branding, search, user actions, and often needs to behave differently on mobile vs desktop. The goal is a predictable structure: container, spacing, alignment, active states, and accessible focus behavior.
Baseline navbar structure
Use a border to separate the navbar from content. Use container + padding for consistent gutters.
<header class="border-b border-slate-200 bg-white">
<div class="container mx-auto px-4 h-14 flex items-center justify-between">
<div class="flex items-center gap-3">
<a href="#" class="font-semibold text-slate-900">Brand</a>
<nav class="hidden md:flex items-center gap-6">
<a class="text-sm text-slate-600 hover:text-slate-900">Docs</a>
<a class="text-sm text-slate-600 hover:text-slate-900">API</a>
<a class="text-sm text-slate-600 hover:text-slate-900">Guides</a>
</nav>
</div>
<div class="flex items-center gap-2">
<button class="hidden md:inline-flex px-3 py-2 rounded-md border border-slate-300 hover:bg-slate-50">Sign in</button>
<button class="md:hidden px-3 py-2 rounded-md border border-slate-300 hover:bg-slate-50">Menu</button>
</div>
</div>
</header>
Active link styling
Navigation needs a clear active state. Use color plus a subtle underline or border indicator. Keep it consistent across the site.
<a class="text-sm font-medium text-slate-900 border-b-2 border-blue-600 pb-4"> Docs </a>
Focus styles for accessibility
Links in a navbar must be keyboard navigable and show visible focus. Never remove outlines without replacing them.
<a class="text-sm text-slate-600 hover:text-slate-900
focus:outline-none focus:ring-2 focus:ring-blue-500 focus:ring-offset-2 rounded">
Guides
</a>
Sticky navbar pattern
Sticky navbars are common in docs and dashboards. Always set background and z-index so the bar stays readable and above content.
<header class="sticky top-0 z-50 bg-white border-b border-slate-200"> ... </header>
Mobile menu: structure first
The mobile menu usually becomes a vertical panel. Tailwind handles the layout; JavaScript handles open/close. Keep the HTML structure clean and predictable.
Simple mobile dropdown panel
<div class="md:hidden border-t border-slate-200 bg-white">
<nav class="px-4 py-3 space-y-1">
<a class="block px-3 py-2 rounded-md text-sm text-slate-700 hover:bg-slate-50">Docs</a>
<a class="block px-3 py-2 rounded-md text-sm text-slate-700 hover:bg-slate-50">API</a>
<a class="block px-3 py-2 rounded-md text-sm text-slate-700 hover:bg-slate-50">Guides</a>
</nav>
</div>
Navbar with search input
Docs sites often have search. Use a subtle input style with ring focus. On mobile, search can move into the menu panel.
<div class="hidden lg:flex items-center">
<input
class="w-72 rounded-md border border-slate-300 px-3 py-2 text-sm
focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-blue-500"
placeholder="Search..."
/>
</div>
Dark mode navbar
In dark mode, adjust background, border, and text roles. Keep hover contrast visible.
<header class="border-b border-slate-200 bg-white
dark:bg-slate-950 dark:border-slate-800">
<div class="container mx-auto px-4 h-14 flex items-center justify-between">
<a class="font-semibold text-slate-900 dark:text-slate-100">Brand</a>
<a class="text-sm text-slate-600 hover:text-slate-900
dark:text-slate-400 dark:hover:text-slate-100">Docs</a>
</div>
</header>
Common mistakes
- Navbar without consistent gutters (content jumps between pages).
- Weak active state (users don't know where they are).
- No focus styles (keyboard navigation becomes invisible).
- Sticky navbar without background or z-index (content bleeds under).
- Mobile menu treated as an afterthought (links become cramped).
Production checklist
- Use container + px-* for stable gutters.
- Define one clear active link pattern site-wide.
- Add focus:ring styles for all interactive elements.
- Design mobile menu as a real vertical navigation, not a squeezed row.
- For sticky navbars, always set bg + z-index.