This is the second mini project for Going further with CSS. You will build a dashboard shell: persistent navigation, scrollable main content, optional aside, and layout that survives real-world content lengths. No chart libraries or JavaScript frameworks required – HTML and CSS only.
The scenario
Taskwell is a fictional task management app. You are styling the logged-in shell: sidebar nav, top bar with search and user menu placeholder, main content area with sample widgets, and a right aside for activity or filters. Think admin UI, not marketing fluff.
Layout requirements
- Sidebar – fixed width on desktop (~240px), logo, nav links with active state, collapses or hides on narrow viewports (drawer pattern optional; off-canvas or stacked nav both fine)
- Top bar – spans remaining width; search field, notification icon placeholder, user avatar placeholder
- Main – scrollable content; page title, breadcrumb optional, grid of stat cards and a data table placeholder
- Aside – visible on wide screens; hidden or below main on small screens
Named grid areas approach
Use Grid named areas for the desktop shell:
.app-shell {
display: grid;
min-block-size: 100dvh;
grid-template-columns: 240px 1fr 280px;
grid-template-rows: auto 1fr;
grid-template-areas:
"sidebar topbar topbar"
"sidebar main aside";
}
.app-sidebar { grid-area: sidebar; }
.app-topbar { grid-area: topbar; }
.app-main { grid-area: main; overflow-y: auto; }
.app-aside { grid-area: aside; overflow-y: auto; }
At a breakpoint (~768px or when aside would crush main), switch to a two-column or single-column template without the aside column.
@media (max-width: 64rem) {
.app-shell {
grid-template-columns: 240px 1fr;
grid-template-areas:
"sidebar topbar"
"sidebar main";
}
.app-aside { display: none; /* or move below main */ }
}
@media (max-width: 48rem) {
.app-shell {
grid-template-columns: 1fr;
grid-template-areas:
"topbar"
"main";
}
.app-sidebar {
/* your mobile pattern: fixed off-screen, or horizontal nav */
}
}
Sticky sidebar and top bar
Sidebar should stay visible while main scrolls on desktop. Options:
- Grid row stretches sidebar to full height; sidebar inner nav uses
position: sticky; top: 0 - Or sidebar is
position: sticky; align-self: startwithin the grid cell
.app-sidebar {
position: sticky;
top: 0;
align-self: start;
block-size: 100dvh;
overflow-y: auto;
padding-block: 1rem;
border-inline-end: 1px solid #e5e7eb;
}
.app-topbar {
position: sticky;
top: 0;
z-index: 10;
background: var(--color-surface);
border-block-end: 1px solid #e5e7eb;
}
Test that no ancestor has overflow: hidden breaking sticky. The grid cell itself is usually fine.
Sample main content
Include placeholder content so layout stress-tests:
- Row of four stat cards (
auto-fitgrid withminmax) - Table with enough rows to scroll (use
overflow-x: autowrapper on small screens) - Long sidebar nav list to verify sidebar scroll independent of main
<div class="app-shell">
<aside class="app-sidebar" aria-label="Main navigation">…</aside>
<header class="app-topbar">
<form class="search" role="search">
<label class="sr-only" for="q">Search</label>
<input id="q" type="search" placeholder="Search tasks…">
</form>
</header>
<main class="app-main">
<h1>Dashboard</h1>
<div class="stat-grid">…</div>
<div class="table-wrap">
<table>…</table>
</div>
</main>
<aside class="app-aside" aria-label="Activity">…</aside>
</div>
CSS requirements
- BEM or consistent component naming (
.app-sidebar,.stat-card) - Tokens for sidebar width, topbar height, colours
- Flexbox in topbar (search grows with
min-width: 0on the flex child) - Table wrapper with horizontal scroll on narrow viewports
- Active nav link styling via
[aria-current="page"] - Dark mode tokens via
prefers-color-scheme
Acceptance checklist
- Main content scrolls; sidebar and topbar behave as designed on desktop
- Mobile layout usable without horizontal page scroll
- Search input in flex topbar does not blow out width (check
min-width: 0) - Table readable on phone (scroll wrapper or stacked pattern)
- Keyboard focus visible on nav links and search
Stretch goals
- Container queries on stat cards inside main
- Subgrid on stat cards so footers align across a row
scroll-marginif main has in-page anchor sections
That completes Going further with CSS. You have cascade control, modern layout tools, accessible UI states, architecture habits, and two projects that resemble real client work. The advanced tutorials goes deeper on view transitions, anchor positioning, and component systems at scale.

