All work

Design System

A neutral system for the whole product, built to be re-skinned

A Design System title card reading "Components, typography, colors and variables", over three overlapping sheets from the file: the icon set, the badges, and the checkbox states.
Role
Product Designer
Scope
Design system, foundations to components
Timeline
2 to 3 months
Platform
Responsive web, built on Figma variables

The problem

EC Affiliates is a name changed here for confidentiality. Its product had two problems happening at the same time: the interface was outdated, and there was no system underneath holding everything together.

Without a design system, every screen was assembled by hand. The same button, table row, and input existed in slightly different versions across different parts of the product, and none of those differences were intentional decisions. That made the product easy to design but expensive to build. Engineers had to interpret each screen individually, and every small inconsistency became a question, which often led to rework.

So the brief was not simply about giving the product a visual refresh. The goal was to give the entire product a consistent design language, and then build the new interface within that system rather than designing each screen independently.

Deliberately neutral

The request was for a system without a strong opinion of its own. The company wanted the option to white label the product in the future, so nothing could depend on a single brand’s personality. It needed to be clean, direct, and quiet enough that another brand could be introduced without the system working against it.

That constraint turned out to be useful. A system that cannot rely on a brand has to earn its clarity through structure instead: consistent spacing, contrast that remains effective across different color palettes, and components that behave consistently regardless of the colors they use.

Foundations

Seven layers, each its own page in the file, each one a decision made once so it would not have to be made again on every screen.

  1. 01

    Color

    Eleven families, each a full tonal ramp from the lightest tint to the deepest shade. A re-skin changes the ramp; nothing that uses it has to change at all.

  2. 02

    Typography

    One scale, from Display 2xl down to the smallest supporting text, each step available in Regular, Medium, Semibold and Bold, set in Outfit.

  3. 03

    Icons

    Heroicons as the working set, alongside brand and country icon sheets for the surfaces that needed them.

  4. 04

    Spacing

    A single scale carrying both px and rem, so design and code could not quietly disagree about what one step meant.

  5. 05

    Shadows

    Six elevation steps, from a card at rest up to a modal, so depth became a token rather than a judgement call.

  6. 06

    Grid layouts

    Column systems for desktop, tablet and mobile, defined once so responsive behaviour was inherited instead of improvised.

  7. 07

    Border radius

    One radius scale, applied everywhere, which is most of what stops an interface from looking assembled by several people.

The type page: the Outfit specimen above a scale running from Display 2xl to Text xs, each step in Regular, Medium, Semibold and Bold with its size and line height in px and rem.
The icon page: the Heroicons set in full, every icon shown in four variants beside the name engineering references it by.
The grid page: desktop at 1,280 pixels, tablet at 768 and mobile at 360, each drawn with its columns, gutters and content width measured.
The border radius scale: eight named steps from SM at 2 pixels to Full at 999 pixels, each shown on a sample shape.

Typography

Eleven steps, from Display 2xl at 72px down to Text xs at 12px, each carrying its line height in both px and rem, and each drawn in four weights (forty-four styles in all). Set in Outfit.

Icons

The Heroicons set in full, each icon in all four variants and labelled with the exact name the build would call it by (academic-cap, battery-100, chevron-double-left).

Grid layouts

Three breakpoints, each with its own columns: 1,280px desktop over a 1,216px content width, 768px tablet over 704px, and 360px mobile over 328px. Gutters of 32px above, 16px on mobile. Settled once, so responsive behaviour was inherited rather than argued out per screen.

Border radius

Eight steps, SM at 2px through to Full at 999px. Naming the pill Full rather than a number is what keeps it a pill when the component around it changes size.

One set of variables, two themes

No color in the system is a hex sitting on a shape. Every one is a variable, and light and dark are two modes of the same set.

That means a screen gets designed once. The variables decide which theme it renders in, so dark mode is not a second file to keep in step with the first, which is how dark modes usually rot, quietly drifting a few components behind the light version until someone notices.

That is what the variables panel holds: each named for the job it does rather than the color it happens to be. Title Color, Border Secondary, Background Modal. Every one resolves to a different step of the ramp in each mode.

It pays off twice. Once for the themes, and again for every color decision afterwards: because the variables are grouped by what uses them (alerts, status, inputs, tabs, buttons, the sidebar) a change to one family lands everywhere that family is used, across the whole system, from a single edit.

The Figma variables panel: 146 variables grouped by what uses them, each row mapping a semantic name such as Title Color or Border Secondary to one color token in the Light column and a different one in the Dark column.
146 variables, each naming a job rather than a color, and each resolved twice.

Below is the same requests screen in both modes. It was drawn once. Nothing was repositioned, nothing was redrawn, and no component has a light twin and a dark twin, The variables resolve to one palette or the other and every element follows.

The requests screen shown in both themes at once: the light theme fills the left of the frame and the dark theme the right, split by a draggable handle. Light Dark
Drag the handle. One screen, both themes: nothing moves but the palette.

Built to be used

Foundations only matter if the things built on them are complete enough to reach for. The components covered as many of the product's future cases as could be anticipated, not only the screens that existed on the day.

Everything was fully responsive, and the interactive pieces (including drag and drop) were specified as part of the component instead of being left as a note for engineering to interpret.

The checkbox and radio sheet: every control drawn in its default, hover, focused and disabled state, at two sizes.
The button sheet: filled and outlined buttons at three sizes, with a leading icon, a trailing icon and neither, each in default, hover, focused and disabled.
The badge sheet: one badge in every color family the palette carries, at three sizes, with a leading icon, a trailing icon and neither.
The alert sheet: success, warning, error and hint messages, each shown with and without a Learn more link.

States

Checkboxes and radios drawn in default, hover, focused and disabled, at both sizes. Focus is part of the component rather than a note for engineering to add later.

Buttons

Filled and outlined, at three sizes, with the icon leading, trailing or absent, every one of them drawn in default, hover, focused and disabled.

Badges

One component in every family the palette carries, at three sizes, with the icon leading, trailing or absent. The ramp does the work, so the badge itself never changes.

Alerts

Success, warning, error and hint, each with and without a follow-up link. The state is carried by an icon and a word as well as by color, so the message still reads for anyone who cannot separate green from red.

The system in use

The point of all of it: screens assembled out of the vocabulary rather than drawn beside it.

Nothing in either screen is bespoke. The stat cards, the segmented toggles, the filter selects, the platform tags, the approve and reject buttons: each one is a component from the library, and a screen is an arrangement of them rather than a fresh drawing. The green change indicators are the badge component in its success family, which is why they agree with every other badge in the product without anyone having to remember what green was supposed to mean.

The affiliate dashboard: a sidebar, an Earnings and Performance toggle, a filter row, four stat cards showing total sales, earnings, clicks and earnings per click, and a twelve-month earnings chart with a hover tooltip.
The affiliate dashboard. Stat cards, toggles, selects and badges, all straight from the library.
The requests screen: incoming affiliate requests as cards, each with an avatar, a platform tag, commission and audience details, the applicant's message, and approve and reject buttons.
Requests. The same components again, carrying a completely different job.

Accessibility, built in

The interface was checked against WCAG as it was designed, rather than styled first and audited afterwards.

The color structure is what makes that maintainable. Because every family runs as a full tonal ramp rather than a handful of hand-picked values, contrast stops being an argument had again on every screen and becomes a question of which steps sit together, the kind of decision a system can carry on behalf of everything built on it.

It matters more here than on most products. This is an interface people read numbers off, and on a dashboard legibility is not a finishing touch; it is the difference between the product working and not working.

Made to be maintained

A system is only as good as its second year, so the file was organised to be added to rather than admired.

Each foundation is its own page (color, type, icons, spacing, shadows, grids, radius), so there is exactly one place to change any given decision and no second copy to fall out of step with it. The tokens are named as scales rather than descriptions: shadow-md through shadow-3xl, spacing steps carrying both px and rem, color steps numbered along their ramp. Names like that survive a rebrand, because none of them describes the value it currently holds.

The variables carry the same load. With color held as variables instead of hexes, changing a theme (or the whole brand) is an edit in one place rather than a search across every component that used it.

What the system never got was a long life. It ran for months before the company pivoted, so it was never stress-tested by years of contributions from several teams. That would have needed the rest of the apparatus around it: a written route for proposing a component, versioning, and a deprecation path for the things it replaced. It is the first thing I would set up earlier next time.

The result

The system shipped, and then outlived the product it was built for.

The design was approved and implemented, and ran live for several months. Then the company pivoted and replaced the product entirely. The new product has a design system of its own, and several ideas from this one were carried straight into it. So the work did two jobs: it organised the build the first time, and it shaped the system that replaced it.

The engineers said the library was the part that helped most: with the components already there, building a new screen became assembly rather than reinvention.

The client described the interface as clean enough that nothing competed with the data itself, and called the change night and day.

Have a company worth skyrocketing?

I'm open to full-time roles and looking to join a team where I can bring a decade of product design and make a meaningful impact. If you're hiring, I'd love to hear about what you're building.