Redesign: put the app on the Back Bar design tokens - #50
Merged
Conversation
Copies of what came out of Claude Design, kept with the code so the two do not drift. Nothing here is wired up yet. tokens.css is the part that becomes real code: colours, type, spacing and motion as Tailwind v4 custom properties, with light and dark sharing one set of names. That is what will let the !important overrides in frontend/src/index.css go away rather than being ported. The .html files are specimen pages, not components. support.js is only what those pages need to draw themselves and is not part of the app. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
index.css was 327 lines, nearly all of it a second copy of the colour scheme written as !important overrides on Tailwind's own utility classes (.bg-white, .text-gray-600 and so on). Every new screen had to be remembered twice, and one of them — the past orders page — was only ever dark because of it, having no dark styling of its own. It is now the Back Bar token sheet: one set of names, defined light, and redefined once for dark. A component asks for `surface` or `text-muted` and is correct in both, so nothing needs a `dark:` prefix and nothing needs an override. Also drops the leftover .fallback-test and .test-element debugging rules. tailwind.config.js goes with it. Tailwind v4 only reads a JS config when the stylesheet asks for one with @config, and nothing here does, so it has not been doing anything. Verified: the built stylesheet is byte-identical with and without it. Components still use the old grey utilities and are migrated next. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
The five steps no longer each get their own colour. Ready is the only one that lights up, because it is the only one that needs somebody to move; the rest ride the grey ramp and are told apart by the bar down the left edge of the row, which is a shape rather than a hue. The queue rows now follow the design: one action per row, always the same size and in the same place, with reject as a different shape set apart from it, so the common case can be hit without looking. The count beside "pending orders" turns the signal colour when a drink is waiting to be collected. orderStatus loses its per-step icons and gains statusPill and statusRail. It is now a .ts file, since it holds no markup. Two tests were reaching for class names — one for `div.rounded-lg`, one matching the exact shape of a class string — so they broke on the restyle without anything being wrong. Both now check what they were actually for: the status card is found by its accessible name, and the steps are still required to differ from one another in more than one way. Giving the card that name is also a small improvement for anyone using a screen reader. Checked that the rewritten test fails when the name is taken away. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
The drink card follows the design: the picture, then the name and the description, then one strip along the bottom holding the recipe and the order button. Without a picture the name is set large in its place, so a menu where only some drinks have photos still reads as one grid. The order button now says why it cannot be used — "you can only have one active order at a time" — instead of going grey and only explaining itself in a pop-up after the guest has already tapped it. The wording was already translated, so nothing new had to be written. Section headings lose their colours and their emoji and become a quiet label with a rule, which lets the drinks be the loud thing. Surprise me is no longer pink: the signal colour means a drink is ready to collect and is not spent on anything else, so it is an ordinary bordered button. Four tests were asking for the drink name with getByText, which now matches twice because the name is also the picture. They ask for the heading instead, which is what a guest reads and what a screen reader announces. The one covering the one-drink-at-a-time rule now checks the button explains itself, which is the thing that changed. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
The remaining screens still used the old grey-and-blue utilities, which had been kept upright by the override sheet that went in the first commit. Without it they would have been light-only, so this finishes the job: bartender screens, drink form, categories, settings, reports, the recipe view, past orders, sign in and the way in from a QR code. Most of it was a mechanical swap of one palette for another. Three parts were not: The landing page loses its purple gradient for the sign the design asks for — an ink panel, the name of the thing set large, a rule, and a line about what it is. That needed a token the sheet did not have. Every colour so far flips between the two schemes, but a painted sign does not lighten when the lights come up, so `sign` and `sign-fg` are defined once and deliberately left out of the dark block. The same panel is used on the QR arrival screens. That flipping caught two real bugs in the mechanical swap. Text sitting on a photo, in the recipe view and on the QR screens, had been given the "inverse" colour, which is white in the light scheme but near-black in the dark one — so it would have vanished against the dark end of a photograph. Those now use the sign colour, which is white in both. Dialogs keep the larger corner the design reserves for them, and gain a border, since a shadow alone barely reads against a near-black room. Two new strings for the landing panel, in both languages. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Where a control rested on the sunken surface and lifted to a slightly darker grey, both greys mapped to the same token and the hover stopped being visible. Those now lift to the border colour instead. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Replaces the dark mode override sheet with a real set of design tokens, and
puts every screen on them.
Reviewing this
docs/design/is ~6.5k lines of generated reference material from ClaudeDesign — worth collapsing. The four code commits are each readable on their
own and in order:
344dab234b8f1d89b948fc0ef66b6fa9bfdWhat it does
index.csswas 327 lines, nearly all of it a second copy of the colourscheme written as
!importantoverrides on Tailwind's own utility classes.Every new screen had to be remembered twice, and the past orders page was
only ever dark because of it, having no dark styling of its own.
It is now one set of role-named tokens, defined light and redefined once for
dark. Nothing has a
dark:prefix any more. Colour also stops carrying thefive order steps: only ready lights up, because it is the only one that
needs somebody to move, and the rest are told apart by the bar down the left
edge of the row.
tailwind.config.jsis deleted. Tailwind v4 only reads a JS config when thestylesheet asks for one with
@config, and nothing here did — the builtstylesheet is byte-identical with and without it.
Worth a closer look
The landing sign has to be ink in both, so it gets its own
signtoken,deliberately left out of the dark block.
QR screens would have gone near-black in dark mode.
explaining itself in a pop-up after the guest has already tapped it. This
is a behaviour change; the wording was already translated.
now matches twice; they ask for headings and accessible names instead. I
checked the rewritten status-card test fails when the accessible name is
removed, so it is not passing for free.
Checked
npm test39/39,npm run lint,npm run typecheck,npm run buildallclean. Backend untouched, so its checks were not run.
Not yet seen in a browser. It compiles and behaves under test; no screen
has been looked at.
Not in this PR
The structural work from the two shell documents: the guest dock that keeps
the live order visible from every guest screen, the bartender rail and the
demotion of the four setup screens, tabs as URLs, and rendering the drink
form and recipe view as modals over the shell instead of replacing the whole
app. Each is worth its own change.
Some hardcoded English strings also remain untranslated — all pre-existing.
🤖 Generated with Claude Code