What I do at Uploadcare 1. File Uploader

Jan 2025

It's a web UI component that allows your users to upload files to your Uploadcare project. My role is to design it's look, flow and code it's theme. It's in continuous development, tons of decisions are made at each iteration. I'll describe a few big ones made with my direct involvement.

Criteria

The previous version was the first of its kind. It was very much in the era of social sharing buttons. Now, file sharing is a much more trivial, often annoying process, and the role of social networks in it is diminished. In the modern app, uploading is an intermediate step, never the goal. My aim was:

  • To minimize interruptions to the flow of the host application. Fewer steps, smaller windows.

  • To create a neutral, system-agnostic appearance. Tap into modern OS styles.

  • To allow easy theme customization. Limit color and size choices.

Minimal mode

The Swiss Army Knife, while a great tool as a whole, consists of a bad knife, a bad screwdriver, and a bad fork. Versatility comes at a cost. Likewise, not every upload requires a list of sources or even multiple files. Minimal mode has no windows and embeds directly into the page.

Theme

There was one condition: it should be vanilla css, no frameworks, no preprocessors. At first I tried to derive all values from 3 basic ones. It worked, but any customization beyond those values was incomprehensible. Since the relative color syntax doesn't have the browser support we promise, I needed a lot of huge formulas to do the trick:

--clr-background-muted: hsl(
  var(--h-background),
  var(--s-background),
  calc(var(--l-background) + 4% * var(--darkmode))
);

My second attempt was focused on readability. To reduce the number of parameters I limited my color choices even more:

  • Only 3 gray colors

  • No “active” state for most elements

  • Only brand color has derivatives

We also switched from HLS to OKLCH because it's easier to maintain contrast levels when changing colors. Plus it gives access to a wider range of colors of modern displays. Now the entire color scheme looks like this:

--uc-primary-oklch-light: 47% 0.22 264; 
--uc-primary-light: oklch(var(--uc-primary-oklch-light));
--uc-primary-hover-light: oklch(var(--uc-primary-oklch-light) / 90%);
--uc-primary-transparent-light: oklch(var(--uc-primary-oklch-light) / 7%);
--uc-background-light: oklch(100% 0 0);
--uc-foreground-light: oklch(21% 0 0);
--uc-primary-foreground-light: oklch(100% 0 0);
--uc-secondary-light: oklch(21% 0 0 / 0.05);
--uc-secondary-hover-light: oklch(21% 0 0 / 0.08);
--uc-secondary-foreground-light: oklch(21% 0 0);
--uc-muted-light: oklch(97% 0 0);
--uc-muted-foreground-light: oklch(40% 0 0);
--uc-destructive-light: oklch(59% 0.235 28.5 / 0.05);
--uc-destructive-foreground-light: oklch(59% 0.235 28.5);
--uc-border-light: oklch(92% 0 0);
--uc-dialog-shadow-light: 0px 6px 20px oklch(0% 0 0 / 0.1);

As a final touch, we've added a few shorthand classes so you can force a color scheme or change the primary color without CSS:

<uc-file-uploader-regular
  class="uc-dark uc-purple"
  ctx-name="my-uploader"
></uc-file-uploader-regular>

See more details in documentation.