/* MaeVae site: the drawing kit.

   No picture of the app on this site is a screenshot. Every one is a
   drawing, built from the parts in this file in HTML and CSS, and the
   parts follow the app's own window: a frameless window with the rail of
   profiles on the left, the top bar, and the panes, each with its header,
   its terminal and its HUD strip; then the app's panels: the profile
   editor, the new-profile steps, Quick settings, the Isolation report, the
   command palette, the usage dashboard, a notice, a Windows notification
   and the tray.

   The drawings use the page's Stage palette rather than the app's theme.
   The app's grounds are drawn with the window tokens of styles.css; its
   cyan accent and its per-segment HUD colours are drawn in one neutral
   ink, so a drawing reads as part of the page and not as a second brand.
   The state colours stay, because in the app they carry meaning: green
   for Isolated, PASS and a finished turn; red for Breach, FAIL, deny and
   panic; amber for an agent that is waiting for you and, as in the app,
   for Drift and WARN. Amber fills a field only where an agent waits (the
   notification); for Drift it is only the badge's dot and word.

   Sizes are in em from the drawing's root, so a drawing set at another
   size grows or shrinks as one piece. At the default size nothing in a
   drawing is below 14px.

   States are classes. The scene stepper (mock.js) adds and removes them,
   and the rules near the end of this file say how a scene arrives. A
   drawing with no script, under reduced motion and in print is its markup
   as written: the finished frame. */

:root {
  /* The drawn app's grounds: the page's window tokens, the terminal's
     among them, which the hero's window shares, plus a darker rail so the
     panes read as the app's */
  --m-edge: var(--night-line-strong);
  --m-rail: #171b1f;
  --m-chrome: var(--w-chrome);
  --m-pane: var(--w-pane);
  --m-term: var(--w-term);
  --m-split: var(--w-split);
  --m-field: #13171a;
  --m-field-edge: #6b747d;
  --m-select: #2b3239;
  --m-raised: var(--night-raised);

  /* The drawn app's ink */
  --m-ink: var(--night-ink);
  --m-body: var(--night-body);
  --m-quiet: var(--night-quiet);
  --m-faint: var(--night-faint);

  /* The state colours, as the app uses them; text on amber is night */
  --m-amber: var(--amber);
  --m-on-amber: var(--night);
  --m-ok: #7bc96f;
  --m-red: #e27d98;

  /* Four example profile colours. The app lets each profile pick its own;
     these take the hues of its swatch row, lightened so a name drawn in its
     colour reads at 4.5:1 or more on every drawn ground. */
  --m-p1: #93b4e6;
  --m-p2: #c4b2e2;
  --m-p3: #9fc7c0;
  --m-p4: #c9c6d8;

  /* The drawing's reading size */
  --m-fs: 0.9375rem;

  /* The app's backdrop behind a panel that opens over the window (black at
     half strength), and the app's own panel widths in the drawing's em:
     New profile 460px, the command palette 560px, the usage dashboard up
     to 1000px, each at the drawing's 15px */
  --m-scrim: rgb(0 0 0 / 0.5);
  --m-w-wizard: 31em;
  --m-w-palette: 37em;
  --m-w-dash: 67em;

  /* The frame of night ground a plate leaves round its drawing */
  --plate-pad: clamp(16px, 1.6vw, 24px);

  /* The scenes share the hero's one tempo */
  --m-beat: var(--beat, 480ms);
  --m-half: var(--half-beat, 240ms);
  --m-arrive: var(--arrive, cubic-bezier(0.22, 1, 0.36, 1));
  --m-leave: var(--leave, cubic-bezier(0.5, 0, 0.75, 0));
}

/* ------------------------------------------------------------------ roots */

/* Any element that starts a drawing. The marks of styles.css (.key) and
   the focus ring are set for the dark drawing, whatever ground it stands
   on. Zero specificity, so each part below can override it. */
:where(.mock, .mock-window, .mock-pane, .mock-dialog, .mock-editor,
       .mock-report, .mock-palette, .mock-quick, .mock-desk, .mock-toast) {
  --key-bg: var(--night-ink);
  --key-ink: var(--night);
  --focus: var(--night-ink);
  position: relative;
  max-width: 100%;
  color: var(--m-ink);
  font-family: var(--sans);
  font-size: var(--m-fs);
  font-weight: 400;
  line-height: 1.45;
  letter-spacing: 0;
  text-align: left;
  overflow-wrap: break-word;
}

:where(.mock, .mock-window, .mock-pane, .mock-dialog, .mock-editor,
       .mock-report, .mock-palette, .mock-quick, .mock-desk, .mock-toast) ::selection {
  background: var(--night-select);
  color: var(--night-ink);
}

/* The parts that change with their width ask their own width, so the same
   drawing works in a narrow column and across a wide band. A container
   must fill its parent: never let one size itself to its content. */
.mock,
.mock-window,
.mock-dialog,
.mock-editor,
.mock-report,
.mock-palette,
.mock-quick,
.mock-desk {
  container: mock / inline-size;
}

.mock-pane {
  container: mock-pane / inline-size;
}

/* The drawing's root (the part that carries role="img") is also named
   mock-root, so a part deep inside can ask how large the whole drawing is,
   not only the panel or pane it sits in. */
:is(.mock, .mock-window, .mock-dialog, .mock-editor, .mock-report,
    .mock-palette, .mock-quick, .mock-desk)[role="img"] {
  container-name: mock mock-root;
}

.mock-pane[role="img"] {
  container-name: mock-pane mock-root;
}

/* Density. A large drawing with three lines in it reads as an empty
   frame, and a small one with twelve reads as a wall. So a drawing carries
   the rows the app would show at its largest size, and marks the extra
   ones: mock-more shows once the whole drawing is 760px wide (the size of
   a chapter's drawing), mock-most once it is 1200px wide (the hero window,
   the showcase). Below those widths the extra rows take no room. */
@container mock-root (max-width: 47.499rem) {
  .mock-more {
    display: none !important;
  }
}

@container mock-root (max-width: 74.999rem) {
  .mock-most {
    display: none !important;
  }
}

/* The scene stepper hides and shows parts with the hidden attribute; a
   part's own display rule must never bring a hidden part back. */
.mock [hidden],
.mock-window [hidden],
[data-scene] [hidden] {
  display: none !important;
}

.mock p {
  max-width: none;
}

/* Small shared pieces */

.mock-spacer {
  flex: 1 1 auto;
}

.mock-dim {
  color: var(--m-quiet);
}

.mock-faint {
  color: var(--m-faint);
}

.mock-code {
  font-family: var(--mono);
  color: var(--m-ink);
}

/* The app sets its small labels in capitals; the drawing keeps that, at a
   readable size and a lighter tracking than the app's tiny type needs. */
.mock-caps {
  font-family: var(--mono);
  font-size: 0.94em;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}

/* ------------------------------------------------------------------ icons */

/* The app draws its small controls with glyphs. A glyph can be missing
   from a reader's fonts, so the drawing draws each one with borders, in
   the current ink, in one stroke. */
.mock-ico {
  position: relative;
  display: inline-block;
  flex: none;
  width: 1em;
  height: 1em;
  vertical-align: -0.15em;
}

.mock-ico::before,
.mock-ico::after {
  content: "";
  position: absolute;
  box-sizing: border-box;
}

/* Close: two strokes crossed */
.mock-ico-close::before,
.mock-ico-close::after {
  top: 50%;
  left: 50%;
  width: 0.85em;
  border-top: 1.5px solid currentColor;
  transform: translate(-50%, -50%) rotate(45deg);
}

.mock-ico-close::after {
  transform: translate(-50%, -50%) rotate(-45deg);
}

/* Minimize: one stroke */
.mock-ico-min::before {
  top: 50%;
  left: 50%;
  width: 0.7em;
  border-top: 1.5px solid currentColor;
  transform: translate(-50%, -50%);
}

/* Maximize: an open square */
.mock-ico-max::before {
  top: 50%;
  left: 50%;
  width: 0.62em;
  height: 0.62em;
  border: 1.5px solid currentColor;
  transform: translate(-50%, -50%);
}

/* Redraw: a ring open at one corner, with its arrowhead */
.mock-ico-redraw::before {
  top: 50%;
  left: 50%;
  width: 0.78em;
  height: 0.78em;
  border: 1.5px solid currentColor;
  border-top-color: transparent;
  border-radius: 50%;
  transform: translate(-50%, -50%) rotate(45deg);
}

.mock-ico-redraw::after {
  top: 0.02em;
  right: 0.12em;
  border-top: 0.2em solid transparent;
  border-bottom: 0.2em solid transparent;
  border-left: 0.26em solid currentColor;
  transform: rotate(-20deg);
}

/* Fill the window: a square with a square inside */
.mock-ico-fill::before,
.mock-ico-showall::before,
.mock-ico-cols::before,
.mock-ico-rows::before,
.mock-ico-grid::before {
  top: 50%;
  left: 50%;
  width: 0.82em;
  height: 0.82em;
  border: 1.5px solid currentColor;
  border-radius: 1px;
  transform: translate(-50%, -50%);
}

.mock-ico-fill::after {
  top: 50%;
  left: 50%;
  width: 0.36em;
  height: 0.36em;
  border: 0.18em solid currentColor;
  transform: translate(-50%, -50%);
}

/* Show all and the grid layout share the app's glyph: a square in four */
.mock-ico-showall::after,
.mock-ico-grid::after,
.mock-ico-cols::after,
.mock-ico-rows::after {
  top: 50%;
  left: 50%;
  width: 0.82em;
  height: 0.82em;
  background-repeat: no-repeat;
  transform: translate(-50%, -50%);
}

.mock-ico-showall::after,
.mock-ico-grid::after {
  background-image: linear-gradient(currentColor, currentColor),
                    linear-gradient(currentColor, currentColor);
  background-position: center, center;
  background-size: 1.5px 100%, 100% 1.5px;
}

/* Columns and rows: a square in three */
.mock-ico-cols::after {
  background-image: linear-gradient(currentColor, currentColor),
                    linear-gradient(currentColor, currentColor);
  background-position: 33.3% 0, 66.7% 0;
  background-size: 1.5px 100%, 1.5px 100%;
}

.mock-ico-rows::after {
  background-image: linear-gradient(currentColor, currentColor),
                    linear-gradient(currentColor, currentColor);
  background-position: 0 33.3%, 0 66.7%;
  background-size: 100% 1.5px, 100% 1.5px;
}

/* Stop, as on the panic button: a small solid square */
.mock-ico-stop::before {
  top: 50%;
  left: 50%;
  width: 0.6em;
  height: 0.6em;
  border: 0.3em solid currentColor;
  transform: translate(-50%, -50%);
}

/* ----------------------------------------------------------- the window */

/* The app's window has no Windows title bar of its own: the rail's top
   carries the name, the top bar carries the window's three buttons. The
   rail and the stage sit side by side and wrap to one column on a narrow
   screen, so the drawing never needs a scroll bar. */
.mock-window {
  display: flex;
  flex-wrap: wrap;
  overflow: hidden;
  overflow: clip;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-term);
}

/* The rail. Below 40rem of drawing it is left out, as the app's auto-hide
   rail is out of view; from 40rem it is the app's collapsed rail (the
   lights only); from 60rem the full rail with names. is-rail keeps the
   full rail at every width, stacked above the stage on a phone. */
.mock-rail {
  display: none;
  flex: 0 0 14em;
  flex-direction: column;
  min-width: 0;
  border-right: 1px solid var(--m-split);
  background: var(--m-rail);
  color: var(--m-ink);
}

.mock-window.is-rail > .mock-rail {
  display: flex;
  flex-basis: 100%;
  border-right: 0;
  border-bottom: 1px solid var(--m-split);
}

@container mock (min-width: 40rem) {
  .mock-rail {
    display: flex;
  }

  .mock-window.is-rail > .mock-rail {
    flex-basis: 14em;
    border-right: 1px solid var(--m-split);
    border-bottom: 0;
  }
}

/* The collapsed rail, between 40rem and 60rem of drawing: the lights and
   the mark, no words */
@container mock (min-width: 40rem) and (max-width: 59.999rem) {
  .mock-window:not(.is-rail) > .mock-rail {
    flex-basis: 3.2em;
  }

  .mock-window:not(.is-rail) .mock-rail-name,
  .mock-window:not(.is-rail) .mock-rail-sub,
  .mock-window:not(.is-rail) .mock-group,
  .mock-window:not(.is-rail) .mock-brand-name,
  .mock-window:not(.is-rail) .mock-rail-foot,
  .mock-window:not(.is-rail) .mock-rail-empty {
    display: none;
  }

  .mock-window:not(.is-rail) .mock-rail-item {
    grid-template-columns: auto;
    justify-content: center;
    padding-inline: 0;
  }

  .mock-window:not(.is-rail) .mock-brand {
    justify-content: center;
    padding-inline: 0;
  }
}

/* The rail's top: the app's name. The app also prints its version here;
   the site never shows a version, so the drawing leaves it out. The mark
   is the site's own stand-in for the app's icon. */
.mock-brand {
  display: flex;
  align-items: center;
  gap: 0.55em;
  min-height: 2.9em;
  padding: 0.6em 0.8em;
  border-bottom: 1px solid var(--m-split);
  font-weight: 600;
  letter-spacing: 0.02em;
}

.mock-rail-list {
  display: grid;
  align-content: start;
  gap: 0.15em;
  padding: 0.5em 0;
  flex: 1 1 auto;
}

/* The heading over each agent's profiles, the agent's own label */
.mock-group {
  padding: 0.6em 0.8em 0.25em;
  color: var(--m-body);
  font-family: var(--mono);
  font-size: 0.94em;
  font-weight: 600;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}

.mock-group .mock-warn {
  margin-left: 0.5em;
  color: var(--m-red);
  font-weight: 400;
  text-transform: none;
}

/* One profile in the rail: its light, its name, and under the name its
   account label, or its project folder when it has no label */
.mock-rail-item {
  display: grid;
  grid-template-columns: auto minmax(0, 1fr);
  align-items: center;
  gap: 0.1em 0.6em;
  margin: 0 0.35em;
  padding: 0.4em 0.7em;
  border-radius: 6px;
}

.mock-rail-item.is-sel {
  background: var(--m-select);
}

.mock-rail-name {
  min-width: 0;
  overflow: hidden;
  font-weight: 600;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.mock-rail-sub {
  grid-column: 2;
  min-width: 0;
  overflow: hidden;
  color: var(--m-quiet);
  font-size: 0.94em;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* The app sets "· restricted" in its amber. On this site amber is kept
   for an agent that waits and for Drift, so the drawing sets it in the
   quiet ink and lets the words carry it. */
.mock-rail-lock {
  margin-left: 0.4ch;
  color: var(--m-body);
}

/* The small green dot after a signed-in profile's name */
.mock-auth {
  display: inline-block;
  width: 0.4em;
  height: 0.4em;
  margin-left: 0.45em;
  border-radius: 50%;
  background: var(--m-ok);
  vertical-align: 0.15em;
}

.mock-rail-foot {
  display: flex;
  padding: 0.6em 0.7em 0.7em;
  border-top: 1px solid var(--m-split);
}

.mock-rail-foot .mock-btn {
  flex: 1 1 auto;
  justify-content: center;
}

.mock-rail-empty {
  display: grid;
  gap: 0.6em;
  padding: 0.9em 0.8em;
  color: var(--m-quiet);
}

/* The rail light. Grey when the profile has no pane open; the profile's
   colour while a pane runs; amber while it waits for you; green when a
   turn has finished. The app's light glows and pulses; the drawing keeps
   it flat and still. */
.mock-led {
  display: inline-block;
  flex: none;
  width: 0.5em;
  height: 0.5em;
  border-radius: 50%;
  background: var(--m-faint);
}

.mock-led.is-on,
.mock-led.is-working {
  background: var(--m-accent, var(--m-body));
}

.mock-led.is-approval {
  background: var(--m-amber);
}

.mock-led.is-done {
  background: var(--m-ok);
}

/* Profile colours: a class on the pane, the rail item or a swatch */
.mock-p1 { --m-accent: var(--m-p1); }
.mock-p2 { --m-accent: var(--m-p2); }
.mock-p3 { --m-accent: var(--m-p3); }
.mock-p4 { --m-accent: var(--m-p4); }

/* The stage: the top bar over the panes */
.mock-stage {
  display: flex;
  flex: 1 1 24rem;
  flex-direction: column;
  min-width: 0;
  background: var(--m-term);
}

.mock-window.is-rail > .mock-stage {
  flex-basis: 100%;
}

@container mock (min-width: 40rem) {
  .mock-window.is-rail > .mock-stage {
    flex-basis: 24rem;
  }
}

/* The top bar, left to right as the app has it: how many panes are open,
   Show all while one pane fills the window, the three layout buttons, the
   Broadcast box (two panes or more), usage, panic, Close all, and the
   window's own buttons. It wraps on a narrow drawing; mock-opt marks the
   parts a narrow drawing can leave out. */
.mock-topbar {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.35em 0.6em;
  min-height: 2.9em;
  padding: 0.3em 0 0.3em 0.8em;
  border-bottom: 1px solid var(--m-split);
  background: var(--m-chrome);
  color: var(--m-quiet);
}

.mock-count {
  color: var(--m-quiet);
}

.mock-layout-label {
  color: var(--m-faint);
}

/* A layout button: the app's glyph in a small frame; the chosen layout
   is filled */
.mock-layout {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 2em;
  height: 1.8em;
  border: 1px solid transparent;
  border-radius: 4px;
  color: var(--m-quiet);
}

.mock-layout.is-sel {
  border-color: var(--m-field-edge);
  background: var(--m-select);
  color: var(--m-ink);
}

.mock-broadcast {
  display: none;
  width: 12em;
  padding: 0.15em 0.5em;
  border: 1px solid var(--m-field-edge);
  border-radius: 4px;
  background: var(--m-field);
  color: var(--m-faint);
  font-size: 0.94em;
  white-space: nowrap;
}

.mock-panic {
  display: inline-flex;
  align-items: center;
  gap: 0.35em;
  padding: 0.1em 0.5em;
  border: 1px solid var(--m-red);
  border-radius: 4px;
  color: var(--m-red);
}

.mock-panic.is-pressed {
  background: var(--m-select);
}

.mock-winctl {
  display: flex;
  align-self: stretch;
  margin-left: 0.2em;
}

.mock-winctl > .mock-ico {
  width: 2.6em;
  height: auto;
  min-height: 2.3em;
  color: var(--m-quiet);
}

/* On a narrow drawing the window's own three buttons are left out too, so
   they never wrap onto a row of their own, and the bar's last part stands
   clear of the drawing's edge */
@container mock (max-width: 39.999rem) {
  .mock-opt,
  .mock-layout-label,
  .mock-winctl {
    display: none !important;
  }

  .mock-topbar {
    padding-right: 0.8em;
  }
}

@container mock (min-width: 48rem) {
  .mock-broadcast {
    display: inline-block;
  }
}

/* The panes. On a narrow drawing they stack, as rows; two panes stand
   side by side as columns from 40rem, three or more from 50rem, where each
   column is still wide enough for a pane's name and agent on one line
   (below that, three columns of about 230px wrapped every header onto five
   lines); the grid is two by two from 32rem, and with three panes the last
   one spans the row, as the app's grid does. While one pane fills the
   window (is-filled) the others are hidden, not closed, as in the app. The
   1px gap over the splitter colour draws the splitters. A scene that
   changes the layout sets --m-panes-h, so the drawing keeps its height
   through the change. */
.mock-panes {
  display: flex;
  flex: 1 1 auto;
  flex-direction: column;
  gap: 1px;
  height: var(--m-panes-h, auto);
  min-height: 0;
  background: var(--m-split);
}

/* Side by side, the columns share the width evenly, whatever each holds */
@container mock (min-width: 40rem) {
  .mock-panes:not(.is-rows):not(.is-grid):not(:has(> .mock-pane:nth-child(3))) {
    flex-direction: row;
  }

  .mock-panes:not(.is-rows):not(.is-grid):not(:has(> .mock-pane:nth-child(3))) > .mock-pane {
    flex-basis: 0;
  }
}

@container mock (min-width: 50rem) {
  .mock-panes:not(.is-rows):not(.is-grid) {
    flex-direction: row;
  }

  .mock-panes:not(.is-rows):not(.is-grid) > .mock-pane {
    flex-basis: 0;
  }
}

@container mock (min-width: 32rem) {
  .mock-panes.is-grid {
    display: grid;
    grid-auto-rows: minmax(0, 1fr);
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  .mock-panes.is-grid > .mock-pane:last-child:nth-child(odd) {
    grid-column: span 2;
  }
}

.mock-panes.is-filled > .mock-pane:not(.is-shown) {
  display: none;
}

.mock-panes.is-filled.is-grid > .mock-pane.is-shown {
  grid-column: 1 / -1;
  grid-row: 1 / -1;
}

/* The stage before any pane is open, in the app's words */
.mock-empty {
  display: grid;
  flex: 1 1 auto;
  align-content: center;
  justify-items: center;
  gap: 0.3em;
  min-height: 9em;
  padding: 1.5em 1em;
  color: var(--m-body);
  text-align: center;
}

.mock-empty .mock-dim {
  color: var(--m-quiet);
}

/* ------------------------------------------------------------- the pane */

/* One pane: its header, its terminal, and the HUD strip under it. A pane
   takes its profile's colour from mock-p1 to mock-p4. is-lit is the
   app's attention ring while the agent waits for you; is-finished its
   green ring after a turn. The app's ring pulses; the drawing holds it. */
.mock-pane {
  display: flex;
  flex: 1 1 auto;
  flex-direction: column;
  min-width: 0;
  min-height: 0;
  overflow: hidden;
  background: var(--m-term);
}

.mock-pane.is-lit {
  outline: 2px solid var(--m-amber);
  outline-offset: -2px;
}

.mock-pane.is-finished {
  outline: 2px solid var(--m-ok);
  outline-offset: -2px;
}

/* A pane drawn on its own, as a detail */
.mock-pane:not(.mock-panes > .mock-pane) {
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
}

/* The header. Left: the colour mark, the profile's name in its colour,
   the agent's label, then while the agent works or waits its state, the
   approve and deny buttons, and the HUD's figures. Right: the pane's own
   buttons, the Isolation badge among them. The underline in the
   profile's colour is the app's. */
.mock-pane-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.35em 0.6em;
  padding: 0.5em 0.7em;
  border-bottom: 2px solid var(--m-accent, var(--m-split));
  background: var(--m-chrome);
  color: var(--m-quiet);
}

.mock-accent {
  flex: none;
  width: 0;
  height: 1em;
  border-left: 3px solid var(--m-accent, var(--m-body));
  border-radius: 2px;
}

.mock-name {
  min-width: 0;
  overflow: hidden;
  color: var(--m-accent, var(--m-ink));
  font-family: var(--mono);
  font-weight: 600;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* The small framed pieces are inline blocks, so a scene can lift them
   into place (a transform does not move a plain inline box) */
.mock-tag,
.mock-chip,
.mock-hbtn,
.mock-hchip,
.mock-hval,
.mock-git,
.mock-flag,
.mock-hint,
.mock-live,
.mock-notice-tag {
  display: inline-block;
}

/* The agent's label, in a frame, in capitals as the app sets it */
.mock-tag {
  padding: 0 0.4em;
  border: 1px solid var(--m-split);
  border-radius: 3px;
  color: var(--m-quiet);
  font-family: var(--mono);
  font-size: 0.94em;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  white-space: nowrap;
}

/* The agent's state while it has one: working, waiting (for an approval),
   done, or waiting for you (its turn is over) */
.mock-chip {
  padding: 0 0.4em;
  border: 1px solid var(--m-split);
  border-radius: 3px;
  color: var(--m-body);
  font-family: var(--mono);
  font-size: 0.94em;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  white-space: nowrap;
}

.mock-chip.is-waiting {
  border-color: var(--m-amber);
  color: var(--m-amber);
}

.mock-chip.is-done {
  border-color: var(--m-ok);
  color: var(--m-ok);
}

/* approve and deny, in the header while an agent waits */
.mock-hbtn {
  padding: 0 0.45em;
  border: 1px solid currentColor;
  border-radius: 3px;
  font-family: var(--mono);
  font-size: 0.94em;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  white-space: nowrap;
}

.mock-hbtn.is-ok {
  color: var(--m-ok);
}

.mock-hbtn.is-no {
  color: var(--m-red);
}

.mock-hbtn.is-pressed {
  background: var(--m-select);
  transform: translateY(1px);
}

/* The header's copy of the HUD: the model in a frame, then the figures */
.mock-hchip {
  padding: 0 0.4em;
  border: 1px solid var(--m-split);
  border-radius: 3px;
  color: var(--m-accent, var(--m-ink));
  font-family: var(--mono);
  font-size: 0.94em;
  white-space: nowrap;
}

.mock-hval {
  color: var(--m-quiet);
  font-family: var(--mono);
  font-size: 0.94em;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.mock-hval.is-caps {
  letter-spacing: 0.04em;
  text-transform: uppercase;
}

.mock-hctx {
  display: inline-flex;
  align-items: center;
  gap: 0.4em;
  color: var(--m-quiet);
  font-family: var(--mono);
  font-size: 0.94em;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

/* A gauge. Set its share with style="--pct: 41". In the header it fills
   in the profile's colour; in the HUD strip (is-strip) in green, as the
   app's strip does below 65 percent. Above 65 percent the app turns the
   gauge amber and above 85 red, so the drawings keep their examples
   under 65. */
.mock-bar {
  position: relative;
  display: inline-block;
  flex: none;
  width: 4em;
  height: 0.4em;
  overflow: hidden;
  border: 1px solid var(--m-split);
  border-radius: 3px;
  background: var(--m-field);
  vertical-align: 0.1em;
}

.mock-bar::before {
  content: "";
  position: absolute;
  top: 0;
  bottom: 0;
  left: 0;
  width: calc(var(--pct, 0) * 1%);
  background: var(--m-accent, var(--m-body));
}

.mock-bar.is-strip::before {
  background: var(--m-ok);
}

/* The pane's own buttons, pushed to the header's end */
.mock-acts {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.3em 0.75em;
  margin-left: auto;
  color: var(--m-quiet);
}

.mock-act {
  color: var(--m-quiet);
  white-space: nowrap;
}

/* In a pane narrower than 22rem the header's copy of the HUD figures is
   left out, as mock-opt leaves parts of a narrow top bar out: the strip
   under the terminal still shows every figure, and the header keeps the
   name, the agent, the model and its buttons on two or three lines
   instead of five. */
@container mock-pane (max-width: 21.999rem) {
  .mock-pane-head > .mock-hval,
  .mock-pane-head > .mock-hctx {
    display: none;
  }
}

/* The git chip: the branch of the profile's project folder. The app marks
   uncommitted changes with an amber dot; the drawings show a clean branch. */
.mock-git {
  padding: 0 0.4em;
  border: 1px solid var(--m-split);
  border-radius: 3px;
  color: var(--m-quiet);
  font-family: var(--mono);
  font-size: 0.94em;
  white-space: nowrap;
}

/* The Isolation badge: the word Isolation with a dot. Green Isolated,
   amber Drift, red Breach, grey Unchecked; on Drift and Breach the word
   takes the colour too, as in the app. The same dot stands alone in the
   report and in Quick settings. */
.mock-badge {
  display: inline-flex;
  align-items: center;
  gap: 0.4em;
  color: var(--m-quiet);
  white-space: nowrap;
}

.mock-dot {
  display: inline-block;
  flex: none;
  width: 0.5em;
  height: 0.5em;
  border-radius: 50%;
  background: var(--m-faint);
}

.mock-badge.is-drift { color: var(--m-amber); }
.mock-badge.is-breach { color: var(--m-red); }

.mock-dot.is-isolated,
.is-isolated > .mock-dot { background: var(--m-ok); }

.mock-dot.is-drift,
.is-drift > .mock-dot { background: var(--m-amber); }

.mock-dot.is-breach,
.is-breach > .mock-dot { background: var(--m-red); }

.mock-dot.is-unchecked,
.is-unchecked > .mock-dot { background: var(--m-faint); }

/* --------------------------------------------------------- the HUD strip */

/* The strip under a pane's terminal: a line of figures, each with its
   label as the app writes it (Model:, Cost:, Up:, Total:, Weekly:,
   Context:), the separators drawn between them. The app colours each
   figure its own way; the drawing keeps one ink. A figure the agent does
   not report shows n/a in the muted colour (is-na). In a terminal
   (is-term) the same figures are the agent's own status line. */
.mock-hud {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.2em 0.6em;
  padding: 0.45em 0.7em;
  border-top: 1px solid var(--m-split);
  background: var(--m-chrome);
  color: var(--m-ink);
  font-family: var(--mono);
  font-size: 0.94em;
  font-variant-numeric: tabular-nums;
}

.mock-hud.is-term {
  padding: 0.35em 0 0;
  border-top: 0;
  background: transparent;
}

.mock-seg {
  display: inline-flex;
  align-items: center;
  gap: 0.5ch;
  white-space: nowrap;
}

.mock-seg + .mock-seg::before {
  content: "\00B7";
  margin-right: 0.6em;
  color: var(--m-faint);
}

/* The state word and the profile's name sit together, as in the app */
.mock-seg.is-state + .mock-seg::before {
  content: none;
}

.mock-seg.is-state {
  color: var(--m-body);
}

.mock-seg.is-state.is-waiting {
  color: var(--m-amber);
}

.mock-seg.is-state.is-done {
  color: var(--m-ok);
}

.mock-k {
  color: var(--m-faint);
}

.mock-seg.is-na .mock-v {
  color: var(--m-faint);
}

/* ---------------------------------------------------------- the terminal */

/* The terminal body: example lines of an agent at work, in monospace,
   cut with an ellipsis where a narrow pane cannot hold them. These are
   the agent's own words, not MaeVae's; the drawings make them up and keep
   them harmless. */
.mock-term {
  display: flex;
  flex: 1 1 auto;
  flex-direction: column;
  gap: 0.3em;
  min-height: 0;
  overflow: hidden;
  padding: 0.8em 0.7em 0.9em;
  background: var(--m-term);
  color: var(--m-quiet);
  font-family: var(--mono);
}

.mock-line {
  display: block;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.mock-line.is-wrap {
  white-space: normal;
}

.mock-line.is-now {
  color: var(--m-ink);
}

/* A command typed at the prompt, behind the drawn chevron */
.mock-line.is-cmd {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.4em 0.7em;
  color: var(--m-ink);
}

.mock-line.is-cmd::before,
.mock-prompt::before {
  content: "";
  flex: none;
  width: 0.45em;
  height: 0.45em;
  margin-right: 0.1em;
  border-top: 2px solid var(--m-quiet);
  border-right: 2px solid var(--m-quiet);
  transform: rotate(45deg);
}

/* The prompt waiting at the foot of the terminal */
.mock-prompt {
  display: flex;
  align-items: center;
  gap: 0.6em;
  margin-top: auto;
  padding-top: 0.4em;
}

/* The caret is still. A scene may let it blink a few times (is-blink);
   it never blinks without end. */
.mock-caret {
  display: inline-block;
  width: 0.6em;
  height: 1.15em;
  background: var(--m-ink);
}

/* The drawing's own mark on a refused command. The agent prints its own
   refusal; the mark is the page's note on it, not a MaeVae label, and it
   is drawn in the page's sans, not the terminal's type. */
.mock-flag {
  padding: 0 0.45em;
  border: 1px solid var(--m-quiet);
  border-radius: 3px;
  color: var(--m-ink);
  font-family: var(--sans);
  font-weight: 600;
  white-space: nowrap;
}

/* An agent's own question, in the frame its terminal draws. In a lit
   pane the frame takes the attention colour, as part of the lit pane. */
.mock-ask {
  display: grid;
  gap: 0.2em;
  margin-top: auto;
  padding: 0.5em 0.7em;
  border: 1px solid var(--m-faint);
  border-radius: 3px;
}

.mock-pane.is-lit .mock-ask {
  border-color: var(--m-amber);
}

.mock-ask-opt {
  display: flex;
  gap: 0.6em;
  color: var(--m-quiet);
}

.mock-ask-opt::before {
  content: "";
  flex: none;
  width: 0.4em;
}

.mock-ask-opt.is-sel {
  color: var(--m-ink);
}

.mock-ask-opt.is-sel::before {
  height: 0.4em;
  margin-top: 0.5em;
  border-top: 2px solid currentColor;
  border-right: 2px solid currentColor;
  transform: rotate(45deg);
}

/* ------------------------------------------------- panels and dialogs */

/* The app's panels share one shape: a bar with the title, a body, and a
   foot with the buttons. The usage dashboard, the backup, the new-profile
   steps and the pane's Isolation report all use it. */
.mock-dialog {
  overflow: hidden;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-pane);
}

.mock-dialog-head,
.mock-report-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.3em 0.6em;
  padding: 0.55em 0.8em;
  border-bottom: 1px solid var(--m-split);
  background: var(--m-chrome);
}

.mock-dialog-head > strong,
.mock-report-head > strong {
  color: var(--m-ink);
  font-weight: 600;
}

.mock-dialog-head > .mock-ico-close,
.mock-report-head > .mock-ico-close {
  margin-left: auto;
  color: var(--m-quiet);
}

.mock-dialog-body {
  display: grid;
  align-content: start;
  gap: 0.7em;
  padding: 0.8em;
}

.mock-dialog-foot {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.5em;
  padding: 0.6em 0.8em;
  border-top: 1px solid var(--m-split);
}

/* The step count of the new-profile steps, in capitals as the app sets it */
.mock-wiz-step {
  color: var(--m-quiet);
  font-family: var(--mono);
  font-size: 0.94em;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}

/* Two tabs, as in the backup panel: Back up, Restore */
.mock-tabs {
  display: flex;
  gap: 0.4em;
  padding: 0.5em 0.8em 0;
}

.mock-tab {
  padding: 0.2em 0.7em;
  border: 1px solid transparent;
  border-radius: 4px;
  color: var(--m-quiet);
}

.mock-tab.is-sel {
  border-color: var(--m-field-edge);
  background: var(--m-select);
  color: var(--m-ink);
}

/* ------------------------------------------------------ fields, buttons */

/* The small capital title the app sets over a form or a panel */
.mock-form-title,
.mock-qlabel {
  color: var(--m-body);
  font-family: var(--mono);
  font-size: 0.94em;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
}

/* A field: its label as the app writes it, then the control */
/* A field never sizes itself to the full length of its value: the one
   column may shrink, and a long value ends in an ellipsis inside its box
   rather than pushing the field past the drawing's edge */
.mock-field {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: 0.25em;
  min-width: 0;
  color: var(--m-quiet);
}

.mock-field-head {
  color: var(--m-ink);
  font-weight: 600;
}

/* A drawn text box. It holds its value; is-placeholder for the app's grey
   hint text in an empty box. */
.mock-input,
.mock-select {
  display: block;
  min-height: 2em;
  overflow: hidden;
  padding: 0.3em 0.55em;
  border: 1px solid var(--m-field-edge);
  border-radius: 4px;
  background: var(--m-field);
  color: var(--m-ink);
  text-overflow: ellipsis;
  white-space: nowrap;
}

.mock-input.is-placeholder,
.mock-select.is-placeholder {
  color: var(--m-faint);
}

/* A drawn drop-down: a text box with the chevron at its end */
.mock-select {
  position: relative;
  padding-right: 2em;
}

.mock-select::after {
  content: "";
  position: absolute;
  top: 50%;
  right: 0.75em;
  width: 0.4em;
  height: 0.4em;
  border-right: 1.5px solid var(--m-quiet);
  border-bottom: 1.5px solid var(--m-quiet);
  transform: translateY(-70%) rotate(45deg);
}

/* A drawn check box, and a drawn radio button; is-on when ticked */
.mock-check,
.mock-radio {
  display: flex;
  align-items: flex-start;
  gap: 0.55em;
  color: var(--m-body);
}

.mock-check::before,
.mock-radio::before {
  content: "";
  flex: none;
  width: 0.95em;
  height: 0.95em;
  margin-top: 0.22em;
  border: 1.5px solid var(--m-field-edge);
  border-radius: 3px;
  background: var(--m-field);
}

.mock-radio::before {
  border-radius: 50%;
}

/* Ticked: an ink square inside the box, with a ring of the field's ground
   between them. The ink is clipped to the content box, so no shadow is
   needed to draw the ring. */
.mock-check.is-on::before,
.mock-radio.is-on::before {
  padding: 0.16em;
  border-color: var(--m-ink);
  background: var(--m-ink);
  background-clip: content-box;
}

/* The colour row of the profile editor. Each swatch takes a profile class
   (mock-p1 to mock-p4) or style="--m-accent: #hex"; is-sel is the chosen one. */
.mock-swatches {
  display: flex;
  flex-wrap: wrap;
  gap: 0.35em;
}

.mock-swatch {
  display: inline-block;
  width: 1.3em;
  height: 1.3em;
  border: 1px solid var(--m-split);
  border-radius: 4px;
  background: var(--m-accent, var(--m-faint));
}

.mock-swatch.is-sel {
  outline: 2px solid var(--m-ink);
  outline-offset: 2px;
}

/* The app's grey help text under a field */
.mock-note {
  color: var(--m-quiet);
  font-size: 0.94em;
  line-height: 1.5;
}

.mock-row-btns {
  display: flex;
  flex-wrap: wrap;
  gap: 0.45em;
}

/* A drawn button. Plain: a framed button. is-primary: the app's main
   action (Create, Save changes, Create & open, Back up now), drawn as a
   light field. is-ghost: a frameless one. is-ok and is-no: the green and
   red of approve and deny. is-on: a switch button that is on.
   is-pressed: the moment a scene presses it. is-disabled: greyed. */
.mock-btn {
  display: inline-flex;
  align-items: center;
  gap: 0.4em;
  padding: 0.2em 0.7em;
  border: 1px solid var(--m-field-edge);
  border-radius: 4px;
  color: var(--m-ink);
  font-size: 0.94em;
  line-height: 1.5;
  white-space: nowrap;
}

.mock-btn.is-primary {
  border-color: var(--m-ink);
  background: var(--m-ink);
  color: var(--night);
  font-weight: 600;
}

.mock-btn.is-ghost {
  border-color: transparent;
  color: var(--m-quiet);
}

.mock-btn.is-ok {
  border-color: var(--m-ok);
  color: var(--m-ok);
}

.mock-btn.is-no {
  border-color: var(--m-red);
  color: var(--m-red);
}

.mock-btn.is-on {
  border-color: var(--m-ok);
}

.mock-btn.is-disabled {
  color: var(--m-faint);
}

.mock-btn.is-pressed {
  background: var(--m-select);
  transform: translateY(1px);
}

.mock-btn.is-primary.is-pressed {
  border-color: var(--m-body);
  background: var(--m-body);
}

/* A part of a panel under a hairline, with its field head */
.mock-section {
  display: grid;
  gap: 0.55em;
  padding-top: 0.7em;
  border-top: 1px solid var(--m-split);
}

/* ---------------------------------------------------- the profile editor */

/* The profile editor, drawn on its own. In the app it opens in the rail,
   under the profiles. Its fields appear in the app's order.
   The new-profile steps are the dialog shape above with mock-wiz-step. */
.mock-editor {
  display: grid;
  align-content: start;
  gap: 0.75em;
  padding: 0.9em;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-rail);
}

/* ------------------------------------------------------ Quick settings */

/* Quick settings, as the rail shows it: the title, the two Add buttons,
   then its sections, each under its small capital label */
.mock-quick {
  display: grid;
  align-content: start;
  gap: 0.8em;
  padding: 0.9em;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-rail);
}

.mock-qsection {
  display: grid;
  gap: 0.5em;
  padding-top: 0.7em;
  border-top: 1px solid var(--m-split);
}

/* --------------------------------------------------- the Isolation report */

/* The report: the badge and when it was checked, then the four faces,
   each with its worst status, its rows, the fix on offer, the notes Seal
   leaves, and the four buttons. It stands in a pane's place (the pane's
   report panel) or on its own. */
.mock-report {
  display: grid;
  align-content: start;
  gap: 0.6em;
  padding: 0.8em;
  background: var(--m-pane);
}

.mock-pane > .mock-report {
  flex: 1 1 auto;
  min-height: 0;
  overflow: hidden;
}

.mock-report:not(.mock-pane > .mock-report):not(.mock-section .mock-report) {
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
}

.mock-report-sum {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.2em 0.5em;
  color: var(--m-quiet);
}

.mock-report-sum > strong {
  color: var(--m-ink);
  font-weight: 600;
}

.mock-face {
  display: grid;
  gap: 0.35em;
  padding-top: 0.45em;
  border-top: 1px dashed var(--m-split);
}

.mock-face-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.2em 0.6em;
  color: var(--m-ink);
  font-weight: 600;
}

.mock-face-head .mock-dim {
  font-weight: 400;
}

/* One rule: its status, then the rule's name and the reason, and under
   them the fix Seal would apply */
.mock-row {
  display: grid;
  grid-template-columns: 4.6em minmax(0, 1fr);
  align-items: start;
  gap: 0.15em 0.6em;
  color: var(--m-quiet);
}

.mock-rule {
  margin-right: 0.6ch;
  color: var(--m-ink);
  font-family: var(--mono);
}

.mock-fix {
  display: block;
  margin-top: 0.15em;
  color: var(--m-body);
  font-size: 0.94em;
}

/* PASS, WARN, FAIL, INFO, in a frame of their own colour. The app draws
   INFO in its accent; the drawing keeps it in the plain ink. */
.mock-status {
  justify-self: start;
  padding: 0 0.3em;
  border: 1px solid currentColor;
  border-radius: 3px;
  color: var(--m-body);
  font-family: var(--mono);
  font-size: 0.94em;
  letter-spacing: 0.04em;
  line-height: 1.4;
}

.mock-status.is-pass { color: var(--m-ok); }
.mock-status.is-warn { color: var(--m-amber); }
.mock-status.is-fail { color: var(--m-red); }
.mock-status.is-info { color: var(--m-body); }

/* What Seal wrote, listed after the faces; green in the app */
.mock-notes {
  display: grid;
  gap: 0.2em;
  margin: 0;
  padding-left: 1.1em;
  color: var(--m-ok);
  font-size: 0.94em;
}

.mock-notes > li::marker {
  color: var(--m-faint);
}

.mock-report-acts {
  display: flex;
  flex-wrap: wrap;
  gap: 0.45em;
}

/* A row picked out by a scene, so the eye finds it. Not amber: the
   status beside it already says what kind of row it is. */
.mock-row.is-marked,
.mock-face.is-marked {
  outline: 1px solid var(--m-field-edge);
  outline-offset: 0.25em;
  border-radius: 2px;
}

/* ------------------------------------------------- the command palette */

/* The palette Ctrl+K opens: the search box and the list of actions, each
   with its key hint; is-sel is the highlighted one */
.mock-palette {
  overflow: hidden;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-pane);
}

.mock-palette-input {
  display: block;
  padding: 0.6em 0.8em;
  border-bottom: 1px solid var(--m-split);
  color: var(--m-ink);
}

.mock-palette-input.is-placeholder {
  color: var(--m-faint);
}

/* The list's one column is never wider than the palette. Left to size
   itself, the column took the full width of its longest row, so on a
   narrow drawing every row ran past the palette's edge and was cut off;
   held to the palette, a long action ends in an ellipsis, as the app's
   own list does, and the key hint beside it keeps its place. */
.mock-palette-list {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  padding: 0.3em 0;
}

.mock-palette-item {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1em;
  padding: 0.4em 0.8em;
  color: var(--m-body);
}

.mock-palette-item > :first-child {
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.mock-palette-item.is-sel {
  background: var(--m-select);
  color: var(--m-ink);
}

.mock-hint {
  flex: none;
  padding: 0 0.35em;
  border: 1px solid var(--m-split);
  border-radius: 3px;
  color: var(--m-quiet);
  font-family: var(--mono);
  font-size: 0.94em;
}

/* ---------------------------------------------- the dashboard's table */

/* A table drawn as rows of a grid. Set the columns on the table:
   style="--m-cols: 1.6fr 1fr 0.8fr 0.8fr; --m-cols-narrow: 1.6fr 1fr";
   cells marked mock-col-opt are left out on a narrow drawing, and the
   narrow template drops their columns. */
.mock-table {
  display: grid;
  font-size: 0.94em;
  font-variant-numeric: tabular-nums;
}

.mock-tr {
  display: grid;
  grid-template-columns: var(--m-cols-narrow, var(--m-cols, 1fr));
  align-items: baseline;
  gap: 0 0.8em;
  padding: 0.35em 0;
  border-bottom: 1px solid var(--m-split);
}

.mock-tr.is-head {
  color: var(--m-faint);
}

.mock-tr.is-foot {
  border-bottom: 0;
  color: var(--m-body);
}

.mock-td {
  display: block;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* The dashboard's dot in the profile's own colour, before its name */
.mock-pdot {
  display: inline-block;
  width: 0.5em;
  height: 0.5em;
  margin-right: 0.45em;
  border-radius: 50%;
  background: var(--m-accent, var(--m-faint));
}

.mock-col-opt {
  display: none;
}

@container mock (min-width: 40rem) {
  .mock-tr {
    grid-template-columns: var(--m-cols, 1fr);
  }

  .mock-col-opt {
    display: block;
  }
}

/* The "live" mark after a profile with a pane open */
.mock-live {
  margin-left: 0.45em;
  padding: 0 0.3em;
  border: 1px solid var(--m-ok);
  border-radius: 3px;
  color: var(--m-ok);
  font-size: 0.94em;
}

/* ------------------------------------------------------------- a notice */

/* The notice at the window's lower right after an agent update: its tag
   (Done, Warning, Error, Working) and its headline */
.mock-notice {
  display: grid;
  gap: 0.3em;
  padding: 0.6em 0.8em;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-chrome);
}

.mock-notice-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.3em 0.6em;
}

.mock-notice-tag {
  padding: 0 0.35em;
  border: 1px solid var(--m-field-edge);
  border-radius: 3px;
  color: var(--m-body);
  font-size: 0.94em;
  font-weight: 600;
}

.mock-notice.is-over {
  position: absolute;
  right: 0.8em;
  bottom: 0.8em;
  z-index: 2;
  width: min(22rem, 100% - 1.6em);
}

/* ------------------------------------- a notification, the desk, the tray */

/* A Windows notification from MaeVae. Windows draws the real one; this is
   the page's drawing of it, in the attention colour, because it says an
   agent is waiting for you. is-over places it over the window's lower
   right, or over the taskbar in a desk. */
.mock-toast {
  display: grid;
  gap: 2px;
  width: min(21rem, 100%);
  padding: 0.85em 1em 0.95em;
  border-radius: var(--radius);
  background: var(--m-amber);
  color: var(--m-on-amber);
  line-height: 1.4;
}

.mock-toast.is-over {
  position: absolute;
  right: 0.8em;
  bottom: 0.8em;
  z-index: 3;
  width: min(21rem, 100% - 1.6em);
}

.mock-toast-app {
  display: inline-flex;
  align-items: center;
  gap: 0.5em;
  font-size: 0.94em;
  font-weight: 600;
}

.mock-toast-title {
  margin-top: 2px;
  font-size: 1.13em;
  font-weight: 600;
  line-height: 1.3;
}

/* The desk: a window over a taskbar, for the scenes that close the window
   to the tray. is-closed is the window hidden to the tray. */
.mock-desk {
  display: grid;
  gap: 1em;
  padding: 1em 1em 0;
  overflow: hidden;
  overflow: clip;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--night);
}

.mock-desk > .mock-window.is-closed {
  opacity: 0;
  transform: translateY(6px);
}

.mock-desk > .mock-toast.is-over {
  right: 1em;
  bottom: 4em;
}

.mock-taskbar {
  display: flex;
  align-items: center;
  justify-content: flex-end;
  height: 3em;
  margin: 0 -1em;
  padding: 0 1em;
  border-top: 1px solid var(--m-split);
  background: var(--m-raised);
}

.mock-tray {
  position: relative;
  display: inline-flex;
  align-items: center;
  gap: 1.1em;
  color: var(--m-quiet);
}

.mock-tray-chev {
  width: 0.5em;
  height: 0.5em;
  border-top: 2px solid currentColor;
  border-left: 2px solid currentColor;
  transform: translateY(2px) rotate(45deg);
}

.mock-tray-glyph {
  width: 0.9em;
  height: 0.8em;
  border: 2px solid currentColor;
  border-radius: 2px;
}

.mock-tray-glyph + .mock-tray-glyph {
  width: 0.85em;
  height: 0.85em;
  border-radius: 50%;
}

/* MaeVae's tray icon, drawn with the site's mark. is-badged is the amber
   dot the app sets on it while a pane waits for you. */
.mock-tray-icon {
  position: relative;
  display: inline-flex;
  color: var(--m-ink);
}

.mock-tray-icon.is-badged::after {
  content: "";
  position: absolute;
  top: -0.5em;
  right: -0.55em;
  width: 1.05em;
  height: 1.05em;
  border: 2px solid var(--m-raised);
  border-radius: 50%;
  background: var(--m-amber);
}

/* The tray's menu, over the icon: Show MaeVae, Panic stop, Quit */
.mock-tray-menu {
  position: absolute;
  right: 0;
  bottom: calc(100% + 0.9em);
  z-index: 3;
  display: grid;
  min-width: 11em;
  padding: 0.3em 0;
  border: 1px solid var(--m-edge);
  border-radius: var(--radius);
  background: var(--m-chrome);
  color: var(--m-ink);
}

.mock-tray-item {
  padding: 0.35em 0.9em;
  white-space: nowrap;
}

.mock-tray-item.is-sel {
  background: var(--m-select);
}

/* ------------------------------------------ a panel over the window */

/* The app opens New profile, the command palette and the usage dashboard
   as a panel over the whole window, on a backdrop that dims it. A large
   drawing shows them the same way: the window as it stands, the backdrop
   over it, and the panel at the app's own width, so the frame is full of
   the app and the panel is not stretched across it. The panel never grows
   past the window, so the window must be at least as tall as the panel:
   give its panes a height with --m-panes-h. */
.mock-modal {
  position: absolute;
  inset: 0;
  z-index: 4;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 1em;
  background: var(--m-scrim);
}

/* The palette opens near the top of the window, as in the app */
.mock-modal.is-top {
  align-items: flex-start;
  padding-top: 2.5em;
}

.mock-modal > * {
  max-height: 100%;
  overflow: hidden;
}

.mock-modal > .mock-dialog {
  width: min(var(--m-w-wizard), 100%);
}

.mock-modal > .mock-dialog.is-dash {
  width: min(var(--m-w-dash), 100%);
}

.mock-modal > .mock-palette {
  width: min(var(--m-w-palette), 100%);
}

/* The profile editor and Quick settings open inside the rail, under the
   profiles, as in the app; there they lose their own frame. The app never
   folds the rail while one of them is open, so such a window carries
   is-rail. */
.mock-rail > .mock-editor,
.mock-rail > .mock-quick {
  border: 0;
  border-top: 1px solid var(--m-split);
  border-radius: 0;
  background: transparent;
}

/* ------------------------------------------------- swaps for the scenes */

/* Two versions of one thing in the same place: the earlier one
   (mock-was) is shown only while a scene plays, the final one is the
   drawing at rest. Both keep their room in the box, so the drawing never
   changes size when one gives way to the other. */
.mock-swap {
  display: inline-grid;
}

.mock-swap.is-block {
  display: grid;
}

.mock-swap > * {
  grid-area: 1 / 1;
}

.mock-was {
  visibility: hidden;
}

/* ----------------------------------------------- scenes and their controls */

/* A scene is a figure that holds a drawing, its controls and its caption.
   The controls are shown only once the stepper has armed the scene: never
   without script, never under reduced motion, never in print. */
.mock-scene {
  margin: 0;
}

.mock-controls {
  display: none;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--s2) var(--s3);
  margin-top: var(--s3);
}

.mock-controls .btn[disabled] {
  opacity: 0.5;
  cursor: default;
}

/* The chapter marks of a long scene: plain underlined words, as links are
   on this site, so they cannot read as a signal; the chapter playing now
   has the thicker line. */
.mock-chapters {
  display: flex;
  flex-wrap: wrap;
  gap: 0 var(--s3);
  margin: 0;
  padding: 0;
  list-style: none;
}

.mock-chapter {
  min-height: 40px;
  padding: 0 var(--s1);
  border: 0;
  background: none;
  color: var(--quiet);
  font: inherit;
  font-size: var(--fs-small);
  text-decoration: underline;
  text-decoration-thickness: 1px;
  text-underline-offset: 0.25em;
  cursor: pointer;
}

.mock-chapter:hover {
  color: var(--ink);
}

.mock-chapter[aria-current="step"] {
  color: var(--ink);
  text-decoration-thickness: 2px;
}

.night .mock-chapter {
  color: var(--night-quiet);
}

.night .mock-chapter:hover,
.night .mock-chapter[aria-current="step"] {
  color: var(--night-ink);
}

/* One line under the drawing that says what happened */
.mock-caption {
  max-width: 62ch;
  margin-top: var(--s3);
  color: var(--quiet);
  font-size: var(--fs-meta);
  line-height: 1.55;
}

.night .mock-caption {
  color: var(--night-quiet);
}

/* The chapter marks of a scene stand on a hairline, in small monospace as
   the site's labels are. They keep their place in the markup, after Play
   and Stop, so the order on screen is the order a keyboard reaches them.
   The chapter playing now keeps the thicker underline. */
.mock-chapter {
  font-family: var(--mono);
  font-size: var(--fs-tag, 0.9375rem);
  letter-spacing: 0.04em;
}

.mock-controls:has(> .mock-chapters) {
  padding-top: var(--s3);
  border-top: 1px solid var(--line);
}

.night .mock-controls:has(> .mock-chapters) {
  border-top-color: var(--night-line);
}

.mock-controls > .mock-chapters {
  flex: 1 1 auto;
}

/* On a dark ground or a plate a drawing's top edge is one step lighter
   than its sides, so it reads as lit from above without a shadow */
:is(.night, .plate) :is(.mock-window, .mock-dialog, .mock-editor, .mock-quick,
    .mock-palette, .mock-desk, .mock-report, .mock-pane)[role="img"] {
  border-top-color: var(--night-edge-top);
}

/* ------------------------------------------------------------ the plate */

/* A plate gives a medium drawing in a light passage something to stand
   on: the night ground with the field's dots, faded at its edges, and no
   veil. It holds the drawing only; the scene's controls and caption stay
   on the light ground under it. It is the page's ground, not part of the
   app, so it claims nothing. At 1440px a plate in a band's wide column
   leaves its drawing 719px. */
.plate {
  --focus: var(--night-ink);
  --line-ink: var(--night-ink);
  --line-edge: var(--night-faint);
  --line-hover: var(--night-hover);
  --key-bg: var(--night-ink);
  --key-ink: var(--night);
  position: relative;
  isolation: isolate;
  padding: var(--plate-pad);
  border-radius: var(--radius);
  background: var(--night);
  color: var(--night-body);
}

.plate::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  border-radius: inherit;
  pointer-events: none;
  background-image: radial-gradient(circle, var(--field-dot) var(--field-dot-r), transparent calc(var(--field-dot-r) + 0.5px));
  background-position: center;
  background-size: var(--field-pitch) var(--field-pitch);
  -webkit-mask-image: linear-gradient(to bottom, transparent, #000 12px, #000 calc(100% - 12px), transparent);
  mask-image: linear-gradient(to bottom, transparent, #000 12px, #000 calc(100% - 12px), transparent);
}

@supports (mask-composite: intersect) {
  .plate::before {
    -webkit-mask-image:
      linear-gradient(to right, transparent, #000 12px, #000 calc(100% - 12px), transparent),
      linear-gradient(to bottom, transparent, #000 12px, #000 calc(100% - 12px), transparent);
    -webkit-mask-composite: source-in;
    mask-image:
      linear-gradient(to right, transparent, #000 12px, #000 calc(100% - 12px), transparent),
      linear-gradient(to bottom, transparent, #000 12px, #000 calc(100% - 12px), transparent);
    mask-composite: intersect;
  }
}

/* A drawing narrower than its plate, such as a panel at the app's own
   width, stands in the plate's middle */
.plate > [role="img"] {
  margin-inline: auto;
}

@media print {
  .plate::before {
    display: none;
  }
}

/* How a scene plays, where motion is allowed. The stepper arms the scene
   (is-armed), puts it in its starting state, adds the step names as it
   reaches them, and ends with is-done, which hands the drawing back to
   its markup. Every rule here needs an armed scene without is-done, so
   the finished frame is the markup unchanged.

   A part marked data-in waits unseen, holding its room, until its step,
   then rises 4px into place on the page's one tempo. A part marked
   data-out fades where it stands. A colour or a state switches in one
   step, the way the app's own states switch. Only opacity and transform
   move. is-jumping holds every transition while a scene resets or jumps
   to a chapter, so a replay starts clean. */
@media screen and (prefers-reduced-motion: no-preference) {
  [data-scene].is-armed .mock-controls {
    display: flex;
  }

  [data-scene].is-armed:not(.is-done) .mock-was {
    visibility: visible;
  }

  [data-scene].is-armed:not(.is-done) [data-in]:not(.is-in) {
    opacity: 0;
    transform: translateY(4px);
    transition: none;
  }

  [data-scene].is-armed:not(.is-done) [data-in].is-in {
    opacity: 1;
    transform: none;
    transition: opacity var(--m-beat) var(--m-arrive),
                transform var(--m-beat) var(--m-arrive);
  }

  [data-scene].is-armed:not(.is-done) [data-out].is-out {
    opacity: 0;
    transform: none;
    transition: opacity var(--m-half) var(--m-leave);
  }

  /* A part marked data-show takes no room until its step; the stepper
     marks it is-arriving when it appears during play, never on a jump */
  [data-scene].is-armed:not(.is-done) [data-show].is-arriving {
    animation: mock-arrive var(--m-beat) var(--m-arrive);
  }

  [data-scene].is-armed:not(.is-done) .mock-hide {
    opacity: 0 !important;
    transition: opacity var(--m-half) var(--m-leave);
  }

  /* The window closing to the tray, and coming back */
  [data-scene].is-armed:not(.is-done) .mock-desk > .mock-window {
    transition: opacity var(--m-beat) var(--m-leave),
                transform var(--m-beat) var(--m-leave);
  }

  [data-scene].is-armed:not(.is-done) .mock-caret.is-blink {
    animation: mock-blink 1.1s steps(1, end) 3;
  }

  [data-scene].is-jumping,
  [data-scene].is-jumping * {
    transition: none !important;
    animation: none !important;
  }
}

@keyframes mock-arrive {
  from {
    opacity: 0;
    transform: translateY(4px);
  }
}

@keyframes mock-blink {
  50% { opacity: 0; }
}

@media print {
  .mock-controls {
    display: none !important;
  }
}

/* Windows contrast themes replace backgrounds, which would erase the
   dots, the lights, the gauges, the caret, the splitters and the lit
   ring; real borders and system colours keep them. */
@media (forced-colors: active) {
  .mock-dot,
  .mock-pdot,
  .mock-led,
  .mock-auth,
  .mock-swatch {
    forced-color-adjust: none;
    border: 1px solid CanvasText;
  }

  .mock-bar::before {
    forced-color-adjust: none;
    background: Highlight;
  }

  .mock-caret {
    forced-color-adjust: none;
    background: CanvasText;
  }

  .mock-panes {
    gap: 0;
  }

  .mock-panes > .mock-pane {
    border: 1px solid CanvasText;
  }

  .mock-pane.is-lit,
  .mock-pane.is-finished {
    outline-color: Highlight;
  }

  .mock-toast {
    border: 2px solid CanvasText;
  }

  .mock-tray-icon.is-badged::after {
    forced-color-adjust: none;
    border-color: Canvas;
    background: Highlight;
  }

  .mock-check.is-on::before,
  .mock-radio.is-on::before {
    forced-color-adjust: none;
    background-color: CanvasText;
    background-clip: content-box;
  }

  /* The plate keeps its edge as a frame and drops its dots */
  .plate {
    border: 1px solid CanvasText;
  }

  .plate::before {
    display: none;
  }

  /* The backdrop of a panel over the window becomes a frame round the
     panel, so the panel still stands apart from the window behind it */
  .mock-modal > * {
    border: 2px solid CanvasText;
  }
}
