Hours are hues a fifth apart.
The minute hand is not drawn — it is the discontinuity.

The construction

A clock with no hands

Every hour has a colour. The minute hand isn’t drawn at all — it’s the seam where this hour’s colour is being painted over last hour’s. You read the hour from the hue, and the minute from where the edge has got to.

1 Twelve hues, evenly spread

Each hour’s hue sits 150° around the colour wheel from the last — five twelfths of a turn. Because 5 and 12 share no factor, stepping by them visits all twelve hues before returning home, and neighbouring hours land as far apart as they possibly can. Four o’clock could never be mistaken for five.

It’s the same reason the circle of fifths works in music — and the name is meant literally, though the arc that earns it is the one in §3. The constraint is strict: only 30°, 150°, 210° and 330° are coprime with twelve. A step of 180° would give you two colours for twelve hours.

The hour hues, in clock order. The path is the walk between them.

2 Nothing moves but the seam

Think of a paint roller sweeping clockwise from twelve, laying the new hour’s colour over the old. At any dial angle, the colour was fixed the moment the roller last passed — so it doesn’t change again until the roller comes round.

Which means the colour field is completely static. This isn’t an animated gradient; it’s two fixed gradients and a moving reveal. That reduction is the whole reason the design is possible in a format that forbids running code.

Both layers meet continuously at twelve o’clock, because the fresh layer starts on exactly the hue the stale one ends on. So the only discontinuity anywhere on the dial is the one at the minute hand.

stale — finished at the hour
fresh — being laid down
the reveal
Two static layers, one moving wedge. Nothing else changes.

3 The long way round

Here’s a subtlety. The step sets two things, and they’re taken differently: the hour-to-hour increment is read mod 360, but the arc the gradient sweeps across the dial is a real, signed value.

And −210 ≡ +150 (mod 360). So both give every hour exactly the same colour, and the same pair of colours at the seam. But 150 + 210 = 360 — they’re complementary arcs. One walks the short way between an hour’s hue and the next; the other walks the long way, through everything in between.

Same endpoints. Twice the spectrum. The face uses the long way.

Which is also where the name comes in, and it turns out to be literal. Count 30° as one step of a twelve-tone wheel: a perfect fifth is seven of them, and −210° is exactly −7/12 of a turn — a fifth, taken downward, which is how the circle of fifths is usually drawn. The short way, +150° = 5/12, is a fourth. A fourth up and a fifth down land on the same note — which is precisely why the twelve hours keep the same colours either way.

The arc from one hour’s hue to the next, drawn on the wheel.

4 A colour space stood on its corner

The palette doesn’t use HSL. It uses an HSI space in linear light: take the RGB cube, stand it on its black–white diagonal, and call height along that axis intensity and distance from it chroma.

The useful property is that every channel comes out proportional to intensity — so intensity is a plain scalar on linear light, not a separate dimension. That’s what makes the brightness control a single black sheet: multiplying the whole face by a constant is turning the intensity down. Measured against a true intensity change, hue drifts less than a degree.

Push it far enough and it clips. At i = 2/3 the plane cuts the cube through exactly three corners, so the slice is a triangle: yellow, magenta and cyan reach a chroma of 0.333 at the corners, falling to as little as 0.167 at the edge midpoints between them. Ask a hue for more than it can hold — drag the intensity up — and the dashed requested ring escapes the triangle. Rather than clip each channel, which would drag the hue somewhere else, the clamp pulls the colour straight back toward the grey axis, preserving hue and intensity and spending only saturation.

The shipped palette doesn’t clip. It sits at i = 3/5, SAT = 0.27 (chroma 0.162) — just inside the wall at every hue: the softer look the earlier, more-saturated version reached for by trimming, but reached cleanly. The clamp is the graceful fallback that made that version possible; drag the slider up past 3/5 to watch it start firing again.

The in-gamut slice at this intensity, with the twelve hours dropped on it. Hollow rings are where a colour was asked for; the filled dot is where it actually landed.

5 No code allowed

Wear OS watch faces must now ship as Watch Face Format — declarative XML, with no executable code. No shaders. No draw loop. Nothing that computes a colour at runtime.

So every colour here is baked at build time. A generator runs the colour space in JavaScript, emits the sweep gradients as literal hex, and the watch never does any colour maths. The only thing that moves is an arc’s end angle[MINUTE] * 6 for the seam, and 30 * [HOUR_0_11] + [MINUTE] * 0.5 for the inner disc’s, so that one creeps rather than jumping on the hour.

The constraint turned out to be the design. A face that had to be static-with-one-moving-edge is a better idea than the shader I set out to write.

<SweepGradient
    colors="#ffffbcbc #ffffb5c1 #ffffafc7 …"
    positions="0.0000 0.0333 0.0667 …" />

<Arc startAngle="0">
  <Transform target="endAngle"
             value="[MINUTE] * 6" />
</Arc>
Verbatim from the shipped face: the first three of thirty-one baked stops, and the one line that moves.