@sofidevo/astro-dynamic-header
v3.1.0
Published
A dynamic Astro header component that switches between floating and fullscreen styles
Maintainers
Readme
@sofidevo/astro-dynamic-header
A dynamic, responsive header component for Astro projects. Supports floating and fullscreen layouts, multi-level dropdown navigation, native CSS variable customization, dark mode, and TypeScript — all with zero external icon dependencies.
Features
- Floating & Fullscreen layouts — switch layouts with a single prop.
- Fully Responsive — mobile-first accordion dropdowns with optimized hit targets.
- 3-level Dropdowns — top, secondary, and tertiary nested navigation items.
- Dark Mode Ready — auto-detects
.darkon<html>, or forces a state withpreset. - Inline SVG Icons — no external CDNs, no extra network requests, no flash of missing icons.
- Slot Support — inject your custom logo and header actions directly into slots.
- Pure CSS Customization — customize background, blur, and colors using native CSS variables.
- Full TypeScript — all props and config interfaces are fully typed.
Live Demo
https://base-astro-psi.vercel.app/fullscreen-demo
Installation
npm i @sofidevo/astro-dynamic-headerNo external CDN scripts or stylesheet additions are required.
Quick Start
---
import Header from '@sofidevo/astro-dynamic-header/Header';
const menuItems = [
{ link: '/about', text: 'About' },
{ link: '/contact', text: 'Contact' },
];
---
<Header navigation={{ menuItems }}>
<a slot="logo" href="/">MyLogo</a>
</Header>Component Props
<Header>
| Prop | Type | Default | Description |
| ------------ | ----------------------------- | ------------ | ------------------------------------------------- |
| headerType | "floating" \| "fullscreen" | "floating" | Layout style |
| preset | "light" \| "dark" \| "auto" | "auto" | Theme mode. "auto" follows .dark on <html>. |
| navigation | NavConfig | {} | Menu items, home link, and custom CSS classes |
| theme | DualThemeConfig | {} | Optional theme overrides (prefer CSS variables) |
| classNames | HeaderClassNames | {} | Inject CSS classes into structural elements |
Configuration Objects
NavConfig
| Property | Type | Default | Description |
| --------------------- | ------------ | ------- | ------------------------------------------------------- |
| menuItems | MenuItem[] | [] | Top-level navigation items |
| homeUrl | string | "/" | URL for the home link |
| header__menu__class | string | — | Extra CSS class(es) for the desktop <nav> element |
| header__item__class | string | — | Extra CSS class(es) for each top-level <li> menu item |
| menu__link__class | string | — | Extra CSS class(es) for each top-level <a> link |
MenuItem
| Property | Type | Required | Description |
| --------- | --------------------- | -------- | --------------------------------- |
| link | string | ✅ | URL the item points to |
| text | string | ✅ | Display label |
| submenu | SecondaryMenuItem[] | — | Optional nested items (2nd level) |
SecondaryMenuItem
| Property | Type | Required | Description |
| --------- | -------------------- | -------- | --------------------------------- |
| link | string | ✅ | URL the item points to |
| text | string | ✅ | Display label |
| submenu | TertiaryMenuItem[] | — | Optional nested items (3rd level) |
TertiaryMenuItem
| Property | Type | Required | Description |
| -------- | -------- | -------- | ---------------------- |
| link | string | ✅ | URL the item points to |
| text | string | ✅ | Display label |
Custom Class Names
The classNames prop lets you inject CSS classes into specific structural elements.
HeaderClassNames
| Property | Target element | Common use cases |
| ----------- | -------------------------------------- | ------------------------------------------------- |
| container | Outer <div> wrapping the header | Positioning, padding, z-index |
| header | Inner <header> element | Shadows, borders, transitions |
| logo | <a> tag surrounding the logo slot | Hover effects, focus rings |
| logoText | <span> containing the logo text | Font weight, tracking, text transforms |
| nav | <div> wrapping the desktop nav items | Spacing, alignment, responsive visibility |
| mobileNav | Root <nav> of the mobile panel | Backdrop blur, custom z-index, slide-in overrides |
<!-- Tailwind example -->
<Header
classNames={{
header: "shadow-xl border-b border-black/5 dark:border-white/10",
container: "top-4 px-6",
mobileNav: "backdrop-blur-md",
}}
/>Slots
| Slot name | Visible on | Description |
| --------- | ---------------- | ---------------------------------------------------------- |
| logo | Header | Render your logo exactly as you need (native HTML/widgets) |
| actions | Desktop + mobile | Add buttons, links, or utility widgets |
<Header navigation={{ menuItems }}>
<a slot="logo" href="/" class="logo-link">
<img src="/logo.svg" alt="Branding" width="40" />
<span>MyBrand</span>
</a>
<div slot="actions">
<a href="/login" class="btn">Log in</a>
</div>
</Header>Customization & Theme Config
You can fully customize the color scheme using CSS Custom Properties (recommended) or the theme prop.
Option 1: Native CSS Variables (Recommended)
Set CSS variables globally in your :root style block:
:root {
/* Light theme overrides */
--l-accent: #7c3aed;
--l-bg: rgba(255, 255, 255, 0.85);
--l-bg-opaque: #ffffff;
--l-text: #1a1a1a;
--l-blur: blur(20px);
/* Dark theme overrides */
--d-accent: #a78bfa;
--d-bg: rgba(10, 10, 10, 0.85);
--d-bg-opaque: #0a0a0a;
--d-text: #f5f5f5;
--d-blur: blur(20px);
/* Hamburger lines override */
--color-hamburger-lines: #7c3aed;
}Option 2: JS Theme Prop
---
import { defaultThemes } from '@sofidevo/astro-dynamic-header';
const theme = {
light: {
...defaultThemes.light,
accentColor: "#7c3aed",
backgroundColor: "rgba(255, 255, 255, 0.85)",
},
dark: {
...defaultThemes.dark,
accentColor: "#a78bfa",
}
};
---
<Header theme={theme} />[!IMPORTANT] When using transparent backgrounds, always supply a solid fallback in
backgroundColorOpaque. Submenus and mobile panels utilize this solid color to prevent visual glitches with nested blur effects.
TypeScript
---
import Header from '@sofidevo/astro-dynamic-header/Header';
import type {
MenuItem,
NavConfig,
HeaderClassNames,
HeaderProps,
} from '@sofidevo/astro-dynamic-header';
const menuItems: MenuItem[] = [
{ link: '/about', text: 'About' }
];
const navigation: NavConfig = {
menuItems,
homeUrl: "/",
header__menu__class: "flex gap-4"
};
const classNames: HeaderClassNames = {
header: "shadow-lg"
};
---
<Header
navigation={navigation}
classNames={classNames}
/>Troubleshooting & FAQ
Import issues
Import using the direct subpath:
import Header from '@sofidevo/astro-dynamic-header/Header';Other components are exported similarly:
import NavMenu from '@sofidevo/astro-dynamic-header/NavMenu';
import MobileNav from '@sofidevo/astro-dynamic-header/MobileNav';
import ChevronIcon from '@sofidevo/astro-dynamic-header/ChevronIcon';Acordion icons not showing up
Icons are rendered as inline SVG components. If you are upgrading from v1.x or v2.0 and have the old ChevronIcon CDN <script> tag in your layout <head>, you can safely remove it.
Compatibility
- Astro 7.x
- SSG, SSR, and Hybrid project outputs.
License
MIT License.
