90 lines
4.3 KiB
Markdown
90 lines
4.3 KiB
Markdown
# 04. Layout Components — Navbar, Footer, PageContainer, AppShell
|
|
|
|
meta:
|
|
id: shieldai-unified-restructure-04
|
|
feature: shieldai-unified-restructure
|
|
priority: P0
|
|
depends_on: [shieldai-unified-restructure-01, shieldai-unified-restructure-02, shieldai-unified-restructure-03]
|
|
tags: [frontend, layout, navigation, solidjs]
|
|
|
|
objective:
|
|
- Build the structural layout components that wrap every page: a responsive navbar with navigation and auth state, a footer, a page container for consistent padding/max-width, and an AppShell that composes them all with the theme background.
|
|
|
|
deliverables:
|
|
- `web/src/components/layout/Navbar.tsx` — Responsive nav with:
|
|
- ShieldAI logo/wordmark (SVG)
|
|
- Navigation links: Features, Pricing, Blog, Dashboard
|
|
- Auth buttons: Sign In (secondary), Get Started (primary)
|
|
- Mobile hamburger menu with slide-out drawer
|
|
- Theme toggle button (light/dark/system)
|
|
- Scroll-aware background blur/glass effect when scrolled
|
|
- `web/src/components/layout/Footer.tsx` — Multi-column footer with:
|
|
- Logo and tagline
|
|
- Link columns: Product, Company, Resources, Legal
|
|
- Social links (GitHub, Twitter/X, LinkedIn placeholders)
|
|
- Copyright and privacy/terms links
|
|
- `web/src/components/layout/PageContainer.tsx` — Wrapper with:
|
|
- `max-width` and centered layout
|
|
- Responsive horizontal padding (`px-4 md:px-6 lg:px-8`)
|
|
- Optional vertical padding prop
|
|
- `class` prop for additional overrides
|
|
- `web/src/components/layout/AppShell.tsx` — Root layout component:
|
|
- Renders `<Navbar />`, `<main>{children}</main>`, `<Footer />`
|
|
- Applies dot-grid background to main content area
|
|
- Handles scroll-to-top on route change
|
|
- Wraps with `MetaProvider` and `Title`
|
|
- `web/src/components/layout/index.ts` — Barrel export.
|
|
|
|
steps:
|
|
1. Create `web/src/components/layout/` directory.
|
|
2. **Navbar**:
|
|
- Use SolidJS `createSignal` for mobile menu open state
|
|
- Use `onMount` + scroll listener to toggle `scrolled` class for glass effect
|
|
- Logo: create a simple SVG shield icon with gradient fill (reference Lendair's logo approach)
|
|
- Links use `<A>` from `@solidjs/router` for SPA navigation
|
|
- Theme toggle uses `useTheme()` hook from task 02
|
|
- Auth buttons conditionally render based on auth state (stub for now, wire in task 23)
|
|
3. **Footer**:
|
|
- Grid layout: 4 columns on desktop, 2 on tablet, 1 on mobile
|
|
- Link groups as data arrays mapped with `<For>`
|
|
- Bottom bar with copyright text
|
|
4. **PageContainer**:
|
|
- Simple wrapper `div` with `max-w-7xl mx-auto` and padding classes
|
|
- Accept `class` prop and merge with defaults
|
|
5. **AppShell**:
|
|
- Import `MetaProvider`, `Title` from `@solidjs/meta`
|
|
- Import `Navbar`, `Footer`
|
|
- Render children inside `<main>` with `min-h-screen`
|
|
- Add `onCleanup` to remove scroll listener if added in Navbar
|
|
- Use SolidStart `root` pattern: this becomes the `root` component passed to `<Router>`
|
|
6. Wire AppShell into `web/src/app.tsx` as the Router root.
|
|
7. Create barrel export.
|
|
|
|
steps:
|
|
- Unit: Navbar renders all links; mobile menu toggles
|
|
- Unit: Footer renders all link columns
|
|
- Unit: PageContainer applies correct max-width and padding classes
|
|
- Unit: AppShell renders Navbar + children + Footer in correct order
|
|
- Visual: Resize browser to verify responsive breakpoints
|
|
|
|
acceptance_criteria:
|
|
- [ ] Navbar is sticky/fixed at top with glass effect on scroll
|
|
- [ ] Mobile hamburger menu opens/closes smoothly
|
|
- [ ] Theme toggle button changes theme immediately
|
|
- [ ] Footer is responsive and all links are clickable
|
|
- [ ] PageContainer centers content with consistent padding
|
|
- [ ] AppShell wraps all routes correctly via SolidStart `root`
|
|
- [ ] No layout shift on initial load
|
|
|
|
validation:
|
|
- `cd web && pnpm test` passes layout tests
|
|
- Open `http://localhost:3000` and verify navbar/footer render on all routes
|
|
- Test mobile viewport (<768px) and verify hamburger menu works
|
|
- Toggle theme and verify navbar/footer colors shift correctly
|
|
|
|
notes:
|
|
- Reference Lendair: `~/code/Lendair/web/src/components/layout/Navbar.tsx`, `Footer.tsx`, `PageContainer.tsx`
|
|
- The AppShell replaces the current `app.tsx` Router root. Make sure `<FileRoutes />` still works inside it.
|
|
- For auth state in Navbar, create a stub `useAuth()` hook that returns `{ isAuthenticated: false }` for now; it will be wired to tRPC in task 23.
|
|
- Keep the Navbar height consistent to avoid layout shift when the glass effect activates.
|