STYLE.md ·
How Catalogue works. Every rule, written down.
Information, filed: index cards standing in a catalogue drawer, wide Archivo headlines, mono call numbers, one index red and a plain yellow warning band.
Plain · exact · trustworthy
Best for
- Canadian cannabis stores, written to the Cannabis Act's information-only rules: no people, no lifestyle, no offers, a province check that knows the legal age (see "Cannabis retail in Canada")
- Anyone whose product is the information: libraries (Eastgate), parts and hardware suppliers (Brass & Bolt), archives, seed and specimen catalogues, wine lists, spec-driven B2B
- Audiences: people comparing like with like, who want the facts on the label before they come in
Less suited to: anything that sells on mood, people or story (Folio, Atelier, Marquee); clinical services (Remedy, Vigil, Candour).
Personality and voice
Plain and exact, like a good reference librarian: what it is, what's in it, where it is, whether it's in. Never sells, never jokes about the product.
- Headlines: "Every product, on file." · "What's on a card, and why." · "Information, and only information." · "The right screw, first time."
- Buttons: "Open the catalogue" · "Reserve" · "Reserve for pickup" · "Hours and address"
- Microcopy: "Availability updated every hour." · "We copy the label exactly." · "Reservations are held until close."
- Words to avoid on a cannabis site: anything about effects, mood, health, sleep, pain, relaxation or energy; lifestyle words (adventure, chill, vibes, party, escape); "free", "deal", "rewards", "win"; any comparison to alcohol, food, candy or drinks brands.
Colour
| Token | Reading room (light) | Night stacks (dark) | Role |
|---|---|---|---|
--paper |
#f4f2ec |
#121212 |
Off-white paper; a dark reading room at night |
--card |
#fffefa |
#1c1b19 |
Forms, tables |
--manila / --manila-2 |
#f2e8cd / #e8dbb8 |
#2a2620 / #3a342a |
Index cards and their tabs |
--well |
#e9e6dc |
#171614 |
Alternate sections |
--line |
#d7d2c4 |
#34322d |
Hairlines |
--rule-blue |
#a9c0e3 |
#2f3f5c |
The ruled lines on a card (never text) |
--ink / --ink-2 |
#151515 / #383733 |
#f2f0ea / #d1cec5 |
Text, the 2px rules |
--muted |
#5f5d56 |
#a19d93 |
Labels, call numbers |
--red |
#b4231b |
#ff7a6e |
The one accent: the card's top rule, buttons, links, the lit phrase |
--warn-bg / --warn-ink |
#ffd83d / #111111 |
same | The warning band, plain-pack yellow |
--steel / --brass |
#2c2d2f / #b58a3c |
same | The drawer front and its label holder |
Measured contrast (WCAG): ink on paper 16.3:1 · muted on paper 5.9:1 (on manila 5.4:1) · red on paper 5.9:1, on manila 5.4:1 · white on red 6.6:1 · warning text 13.6:1. Night stacks: ink 16.4:1 · muted 6.9:1 (on manila 5.6:1) · red 7.4:1 (on manila 5.9:1) · text on red 7.4:1 · ink on manila 13.2:1.
No green, no leaves, no lifestyle photography. The cards are the picture.
Typography
- Display: Archivo 700–800 at 110–125% width: wide, square, institutional.
- Body: Source Sans 3 400–700: clear at 18px.
- Records: Azeret Mono 500–600: call numbers, THC and CBD ranges, sizes, labels.
| Token | Size | Use |
|---|---|---|
--fs-h1 |
clamp(44px, 6.2vw, 92px), weight 800, width 125% | Page headline |
--fs-h2 |
clamp(32px, 3.9vw, 56px), weight 800, width 118% | Section headline |
--fs-h3 |
21px, weight 700 | Card and fact titles |
--fs-lead |
clamp(18px, 1.35vw, 21px) | Intro paragraphs |
--fs-body |
18px | Body |
--fs-label |
11.5px mono caps | Eyebrows with a boxed call number |
The signature move: every eyebrow carries a boxed call number (NL·01, FS·02), and every headline ends on the plain fact, in red.
Layout
- 1200px wrap, gutter
max(20px, 4vw). A yellow warning band above a sticky header with a 1px ink rule. - Hero: copy left, the drawer right. Then a "reading a card" table, a facts strip, a FAQ with call numbers, and a steel closing card.
- Index cards are ruled every 26px and their content snaps to the rules: the name on the first line under the red rule, then facts in label/value pairs, then the price.
Shape
- Filed and squared:
--r-s3px,--r-m6px,--r-l10px. Index cards have a tab on their top edge in one of three positions. - The drawer is steel with a brass label holder, a dark well and a lip at the front.
- The brand mark is an index card on its edge.
Motion language
- The drawer: pick a tab and that card is pulled up out of the stack and set down in front (550ms); the others step back. While motion is on and nobody has touched it, the drawer flips to the next card every 4.5 seconds.
- The warning band steps through its messages every 7 seconds.
- Shop filters re-deal the cards with a 28ms stagger.
- Reveals: 14px rise and fade, 550ms. The phone menu pulls down as a list of guide cards with call numbers.
- Motion switch in the footer (
[data-motion-toggle],html.calm, remembered assite-motion, default fromprefers-reduced-motion). Calm keeps the drawer still on its first card and the band on its first message. - Night stacks switch (
[data-theme-toggle]), remembered assite-theme;theme-colorfollows.
Imagery and illustration
The drawer, the cards and drawn maps. Line icons only where they label a fact. No photographs or drawings of people, characters or animals on cannabis sites (the Cannabis Act forbids them), and no lifestyle scenes, product glamour shots, leaves or smoke anywhere in the style.
Signature components
.drawer[data-drawer][data-cycle]›.drawer-label > span›.drawer-tabs(empty; buttons made from each card'sdata-tab) ›.drawer-well > .cards > .icard[data-tab]›.drawer-front..icard›.call(call number,.avail/.avail.low/.avail.out) ›h3›dl > div > dt + dd(pairs, three across) ›.icard-foot(.price, a button or note). In a grid:.card-grid..provgate[data-prov-gate][data-no-text]›.provgate-card(select[data-prov]with options"ON|Ontario|19",[data-prov-age],[data-prov-yes],[data-prov-no],[data-prov-out]);[data-prov-open]and[data-prov-show]in the header..warnband[data-warnings='[...]']›b+[data-warning];.facts[style="--n:4"],.notice,.faq summary[data-call],.licence,.close-card(--close-em).
Multi-page kit
- Phone menu:
.menu-btn[aria-controls]opens.site-menu(links withdata-call); Escape, outside click and links close it; Tab stays inside while open. - Current page:
aria-current="page"(a red underline). - Inner pages:
.page-headwith.crumbs, a.tagand a smaller.h1. - Fields:
.field,.fields,.field-wide,fieldset.field-set,.check,.form-card,[aria-invalid="true"];form[data-template]. - Tiles:
.choices›label.choice > input + span > b + small. Segmented control:.seg(mono labels;button[aria-pressed]withdata-filter/data-value, orlabel > input + text). - Gate:
[data-gate]withbutton[data-show="panel-id"](content panels; the age check is.provgate). - Slider, switch, tables, layout:
input.range,.switch[role=switch](firesswitchwithdetail.on),.table/.table.stack,.r,.grid-2.lean. - Helpers:
Catalogue.province()returns the chosen code;Catalogue.refresh(root).
Cannabis retail in Canada
Federal rules (the Cannabis Act and Regulations) apply everywhere; provinces add licensing, ages and store rules. Catalogue is built to the federal promotion rules as Health Canada describes them:
- Information and brand-preference only: what a product is, its characteristics (THC and CBD as on the label, size, type, producer), price and availability, behind reasonable steps to keep young people out: the province check sets the legal age (18 in Alberta, 21 in Quebec, 19 elsewhere).
- No depictions of people, characters or animals, real or fictional; no testimonials or endorsements, including reviews; nothing appealing to young persons.
- No lifestyle: nothing that associates cannabis with glamour, recreation, excitement, vitality, risk or daring.
- No inducements: no free products, BOGO, contests, gifts or loyalty rewards tied to cannabis.
- No health or cosmetic claims, and nothing false or misleading.
- The licensed name on the site, with the provincial licence and regulator in every footer.
Provincial rules on online reservations, delivery and store displays differ; check them. These notes are design guidance, not legal advice.
Do and don't
- Do copy the label exactly, ranges and all.
- Do keep availability honest and dated.
- Do give every section and card a call number.
- Don't add photos of people, staff portraits or customer pictures on a cannabis site.
- Don't describe effects, moods or occasions.
- Don't run offers, points or prizes on cannabis.
Accessibility
AA contrast throughout (measured above). Skip link, 3px blue focus ring (cream inside the drawer). The drawer's tabs are real buttons with aria-pressed; cards behind the front one are hidden from assistive tech and inert, so a screen reader reads one full card at a time. The province check is a modal dialog with a labelled select, a live age line and focus kept inside. The warning band changes quietly (aria-live="off"). Tables stack on phones. Responsive to 360px; tested with motion on and off, in Reading room and Night stacks.
How to make it yours
| Dial | Range |
|---|---|
| Accent | Index red (default), harbour blue (Ferry Street), library green (Eastgate), workshop navy (Brass & Bolt); set --red, --red-2, --red-soft for both modes and --close-em |
| Cards | Manila (default), cool grey, steel; set --manila and --manila-2 |
| Drawer | What's in it: products, new arrivals, parts; tab text from data-tab |
| Band | Warnings, notices or trade news; keep it plain yellow |
| Not negotiable | Archivo set wide, mono call numbers, ruled index cards that snap to their lines, the drawer or another real catalogue, and on cannabis sites the province check, no people or lifestyle, no offers, licence in every footer; the Motion switch |



