/* surface-sheets.css
   Scoped styling for the sheets surface, loaded after css/orco.css so it inherits
   the material defined there: the gold hairline, gold focus, Georgia on his
   names, and the one primary action. Direction and reasoning:
   docs/beta-run/UX-VISUAL-DIRECTION.md

   This file exists so that four surfaces can be worked on at once without
   four seats editing one 4,250 line stylesheet. Everything here is scoped to
   this surface's own classes. Nothing here redefines a token.

   =========================================================================
   THE IDEA THIS SURFACE IS BUILT ON: THE LEDGER LEAF
   =========================================================================

   A publication is a fact with a time on it, and the honest way to draw a
   fact with a time on it is a ledger line: a rule down the left margin, the
   claim set in the interface face, the address in a monospace because a URL
   is compared character by character, and the arithmetic underneath in the
   reader's own units. No badges doing the work of sentences.

   THE ONE VISUAL PROMISE, and it is the reason this surface can be trusted:

       A SOLID LEFT RULE MEANS ORCO KNOWS THIS.
       A DASHED LEFT RULE MEANS ORCO IS TELLING YOU WHAT IT LAST SAW.

   Two states get the dash and only two: offline, and a link Orco could not
   reach. That scarcity is what makes it read. It is the UX-STATE-MODEL's
   separation of `status` (what is known) from `remote` (what was checked),
   drawn rather than described, and it survives greyscale, colour blindness
   and a phone at arm's length.

   Every state carries three redundant signals, any one of which is enough to
   tell it from the others: a SHAPE (one glyph per state, drawn in
   js/orco-publish.js, no two alike in silhouette), a WORD (a small-caps
   eyebrow naming the state), and the RULE above. Colour is the fourth and
   least load-bearing, which is the right order.

   Gold appears three times on this surface and no more: the focus ring, the
   hairline under a raised sheet, and the primary action. Semantic colour is
   never decorative here; it appears only on a state.
   ========================================================================= */

/* =====================================================================
   1. THE SHEET ITSELF
   ===================================================================== */

.pubx-sheet .sheet-list {
  padding: 4px 18px 18px;
  display: block;
}

.pubx-sheet .sheet-head {
  /* The head carries the name of his talk, so it is set in the face his
     slides are set in. A title on the sheet and the same title on the slide
     should be one voice. */
  padding-bottom: 14px;
}
.pubx-sheet .sheet-head strong {
  font-family: var(--font-display);
  font-size: 19px;
  font-weight: 600;
  letter-spacing: -0.015em;
  line-height: 1.25;
}
.pubx-sheet .sheet-head span {
  font-size: 12.5px;
  color: var(--ink-3);
  max-width: 62ch;
}

/* The single gold hairline under the head: the rule that tells the eye where
   a place begins. One per sheet. */
.pubx-sheet .sheet-head::after {
  content: '';
  display: block;
  height: 1px;
  margin: 12px -18px -14px;
  background: linear-gradient(90deg, transparent, var(--hair-2) 12%, var(--hair-2) 88%, transparent);
  transition: background var(--t-surface) var(--ease);
}

.pubx-sheet .sheet-foot {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
}
.pubx-foot-gap { flex: 1 1 auto; }

/* =====================================================================
   2. THE EYEBROW. Small caps, wide tracking, the state's own colour.
   ===================================================================== */

.pubx-eyebrow {
  margin: 0 0 3px;
  font-size: 10px;
  font-weight: 700;
  letter-spacing: 0.09em;
  text-transform: uppercase;
  color: var(--ink-4);
  font-variant-numeric: tabular-nums;
}

/* =====================================================================
   3. THE GLYPH. 16px, stroked in currentColor, never filled.
   ===================================================================== */

.pubx-glyph {
  width: 16px;
  height: 16px;
  flex: none;
  fill: none;
  stroke: currentColor;
  stroke-width: 1.4;
  stroke-linecap: round;
  stroke-linejoin: round;
  vertical-align: -3px;
}

/* =====================================================================
   4. THE NOTICE: every failure state, and the two good ones.
   ===================================================================== */

.pubx-notice {
  display: flex;
  gap: 11px;
  align-items: flex-start;
  margin: 12px 0;
  padding: 12px 14px 12px 13px;
  border-radius: 10px;
  border: 1px solid var(--hair);
  border-left: 3px solid var(--ink-4);
  background: var(--panel);
  color: var(--ink-2);
}

/* THE PROMISE. Dashed left edge means "last known", never "now".
   DRAWN ON A PSEUDO-ELEMENT, not as a background-image on the box, and that
   is not a style preference. The first version painted the dash with
   `background-image` and every state class below then set a `background:`
   SHORTHAND, which resets background-image to none. The dash was invisible in
   the render and the two states that carry the whole promise looked like
   states with no rule at all. Caught by looking at the PNG, not by reading the
   file. A pseudo-element cannot be reset by a shorthand on its parent. */
.pubx-notice { position: relative; overflow: hidden; }
.pubx-notice.is-unsure {
  border-left-color: transparent;
  border-left-width: 0;
  padding-left: 16px;
}
.pubx-notice.is-unsure::before {
  content: '';
  position: absolute;
  left: 0; top: 0; bottom: 0;
  width: 3px;
  border-radius: 10px 0 0 10px;
  background: repeating-linear-gradient(180deg,
    currentColor 0 7px, transparent 7px 13px);
}

.pubx-notice-mark { flex: none; padding-top: 1px; }
.pubx-notice-body { flex: 1; min-width: 0; }

.pubx-notice-title {
  margin: 0;
  font-size: 13px;
  font-weight: 620;
  line-height: 1.4;
  color: var(--ink);
  letter-spacing: -0.005em;
}
.pubx-notice-text {
  margin: 5px 0 0;
  font-size: 12.5px;
  line-height: 1.52;
  color: var(--ink-2);
  max-width: 66ch;
}
.pubx-notice-second { color: var(--ink-3); }

.pubx-notice-acts {
  display: flex;
  gap: 8px;
  flex-wrap: wrap;
  margin-top: 10px;
}

/* --- the seven failure identities, plus wait and good ---------------- */

/* Solid rule: Orco knows this happened. */
.pubx-notice.is-publish-failed,
.pubx-notice.is-save-failed,
.pubx-notice.is-damaged {
  border-left-color: var(--bad);
  background: linear-gradient(90deg, var(--bad-bg), transparent 62%), var(--panel);
}
.pubx-notice.is-publish-failed .pubx-notice-mark,
.pubx-notice.is-publish-failed .pubx-eyebrow,
.pubx-notice.is-save-failed .pubx-notice-mark,
.pubx-notice.is-save-failed .pubx-eyebrow,
.pubx-notice.is-damaged .pubx-notice-mark,
.pubx-notice.is-damaged .pubx-eyebrow { color: var(--bad); }

/* A hard failure gets one more signal the uncertain ones never get: a
   hatched top edge. Two states can share a colour and still not be confused. */
.pubx-notice.is-publish-failed,
.pubx-notice.is-save-failed {
  box-shadow: inset 0 2px 0 color-mix(in srgb, var(--bad) 55%, transparent);
}

.pubx-notice.is-sync-failed,
.pubx-notice.is-conflict {
  border-left-color: var(--warn);
  background: linear-gradient(90deg, var(--warn-bg), transparent 62%), var(--panel);
}
.pubx-notice.is-sync-failed .pubx-notice-mark,
.pubx-notice.is-sync-failed .pubx-eyebrow,
.pubx-notice.is-conflict .pubx-notice-mark,
.pubx-notice.is-conflict .pubx-eyebrow { color: var(--warn); }

/* Damaged is red but reads as an artefact rather than an event: it gets the
   warn ground and the bad rule, which is a combination nothing else has. */
.pubx-notice.is-damaged {
  background: linear-gradient(90deg, var(--warn-bg), transparent 62%), var(--panel);
  box-shadow: none;
}

/* Dashed rule: Orco cannot confirm this. */
.pubx-notice.is-offline {
  color: var(--ink-3);
  background: var(--panel);
}
.pubx-notice.is-offline .pubx-notice-mark,
.pubx-notice.is-offline .pubx-eyebrow { color: var(--ink-3); }

.pubx-notice.is-unreachable {
  color: var(--warn);
  background: linear-gradient(90deg, var(--warn-bg), transparent 55%), var(--panel);
}
.pubx-notice.is-unreachable .pubx-notice-mark,
.pubx-notice.is-unreachable .pubx-eyebrow { color: var(--warn); }
.pubx-notice.is-unreachable .pubx-notice-title,
.pubx-notice.is-offline .pubx-notice-title { color: var(--ink); }

.pubx-notice.is-wait {
  border-left-color: var(--hair-2);
  background: var(--panel);
}
.pubx-notice.is-wait .pubx-notice-mark,
.pubx-notice.is-wait .pubx-eyebrow { color: var(--ink-3); }

.pubx-notice.is-good {
  border-left-color: var(--ok, var(--good));
  background: linear-gradient(90deg, var(--ok-bg, transparent), transparent 62%), var(--panel);
}
.pubx-notice.is-good .pubx-notice-mark,
.pubx-notice.is-good .pubx-eyebrow { color: var(--ok, var(--good)); }

/* =====================================================================
   5. THE ADDRESS WELL. A URL gets a monospace and a field of its own.
   ===================================================================== */

.pubx-url {
  display: flex;
  align-items: center;
  gap: 8px;
  margin: 8px 0 0;
  padding: 5px 5px 5px 11px;
  border-radius: 8px;
  border: 1px solid var(--hair);
  background: var(--field);
  min-width: 0;
}
.pubx-url-text {
  flex: 1;
  min-width: 0;
  font-family: var(--font-mono);
  font-size: 12.5px;
  line-height: 1.45;
  color: var(--ink);
  text-decoration: none;
  word-break: break-all;
  border-radius: 4px;
}
.pubx-url-text:hover { color: var(--accent-2); text-decoration: underline; text-underline-offset: 3px; }
.pubx-url-text:focus-visible { outline: 2px solid var(--accent); outline-offset: 3px; }

.pubx-url-copy {
  flex: none;
  min-height: 30px;
  padding: 0 11px;
  border-radius: 7px;
  border: 1px solid var(--hair);
  background: transparent;
  color: var(--ink-3);
  font: inherit;
  font-size: 11.5px;
  font-weight: 600;
  cursor: pointer;
  transition: color var(--t-state) var(--ease), border-color var(--t-state) var(--ease),
              background-color var(--t-state) var(--ease);
}
.pubx-url-copy:hover { color: var(--ink); border-color: var(--accent-2); background: var(--accent-soft); }
.pubx-url-copy:focus-visible { outline: none; box-shadow: var(--glow-ring); border-color: var(--accent); }
.pubx-url-copy.is-done { color: var(--ok, var(--good)); border-color: var(--ok, var(--good)); }

/* =====================================================================
   6. THE LEDGER LEAF: one public address.
   ===================================================================== */

.pubx-row {
  position: relative;
  margin: 9px 0;
  padding: 11px 14px 12px 15px;
  border-radius: 11px;
  border: 1px solid var(--hair);
  border-left: 3px solid var(--ink-4);
  background: var(--panel);
  /* One inner highlight along the top edge, so a raised surface catches light
     like an anodised panel rather than floating. */
  box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.05);
  transition: border-color var(--t-state) var(--ease), background-color var(--t-state) var(--ease);
}
.pubx-row:hover { border-color: var(--hair-2); }

/* The only ornament in the product: a 10px L-bracket tick at two opposing
   corners. It appears on a ledger leaf and nowhere else on this surface. */
.pubx-row::after {
  content: '';
  position: absolute;
  right: 7px;
  bottom: 7px;
  width: 10px;
  height: 10px;
  border-right: 1px solid var(--hair-2);
  border-bottom: 1px solid var(--hair-2);
  border-bottom-right-radius: 3px;
  opacity: 0.75;
  pointer-events: none;
}

.pubx-row.is-ok      { border-left-color: var(--ok, var(--good)); }
.pubx-row.is-warn    { border-left-color: var(--warn); }
.pubx-row.is-bad     { border-left-color: var(--bad); }
.pubx-row.is-wait    { border-left-color: var(--hair-2); }
.pubx-row.is-mute    { border-left-color: var(--ink-4); opacity: 0.82; }

/* Uncertainty gets the dash, on a card exactly as it does on a notice, and
   for the same reason it is a pseudo-element and not a background-image. */
.pubx-row.is-unsure {
  border-left-color: transparent;
  border-left-width: 0;
  padding-left: 19px;
  color: var(--ink-2);
}
.pubx-row.is-unsure::before {
  content: '';
  position: absolute;
  left: 0; top: 0; bottom: 0;
  width: 3px;
  border-radius: 11px 0 0 11px;
  background: repeating-linear-gradient(180deg,
    var(--warn) 0 7px, transparent 7px 13px);
}

.pubx-row-head {
  display: flex;
  align-items: baseline;
  gap: 10px;
  flex-wrap: wrap;
}
.pubx-row-name {
  font-family: var(--font-display);
  font-size: 15.5px;
  font-weight: 600;
  color: var(--ink);
  letter-spacing: -0.012em;
  line-height: 1.3;
  flex: 1 1 auto;
  min-width: 0;
  overflow-wrap: anywhere;
}

.pubx-chip {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  flex: none;
  padding: 3px 9px 3px 7px;
  border-radius: 999px;
  border: 1px solid var(--hair);
  font-size: 11px;
  font-weight: 640;
  letter-spacing: 0.005em;
  white-space: nowrap;
  color: var(--ink-3);
  background: var(--ground-2, var(--field));
}
.pubx-chip .pubx-glyph { width: 13px; height: 13px; stroke-width: 1.5; }
.pubx-chip.is-ok     { color: var(--ok, var(--good)); border-color: color-mix(in srgb, var(--ok, var(--good)) 34%, transparent); }
.pubx-chip.is-warn   { color: var(--warn); border-color: color-mix(in srgb, var(--warn) 34%, transparent); }
.pubx-chip.is-bad    { color: var(--bad);  border-color: color-mix(in srgb, var(--bad) 34%, transparent); }
.pubx-chip.is-unsure { color: var(--warn); border-style: dashed; border-color: color-mix(in srgb, var(--warn) 44%, transparent); }
.pubx-chip.is-wait   { color: var(--ink-3); }
.pubx-chip.is-mute   { color: var(--ink-4); }

/* The arithmetic. This is the sentence that does the real work on the screen,
   so it gets a comfortable measure and tabular numerals: the two screen counts
   are meant to be compared, and proportional digits make that harder. */
.pubx-row-meta {
  margin: 8px 0 0;
  font-size: 12.5px;
  line-height: 1.55;
  color: var(--ink-2);
  max-width: 68ch;
  font-variant-numeric: tabular-nums;
}
.pubx-row-unsure { color: var(--ink-3); }

.pubx-row-acts {
  display: flex;
  gap: 7px;
  flex-wrap: wrap;
  margin-top: 10px;
}

.pubx-act {
  min-height: 34px;
  font-size: 12px;
  padding: 0 12px;
  text-decoration: none;
  display: inline-flex;
  align-items: center;
}
.pubx-act:disabled { opacity: 0.42; cursor: not-allowed; }

/* The action worth reaching for, marked by weight and a hairline rather than
   by the gold primary. Gold is spent three times a screen and no more. */
.pubx-act--lead {
  border-color: color-mix(in srgb, var(--accent) 52%, var(--hair));
  color: var(--ink);
  font-weight: 650;
  background: var(--accent-soft, transparent);
}
.pubx-act--lead:hover:not(:disabled) { border-color: var(--accent); }

/* Used on footer buttons the confirmation replaces. `.tool` declares its own
   display, which outranks the user agent's [hidden] rule, so the attribute
   alone leaves the button on screen. */
.pubx-hide { display: none !important; }

/* A destructive action is never the loudest thing on the card. It is quiet
   until it is reached for, and then it is unambiguous. */
.pubx-danger { min-height: 34px; }

/* A row that was just published gets one calm acknowledgement, and it fades.
   It is a confirmation, not a state, so it must not persist as one. */
.pubx-row.is-fresh {
  animation: pubx-land var(--t-surface) var(--ease);
  border-color: var(--hair-2);
}
@keyframes pubx-land {
  from { transform: translateY(-3px); opacity: 0.4; }
  to   { transform: none; opacity: 1; }
}

/* =====================================================================
   7. THE PUBLISH SHEET: standing state, wait door, replace confirmation
   ===================================================================== */

.pubx-standing:empty { display: none; }
.pubx-standing { margin-bottom: 4px; }
.pubx-standing .pubx-row { margin: 8px 0 12px; }

/* First publish. Quiet, and it does not pretend to be a warning. */
.pubx-first {
  display: flex;
  gap: 11px;
  align-items: flex-start;
  margin: 12px 0 14px;
  padding: 11px 14px;
  border-radius: 10px;
  border: 1px dashed var(--hair-2);
  background: transparent;
  color: var(--ink-3);
}
.pubx-first .pubx-glyph { color: var(--accent); margin-top: 1px; }
.pubx-first-title {
  margin: 0;
  font-size: 13px;
  font-weight: 620;
  color: var(--ink);
}
.pubx-first-text {
  margin: 4px 0 0;
  font-size: 12.5px;
  line-height: 1.5;
  color: var(--ink-3);
  max-width: 66ch;
}

.pub-legend + .pubx-row { margin-top: 8px; }

/* --- the waiting door ------------------------------------------------
   The form is dimmed and inert behind a calm panel, and when the count
   settles the panel opens and the form comes up. A door, not a page. */

.pubx-sheet .sheet-list.is-waiting > .pubx-standing,
.pubx-sheet .sheet-list.is-waiting > .pub-legend,
.pubx-sheet .sheet-list.is-waiting > .pub-bar,
.pubx-sheet .sheet-list.is-waiting > .pub-tries,
.pubx-sheet .sheet-list.is-waiting > .pub-status {
  opacity: 0.28;
  filter: saturate(0.4);
  pointer-events: none;
  transition: opacity var(--t-surface) var(--ease), filter var(--t-surface) var(--ease);
}
.pubx-sheet .sheet-list > .pub-bar,
.pubx-sheet .sheet-list > .pub-tries,
.pubx-sheet .sheet-list > .pubx-standing {
  transition: opacity var(--t-surface) var(--ease), filter var(--t-surface) var(--ease);
}

.pubx-wait {
  position: relative;
  display: flex;
  gap: 11px;
  align-items: flex-start;
  overflow: hidden;
  margin: 12px 0 16px;
  padding: 14px 16px 15px;
  border-radius: 11px;
  border: 1px solid var(--hair);
  background: var(--panel);
  color: var(--ink-2);
  box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.05);
}
.pubx-wait .pubx-notice-mark { color: var(--accent); }
.pubx-wait .pubx-eyebrow { color: var(--accent); }

/* The gold hairline sweeping along the foot of the panel: the only motion on
   this surface, and it means one thing, which is "still arriving". */
.pubx-wait-sweep {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  height: 1px;
  background: linear-gradient(90deg, transparent, var(--gold), transparent);
  background-size: 42% 100%;
  background-repeat: no-repeat;
  animation: pubx-sweep 1600ms linear infinite;
}
@keyframes pubx-sweep {
  from { background-position: -45% 0; }
  to   { background-position: 145% 0; }
}

/* The door opening: the panel lifts and shortens out of the way rather than
   vanishing, so the eye follows it instead of being surprised by the form. */
.pubx-wait.is-opening {
  animation: pubx-door var(--t-surface) var(--ease) forwards;
  pointer-events: none;
}
@keyframes pubx-door {
  from { opacity: 1; transform: none; max-height: 220px; }
  to   { opacity: 0; transform: translateY(-6px) scaleY(0.92); max-height: 0; margin-bottom: 0; padding-top: 0; padding-bottom: 0; }
}

/* One brightening of the gold hairline as the form becomes usable. The rule
   under the head is the product's signature; brightening it once is how a
   place says it is ready without printing another sentence. */
.pubx-sheet .sheet-list.is-unlocked ~ .sheet-foot { /* nothing, kept for clarity */ }
.pubx-sheet:has(.sheet-list.is-unlocked) .sheet-head::after {
  background: linear-gradient(90deg, transparent, var(--gold) 12%, var(--gold) 88%, transparent);
}

/* --- the replacement confirmation ------------------------------------ */

.pubx-confirm {
  flex: 1 1 100%;
  display: flex;
  align-items: flex-end;
  gap: 14px;
  flex-wrap: wrap;
  padding: 12px 14px;
  border-radius: 10px;
  border: 1px solid color-mix(in srgb, var(--warn) 38%, var(--hair));
  border-left: 3px solid var(--warn);
  background: linear-gradient(90deg, var(--warn-bg), transparent 70%), var(--panel-2);
}
.pubx-confirm-body { flex: 1 1 280px; min-width: 0; }
.pubx-confirm .pubx-eyebrow { color: var(--warn); }
.pubx-confirm-text {
  margin: 0;
  font-size: 12.5px;
  line-height: 1.52;
  color: var(--ink);
  max-width: 62ch;
  font-variant-numeric: tabular-nums;
}
.pubx-confirm-second { margin-top: 5px; color: var(--ink-3); }
.pubx-confirm-acts { display: flex; gap: 8px; flex: none; }

.pubx-trouble:empty { display: none; }

/* =====================================================================
   8. THE MANAGER
   ===================================================================== */

.pubx-remote:empty { display: none; }
.pubx-remote-line {
  display: flex;
  align-items: center;
  gap: 8px;
  margin: 10px 0 2px;
  font-size: 12px;
  color: var(--ink-3);
}
.pubx-remote-line.is-ok { color: var(--ok, var(--good)); }
.pubx-remote-line.is-wait .pubx-glyph { animation: pubx-tick 2400ms linear infinite; }
@keyframes pubx-tick { from { transform: rotate(0); } to { transform: rotate(360deg); } }

.pubx-bulk {
  display: flex;
  align-items: center;
  gap: 9px;
  margin: 12px 0 4px;
  padding: 10px 13px;
  border-radius: 9px;
  border: 1px solid color-mix(in srgb, var(--warn) 30%, var(--hair));
  border-left: 3px solid var(--warn);
  background: linear-gradient(90deg, var(--warn-bg), transparent 70%), var(--panel);
  color: var(--ink);
  font-size: 12.5px;
  line-height: 1.5;
}
.pubx-bulk .pubx-glyph { color: var(--warn); flex: none; }

.pubx-count {
  margin: 14px 0 2px;
  font-size: 11px;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--ink-4);
  font-variant-numeric: tabular-nums;
}

/* --- the empty state, which gets the same care as the full one -------- */

.pubx-empty {
  display: flex;
  gap: 14px;
  align-items: flex-start;
  margin: 18px 0 8px;
  padding: 22px 22px 24px;
  border-radius: 12px;
  border: 1px dashed var(--hair-2);
  background: transparent;
}
.pubx-empty > .pubx-glyph {
  width: 26px;
  height: 26px;
  stroke-width: 1.1;
  color: var(--accent);
  opacity: 0.85;
  margin-top: 2px;
}
.pubx-empty-title {
  margin: 0;
  font-family: var(--font-display);
  font-size: 19px;
  font-weight: 600;
  letter-spacing: -0.015em;
  color: var(--ink);
}
.pubx-empty-text {
  margin: 8px 0 0;
  font-size: 13px;
  line-height: 1.58;
  color: var(--ink-2);
  max-width: 58ch;
}
.pubx-empty-quiet { color: var(--ink-3); font-size: 12.5px; }

/* =====================================================================
   9. UNPUBLISH
   ===================================================================== */

.pubx-unpublish .sheet-head strong { color: var(--ink); }

.pubx-two {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 14px;
  margin-top: 16px;
}
.pubx-col {
  padding: 13px 15px 15px;
  border-radius: 10px;
  border: 1px solid var(--hair);
  background: var(--panel);
}
/* The two columns are deliberately NOT symmetrical in colour. What this does
   is a fact about the product; what it cannot do is a fact about the world,
   and the second one is the one people get wrong. */
.pubx-col.is-does { border-left: 3px solid var(--ink-4); }
.pubx-col.is-cant {
  border-left: 3px solid var(--warn);
  background: linear-gradient(180deg, var(--warn-bg), transparent 70%), var(--panel);
}
.pubx-col.is-cant .pubx-eyebrow { color: var(--warn); }

.pubx-list {
  margin: 8px 0 0;
  padding: 0 0 0 17px;
  font-size: 12.5px;
  line-height: 1.55;
  color: var(--ink-2);
}
.pubx-list li { margin: 0 0 7px; }
.pubx-list li:last-child { margin-bottom: 0; }
.pubx-list li::marker { color: var(--ink-4); }
.pubx-col.is-cant .pubx-list li::marker { color: var(--warn); }

/* The one sentence that has to survive being the only thing read. */
.pubx-plain {
  margin: 16px 0 0;
  padding: 12px 0 0;
  border-top: 1px solid var(--hair);
  font-family: var(--font-display);
  font-size: 14.5px;
  line-height: 1.5;
  color: var(--ink);
  letter-spacing: -0.008em;
  max-width: 62ch;
}

/* A disabled primary must read as UNAVAILABLE, not as a tarnished version of
   the available one. The gold gradient at 45% opacity goes brown, which looks
   like a rendering fault rather than a locked control. */
.pubx-sheet .sheet-foot .tool--present:disabled {
  background: transparent;
  background-image: none;
  border: 1px dashed var(--hair-2);
  color: var(--ink-4);
  box-shadow: none;
  opacity: 1;
  text-shadow: none;
}

/* =====================================================================
   10. THE ADDRESS BAR, refined. Same control, better finish.
   ===================================================================== */

.pubx-sheet .pub-bar {
  min-height: 46px;
  border-radius: 10px;
  box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.04);
  transition: border-color var(--t-state) var(--ease), box-shadow var(--t-state) var(--ease);
}
.pubx-sheet .pub-bar:focus-within { border-color: var(--accent); }
.pubx-sheet .pub-path,
.pubx-sheet .pub-scheme,
.pubx-sheet .pub-slash,
.pubx-sheet .pub-sel { font-family: var(--font-mono); font-size: 13px; }
.pubx-sheet .pub-status { margin-top: 9px; font-variant-numeric: tabular-nums; }
/* An empty status line still reserved a line box and a margin, which opened a
   sixty pixel seam between the address bar and whatever came next. An absent
   sentence should take absent space. */
.pubx-sheet .pub-status:empty { min-height: 0; margin: 0; }
.pubx-sheet .pub-legend { margin-top: 16px; }

/* =====================================================================
   11. PHONE. 390 wide, zero horizontal overflow, 44px targets.
   ===================================================================== */

@media (max-width: 640px) {
  .pubx-sheet .sheet-list { padding: 4px 14px 16px; }
  .pubx-sheet .sheet-head::after { margin-left: -14px; margin-right: -14px; }
  .pubx-sheet .sheet-head strong { font-size: 17.5px; }

  .pubx-two { grid-template-columns: 1fr; gap: 10px; }

  .pubx-row { padding: 12px 13px 13px 14px; }
  .pubx-row.is-unsure { padding-left: 17px; }
  .pubx-row-name { font-size: 15px; }
  .pubx-row-acts { gap: 6px; }

  /* Touch targets. A destructive action on a phone gets the full 44. */
  .pubx-act,
  .pubx-danger,
  .pubx-url-copy { min-height: 44px; }
  .pubx-act { flex: 1 1 auto; justify-content: center; }

  /* The address takes the full line because it is what is being read; Copy
     stays a button beside it rather than becoming a slab under it. */
  .pubx-url { flex-wrap: wrap; padding: 6px 6px 6px 10px; }
  .pubx-url-text { flex: 1 1 100%; font-size: 12px; }
  .pubx-url-copy { flex: 0 0 auto; margin-left: auto; padding: 0 16px; }

  .pubx-confirm { flex-direction: column; align-items: stretch; }
  .pubx-confirm-acts > .pubx-act { flex: 1 1 0; }

  .pubx-empty { padding: 18px 16px 20px; gap: 11px; }
  .pubx-empty-title { font-size: 17px; }

  .pubx-sheet .sheet-foot { gap: 6px; }
  .pubx-sheet .sheet-foot .tool { min-height: 44px; }
  .pubx-foot-gap { flex-basis: 100%; height: 0; }
}

@media (pointer: coarse) {
  .pubx-act, .pubx-danger, .pubx-url-copy { min-height: 44px; }
}

/* Nothing on this surface may push the page sideways. A URL is the one string
   here with no natural break, and it is the one that would do it. */
.pubx-sheet .sheet-list { overflow-x: hidden; }
.pubx-row, .pubx-notice, .pubx-url, .pubx-col { max-width: 100%; }

/* =====================================================================
   12. REDUCED MOTION. The sweep stops, the door opens instantly, and the
        state is identical either way: motion here is never the message.
   ===================================================================== */

@media (prefers-reduced-motion: reduce) {
  .pubx-wait-sweep { animation: none; background: var(--hair-2); background-size: 100% 100%; }
  .pubx-wait.is-opening { animation: none; display: none; }
  .pubx-remote-line.is-wait .pubx-glyph { animation: none; }
  .pubx-row.is-fresh { animation: none; }
  .pubx-sheet *, .pubx-sheet *::before, .pubx-sheet *::after {
    transition-duration: 1ms !important;
  }
}

/* =====================================================================
   13. LIGHT THEME. The tokens already flip; two things do not and are
        corrected here rather than left to chance.
   ===================================================================== */

html[data-theme="light"] .pubx-row,
html[data-theme="light"] .pubx-notice,
html[data-theme="light"] .pubx-wait,
html[data-theme="light"] .pubx-col {
  box-shadow: var(--shadow-1);
  background-color: rgba(255, 255, 255, 0.86);
}
html[data-theme="light"] .pubx-chip { background: rgba(255, 255, 255, 0.9); }
html[data-theme="light"] .pubx-row::after { opacity: 0.5; }
