UX Designer • Design Systems & Accessibility

Where modern code meets clean, timeless craft.

What I do

I live in the deep space between design and engineering.

Most teams lose something between mockup and merge, but I operate on both sides of that line. Decisions made in Figma are reflected in production.

  • UX & product design

    Research, flows, information architecture, and testing that settles arguments. A location-first rebuild of a clinical-trial signup cut form abandonment from 65% to 37%.

  • Design systems

    Tokens, components, and the governance that keeps them honest. LINEAR runs ~266 tokens and ~75 components from one source of truth, rendered in both Figma and Webflow, with 360 brand skins from five theme axes.

  • Web development

    Webflow, WordPress, SvelteKit, and Three.js when the brief calls for it. I write the code, so the prototype isn't a promise someone else has to keep.

  • Brand & identity

    Strategy first, logo second. Vedara Ventures, a $100M+ holding company, got a complete brand in 14 days.

  • Accessibility & MX

    WCAG 2.2 AA is my floor, but I also structure sites AI agents can read with llms.txt, agents.json, and clean semantic markup.

About Me

Your Friendly Neighborhood Design Archaeologist

Select to learn more

Contact Me

Let's build the damn thing.

Looking for a partner or "sidekick" with capable hands to get you through a complex website or mobile app project? Or are you hiring for a UX or systems-related role? Shoot me a message.

Client Website • Headless

Kevin Popke Foundation Leads with the Man, Not the Mission

PageSpeed 98 / 100 / 100 / 100

Redesigned the Kevin Popke Foundation's website around the namesake's story and built a custom headless WordPress CMS on a $2,000 budget. Scores 98–100 on PageSpeed and allows the team to log new grants without a developer.

Problem
The old site led with the organization, buried the man it was named for, and needed a developer for every update, even a single grant.
Solution
A homepage ordered person, purpose, programs, and a headless WordPress build with one custom plugin whose fields map to the page.
Impact
Launched in six weeks on $2,000, scoring 98–100 on PageSpeed, with new grants logged from one photo and no developer.
Client
Kevin Popke Foundation
Role
Lead designer / developer
Timeline
6 weeks
Open case study

Design System

LINEAR: The 15K Line Stylesheet That Became a Design System

1,990 classes → 266 tokens

An agency template with no theming, no dark mode, and over 1,000 spacing classes became a three-tier token system that works the same way in Figma and Webflow.

Problem
VYNE's Webflow template was one 15,209-line stylesheet with 1,990 classes and variables, no theming, and no way to scale up.
Solution
A three-tier token system with components that read semantic tokens only, and class names that match exactly between Figma and Webflow.
Impact
266 tokens instead of 1,990 classes, 360 theme combinations across five axes, and 86 of 86 color pairings passing WCAG 2.2 AA.
Client
VYNE Creative
Role
Lead designer & engineer, AI-assisted
Timeline
8 weeks
Open case study

Client Website

A Little Transparency for SAD Trials Cut Abandonment from 65% to 37%

Screener abandonment: 65% → 37%

Four past campaigns hid trial locations until after the medical screener. Moving them up front changed how many finished.

Problem
A Fortune 100 research team lost 65% of trial candidates in the pre-screener, because people couldn't see trial locations until after sensitive health questions.
Solution
A city directory before the screener, sites kept unnamed until consent, and a three-step flow in plain language.
Impact
Abandonment fell from 65% to 37% and end-to-end conversion rose from ~13% to 35%, and the client reused the flow for two more studies.
Client
SAD Clinical Trials (alias)
Role
Lead designer
Timeline
6 weeks to fall enrollment
Open case study

Client Website • Design + Development

From Phone-Only to 8–19 Web Requests Daily

Created the first website for a commercial truck repair shop on Chicago's South Side. Once paid and social traffic started to roll in by month 2, the site was getting 8–19 additional estimate requests a day. 37.3% of requests became paid service orders, and 59% of people who started the estimate form submitted it (measured: HubSpot, first 60 days).

Open project

A $14,000 average order, and no website

312 Truck Body Repair & Painting on Chicago’s South Side had new owners, a $14,000 average service order, and no website. Every quote happened by phone or walk-in, leaving the shop invisible to fleet managers looking for vendors online. I had six weeks to change that and bring in new estimate requests the shop’s marketing team could convert into service orders.

Four decisions behind the build

1. Design for the task, not the average

Mobile-first is the default, but what matters is what people come to the site to do. These visitors came to request an estimate on a commercial truck: VIN, make, model, year, fleet size, damage photos. I designed the site to be responsive, with the media galleries, service details, and estimate form flexing down to mobile portrait.

2. Proof before the pitch

Nobody approves a $14,000 repair from a paragraph of copy. Before-and-after galleries and a facility tour sit above the service copy. Heavy media and fast pages pull against each other, but the site held a 2.3-second load time through its first two months.

3. A complex form that’s easy to finish

A shop can’t quote a truck repair without the vehicle type, its age, whether it’s part of a fleet, and the damage. I worked closely with the client on a form with conditional logic, so each person only sees the fields that apply to their earlier answers, plus file uploads and fields for VIN, make, model, year, and fleet size. Over the first 60 days, 59% of people who started the form submitted it, against the 35% floor I’d set.

4. One lead, two teams

Every request lands in HubSpot as a lead and goes to two places: the service department, to build the estimate, and marketing, where the lead joins an email sequence with a first-timer discount. The shop quotes and nurtures in parallel, so a fleet manager comparing three vendors hears back from both teams, not just one.

What didn’t work

I first set up the CMS almost like a storefront, with services, service categories, specialties, and certifications, all cross-linked. That was a lot of IA for a catalog nobody needed: fleet managers aren’t browsing collections of sub-services between meetings. I cut the structure back to the main services and service categories and let the estimate form do the work.

Results

At launch, the client’s marketing team started paid ads targeting the South Side and sent social traffic to the site. By month two, the site brought in 8–19 additional estimate requests a day on top of phone and walk-in quotes.

+8–19 requests a day 59% form completion 37.3% close rate
On top of phone and walk-in quotes, by month two Of people who started the estimate form (35% floor) Of requests became paid service orders

Measured in HubSpot over the first 60 days. The site is still live, and about 60–70% of it is unchanged from my build.

Takeaways

The agency moved me to a new project at day 60, so the numbers stop there. Next time, I’d build the client a HubSpot dashboard before handing off (requests, close rate, and lead source, split by channel) so they could see which ads were actually paying off. I’d also add device tracking from launch, so the desktop-first call rests on their own traffic, not an industry assumption.

Client Brand • Website Design

A Brand and Website for a $100M Portfolio in 8 Weeks

Brand + site in 8 weeks on $7.5K

A holding company with 40+ businesses had no logo, no brand, and no website with an investor conference coming up fast. Launched in 8 weeks on a $7.5K budget.

Problem
A holding company with 40+ businesses had no logo, no brand guidelines, and no website, with Q4 investor conferences weeks away.
Solution
Two weeks of brand, then six of web: a nested-V identity that works across industries and a WordPress site the team runs without a developer.
Impact
Launched in 8 weeks on $7.5K, loading in 1.9s, with 12 of 12 testers finding businesses and new companies added in 3–5 minutes.
Client
Vedara Ventures
Role
Lead designer (brand & web) & developer
Timeline
8 weeks
Open case study

Mobile App

A Community-Shaped Companion App for People in Recovery

A nonprofit wanted a digital companion for people in recovery. Testing showed that scoring someone's sobriety felt like a report card, so the app changed course.

Open project

Support, not surveillance

Never Alone Recovery supports people living with mental health conditions and substance use disorders. They wanted an app where people could find nearby support meetings, track their recovery, and journal, with room to add sponsor linking and 24/7 chat later. The hard part wasn’t the features. It was making daily check-ins feel like support, not surveillance, especially for people already getting more than enough of the latter.

Three decisions behind it

1. Status, not scores

The original idea behind the Sobriety Tracker was to distill someone’s risk of relapse into a numerical score. In pilot interviews, journals, and surveys, people said it felt like being kicked when they’re down. I replaced the score with three status words: Stable, Cautious, and At Risk. The trade-off was precision: a word can’t show small day-to-day changes the way a number can.

2. Progress people can feel

“90 days sober” is an abstract milestone. “You’ve saved $___ on alcohol since March” is something tangible. The app pairs each person’s milestones with self-reported data (or national spending averages by default) to estimate concrete wins.

3. A meeting finder by location

A GPS-powered meeting finder shows nearby support groups, because the easiest meeting to get to is the one most likely to be attended. Phase 2 was planned around a pitch to state and local governments: a way to digitally document court-ordered meeting attendance. Location data tied to recovery is about as sensitive as data gets, and that feature would have needed careful consent and data limits. In the end, the funding never came through, and interested partners moved on before Phase 1 reached soft launch.

What didn’t work

Between the pilot feedback and one-to-one usability sessions with NAR’s community volunteers, the same thing kept happening: people scrolled up and down, unsure where to go next. My fix was a persistent dock at the bottom with one-tap access to the three core features (Sobriety Tracker, Meeting Finder, and Achievements) plus the dashboard. In testing after the change, more than 77% of first clicks from the dashboard went to one of the three other dock tabs.

Results

46% at day 120 77%+ “Gentle”
Of a 35-person pilot, with no incentives offered Of first clicks from the dashboard went to a core feature How NAR’s long-term community members described it

Pilot participants came through the nonprofit, so this isn’t app-store retention, but four months is a long time for anyone to keep opening a recovery app that isn’t working for them. The app launched on both Android and iOS, but development was paused shortly after when the nonprofit’s subsidy funding changed.

Takeaways

I now test navigation much earlier in the process. People scrolling around unsure where to go is a problem a five-person test would have caught months sooner.

Concept App • Solo Project

A Calendar That Says No So You Don't Have To

A self-initiated concept app for anyone struggling to balance work, personal, and family calendars. 4 of 4 testers used the wizard to time-block their schedules in under five minutes.

Open project

An empty calendar doesn’t mean free time

I freelance, and more than once a client call landed on the same day and at the same time as a doctor’s appointment. Every calendar was accurate on its own, but my work calendar had no idea the afternoon was spoken for. Four of my colleagues had brought up the same annoyance with me. They needed something that knew which hours belonged to which part of their life.

Constraint: people’s calendars already live in Google, Outlook, Notion, and more. Schedually had to sit on top of them and unite them, not replace them.

Three decisions behind it

1. Blocks are protected, and changes are negotiated

Most calendars color-code your time and let anything book over it. That’s how I got double-booked. In Schedually, an event that lands outside its block triggers a conflict. You pick an open slot inside your rules, and Schedually sends the event’s owner a request to confirm the new time. Nothing moves on their schedule without their sign-off, but nothing lands in the wrong block on yours. One tester put it best: “It’s not me saying no, it’s my schedule saying that that time is already allocated.”

2. Connect calendars before drawing the week

The wizard connects Google, Outlook, or Notion before you draw any blocks, so you draw around events you can already see. That makes it a recognition task, not a memory test: nobody has to remember that Thursday has swim lessons. The cost was a permissions screen right at the start, which is where onboarding usually loses people.

3. Tap to place, drag to adjust

Dragging blocks across a week grid works on desktop. On a phone, the drag fights the scroll and fails on small targets. A tap places a block, and a double-tap unlocks drag handles for fine-tuning the start and end. It’s an extra step for people who’d rather drag everything, but it’s why a whole week fits in one sitting.

What didn’t work

I assumed the week view would be the home screen, since that’s where calendar apps usually open. But once the blocks are set, the week view barely changes. What people needed to see first was what’s coming up next and what still needs a decision. I replaced the calendar view with a dashboard for today’s blocks, upcoming events, and unresolved or pending conflicts.

Results

I ran moderated think-aloud sessions with my four peers, who shared their screens and talked through each step.

4 of 4 3:03 median 4:51 slowest
Testers time-blocked a full week To block out a whole week Still under five minutes

It’s a small, friendly sample, so the results are directional. The request-to-confirm flow also went untested from the other side (the person receiving the request).

Takeaways

Next, I’d recruit testers outside my own circle and wire up the confirmation side for the event’s creator. It’s also worth testing whether a counter-offer only works if it doesn’t come off as rude.

Web Application • Solo Design + Development

Building a Searchable Archive for Hundreds of LinkedIn Posts

A solo-built content HQ whose archive powered a 557-post audit that reshaped my content strategy. Automation stays switched off on purpose.

Open project

Hundreds of posts, and no memory of them

Since late 2024, I’ve posted on LinkedIn every single day. But once I posted something, it almost always evaporated from my mind, given the sheer volume of topics I was covering. I couldn’t answer basic questions: Have I already written about this? Which topics actually travel? What did I pin under that carousel?

Scheduling tools are built for posting, not for archiving. I wanted an archive I could search and analyze.

Three decisions behind it

1. Library and data before scheduling

LinkedWin’s first job is looking back, not posting forward. Import scripts pull content, including links to individual posts, from LinkedIn’s analytics exports and Favikon’s CSVs into one record, tagged by topic and hashtag and refreshed every four hours.

2. A composer built around my habits

LinkedIn’s own composer is built for everyone. Mine is built for how I actually write. It has a palette of the special characters I use, saved footer templates, @mentions, and a staging area for the pinned first comment that goes out with almost every post. The pinned comment used to live in a notes app and get pasted in after publishing. Now it gets drafted alongside the post.

3. Built, but not wired, for automation

I wired the app to schedule and even publish posts through a third-party scheduling API, but I haven’t switched it on, for a simple reason: my LinkedIn account is a professional asset, and automated activity is one of the fastest ways to get an account restricted or banned. Since I can write and schedule right in LinkedWin, publishing by hand costs seconds of my day. Losing the account would cost me my audience.

Results

With 557 deduplicated posts in one place, I could finally audit my own feed, and the audit changed what I post. I identified three topic lanes that performed well for me and started optimizing for saves and dwell time instead of reactions.

557 posts 3 topic lanes Every 4 hours
Deduplicated into one searchable archive Found in the audit, and now the core of what I post The archive refreshes from my exports

Next steps

I’d like to run the publishing pipeline on a sandbox account, so I can test it before it gets anywhere near my real one.

Web Application

ClienTell: From Client Profile to Creative Brief to Signed Contract

A secure, PIN-protected web app built for my consulting business that lets clients seamlessly complete creative briefs, review modular scopes of work, and sign contracts directly in the browser.

Open project

One client, five tools, and a game of telephone

Every new client used to mean an intake form in one tool, follow-up questions over email, and a contract built by hand. I was retyping answers clients had already given me into contracts they then had to sign somewhere else. It was a mini-game of telephone where it’s easy to lose a detail here and there, and that inevitably came back to bite me. And if a client came back for a second project, I was basically starting from scratch.

Five decisions behind it

1. A PIN instead of an account

Clients typically use the portal only a few times per project, so asking them to create an account and invent a password felt like unnecessary friction. Each client gets an email invite to set a 6-digit PIN, and the pair, email and PIN, becomes their login. PINs are hashed with PBKDF2, so nobody, including me, can read them, and sessions use signed cookies.

A 6-digit PIN has a large but finite number of combinations, so attempts are limited. Three wrong tries trigger a 10-minute cooldown. Three more within 24 hours of that cooldown ending lock the account for a full day, or until the client contacts me to unlock it. A forgot-PIN flow covers the usual case, so a lost PIN is a self-serve reset, not an email to me.

2. Autosave is the client’s friend

Some brief questions ask for detailed answers, and nothing makes someone abandon a form faster than losing a paragraph to an accidental refresh. But people don’t trust what they can’t see, so a visible indicator counts down five seconds to each save.

3. Briefs feed contract drafts

ClienTell started as a simple brief builder; contracts came second, built on the same client profiles. As a client completes their brief, specific answers flow into a pending Design Services Agreement, Statement of Work, and optional confidentiality addendum. I still review and edit every contract before it goes out, because legal documents shouldn’t be fully automated. But I start from a draft that already knows the client’s scope, not a blank template.

4. Prewired for returning clients

Good clients come back. Each client profile holds as many briefs and contracts as they have projects, so a returning client starts from everything I already know about them, not a blank intake.

5. Client information kept safe

Migrations are additive-only, and the destructive db:push command is blocked by default. Cleaning up the schema takes more steps that way, which is a fair price for never wiping a client’s answers by accident.

Results

7 clients 1 place, not 5 0 passwords
Onboarded through ClienTell so far For intake, scope, and agreement Clients sign in with their email and a PIN

ClienTell has made quick work of onboarding so far, and it’s in active use with real clients.

Web Application • Solo Design + Development

Contour: Mapping the Shape of a Designer's Skills

A self-assessment where only one skill gets a 10 so the shape it draws is actually yours, designed and launched in 3 weeks.

Open project

Not every designer is T-shaped

“T-shaped” became the default way to describe a designer’s skills: deep in one thing, broad across the rest. But plenty of careers don’t look like that. Some people go deep in two or three areas, and some connect disciplines more than they specialize. In fact, there are a number of different designer “shapes.”

Two decisions behind it

1. Honesty is the policy

Give people free sliders and most skills land at 8 or above. That’s a ceiling effect, and it turns every result into the same flat blob. Only one skill can score a 10, one a 9, and one an 8. Everything from 7 down is unrestricted. You can’t claim to be world-class at everything if you want to truly understand your shape. It was a tricky (and perhaps controversial) rule, but I saw it as the clearest way to make sure the final charted shape means something.

2. Nothing leaves the browser

People rate themselves differently when they think someone’s watching. All scoring and storage happen in the user’s browser. Contour logs no usage and has no back end storing results. The trade-off: no cross-device sync, and with only basic analytics, I can’t tell you how many people have used it.

How Contour reads a shape

Contour reads your ratings as a profile and looks at three things: how many peaks there are, how far the ratings spread, and where they flatten out. One deep peak with little around it is an I. One peak on a broad base is a T. Two peaks on a broad base make a Pi, and three or more make an M. An X pairs deep expertise with enough competency to lead in multiple other disciplines.

Built accessible from day one. Automated Playwright and axe checks run clean for keyboard and screen-reader support. Tooltips open on focus and tap, not just hover, and every animation respects prefers-reduced-motion. A manual VoiceOver pass is next: automated checks catch a lot, but not everything.

Results

~3 weeks 5 shapes 0 data stored
Shipped solo, from concept to live I, T, Pi, M, or X, with a growth guide Every rating stays in the user’s browser

Tool available here. It maps designers to I, T, Pi, M, or X shapes, with a growth guide and chart exports as SVG, PNG, and JPEG. Nothing leaves the user’s browser, so I don’t have usage numbers, on purpose.

Next steps

I’d love to expand Contour with other ways to visualize skills, like the Dreyfus model, radar (“spider”) charts, and treemap diagrams.