Wireframe legend. Solid black border = page viewport. Dashed border = a content region with a label. No colors, no images, no real type. Purpose: agree on layout structure and flow before touching CSS. Routes shown: /, /projects, /projects/[slug], /about, /uses.

Route: /

Landing. Goal: in 60-120s, communicate who Angel is, what he ships, how to contact.
VIEWPORT — /
hero — text only, no image Large name or wordmark. One-line positioning underneath: "Frontend engineer with deep AI-tooling fluency — ships production React and builds custom Claude Code workflows." Below that, a secondary line linking to most recent case study or "Currently at Village Medical." No CTA buttons.
section heading "Selected projects" — small caps or monospace label. Single line.
case study card 1 Title · one-line summary · year · outcome metric. Whole card is clickable → /projects/[slug].
case study card 2 Same shape as card 1. Three cards total, sometimes four.
case study card 3 Same shape.
contact strip Email · LinkedIn · GitHub. Plain text links, no icons-only treatment. Maybe a one-line "Open to remote-US roles."

Route: /projects

Case study index. Same cards as the landing, but full list. Optional filter (year or tag).
VIEWPORT — /projects
page heading "Projects" — single word. Optional one-line intro: "Selected projects, written as postmortems."
case study row 1 Title · year · one-line summary · key metric. Full-width row, not a card grid (denser, more readable).
case study row 2 Same shape.
case study row 3 Same shape.
case study row 4 (optional) Same shape. Skip if it dilutes.

Route: /projects/[slug]

Individual case study. Postmortem format: context · decisions · outcome · what I'd do differently.
VIEWPORT — /projects/[slug]
case study header Project name (large). Below: role · year · stack · one-line outcome. No hero image.
sidebar (desktop only) Sticky table of contents: Context · Decisions · Outcome · Retrospective. Collapses above the body on mobile.
long-form body (MDX) Section: Context — the constraint, 2-3 sentences.
Section: Decisions — 3-5 specific calls with rejected alternatives.
Section: Outcome — measurable result, honest when not.
Section: What I'd do differently — one paragraph.
Inline: code blocks (shiki), occasional pull-quote, optional simple diagram. No carousels.
next/prev case study Two links: ← previous case study · next case study →. Keeps the reader in the work funnel.

Route: /about

Background arc. Who Angel is, what he's looking for. Long-form, first person.
VIEWPORT — /about
page heading "About" — single word.
narrative paragraph 1 — arc Healthcare IT → Salesforce admin → SWE at Village Medical. 3-5 sentences, first person, active voice.
narrative paragraph 2 — current work + AI wedge What Angel does day-to-day. React + TS leadership. Heavy Claude Code use. The "frontend engineer who actually uses AI to ship" framing.
narrative paragraph 3 — what I'm looking for One paragraph. Remote US, mid-level, AI-native or product-engineering. Names of companies he'd love to work with (optional but bold).
chronological strip Three or four rows, plain text. Each row: year-range · company · role. No bullets, no descriptions — the case studies and narrative carry the detail. Example:
2024–present · Village Medical · Software Engineer
2022–2024 · Village Medical · Salesforce Admin
2019–2022 · Gila River · Help Desk / IT
download CV Single line: "Download CV (PDF)" link. Points at the PDF generated by career-ops. No fancy treatment.
contact strip Email · LinkedIn · GitHub. Same as landing.

Route: /uses (optional)

Tools, editor setup, Claude Code workflow. High-signal page for AI-native hiring managers.
VIEWPORT — /uses
page heading "Uses" — single word. One-line intro: "What I reach for daily."
section: hardware Plain list. Machine, monitors, keyboard. One line each.
section: editor & shell VS Code config highlights, terminal, font, theme.
section: AI workflow Claude Code setup. Custom slash commands. MCP servers. One paragraph per workflow with the time saved. This is the signal-dense section — give it the most space.
section: self-hosting Traefik, the box, whatever else runs on it. One-liners. This is where "self-hosted" lives without becoming the lede.