Sprix UI
a personal design system made portable
Sprix UI is a component library and design system I built from scratch using Svelte 5 and Tailwind CSS 4. It exists so I never have to wire up the same Button, Card, or Form twice — and so every product surface I ship starts from a shared, coherent visual foundation.
01 / Why
Every freelance project starts the same way: open a blank file, stub out a Button, wire up a Form, build the same Card layout I've built four times before. The primitives are never quite reusable because they were designed for one project, not a system. That friction was the original problem.
I tried headless libraries — Radix, Headless UI — and they solved the accessibility part well. But they came with no opinion about how things should look or feel. I kept layering the same design decisions on top anyway: zinc surfaces, restrained shadows, strong borders, a consistent type scale. Those decisions were mine. They belonged in a system.
Sprix is what I actually wanted: a component library with a clear point of view. Calm by default, sharp where it matters, and ready to compose into real product screens without ceremony. Building it once meant shipping everything after it faster.
02 / How
Before writing a single component, I settled the design tokens: a zinc-based palette
with light and dark surface ramps, semantic naming (--app-bg, --app-surface, --app-text),
and a single blue-600 accent that would carry all interactive states.
Getting tokens right first meant every component I built after was anchored to the same foundation. Refactoring a color meant one change in one place — not hunting down thirty-two hardcoded hex values.
Svelte 5's runes model made component state feel direct — no boilerplate, no wrapping everything in signals. Tailwind 4's Vite plugin made the design system CSS-first: tokens live in CSS, not a config object, which meant the components stayed close to the styling decisions.
The tradeoff: less ecosystem than a React/shadcn approach. No massive open-source community publishing Sprix-compatible blocks. But the APIs stay direct, the bundle stays lean, and the components feel exactly how I want them to feel — not shaped by another library's opinions.
The single biggest design decision: use strong edges instead of elevation shadows to
separate surfaces. A card on Sprix has a 1px zinc-200 border and a white background. No shadow-xl.
This keeps the UI calm in both light and dark modes — shadows shift in color across themes, borders don't. It forces hierarchy to come from whitespace, typography weight, and surface contrast instead of depth illusions. The result reads as flat but not blank.
The guiding rule was: each component does one thing well and accepts props that make the
common cases easy. No giant polymorphic base classes, no deep inheritance chains. A Button is a
Button. A Card is a Card.
Compose them at the page level.
Navigation
Inputs
Display
Feedback
Data
Forms
A component library that only shows isolated components isn't a design system — it's a parts list. To prove Sprix worked, I assembled four real product screen flows using only Sprix primitives: a checkout flow, an auth screen, an operations dashboard, and a CMS editor.
These screens appear on the Sprix site as the showcase section. They're the real test: do the components compose cleanly under pressure? The answer had to be yes before I called the library done.
03 / Components
A sample of what ships with Sprix UI. Every component follows the same token system and composes cleanly into real product screens. Browse all components
Button
6 roles · 6 variants · 5 sizes
Badge
6 roles · 5 variants · 3 sizes
Avatar
Image · initials fallback · 7 sizes
Spinner
7 roles · 7 sizes · with label
Kbd
Keyboard key indicator
Card
Header · content · footer slots
Total revenue across all active projects this month.
04 / What's next
The next checkout flow, dashboard, or CMS interface scaffolds in hours rather than days. Tokens are set, components are tested, the visual language is consistent. I'm not reinventing the Button on every project — I'm composing screens from a trusted set of pieces and spending the freed time on what actually differentiates each product.
Token names are semantic, component APIs are minimal and direct, and the system is documented on the live site. Handing off a project to another developer or designer means pointing them at the docs — not walking them through a custom setup. The clarity of naming is a feature, not a side effect.
Sprix's principles — calm by default, hierarchy through contrast, borders over shadows — have fed back into how I design every other product surface. This case study page is a small example: the same zinc palette, the same blue accent, the same surface logic, living inside a portfolio that deliberately looks nothing like it.
The components are ready. The tokens are set. If you're building a product interface and want something calm, sharp, and unmistakably yours — let's talk.
Ready-to-compose primitives for real product screens.
sprix ui · v3 · 2026