Layout layoutgridholygraildashboardstructure
Holy Grail Grid
Modern CSS grid-based responsive layout with header, collapsible left sidebar, dynamic main content area, right aside, and footer.
Preview
Usage
Copy the full block below to use this component with its imports.
astro
---
import { HolyGrailGrid } from 'astro-component-kit';
---
<HolyGrailGrid><div slot="header">Header</div><div slot="left">Sidebar</div><div slot="main">Content</div><div slot="footer">Footer</div></HolyGrailGrid> ---
import { HolyGrailGrid } from 'astro-component-kit';
---
<HolyGrailGrid><div slot="header">Header</div><div slot="left">Sidebar</div><div slot="main">Content</div><div slot="footer">Footer</div></HolyGrailGrid> Manual Installation
If you are not using the npm package, create a new file src/components/lib/HolyGrailGrid.astro and paste the following code:
astro
---
/**
* HolyGrailGrid — Production-grade CSS grid layout container with sticky header, dual sidebars, fluid content, and footer.
*
* @param {string} leftWidth - Left sidebar width. Default is '240px'.
* @param {string} rightWidth - Right sidebar width. Default is '220px'.
* @param {string} gap - Spacing gap between grid regions. Default is '1.5rem'.
* @param {string} className - Optional CSS class.
*/
interface Props {
leftWidth?: string;
rightWidth?: string;
gap?: string;
className?: string;
}
const {
leftWidth = '240px',
rightWidth = '220px',
gap = '1.5rem',
className = '',
} = Astro.props;
---
<div
class:list={['holy-grail', className]}
style={`--hg-left: ${leftWidth}; --hg-right: ${rightWidth}; --hg-gap: ${gap};`}
>
<header class="holy-grail__header">
<slot name="header" />
</header>
<div class="holy-grail__middle">
<aside class="holy-grail__left">
<slot name="left" />
</aside>
<main class="holy-grail__main">
<slot />
</main>
<aside class="holy-grail__right">
<slot name="right" />
</aside>
</div>
<footer class="holy-grail__footer">
<slot name="footer" />
</footer>
</div>
<style>
.holy-grail {
display: flex;
flex-direction: column;
min-height: 100vh;
width: 100%;
color: var(--c-text-1, #ffffff);
font-family: var(--font-sans, system-ui, sans-serif);
}
.holy-grail__header {
width: 100%;
padding: var(--sp-4, 1rem) var(--sp-6, 1.5rem);
background: rgba(10, 10, 14, 0.8);
backdrop-filter: blur(16px);
border-bottom: 1px solid rgba(255, 255, 255, 0.08);
}
.holy-grail__middle {
display: grid;
grid-template-columns: var(--hg-left) 1fr var(--hg-right);
gap: var(--hg-gap);
flex: 1;
max-width: 1440px;
margin: 0 auto;
width: 100%;
padding: var(--sp-6, 1.5rem);
}
.holy-grail__left,
.holy-grail__right {
padding: var(--sp-4, 1rem);
background: rgba(255, 255, 255, 0.02);
border: 1px solid rgba(255, 255, 255, 0.06);
border-radius: var(--r-lg, 16px);
height: fit-content;
position: sticky;
top: 2rem;
}
.holy-grail__main {
padding: var(--sp-6, 1.5rem);
background: rgba(255, 255, 255, 0.015);
border: 1px solid rgba(255, 255, 255, 0.06);
border-radius: var(--r-lg, 16px);
min-height: 400px;
}
.holy-grail__footer {
width: 100%;
padding: var(--sp-6, 1.5rem);
background: rgba(10, 10, 14, 0.9);
border-top: 1px solid rgba(255, 255, 255, 0.08);
margin-top: auto;
}
@media (max-width: 1024px) {
.holy-grail__middle {
grid-template-columns: var(--hg-left) 1fr;
}
.holy-grail__right {
display: none;
}
}
@media (max-width: 768px) {
.holy-grail__middle {
grid-template-columns: 1fr;
}
.holy-grail__left {
position: static;
}
}
</style> ---
/**
* HolyGrailGrid — Production-grade CSS grid layout container with sticky header, dual sidebars, fluid content, and footer.
*
* @param {string} leftWidth - Left sidebar width. Default is '240px'.
* @param {string} rightWidth - Right sidebar width. Default is '220px'.
* @param {string} gap - Spacing gap between grid regions. Default is '1.5rem'.
* @param {string} className - Optional CSS class.
*/
interface Props {
leftWidth?: string;
rightWidth?: string;
gap?: string;
className?: string;
}
const {
leftWidth = '240px',
rightWidth = '220px',
gap = '1.5rem',
className = '',
} = Astro.props;
---
<div
class:list={['holy-grail', className]}
style={`--hg-left: ${leftWidth}; --hg-right: ${rightWidth}; --hg-gap: ${gap};`}
>
<header class="holy-grail__header">
<slot name="header" />
</header>
<div class="holy-grail__middle">
<aside class="holy-grail__left">
<slot name="left" />
</aside>
<main class="holy-grail__main">
<slot />
</main>
<aside class="holy-grail__right">
<slot name="right" />
</aside>
</div>
<footer class="holy-grail__footer">
<slot name="footer" />
</footer>
</div>
<style>
.holy-grail {
display: flex;
flex-direction: column;
min-height: 100vh;
width: 100%;
color: var(--c-text-1, #ffffff);
font-family: var(--font-sans, system-ui, sans-serif);
}
.holy-grail__header {
width: 100%;
padding: var(--sp-4, 1rem) var(--sp-6, 1.5rem);
background: rgba(10, 10, 14, 0.8);
backdrop-filter: blur(16px);
border-bottom: 1px solid rgba(255, 255, 255, 0.08);
}
.holy-grail__middle {
display: grid;
grid-template-columns: var(--hg-left) 1fr var(--hg-right);
gap: var(--hg-gap);
flex: 1;
max-width: 1440px;
margin: 0 auto;
width: 100%;
padding: var(--sp-6, 1.5rem);
}
.holy-grail__left,
.holy-grail__right {
padding: var(--sp-4, 1rem);
background: rgba(255, 255, 255, 0.02);
border: 1px solid rgba(255, 255, 255, 0.06);
border-radius: var(--r-lg, 16px);
height: fit-content;
position: sticky;
top: 2rem;
}
.holy-grail__main {
padding: var(--sp-6, 1.5rem);
background: rgba(255, 255, 255, 0.015);
border: 1px solid rgba(255, 255, 255, 0.06);
border-radius: var(--r-lg, 16px);
min-height: 400px;
}
.holy-grail__footer {
width: 100%;
padding: var(--sp-6, 1.5rem);
background: rgba(10, 10, 14, 0.9);
border-top: 1px solid rgba(255, 255, 255, 0.08);
margin-top: auto;
}
@media (max-width: 1024px) {
.holy-grail__middle {
grid-template-columns: var(--hg-left) 1fr;
}
.holy-grail__right {
display: none;
}
}
@media (max-width: 768px) {
.holy-grail__middle {
grid-template-columns: 1fr;
}
.holy-grail__left {
position: static;
}
}
</style>
Quick Info
- Category
- Layout
- Filename
HolyGrailGrid.astro- Dependencies
- None — pure Astro + CSS
- Tags
- layoutgridholygraildashboardstructure