
Technologies used
Released 2026
Overview
The portfolio you are reading is built as a single-page home with dedicated case-study routes. Content lives in typed data files, sections compose the home page, and the project pages render long-form notes, screenshots, and technology details from the same source. The site is designed dark-first, with a no-flash theme script, a keyboard command menu, and a contact form that sends mail through a server action. It took several attempts to get here: every earlier version hit a point where it felt too static, not interactive enough, or simply not good enough, and I would start over. This is the first version I was proud to ship.
Content-driven structure
Profile details, social links, and every project entry live in data files. The home page composes section components around that content, while the project route reads the same project array to generate static params, metadata, and case-study pages. Adding a project means adding one typed object, not touching page markup.
Navigation & theme
The command menu is available with Cmd/Ctrl+K and exposes sections, projects, social links, and theme controls. The theme toggle animates with the View Transitions API when available, and a small inline script applies the stored preference before paint so the page never flashes the wrong theme.
- Cmd/Ctrl+K command palette with keyboard navigation
- Tab shortcut to toggle the theme outside form fields
- Animated theme transition with a fallback path
- Skip link and semantic landmarks for accessibility
From restarts to shipped
I went through more versions of this site than I can count. Each one started with a clear idea and then hit the same wall halfway through: it felt too static, not interactive enough, or simply not good enough. I would rebuild instead of finishing.
This version shipped because I stopped trying to prove everything at once. The difference was narrowing the scope, keeping the interactions that helped people navigate, and accepting the rest as future work.
The portfolio I'm proud of didn't come from adding more. It came from finally deciding what was enough.
SEO, metadata & contact
Every route defines canonical metadata, Open Graph and Twitter cards, and JSON-LD for the person, site, and projects. The project routes are statically generated, included in the sitemap, and expose breadcrumb structured data. The contact form validates on the server, escapes user input before building the email, and reports a clear unconfigured state when the Resend key is missing.
- Per-project metadata and canonical URLs
- Person, WebSite, CreativeWork, and BreadcrumbList JSON-LD
- Dynamic Open Graph image and web app manifest
- Server action with validation and HTML escaping
Screenshots










What it includes
- Content-driven sections powered by typed data files
- Dark-first theme with a no-flash initialization script
- Keyboard command menu with section and social shortcuts
- Animated theme toggle and scroll reveals
- Resend-powered contact form with server-side validation
- Dynamic Open Graph image, JSON-LD, sitemap, and robots
- Static project routes generated from project data