/* Site layout beyond the visual system. Tokens only; no colour literal. */
.md-table { overflow-x: auto; max-width: 100%; }
.md-table table, .site-table { width: 100%; border-collapse: collapse; font-size: var(--t-small); background: var(--white); }
.md-table th, .md-table td, .site-table th, .site-table td { text-align: left; vertical-align: top; padding: var(--s2) var(--s3); border-bottom: 1px solid var(--rule); }
.md-table th, .site-table th { font-weight: 600; }
/* Both scrolling wrappers carry tabindex="0" in the markup. A region that scrolls sideways has to be
   reachable by keyboard or its right hand columns are unreadable without a pointer; axe reports the
   absence as scrollable-region-focusable, serious, and did so on five routes at 390 wide. */
.table-scroll { overflow-x: auto; max-width: 100%; }
.claims .claim { display: grid; gap: var(--s2); }
.evidence-links { padding-left: 1.2em; }
.evidence-links li { overflow-wrap: anywhere; }
/* THE SIXTH TARGET FAMILY UNDER THE MINIMUM. Each of these rows holds one link to one artefact and
   no other text, so neither exemption in WCAG 2.2 clause 2.5.8 applies: not the inline one, because
   the link is not in a sentence, and not the spacing one, because consecutive rows measured 19 px
   tall with 22.5 px between centres, so the 24 px circles intersect. Measured on four routes.
   The five families fixed earlier in this branch each got the same 24 px minimum; this one was
   missed because the instrument that found them exempts anything left at `display: inline`, and
   these were. */
.evidence-links li a { display: inline-flex; align-items: center; min-height: 24px; }
.raw-get { display: grid; gap: var(--s3); padding-top: var(--s4); border-top: 1px solid var(--rule); }
.raw-get:first-of-type { border-top: 0; padding-top: 0; }
/* A grid item's automatic minimum size is its content, so a track sized 1fr grows to whatever the
   longest unbroken line inside it needs and the `overflow-x: auto` on the `pre` two levels down
   never gets a chance to scroll: the pre is already as wide as its text. These panels hold single
   line curl commands and base64url segments, which are the longest unbroken lines on the site, and
   an artefact drawer opened at 390 wide took the document to 3228px. Nothing caught it because the
   drawers ship closed and every responsive reading was taken of a shut drawer. */
.raw-get > * { min-width: 0; }
.term-strip { display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); gap: var(--s3) var(--s5); font-size: var(--t-small); padding: var(--s4); background: var(--white); border-radius: var(--r-2); }
.term-strip dt { font-weight: 600; }
.term-strip dd { margin: 0; color: var(--ink-2); }
/* The hero splits 55/45 rather than evenly. The headline is the longest line on the site and the
   column, not the measure, is what breaks it: at an even split the third line wrapped and the
   reference's three line block became four. */
/* CENTRED, AND THE MEASURED TARGET SAYS OTHERWISE. Recorded because the obvious change is the
   wrong one and somebody will try it again.

   The reference puts its eyebrow at about y=127 and ours sat at 242, so the text column reads as
   floating. align-items: start lands it at 129, a two pixel match, and the page gets WORSE: the
   reference's hero figure is LANDSCAPE, about 797 by 446, and ends level with its own buttons,
   while ours is square at 591 and runs 226 pixels below the last button. Top aligned, that leaves
   a hole under the text and the band reads as half empty.

   The number was reachable and the thing the number stood for was not. Closing that properly means
   making the figure landscape, which is a change to the globe partial's own geometry rather than to
   this rule, and it is not worth it for two pixels of eyebrow. Centred is the better page. */
.hero { display: grid; grid-template-columns: minmax(0, 1.22fr) minmax(0, 1fr); gap: var(--s6); align-items: center; }

/* ---------------------------------------------------------------------------
   THE HOME HERO, rebuilt against the Raidiam Agents reference.

   A PHOTOGRAPH UNDER THE COPY, not a figure beside it. The reference lays a
   network image across the full width, fades it into the page ground from the
   left so the statement stays legible, and fades the bottom edge into the next
   band so the picture has no seam.

   THE TWO FADES ARE GRADIENTS OF ONE TOKEN. packages/ui/tests/stylesheet.test.ts
   refuses a colour literal, and it exempts a gradient from the colour-mix rule
   precisely because the contrast gate cannot name a mix. Both fades therefore
   run var(--paper) to transparent and introduce no new colour at all.

   THE IMAGE IS DECORATION AND IS MARKED AS ONE. Empty alt and aria-hidden: it
   carries no claim, and a reader on a screen reader is told nothing by it.
   --------------------------------------------------------------------------- */
/* The section sits OUTSIDE .wrap in the view, which is what lets the photograph reach both edges;
   the copy inside carries .wrap so it lines up with every band below it. A 100vw trick was the
   alternative and it is the one that adds a horizontal scrollbar on a page that has a vertical
   one, which this estate has already paid for once. */
.hero-band { position: relative; overflow: hidden; padding-block: var(--s8) var(--s7); }
/* The closing band, on the same treatment as the hero: the reference's night-earth photograph with
   a gradient fading it into the page ground. The picture is decoration, so it carries an empty alt
   and aria-hidden and no claim on the page depends on it. */
.cta-band { position: relative; overflow: hidden; }
.cta-bg { position: absolute; inset: 0; z-index: 0; width: 100%; height: 100%; object-fit: cover; object-position: center; opacity: 0.45; }
.cta-veil {
  position: absolute; inset: 0; z-index: 1; pointer-events: none;
  background: linear-gradient(to top, var(--paper) 0%, transparent 85%),
              linear-gradient(to right, var(--paper) 0%, transparent 78%);
}
.cta-in { position: relative; z-index: 2; }
/* NO PANEL ON THE PHOTOGRAPH. The base .cta draws a wash ground and a radius, which is right on
   every other page that calls it and wrong here: a card laid over a picture hides the picture and
   gives the band two edges. On this band alone the copy sits straight on the photograph, which is
   what the reference does. The statement takes the display scale for the same reason it does in the
   hero, because it is the second largest thing on the page rather than a panel title. */
.cta-band .cta { background: transparent; border-radius: 0; padding: 0; grid-template-columns: minmax(0, 1fr); }
.cta-band .cta .statement { font-size: var(--t-h1); line-height: var(--t-h1-line); max-width: 22ch; }
.cta-band .cta .cta-sub { max-width: 46ch; }


.hero-bg {
  position: absolute; inset: 0; z-index: 0;
  width: 100%; height: 100%;
  object-fit: cover; object-position: right center;
}
.hero-veil {
  position: absolute; inset: 0; z-index: 1; pointer-events: none;
  background:
    linear-gradient(to top, var(--paper) 0%, transparent 34%),
    linear-gradient(to right, var(--paper) 0%, var(--paper) 34%, transparent 92%);
}
.hero-in { position: relative; z-index: 2; }
/* The reference holds the statement to about 42rem so the line breaks land where
   the picture starts rather than running under it. */
.hero-copy { max-width: 42rem; }
.hero-band .actions { margin-top: var(--s5); }

/* The accent half of the statement carries the reference's glow. It is a text
   shadow of the accent token, so it follows the palette and names no colour. */
/* The glow is the reference's, at the reference's strength. The first draft used the accent at
   full opacity and drew a visible halo box around the line rather than a bloom; the reference
   sets it at 0.5, which color-mix expresses without naming a colour. */
.hero-band .t-display .accent { text-shadow: 0 0 28px color-mix(in srgb, var(--teal-mid) 50%, transparent); }

@media (max-width: 900px) {
  /* The picture is behind the words at this width, so it is dimmed further
     rather than cropped: a fade that works at 1440 leaves the copy on top of
     the bright side of the image at 390. */
  .hero-veil { background: linear-gradient(to top, var(--paper) 0%, transparent 34%), linear-gradient(to right, var(--paper) 0%, var(--paper) 62%, transparent 100%); }
}
.hero-panel { background: var(--white); border-radius: var(--r-2); padding: var(--s5); display: grid; gap: var(--s3); }
.hero-panel .notfound { font-family: var(--mono); font-size: 14px; }
.hero-panel .checks { list-style: none; padding: 0; margin: 0; display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--s2) var(--s4); font-size: var(--t-small); }
.hero-panel .chain { display: flex; flex-wrap: wrap; align-items: center; gap: var(--s2); }
.hero-panel .chain .hop { padding: 4px 10px; border-radius: var(--r-1); font-size: var(--t-small); font-weight: 600; border: 1.5px solid var(--bound); }
.hero-panel .chain .hop[data-treat="product"] { background: var(--teal); color: var(--on-brand); border-color: var(--teal); }
.hero-panel .chain .dots { color: var(--ink-2); letter-spacing: 0.2em; }
.questions { list-style: none; padding: 0; margin: 0; display: grid; gap: var(--s2); font-size: var(--t-h3); }
.two-col { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--s6); }
.people { display: flex; flex-wrap: wrap; gap: var(--s3) var(--s5); font-size: var(--t-small); color: var(--ink-2); }
.session-lines { display: grid; gap: var(--s3); }
.filter-row { display: flex; flex-wrap: wrap; gap: var(--s3); align-items: center; }
.filter-row [data-count-of] { font-size: var(--t-small); }
.matrix-row-note { font-size: var(--t-small); color: var(--ink-2); }
@media (max-width: 900px) { .hero, .two-col { grid-template-columns: minmax(0, 1fr); } }
@media (max-width: 620px) { .hero-panel .checks { grid-template-columns: minmax(0, 1fr); } }

/* ---------------------------------------------------------------------------
   THE PRODUCT SURFACE.
   Added 12 September, after Ralph's note that the references are a visually
   appealing SaaS application and this was a static, relatively boring website.

   He is right, and the comparison harness had been reporting three routes green
   while it was true. That instrument decides palette, accent density and band
   rhythm. None of those was the gap. The gap is components: the references
   carry an eyebrow above every title, pill buttons, a hero illustration, a
   demo action in the masthead, a trust bar, card radius with a visible stroke,
   tabs, filter chips and status pills in a real table. Colour was already right.

   This layer sits in site.css rather than ui.css on purpose. ui.css is shared
   with the films and the gallery, and the films are rendered; moving a radius
   there moves frames that are already cut.
   --------------------------------------------------------------------------- */

:root {
  /* Named for what it is. A custom property called --lift hides that its value is a shadow, and
     the colour rule allows black only in one. Black in a shadow is black, not a palette entry. */
  /* THE ACCENT IS NOT COPIED HERE ANY MORE, and the copy is why this line changed. It held
     rgba(21, 212, 216, ...), which was the old teal accent written out by hand. It passed the
     colour rule only because those three numbers happened to equal the token's value, so when the
     accent moved to the Raidiam blue the glow stayed teal and the rule fired. The gate was right.
     color-mix takes the token, so there is one accent and the glow follows it wherever it goes.
     IT IS --teal-mid RATHER THAN --teal, and that is the vocabulary rather than a preference:
     --teal is the ownership marker and fills a Raidiam product chip and nothing else, which
     packages/ui/tests/stylesheet.test.ts enforces by selector. --teal-mid's declared role in
     tokens.json is graphic fill, which is exactly what a glow behind a hero is. */
  --glow: radial-gradient(60% 60% at 50% 45%, color-mix(in srgb, var(--teal-mid) 16%, transparent), color-mix(in srgb, var(--teal-mid) 0%, transparent) 70%);
}

/* An eyebrow over the title. Small, letterspaced, accent, and the cheapest single
   thing that separates a product page from a document. */
.eyebrow {
  font-size: var(--t-label); font-weight: 700; letter-spacing: 0.14em;
  text-transform: uppercase; color: var(--teal-dark); margin: 0 0 var(--s3);
}

/* Pill actions. The references use one filled accent action and outlined siblings. */
/* A PAGE BUTTON IS A ROUNDED RECTANGLE AND ONLY THE MASTHEAD ACTION IS A PILL, which is the
   reference's distinction and was lost when every button here took the pill. Measured off the
   running reference at /why-raidiam: its two hero buttons are 12px radius at 44 and 50px tall with
   a 14px label, and the one pill on the page is the masthead's "Book a working session".
   A page full of pills reads as a page full of calls to action; the rectangle is what lets the one
   pill in the bar still mean something. */
.btn { border-radius: var(--r-3); padding-inline: var(--s5); font-size: var(--t-label); }
.btn-quiet { background: transparent; border-color: var(--teal-deep); }
.btn-quiet:hover { background: var(--wash-teal); }
.actions { display: flex; flex-wrap: wrap; gap: var(--s3); align-items: center; }

/* The card treatment MOVED to packages/ui/src/ui.css, and it had to.

   It was here, and site.css loads AFTER ui.css, which now contains every component part. So this
   rule beat every part at equal specificity, from a file part authors are told not to touch. It
   reached .figure, .rail .stage and .resolve-seq .step, all of which parts own. Measured on
   /architecture: figure.control-plane computed a 1px --rule border, a 14px radius and a shadow it
   never asked for, and because its own part sets padding: 0 on purpose the caption's glyphs sat ON
   the left stroke. A part writing `border: 0` did NOT fix it; only a second class did, which is
   knowledge nobody had. Four figures on three routes were affected.

   In the base sheet it loads BEFORE the parts, so a part overrides it the ordinary way. */

/* THE MASTHEAD ACTION IS packages/ui/src/parts/mast.css's NOW, INCLUDING ITS PHONE DRAWER STATE.
   It was declared here as a filled pill and the comment below it recorded why: this sheet loads
   after ui.css, so at equal specificity it won. The target draws the action as an OUTLINE pill, and
   the rewrite of the masthead had to reach specificity 0-2-0 to get past this block. Two rules for
   one control, one of them only there to beat the other, is how the next person loses an hour. The
   control has one owner again. */

/* ---- The hero globe ------------------------------------------------------
   Connect at the centre, and around it the kinds of consumer that resolve
   against it. The sphere is drawn, the chips are real HTML so they stay
   readable and translatable, and every label names something this estate has.

   The box is SQUARE on purpose. The partial draws with a 0 0 100 100 viewBox
   and preserveAspectRatio="none", so one SVG unit is one percent of the box on
   both axes and an arc can be made to land on a chip. A non square box would
   draw the sphere as an ellipse.

   TEAL IS CONNECT'S. The card at the centre is the product, so it is the only
   thing here with a brand fill or a brand stroke. The chips are consumers: a
   neutral ground, a rule stroke and ink icons. Making them teal would say they
   are Raidiam, which is the one thing the treatment labels exist to prevent. */
.orbit { position: relative; aspect-ratio: 1 / 1; width: 100%; max-width: 680px; margin-inline: auto; display: grid; place-items: center; }
.orbit svg { position: absolute; inset: 0; width: 100%; height: 100%; }

/* The centre card. A near opaque ground, because the reference card sits ON the
   globe rather than in front of it: at 72 percent the land dots read straight
   through the wordmark and the card looked like a hole. */
/* IT CARRIES data-treat="product" AND SAYS SO IN THE SELECTOR. The centre of the hero globe is
   Raidiam Connect, and this rule puts the brand teal on its border and in four glows. The one
   colour rule allows brand teal only where the selector declares the product, and this was the one
   place on the site using it without declaring it. Nothing moves: the product treatment styling is
   scoped to .treat, .node, .hop and .item, so a bare attribute here paints nothing and only makes
   the claim the figure was already making. The rule went unread for a different reason, which is
   that the stylesheet checks read ui.css alone until now. */
.orbit-core[data-treat="product"] {
  position: relative; z-index: 2; width: 162px; padding: var(--s5) var(--s3);
  display: grid; justify-items: center; gap: 2px; text-align: center;
  /* A PLAIN TOKEN, NOT A colour-mix, and the reason is the checker rather than the colour. It is
     NOT the reason first recorded here, which was that axe cannot resolve a colour-mix. Planted
     four times to settle it: the same failing pair of colours, written once as a colour-mix and
     once as a hex, placed once in clear space and once inside this card. In clear space axe
     reported BOTH as violations, so it resolves a colour-mix perfectly well. Inside this card it
     reported both as incomplete, and said why: "background color could not be determined because
     it partially overlaps other elements". The card lies over the globe's svg. Syntax was never
     the cause and overlap always was.

     The token still earns its place, for the other checker. packages/ui/tools/contrast.mjs
     enumerates TOKEN PAIRS, so `d-ink on d-wash-teal` at 12.11 is gated by name. A colour-mix is
     not a token and the gate cannot see it at all. So this card's text was ungated under the mix
     and is gated now, which is the real gain; axe was never going to read it either way. */
  background: var(--wash-teal);
  border: 1.5px solid var(--teal); border-radius: var(--r-3);
  /* Six layers, and each one is doing a different job. In order: the hairline that doubles the
     border, the tight glow that makes the border read as lit rather than drawn, the wide glow that
     puts light on the sphere around it, a CAST SHADOW below and behind, a second tighter shadow to
     seat the card, and a lit top edge inside. The cast shadow is what makes the card sit above the
     globe instead of being cut into it, and it is the layer the flat version had none of. */
  box-shadow:
    0 0 0 1px color-mix(in srgb, var(--teal) 30%, transparent),
    0 0 14px 0 color-mix(in srgb, var(--teal) 85%, transparent),
    0 0 52px -4px color-mix(in srgb, var(--teal) 90%, transparent),
    0 26px 46px -18px var(--paper),
    0 10px 20px -12px var(--paper),
    inset 0 1px 0 color-mix(in srgb, var(--ink) 26%, transparent),
    inset 0 0 26px -14px color-mix(in srgb, var(--teal) 55%, transparent);
}
.orbit-core .orbit-mark { display: block; line-height: 0; margin-bottom: var(--s3); }
.orbit-core .orbit-mark img { width: 29px; height: 35px; }
/* NOT .mark. That name is already the design system's state glyph, .mark { width: 1em; height: 1em },
   so the card's name inherited a 15px square box, its second line overflowed the grid row, and
   "Identity. Authority." rendered on top of "CONNECT". The old markup had the same collision and
   white-space: nowrap hid it. A component must not reuse a global class name for another purpose. */
.orbit-core .orbit-name { font-weight: 700; letter-spacing: 0.09em; font-size: var(--t-small); line-height: 1.26; }
.orbit-core .line { font-size: var(--t-label); color: var(--teal-dark); line-height: 1.35; }
.orbit-core[data-treat="product"] .line:first-of-type { margin-top: var(--s2); padding-top: var(--s2); border-top: 1px solid color-mix(in srgb, var(--teal) 30%, transparent); width: 100%; }

/* The chip: a label and an icon side by side, the icon inboard toward the globe,
   as the reference has it. left and top arrive inline, from the same table the
   spokes are drawn from. */
.orbit-node {
  position: absolute; z-index: 2; transform: translate(0, -50%);
  display: flex; align-items: center; gap: var(--s2); max-width: 25%;
  padding: 9px 11px; border-radius: var(--r-3);
  /* A plain token, for the reason recorded on .orbit-core above: the contrast gate enumerates
     token pairs, so `d-ink on d-card` at 13.79 is gated by name, and a colour-mix is invisible to
     it. axe resolves five of these six labels outright; the sixth overlaps the sphere far enough
     that axe gives up on it, and no change of syntax alters that. */
  background: var(--white);
  border: 1px solid color-mix(in srgb, var(--rule) 32%, transparent);
  /* A cast shadow and a lit top edge, the same two the card has and for the same reason: these
     sit ON the sphere, and without them they read as holes cut in it. */
  box-shadow:
    0 14px 30px -14px var(--paper),
    0 4px 10px -6px var(--paper),
    inset 0 1px 0 color-mix(in srgb, var(--ink) 12%, transparent);
  font-size: var(--t-label); font-weight: 600; line-height: 1.22;
}
.orbit-node[data-side="left"] { transform: translate(-100%, -50%); flex-direction: row; text-align: right; }
.orbit-node[data-side="left"] .label { order: -1; }
.orbit-node .dot {
  flex: none; width: 38px; height: 38px; border-radius: var(--r-2); display: grid; place-items: center;
  /* THE PAGE GROUND, NOT THE TEAL WASH. A teal ground on a consumer's icon says the consumer is
     Raidiam, which is the one thing the treatment labels exist to prevent, and teal is the marker
     that carries it. Darker than the chip also makes the well read as recessed, which is the
     opposite of the chip's own lit top edge and is free depth. */
  background: var(--paper);
  box-shadow: inset 0 1px 0 color-mix(in srgb, var(--ink) 9%, transparent);
  border: 1px solid color-mix(in srgb, var(--rule) 45%, transparent); color: var(--ink);
}
.orbit-node .dot svg { position: static; width: 20px; height: 20px; }
.orbit-node .label { display: block; }

/* Narrow. The globe used to be display:none under 900px, so a phone visitor got
   the hero's whole right hand side as nothing at all. It stays, smaller, and the
   chips drop their absolute positions and become a list under it, so the six
   labels survive even though the spokes no longer point at them. */
@media (max-width: 1100px) {
  /* 14px, not 13. The floor in packages/ui/tests/stylesheet.test.ts is 14 and allows below it only
     for mono inside a scrolling raw block. These are the six labels naming what the hero globe
     connects, on the widths where the figure is already the smallest it gets, so they are the last
     text on the site that should go under the floor. The check did not fire before because the
     stylesheet rules read ui.css alone and never read this file. */
  .orbit-node { font-size: var(--t-small); padding: 5px 7px; }
  .orbit-node .dot { width: 30px; height: 30px; }
  .orbit-node .dot svg { width: 16px; height: 16px; }
  /* The card holds its words while the figure shrinks, so between 760 and 1100 it takes an ever
     larger share of the sphere. It is squeezed only as far as its longest line allows: below about
     150px "Identity. Authority." breaks in two, the card grows a row, and it ends up TALLER than
     the sphere it sits on. That is worse than a card that is merely large. */
  .orbit-core { width: 156px; padding: var(--s4) var(--s2); }
  .orbit-core .orbit-mark img { width: 22px; height: 27px; }
  .orbit-core .orbit-mark { margin-bottom: var(--s2); }
}
@media (max-width: 760px) {
  .orbit { aspect-ratio: auto; display: block; max-width: 420px; }
  .orbit svg { position: relative; aspect-ratio: 1 / 1; height: auto; }
  /* The card comes OFF the globe here and sits under it, in DOM order. Overlaid it has to be about
     45 percent of the sphere to look right, which the wide layout manages at 162px; at 390 the
     sphere is 210px across, so the same proportion is 95px and "RAIDIAM CONNECT" does not fit in it.
     A card narrow enough to sit on the globe is a card the words break inside. */
  .orbit-core { position: static; transform: none; width: 100%; margin: var(--s4) 0 0; }
  /* The spokes go with the chips. Each one is drawn to a chip position that no longer exists here,
     so left in they are six short lines ending in empty space, which is the fault the coordinate
     table exists to prevent. The nodes stay: they are points on the sphere and still read as such. */
  .orbit-spokes { display: none; }
  .orbit-node {
    position: static; transform: none; max-width: none; width: 100%;
    margin-top: var(--s2);
  }
  /* transform: none on .orbit-node alone does NOT reach these. The side rule carries an
     attribute, so it outranks the class rule whatever the order, and the three left chips kept
     translate(-100%) and stacked 330px off the left edge of a 390 wide screen. Specificity, not
     order, is what decides a media query override. */
  /* Every chip the same way round in the list. row-reverse here put the label back on the left for
     exactly the three chips the order swap had already fixed, so the six read as two groups. */
  .orbit-node[data-side="left"] { transform: none; flex-direction: row; text-align: left; }
  .orbit-node[data-side="left"] .label { order: 0; }
}

/* THE ONE MOVING THING. Each node's outer bloom breathes, staggered, so the figure reads as live
   rather than printed. It is opacity only, on four circles, and it never moves anything a reader
   has to track.

   Under prefers-reduced-motion the rule is `animation: none`, which removes the animation rather
   than pausing it: document.getAnimations() then returns nothing at all, which is what clause V14
   reads. A transition left in place, or a zero duration, would still be an animation object and
   would still count. */
@keyframes orbit-node-breathe {
  0%, 100% { opacity: 0.5; }
  50% { opacity: 1; }
}
.orbit-nodes .bloom { animation: orbit-node-breathe 5.4s ease-in-out infinite; }
@media (prefers-reduced-motion: reduce) {
  .orbit-nodes .bloom { animation: none; opacity: 0.85; }
}

/* ---- The trust bar --------------------------------------------------------
   Figures and named customers, in a band under the hero. Everything in it is a
   statement of fact about Raidiam rather than about this showcase, so it is
   sourced from site.md and not computed here. */
.trust-bar {
  display: flex; flex-wrap: wrap; align-items: center; gap: var(--s4) var(--s6);
  padding: var(--s4) var(--s5); margin-top: var(--s7);
  background: var(--paper-alt); border: 1px solid var(--rule); border-radius: var(--r-3);
}
.trust-bar .lede { font-size: var(--t-label); font-weight: 700; letter-spacing: 0.12em; text-transform: uppercase; color: var(--ink-2); }
.trust-bar .fig { display: grid; }
.trust-bar .fig b { font-size: var(--t-h3); font-weight: 600; line-height: 1.1; }
.trust-bar .fig span { font-size: var(--t-label); color: var(--ink-2); }
.trust-bar .names { margin-left: auto; display: flex; flex-wrap: wrap; gap: var(--s4); align-items: center; font-weight: 600; color: var(--ink-2); }
