/* platform/pulse.css — the founders' Pulse board.
   Lives inside the console frame and borrows its tokens (--font-family,
   --text-*, --card-border, --radius-*). Everything here is prefixed `pulse-`
   so nothing leaks into the other sections. One accent: ink. Status colours
   are reserved for status and always travel with a word. */

.pulse {
  --pulse-ink: var(--text-primary, #363636);
  --pulse-ink-soft: rgba(54, 54, 54, 0.62);
  --pulse-hair: var(--card-border, #E5E5EA);
  --pulse-hair-strong: var(--border-color, #9E9E9E);
  --pulse-wash: rgba(0, 0, 0, 0.035);
  --pulse-wash-strong: rgba(0, 0, 0, 0.07);
  --pulse-good: #1F7A36;
  --pulse-good-wash: rgba(31, 122, 54, 0.10);
  --pulse-warn: #A06200;
  --pulse-warn-wash: rgba(160, 98, 0, 0.12);
  --pulse-bad: #B3261E;
  --pulse-bad-wash: rgba(179, 38, 30, 0.10);
  --pulse-radius: var(--radius-xl, 12px);
  font-family: var(--font-family);
  color: var(--pulse-ink);
  font-feature-settings: "kern" 1, "liga" 1;
  text-rendering: optimizeLegibility;
  padding-bottom: 48px;
}
.pulse * { box-sizing: border-box; }
.pulse a { color: inherit; }
.pulse button { font-family: inherit; }
.pulse code, .pulse .pulse-mono { font-family: var(--font-mono); font-size: 12px; }
.pulse .pulse-num { font-variant-numeric: tabular-nums lining-nums; }

/* ---- Head ---------------------------------------------------------------- */
.pulse-head {
  display: flex; align-items: flex-start; justify-content: space-between; gap: 24px;
  margin-bottom: 20px;
}
.pulse-title { font-size: 22px; font-weight: 400; margin: 0 0 4px; letter-spacing: -0.01em; }
.pulse-sub { font-size: 13px; color: var(--text-secondary); margin: 0; max-width: 62ch; line-height: 1.45; }
.pulse-controls { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; justify-content: flex-end; }
.pulse-seg {
  display: inline-flex; padding: 2px; gap: 2px; border-radius: 999px;
  background: rgba(120, 120, 128, 0.12);
}
.pulse-seg button {
  border: 0; background: transparent; border-radius: 999px; cursor: pointer;
  padding: 6px 12px; font-size: 12.5px; font-weight: 500; color: var(--text-secondary);
  transition: color .15s, background .15s, box-shadow .15s;
}
.pulse-seg button:hover { color: var(--pulse-ink); }
.pulse-seg button[aria-pressed="true"] { background: #FFFFFF; color: var(--pulse-ink); box-shadow: 0 1px 3px rgba(0,0,0,0.10); }
.pulse-seg button:focus-visible, .pulse button:focus-visible, .pulse [tabindex]:focus-visible {
  outline: 2px solid var(--accent-blue, #007AFF); outline-offset: 2px;
}
.pulse-toggle {
  display: inline-flex; align-items: center; gap: 6px; font-size: 12.5px; color: var(--text-secondary);
  cursor: pointer; user-select: none; padding: 6px 10px; border: 1px solid var(--pulse-hair); border-radius: 999px;
  background: #FFFFFF;
}
.pulse-toggle input { accent-color: var(--pulse-ink); margin: 0; }
.pulse-live {
  display: inline-flex; align-items: center; gap: 7px; padding: 6px 11px; border-radius: 999px;
  border: 1px solid var(--pulse-hair); background: #FFFFFF; color: var(--text-secondary);
  font-size: 12.5px; cursor: pointer; transition: border-color .15s, color .15s;
}
.pulse-live:hover { border-color: var(--pulse-hair-strong); color: var(--pulse-ink); }
.pulse-live-dot { width: 7px; height: 7px; border-radius: 50%; background: var(--pulse-good); box-shadow: 0 0 0 2px var(--pulse-good-wash); }
.pulse-live[data-state="loading"] .pulse-live-dot { background: var(--pulse-warn); box-shadow: 0 0 0 2px var(--pulse-warn-wash); animation: pulse-blink 1.1s ease-in-out infinite; }
/* stale: the numbers are real but old (a failed recompute, or a copy painted from this browser). */
.pulse-live[data-state="stale"] .pulse-live-dot { background: var(--pulse-warn); box-shadow: 0 0 0 2px var(--pulse-warn-wash); }
.pulse-live[data-state="stale"] { color: var(--pulse-warn); border-color: rgba(160, 98, 0, 0.35); }
.pulse-live[data-state="error"] .pulse-live-dot { background: var(--pulse-bad); box-shadow: 0 0 0 2px var(--pulse-bad-wash); }
.pulse-live[data-state="error"] { color: var(--pulse-bad); border-color: rgba(179, 38, 30, 0.35); }
@keyframes pulse-blink { 50% { opacity: 0.35; } }

/* ---- Health strip ------------------------------------------------------- */
.pulse-health { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 12px; margin-bottom: 20px; }
.pulse-health-tile {
  display: flex; align-items: flex-start; gap: 12px; padding: 14px 16px;
  border: 1px solid var(--pulse-hair); border-radius: var(--pulse-radius); background: #FFFFFF;
  text-align: left; cursor: pointer; transition: border-color .15s, background .15s; width: 100%;
}
.pulse-health-tile:hover { border-color: var(--pulse-hair-strong); background: rgba(0,0,0,0.008); }
.pulse-health-mark {
  flex: 0 0 auto; width: 26px; height: 26px; border-radius: 50%; display: grid; place-items: center; margin-top: 1px;
}
.pulse-health-mark svg { width: 14px; height: 14px; }
.pulse-health-tile[data-state="good"] .pulse-health-mark { background: var(--pulse-good-wash); color: var(--pulse-good); }
.pulse-health-tile[data-state="warn"] .pulse-health-mark { background: var(--pulse-warn-wash); color: var(--pulse-warn); }
.pulse-health-tile[data-state="bad"]  .pulse-health-mark { background: var(--pulse-bad-wash);  color: var(--pulse-bad); }
.pulse-health-body { min-width: 0; }
.pulse-health-name { display: flex; align-items: baseline; gap: 8px; font-size: 13px; font-weight: 500; }
.pulse-health-state { font-size: 11px; font-weight: 500; letter-spacing: 0.06em; text-transform: uppercase; }
.pulse-health-tile[data-state="good"] .pulse-health-state { color: var(--pulse-good); }
.pulse-health-tile[data-state="warn"] .pulse-health-state { color: var(--pulse-warn); }
.pulse-health-tile[data-state="bad"]  .pulse-health-state { color: var(--pulse-bad); }
.pulse-health-summary { font-size: 13px; color: var(--text-secondary); margin-top: 3px; line-height: 1.4; }

/* ---- KPI row ------------------------------------------------------------ */
.pulse-kpis { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 12px; margin-bottom: 12px; }
.pulse-kpi {
  display: grid; grid-template-columns: minmax(0, 1fr) auto; column-gap: 12px; align-content: start;
  padding: 16px 16px 14px; border: 1px solid var(--pulse-hair); border-radius: var(--pulse-radius);
  background: #FFFFFF; min-width: 0; overflow: hidden;
}
.pulse-kpi-label { grid-column: 1 / -1; }
.pulse-kpi-value, .pulse-kpi-row, .pulse-kpi-foot { grid-column: 1; min-width: 0; }
.pulse-kpi-label { font-size: 13px; color: var(--text-secondary); margin-bottom: 8px; display: flex; justify-content: space-between; gap: 8px; }
.pulse-kpi-scope { font-size: 11px; color: var(--text-tertiary); letter-spacing: 0.04em; text-transform: uppercase; white-space: nowrap; }
.pulse-kpi-value { font-size: 30px; font-weight: 500; letter-spacing: -0.02em; line-height: 1.05; }
.pulse-kpi-row { display: flex; align-items: center; gap: 10px; margin-top: 8px; min-height: 20px; flex-wrap: wrap; }
.pulse-kpi-foot { font-size: 12px; color: var(--text-tertiary); margin-top: 8px; line-height: 1.5; }
.pulse-kpi-foot b { font-weight: 500; color: var(--text-secondary); }
.pulse-kpi-spark { grid-column: 2; grid-row: 2 / span 3; align-self: end; width: 96px; height: 34px; opacity: 0.9; }
.pulse-kpi-spark svg { width: 100%; height: 100%; display: block; overflow: visible; }

.pulse-delta {
  display: inline-flex; align-items: center; gap: 4px; padding: 2px 7px; border-radius: 999px;
  font-size: 12px; font-weight: 500; line-height: 16px; white-space: nowrap; background: var(--pulse-wash); color: var(--pulse-ink-soft);
}
.pulse-delta svg { width: 9px; height: 9px; }
.pulse-delta[data-tone="good"] { background: var(--pulse-good-wash); color: var(--pulse-good); }
.pulse-delta[data-tone="bad"]  { background: var(--pulse-bad-wash);  color: var(--pulse-bad); }
.pulse-delta-vs { font-size: 12px; color: var(--text-tertiary); }

/* ---- Cards -------------------------------------------------------------- */
.pulse-card { border: 1px solid var(--pulse-hair); border-radius: var(--pulse-radius); background: #FFFFFF; margin-bottom: 12px; min-width: 0; }
.pulse-card-head {
  display: flex; align-items: center; justify-content: space-between; gap: 12px;
  padding: 12px 16px; border-bottom: 1px solid var(--pulse-hair);
}
.pulse-card-title { font-size: 14px; font-weight: 500; display: flex; align-items: center; gap: 8px; }
.pulse-card-meta { font-size: 12px; color: var(--text-tertiary); }
.pulse-card-body { padding: 16px; }
.pulse-card-flush { padding: 0; }
.pulse-link {
  background: none; border: 0; padding: 0; font-size: 12.5px; color: var(--text-secondary); cursor: pointer;
  text-decoration: none; border-bottom: 1px solid transparent; transition: color .15s, border-color .15s;
}
.pulse-link:hover { color: var(--pulse-ink); border-bottom-color: var(--pulse-hair-strong); }
.pulse-grid-2 { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 12px; }
.pulse-grid-2 > .pulse-card { margin-bottom: 0; }
.pulse-section-gap { height: 0; margin-bottom: 12px; }

/* ---- Day charts ----------------------------------------------------------- */
.pulse-chart { position: relative; }
.pulse-chart svg { width: 100%; height: 148px; display: block; overflow: visible; }
.pulse-chart-bar { fill: var(--pulse-ink); }
.pulse-chart-bar.is-soft { fill: rgba(54, 54, 54, 0.28); }
/* Today is still being counted: an outline, never a fill that reads as a series (it read as "all linked"). */
.pulse-chart-bar.is-today { stroke: var(--pulse-ink); stroke-width: 1.2; stroke-dasharray: 3 2; }
.pulse-chart-hit { fill: transparent; cursor: crosshair; }
.pulse-chart-hit:hover + .pulse-chart-bar, .pulse-chart-bar.is-hover { opacity: 0.72; }
.pulse-chart-axis { fill: var(--text-tertiary); font-size: 10.5px; font-family: var(--font-family); }
/* The number on every cap: the per-day count is the point of the chart. */
.pulse-chart-val { fill: var(--text-secondary); font-size: 11px; font-weight: 500; font-family: var(--font-family); font-variant-numeric: tabular-nums; pointer-events: none; }
.pulse-chart-val.is-zero { fill: var(--text-tertiary); font-weight: 400; opacity: 0.7; }
.pulse-chart-grid { stroke: var(--pulse-hair); stroke-width: 1; }
.pulse-chart-tip {
  position: absolute; pointer-events: none; z-index: 3; transform: translate(-50%, calc(-100% - 10px));
  background: var(--pulse-ink); color: #FFFFFF; border-radius: 8px; padding: 6px 9px; font-size: 12px; white-space: nowrap;
  box-shadow: 0 6px 20px rgba(0,0,0,0.16); opacity: 0; transition: opacity .12s;
}
.pulse-chart-tip.is-on { opacity: 1; }
.pulse-chart-tip b { font-weight: 600; font-variant-numeric: tabular-nums; }
.pulse-chart-tip span { opacity: 0.72; }
.pulse-chart-table { width: 100%; border-collapse: collapse; font-size: 12px; margin-top: 10px; }
.pulse-chart-table th, .pulse-chart-table td { padding: 4px 8px; text-align: right; border-top: 1px solid var(--pulse-hair); }
.pulse-chart-table th:first-child, .pulse-chart-table td:first-child { text-align: left; }

/* ---- Tables -------------------------------------------------------------- */
.pulse-table-wrap { overflow-x: auto; }
.pulse-table { width: 100%; border-collapse: collapse; font-size: 13px; }
.pulse-table th {
  text-align: left; font-size: 11px; font-weight: 500; letter-spacing: 0.06em; text-transform: uppercase;
  color: var(--text-tertiary); padding: 10px 12px; border-bottom: 1px solid var(--pulse-hair); white-space: nowrap;
}
.pulse-table th:first-child, .pulse-table td:first-child { padding-left: 16px; }
.pulse-table th:last-child, .pulse-table td:last-child { padding-right: 16px; }
.pulse-table td { padding: 10px 12px; border-bottom: 1px solid var(--pulse-hair); vertical-align: middle; }
.pulse-table tr:last-child td { border-bottom: 0; }
.pulse-table th.is-num, .pulse-table td.is-num { text-align: right; font-variant-numeric: tabular-nums lining-nums; }
.pulse-table tbody tr { transition: background .12s; }
.pulse-table tbody tr:hover { background: rgba(0,0,0,0.015); }
.pulse-table tbody tr.is-clickable { cursor: pointer; }
.pulse-table tbody tr.is-selected { background: rgba(0,0,0,0.035); }
.pulse-table .is-muted { color: var(--text-tertiary); }
.pulse-empty { padding: 36px 16px; text-align: center; font-size: 13px; color: var(--text-tertiary); }
.pulse-card-foot { padding: 10px 16px; border-top: 1px solid var(--pulse-hair); font-size: 12.5px; }

/* platform cell */
.pulse-plat { display: flex; align-items: center; gap: 10px; min-width: 0; }
.pulse-plat-mark {
  flex: 0 0 auto; width: 26px; height: 26px; border-radius: 7px; display: grid; place-items: center;
  background: var(--pulse-wash); color: var(--pulse-ink); font-size: 11px; font-weight: 600; overflow: hidden;
}
.pulse-plat-mark img { width: 100%; height: 100%; object-fit: cover; display: block; }
.pulse-plat-name { font-weight: 500; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 260px; }
.pulse-plat-dev { font-size: 12px; color: var(--text-tertiary); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.pulse-tag {
  display: inline-block; font-size: 10.5px; font-weight: 500; letter-spacing: 0.05em; text-transform: uppercase;
  padding: 1px 6px; border-radius: 4px; border: 1px solid var(--pulse-hair); color: var(--text-tertiary); margin-left: 6px; vertical-align: 1px;
}

/* rate bar (converted vs unlinked share) */
.pulse-rate { display: flex; align-items: center; gap: 8px; min-width: 96px; }
.pulse-rate-bar { flex: 1; height: 6px; border-radius: 3px; background: rgba(0,0,0,0.10); overflow: hidden; }
.pulse-rate-fill { height: 100%; background: var(--pulse-ink); border-radius: 3px; }
.pulse-rate-val { font-size: 12px; color: var(--text-secondary); font-variant-numeric: tabular-nums; min-width: 34px; text-align: right; }

/* sparkline cell */
.pulse-spark { width: 84px; height: 26px; display: block; }
.pulse-spark svg { width: 100%; height: 100%; display: block; overflow: visible; }

/* status chips */
.pulse-chip {
  display: inline-flex; align-items: center; gap: 5px; padding: 2px 8px; border-radius: 999px;
  font-size: 12px; line-height: 16px; background: var(--pulse-wash); color: var(--pulse-ink-soft); white-space: nowrap;
}
.pulse-chip::before { content: ""; width: 6px; height: 6px; border-radius: 50%; background: currentColor; opacity: 0.75; }
.pulse-chip[data-tone="good"] { background: var(--pulse-good-wash); color: var(--pulse-good); }
.pulse-chip[data-tone="warn"] { background: var(--pulse-warn-wash); color: var(--pulse-warn); }
.pulse-chip[data-tone="bad"]  { background: var(--pulse-bad-wash);  color: var(--pulse-bad); }
.pulse-chip[data-tone="none"]::before { display: none; }

/* person cell */
.pulse-person { min-width: 0; }
.pulse-person-name { font-weight: 500; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 240px; }
.pulse-person-sub { font-size: 12px; color: var(--text-tertiary); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 260px; }

/* filter banner */
.pulse-filter {
  display: inline-flex; align-items: center; gap: 8px; padding: 4px 6px 4px 10px; border-radius: 999px;
  background: var(--pulse-ink); color: #FFFFFF; font-size: 12px;
}
.pulse-filter button { border: 0; background: rgba(255,255,255,0.18); color: #FFFFFF; border-radius: 999px; width: 18px; height: 18px; cursor: pointer; font-size: 12px; line-height: 18px; padding: 0; }
.pulse-filter button:hover { background: rgba(255,255,255,0.32); }

/* ---- People card tabs ---------------------------------------------------- */
.pulse-tabs { display: flex; align-items: center; gap: 2px; padding: 2px; border-radius: 999px; background: rgba(120, 120, 128, 0.12); }
.pulse-tab {
  appearance: none; border: 0; background: transparent; border-radius: 999px; cursor: pointer;
  padding: 5px 12px; font-size: 13px; font-weight: 500; color: var(--text-secondary);
  display: inline-flex; align-items: center; gap: 6px; transition: color .15s, background .15s, box-shadow .15s;
}
.pulse-tab:hover { color: var(--pulse-ink); }
.pulse-tab[aria-selected="true"] { background: #FFFFFF; color: var(--pulse-ink); box-shadow: 0 1px 3px rgba(0,0,0,0.10); }
.pulse-tab-count { font-size: 11.5px; font-weight: 500; color: var(--text-tertiary); padding: 1px 6px; border-radius: 999px; background: rgba(0,0,0,0.05); }
.pulse-tab[aria-selected="true"] .pulse-tab-count { color: var(--pulse-ink); }

/* ---- Synthesis + errors panels ------------------------------------------ */
.pulse-stats { display: flex; flex-wrap: wrap; gap: 8px 18px; padding: 12px 16px; border-bottom: 1px solid var(--pulse-hair); }
.pulse-stat { display: flex; align-items: baseline; gap: 6px; font-size: 13px; color: var(--text-secondary); }
.pulse-stat b { font-weight: 500; color: var(--pulse-ink); font-variant-numeric: tabular-nums; }
.pulse-list { list-style: none; margin: 0; padding: 0; }
.pulse-list li { display: flex; align-items: flex-start; gap: 12px; padding: 10px 16px; border-bottom: 1px solid var(--pulse-hair); font-size: 13px; }
.pulse-list li:last-child { border-bottom: 0; }
.pulse-list-main { flex: 1; min-width: 0; }
.pulse-list-title { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.pulse-list-msg { color: var(--text-secondary); font-size: 12.5px; margin-top: 2px; line-height: 1.4; overflow-wrap: anywhere; }
.pulse-list-when { flex: 0 0 auto; font-size: 12px; color: var(--text-tertiary); white-space: nowrap; }
.pulse-errbar { display: flex; align-items: center; gap: 10px; }
.pulse-errbar-track { flex: 1; height: 5px; background: rgba(0,0,0,0.06); border-radius: 3px; overflow: hidden; }
.pulse-errbar-fill { height: 100%; background: var(--pulse-bad); opacity: 0.75; }

.pulse-defs { font-size: 12px; color: var(--text-tertiary); line-height: 1.55; max-width: 92ch; margin-top: 16px; }
.pulse-defs b { font-weight: 500; color: var(--text-secondary); }

/* ---- States -------------------------------------------------------------- */
/* Dimming while a slice loads says "these numbers are on their way out". It
   must not say it about the CONTROLS: those are how you change what is
   loading, and a 55%-opacity pill reads as disabled even though it still
   responds. Dimmed controls plus dropdowns that emptied themselves mid-load
   is what made the panel feel frozen - you could not tell that clicking would
   do anything. The numbers fade; the things you steer with do not. */
.pulse.is-loading .pulse-body { opacity: 0.55; transition: opacity .2s; }
.pulse.is-loading .pulse-cohorts,
.pulse.is-loading .pulse-flowbar,
.pulse.is-loading .pulse-flowbar-says,
.pulse.is-loading .pulse-head { opacity: 1; }
.pulse-body { transition: opacity .2s; }
.pulse-error {
  padding: 14px 16px; border: 1px solid var(--pulse-bad); border-radius: var(--pulse-radius); background: var(--pulse-bad-wash);
  color: var(--pulse-bad); font-size: 13px; margin-bottom: 12px;
}
/* A refresh failure with a board still on screen is a note, not an alarm. */
.pulse-error.is-soft { border-color: rgba(160, 98, 0, 0.35); background: var(--pulse-warn-wash); color: var(--pulse-warn); }
.pulse-skeleton { padding: 48px 16px; text-align: center; color: var(--text-tertiary); font-size: 13px; }

/* ---- Motion -------------------------------------------------------------- */
@keyframes pulse-rise { from { opacity: 0; transform: translateY(4px); } to { opacity: 1; transform: none; } }
.pulse-body > * { animation: pulse-rise .28s cubic-bezier(0.2, 0.7, 0.2, 1) both; }
/* ...but NOT the chrome. render() replaces the panel's markup wholesale, so
   every slice change and every background refresh restarted this entrance on
   the toolbar too - and `both` holds the `from` frame, which is opacity 0.
   Measured in the browser mid-change: the filter bar computed to opacity 0
   while somebody was using it. Content arriving deserves a fade; the controls
   you are mid-click on do not move or blink. */
.pulse-body > .pulse-head,
.pulse-body > .pulse-cohorts,
.pulse-body > .pulse-flowbar,
.pulse-body > .pulse-flowbar-says { animation: none; }
.pulse-body > *:nth-child(2) { animation-delay: .04s; }
/* A background refresh of the same view repaints without the entrance (render/paint in pulse.js): replaying it
   every few seconds was the flashing. */
.is-quiet .pulse-body > * { animation: none; }
.pulse-body > *:nth-child(3) { animation-delay: .08s; }
.pulse-body > *:nth-child(4) { animation-delay: .12s; }
.pulse-body > *:nth-child(5) { animation-delay: .16s; }
.pulse-body > *:nth-child(6) { animation-delay: .20s; }
@media (prefers-reduced-motion: reduce) {
  .pulse-body > * { animation: none; }
  .pulse-live[data-state="loading"] .pulse-live-dot { animation: none; }
}

/* ---- Responsive ---------------------------------------------------------- */
@media (max-width: 1180px) {
  .pulse-kpis { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .pulse-grid-2 { grid-template-columns: minmax(0, 1fr); }
}
@media (max-width: 820px) {
  .pulse-head { flex-direction: column; }
  .pulse-controls { justify-content: flex-start; }
  .pulse-health { grid-template-columns: minmax(0, 1fr); }
  .pulse-kpi-spark { display: none; }
}
@media (max-width: 560px) {
  .pulse-kpis { grid-template-columns: minmax(0, 1fr); }
}

/* ---- Hosted flow panel --------------------------------------------------- */
.pulse-cohorts {
  display: inline-flex; align-items: center; gap: 2px; padding: 3px; margin-bottom: 14px;
  border-radius: 999px; background: rgba(120, 120, 128, 0.12);
}
.pulse-cohorts .pulse-tab { padding: 7px 16px; font-size: 13.5px; }

.pulse-head--sub { margin-bottom: 14px; }
.pulse-head--sub .pulse-title { font-size: 19px; }
.pulse-flowbar {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap; margin-bottom: 16px;
  padding-bottom: 14px; border-bottom: 1px solid var(--pulse-hair);
}
/* ---------------------------------------------------------------------------
   The filter menus
   ---------------------------------------------------------------------------
   These are real <select> elements. A native select's popup is drawn by the
   operating system, outside the page, which is why no amount of CSS ever
   reached it and why every product eventually ships a hand-built one — and
   with it fourteen keyboard behaviours, a focus model where DOM focus must
   stay on the trigger, and a new set of bugs.
   `appearance: base-select` opts the same element into being drawn by the
   browser instead, so the menu below is ours to style while the browser keeps
   every keyboard behaviour, the top-layer placement and the accessibility
   tree. Both the control and its ::picker must opt in; opting one in alone
   does nothing.
   Where it is not supported the rules below are simply ignored and a correct,
   keyboard-accessible native select is what renders. That is the fallback. */
.pulse-select {
  font: inherit; font-size: 12.5px; color: var(--pulse-ink); background: #FFFFFF;
  border: 1px solid var(--pulse-hair); border-radius: 999px; padding: 6px 10px; cursor: pointer;
  max-width: 210px;
}
.pulse-select:hover { border-color: var(--pulse-hair-strong); }

.pulse-select, .pulse-select::picker(select) { appearance: base-select; }

.pulse-select {
  display: inline-flex; align-items: center; gap: 8px;
  padding: 6px 10px 6px 12px; text-align: left; white-space: nowrap;
  transition: border-color 0.15s linear, box-shadow 0.15s linear;
}
.pulse-select:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 2px; }
.pulse-select:open { border-color: var(--pulse-hair-strong); box-shadow: 0 1px 3px rgba(0,0,0,0.08); }
.pulse-select::picker-icon {
  color: var(--pulse-ink-soft); transition: transform 0.15s ease; margin-left: auto;
}
.pulse-select:open::picker-icon { transform: rotate(180deg); }

.pulse-select::picker(select) {
  border: 1px solid var(--pulse-hair-strong); border-radius: 12px;
  background: #FFFFFF; padding: 5px; margin-top: 6px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.14);
  max-height: 320px; overflow-y: auto;
  /* The picker is in the top layer, so it needs its own opening transition. */
  opacity: 0; translate: 0 -4px;
  transition: opacity 0.14s ease, translate 0.14s ease, overlay 0.14s allow-discrete, display 0.14s allow-discrete;
}
.pulse-select:open::picker(select) { opacity: 1; translate: 0 0; }
@starting-style { .pulse-select:open::picker(select) { opacity: 0; translate: 0 -4px; } }

.pulse-select option {
  display: flex; align-items: center; gap: 8px;
  padding: 7px 10px; border-radius: 8px; font-size: 13px; color: var(--pulse-ink);
  cursor: pointer;
}
.pulse-select option:hover, .pulse-select option:focus { background: var(--pulse-wash); outline: none; }
.pulse-select option:checked { font-weight: 550; }
.pulse-select option::checkmark { order: 1; margin-left: auto; color: var(--pulse-ink); }

@media (prefers-reduced-motion: reduce) {
  .pulse-select::picker(select) { transition: none; }
  .pulse-select::picker-icon { transition: none; }
}

/* A screenshot of one screen of the real flow. */
.pulse-shot {
  display: block; border-radius: 8px; border: 1px solid var(--pulse-hair); background: #FFFFFF;
  /* contain, never cover: a cropped screenshot of a screen is worse than none,
     and the whole point of these is to recognise the screen at a glance. */
  object-fit: contain; object-position: center;
  aspect-ratio: 912 / 1744;
}
.pulse-shot.is-thumb { width: 54px; height: 76px; }
.pulse-shot.is-hero {
  width: 172px; height: auto; flex: 0 0 auto; border-radius: 12px;
  box-shadow: 0 1px 2px rgba(0,0,0,0.04), 0 8px 24px rgba(0,0,0,0.07);
}
.pulse-shot.is-film {
  width: 100%; height: auto; border-radius: 10px;
  box-shadow: 0 1px 2px rgba(0,0,0,0.04), 0 4px 14px rgba(0,0,0,0.05);
  transition: transform .18s cubic-bezier(0.2,0.7,0.2,1), box-shadow .18s;
}
.pulse-film-cell:hover .pulse-shot.is-film {
  transform: translateY(-2px);
  box-shadow: 0 2px 4px rgba(0,0,0,0.05), 0 12px 28px rgba(0,0,0,0.10);
}
.pulse-shot.is-missing {
  display: grid; place-items: center; color: var(--text-tertiary); font-size: 10px;
  border-style: dashed; background: rgba(0,0,0,0.02); text-align: center; line-height: 1.2;
  aspect-ratio: 912 / 1744;
}
.pulse-shot.is-missing span { padding: 0 4px; }

/* ---- The funnel table ---------------------------------------------------
   One row = one screen. The screenshot is large enough to recognise the
   screen without opening anything; the bar narrows down the page so the
   funnel shape is visible at a glance; and the only saturated colour on the
   whole table is the single worst row's number. */

.pulse-steps { table-layout: fixed; }
.pulse-steps th { padding-top: 14px; padding-bottom: 12px; }
.pulse-steps td { vertical-align: middle; padding-top: 14px; padding-bottom: 14px; }
.pulse-steps tbody tr:hover { background: rgba(0, 0, 0, 0.012); }

/* The screenshot: a real device card, not a postage stamp. */
.pulse-fshot { width: 124px; padding-right: 4px !important; }
.pulse-shot.is-thumb {
  width: 108px; height: auto; border-radius: 10px;
  box-shadow: 0 1px 2px rgba(0, 0, 0, 0.04), 0 6px 16px rgba(0, 0, 0, 0.06);
}
.pulse-shot.is-thumb.is-missing { box-shadow: none; }

.pulse-fname { width: 30%; }
.pulse-step-name { font-size: 14.5px; font-weight: 500; display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.pulse-step-does { font-size: 12.5px; color: var(--text-tertiary); margin-top: 4px; line-height: 1.5; max-width: 52ch; }

/* The flag is a label, not an alarm: ink on a wash, like every other chip. */
.pulse-flag {
  font-size: 10.5px; font-weight: 500; letter-spacing: 0.05em; text-transform: uppercase;
  color: var(--text-secondary); background: var(--pulse-wash);
  border-radius: 4px; padding: 2px 6px; white-space: nowrap;
}

.pulse-freach { width: 30%; }
.pulse-freach-n { font-size: 17px; font-weight: 500; font-variant-numeric: tabular-nums; line-height: 1.1; }

/* ONE bar per row, split where the people split: solid = carried on, hatched =
   stopped here. No track behind it and no rounded pill, because those are the
   grammar of a progress bar and this is a bar-chart mark. The loss is told by
   TEXTURE as well as tone, so it survives a colour-blind reader, a greyscale
   print and forced-colors mode — WCAG 1.4.1 is not satisfied by hue alone. */
.pulse-fbar {
  position: relative;
  display: flex; align-items: stretch;
  height: 8px; margin-top: 10px; border-radius: 2px;
  outline: none;
}
.pulse-fbar-kept { background: var(--pulse-ink); opacity: 0.88; border-radius: 2px 0 0 2px; }
.pulse-fbar-kept:only-child { border-radius: 2px; }
.pulse-fbar-lost {
  border-radius: 0 2px 2px 0;
  background-color: rgba(54, 54, 54, 0.14);
  background-image: repeating-linear-gradient(
    45deg, rgba(54, 54, 54, 0.42) 0 1.5px, transparent 1.5px 4.5px);
}
.pulse-fbar-done { background: var(--pulse-good); opacity: 0.9; border-radius: 2px; }
.pulse-fbar[data-tip] { cursor: default; }
.pulse-fbar[data-tip]:hover .pulse-fbar-kept,
.pulse-fbar[data-tip]:focus-visible .pulse-fbar-kept { opacity: 1; }
.pulse-fbar[data-tip]:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 3px; border-radius: 3px; }

/* The breakdown that opens on the bar. Hoverable by construction — it is a
   child of its trigger, so moving the pointer into it never leaves the
   trigger, which is what WCAG 1.4.13 asks for and what a five-row panel needs
   if anyone is to read row five. */
.pulse-tip {
  position: absolute; left: 0; bottom: calc(100% + 8px); z-index: 30;
  display: none; min-width: 208px; padding: 10px 12px 9px;
  background: #FFFFFF; color: var(--pulse-ink);
  border: 1px solid var(--pulse-hair-strong);
  border-radius: 10px; box-shadow: 0 8px 24px rgba(0, 0, 0, 0.13);
  text-align: left; cursor: default;
}
.pulse-fbar.is-open .pulse-tip { display: block; }
.pulse-tip-head {
  display: block; font-size: 11px; font-weight: 600; letter-spacing: 0.04em;
  text-transform: uppercase; color: var(--pulse-ink-soft); margin-bottom: 7px;
}
.pulse-tip-list { list-style: none; margin: 0; padding: 0; }
.pulse-tip-list li {
  display: flex; justify-content: space-between; gap: 16px;
  font-size: 13px; line-height: 21px; white-space: nowrap;
}
.pulse-tip-k { color: var(--pulse-ink); }
.pulse-tip-v { font-variant-numeric: tabular-nums; color: var(--pulse-ink); font-weight: 500; }
.pulse-tip-foot {
  display: block; margin-top: 7px; padding-top: 7px;
  border-top: 1px solid var(--pulse-hair);
  font-size: 12px; color: var(--pulse-ink-soft);
}

/* A screen not everyone sees, or one people join at. Neither is a loss. */
.pulse-step-note { margin-top: 4px; font-size: 12px; line-height: 17px; color: var(--pulse-ink-soft); }
.pulse-steps tr.is-offpath td { background: rgba(0, 0, 0, 0.018); }
.pulse-steps tr.is-offpath .pulse-step-name { color: var(--pulse-ink-soft); }

.pulse-flost { width: 132px; }
.pulse-flost-n { font-size: 17px; font-weight: 500; font-variant-numeric: tabular-nums; line-height: 1.1; }
.pulse-flost-n.is-worst { color: var(--pulse-bad); }
.pulse-flost-n.is-none { color: var(--text-tertiary); font-weight: 400; font-size: 14px; }
.pulse-flost-p { font-size: 12px; color: var(--text-tertiary); margin-top: 4px; }

.pulse-ftime {
  width: 108px; text-align: right; font-size: 14px;
  font-variant-numeric: tabular-nums; color: var(--text-secondary);
}

/* The worst row is marked by a rule, not by washing the row in red. */
.pulse-steps tr.is-worst td:first-child { box-shadow: inset 3px 0 0 var(--pulse-bad); }
.pulse-steps tr.is-finish td { background: rgba(31, 122, 54, 0.04); }
.pulse-steps tr.is-finish td:first-child { box-shadow: inset 3px 0 0 var(--pulse-good); }

/* The two callouts: biggest drop, longest screen. */
.pulse-callout { display: flex; gap: 20px; padding: 20px; align-items: flex-start; }
.pulse-callout-body { min-width: 0; }
.pulse-callout-figure { font-size: 38px; font-weight: 500; letter-spacing: -0.02em; line-height: 1.05; }
.pulse-callout-label { font-size: 13px; color: var(--text-secondary); margin-top: 6px; line-height: 1.45; }
.pulse-callout-note { font-size: 12.5px; color: var(--text-tertiary); margin-top: 8px; line-height: 1.45; }
.pulse-mini { list-style: none; margin: 10px 0 0; padding: 0; font-size: 12.5px; }
.pulse-mini li { padding: 3px 0; color: var(--text-secondary); }
.pulse-mini b { color: var(--pulse-ink); font-variant-numeric: tabular-nums; }

/* When they gave up. */
.pulse-hours { display: flex; align-items: flex-end; gap: 3px; height: 120px; }
.pulse-hour { flex: 1; display: flex; flex-direction: column; justify-content: flex-end; align-items: center; height: 100%; }
.pulse-hour-stack {
  width: 100%; background: rgba(0,0,0,0.12); border-radius: 3px 3px 0 0;
  display: flex; flex-direction: column; justify-content: flex-end; min-height: 2px;
}
.pulse-hour-lost { width: 100%; background: var(--pulse-ink); border-radius: 3px 3px 0 0; }
.pulse-hour-tick { font-size: 9.5px; color: var(--text-tertiary); margin-top: 4px; height: 12px; }
.pulse-errbar-fill.is-neutral { background: var(--pulse-ink); opacity: 0.55; }

/* The filmstrip: every screen of the flow, in order. */
.pulse-film {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(196px, 1fr)); gap: 20px; padding: 20px;
}
.pulse-film-cell { margin: 0; min-width: 0; }
.pulse-film-cell figcaption { margin-top: 9px; font-size: 12px; line-height: 1.4; }
.pulse-film-cell figcaption b { display: block; font-weight: 500; font-family: var(--font-mono); font-size: 11.5px; color: var(--pulse-ink); }
.pulse-film-cell figcaption span { color: var(--text-tertiary); }

@media (max-width: 820px) {
  .pulse-callout { flex-direction: column; }
  .pulse-shot.is-hero { width: 132px; height: 210px; }
  .pulse-fshot { display: none; }
  .pulse-steps th.pulse-fshot { display: none; }
}

/* ---------------------------------------------------------------------------
   Recomputing
   ---------------------------------------------------------------------------
   A filter change dims what is on screen rather than replacing it. The 200ms
   delay on the transition means a slice that answers from cache never flashes:
   the dim starts only once the wait is long enough to be worth admitting to.
   Under a second, a person does not want feedback, they want the answer. */
.pulse-flow-body { transition: opacity 0.2s 0.2s linear; }
/* What the two control rows currently add up to, in a sentence. The cohort
   pills and the situation menu are different axes - who the visitor was, and
   why the partner sent them - and nothing on screen said so. */
.pulse-flowbar-says {
  margin: 8px 0 0; font-size: 12.5px; line-height: 1.45;
  color: var(--pulse-ink-soft);
}

.pulse-flow-body.is-stale { opacity: 0.45; pointer-events: none; }
.pulse-recomputing {
  display: none; align-items: center; gap: 8px;
  margin: 0 0 12px; font-size: 13px; color: var(--pulse-ink-soft);
}
/* Only once the wait is genuinely long does it earn a line of its own. */
.pulse-flow-body.is-slow .pulse-recomputing { display: flex; }
.pulse-recomputing::before {
  content: ''; width: 11px; height: 11px; border-radius: 50%;
  border: 2px solid var(--pulse-hair-strong); border-top-color: var(--pulse-ink);
  animation: pulse-spin 0.7s linear infinite;
}
@keyframes pulse-spin { to { transform: rotate(360deg); } }

/* First load only: the shape of what is coming, so nothing jumps when it
   lands. Never painted over a chart that already has numbers on it. */
.pulse-flow-loading { font-size: 13px; color: var(--pulse-ink-soft); margin-bottom: 14px; }
.pulse-sk-kpis { display: grid; grid-template-columns: repeat(4, 1fr); gap: 12px; margin-bottom: 18px; }
.pulse-sk-kpi { height: 118px; border-radius: 12px; border: 1px solid var(--pulse-hair); }
.pulse-sk-card { border: 1px solid var(--pulse-hair); border-radius: 12px; padding: 4px 16px; }
.pulse-sk-row { display: flex; align-items: center; gap: 18px; padding: 16px 0; border-bottom: 1px solid var(--pulse-hair); }
.pulse-sk-row:last-child { border-bottom: 0; }
.pulse-sk-shot { width: 108px; height: 207px; border-radius: 10px; flex: none; }
.pulse-sk-lines { display: flex; flex-direction: column; gap: 8px; width: 240px; flex: none; }
.pulse-sk-line { height: 11px; border-radius: 3px; display: block; }
.pulse-sk-line.is-w40 { width: 40%; }
.pulse-sk-line.is-w70 { width: 70%; }
.pulse-sk-bar { height: 8px; border-radius: 2px; }
.pulse-sk-shot, .pulse-sk-line, .pulse-sk-bar, .pulse-sk-kpi {
  background: linear-gradient(90deg, rgba(0,0,0,0.045) 25%, rgba(0,0,0,0.075) 37%, rgba(0,0,0,0.045) 63%);
  background-size: 400% 100%;
  animation: pulse-sheen 1.5s ease-in-out infinite;
}
.pulse-sk-kpi { background-clip: padding-box; }
@keyframes pulse-sheen { 0% { background-position: 100% 50%; } 100% { background-position: 0 50%; } }

/* Motion is decoration here; the dim and the layout carry the meaning. */
@media (prefers-reduced-motion: reduce) {
  .pulse-sk-shot, .pulse-sk-line, .pulse-sk-bar, .pulse-sk-kpi { animation: none; }
  .pulse-recomputing::before { animation: none; }
  .pulse-flow-body { transition: none; }
}

/* ---------------------------------------------------------------------------
   Why a mailbox fill failed
   ---------------------------------------------------------------------------
   The status chip opens the reason. A row that says "Fill failed" and stops
   there sends the reader to the database to find out what happened, which is
   the errand this board exists to save. Click, not hover: the reason is a
   sentence to read, not a label to glance at, and it has to survive on touch. */
.pulse-why-wrap { position: relative; display: inline-flex; }
.pulse-chip.is-why {
  font: inherit; cursor: pointer; border: 0;
  display: inline-flex; align-items: center; gap: 5px;
  transition: filter 0.15s linear;
}
.pulse-chip.is-why:hover { filter: brightness(0.94); }
.pulse-chip.is-why:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 2px; }
.pulse-why-mark {
  display: inline-flex; align-items: center; justify-content: center;
  width: 13px; height: 13px; border-radius: 50%;
  font-size: 9px; font-weight: 700; line-height: 1;
  background: currentColor; color: #FFFFFF; opacity: 0.55;
}
.pulse-chip.is-why:hover .pulse-why-mark,
.pulse-why-wrap.is-open .pulse-why-mark { opacity: 0.9; }

.pulse-why {
  /* Opens to the LEFT of the chip, not below it. Below, a 320px note lands
     exactly on top of the next row's chip in the same column, so the obvious
     next click — the next failure — hits the note instead and nothing happens.
     Beside it, the whole status column stays reachable while one is open. */
  position: absolute; right: calc(100% + 10px); top: -8px; z-index: 40;
  display: none; width: 320px; max-width: 64vw; padding: 11px 13px 10px;
  background: #FFFFFF; color: var(--pulse-ink);
  border: 1px solid var(--pulse-hair-strong);
  border-radius: 10px; box-shadow: 0 10px 28px rgba(0, 0, 0, 0.15);
  text-align: left; white-space: normal; cursor: text;
}
.pulse-why-wrap.is-open .pulse-why { display: block; }
.pulse-why-head {
  display: block; font-size: 11px; font-weight: 600; letter-spacing: 0.04em;
  text-transform: uppercase; color: var(--pulse-ink-soft); margin-bottom: 6px;
}
.pulse-why-head .is-muted { text-transform: none; letter-spacing: 0; font-weight: 400; }
.pulse-why-body { display: block; font-size: 13px; line-height: 19px; }
.pulse-why-foot {
  display: block; margin-top: 8px; padding-top: 7px;
  border-top: 1px solid var(--pulse-hair);
  font-size: 12px; color: var(--pulse-ink-soft);
}

/* ---------------------------------------------------------------------------
   A count you can open
   ---------------------------------------------------------------------------
   Every counter in the Synthesis panel used to name a number and nobody. These
   are buttons: the number and the names behind it are one click apart rather
   than one database query apart. They still read as text, because a panel of
   buttons reads as a toolbar rather than as a summary. */
.pulse-stat.is-open-list {
  font: inherit; color: inherit; background: none; border: 0; padding: 0;
  cursor: pointer; border-bottom: 1px dashed var(--pulse-hair-strong);
  transition: border-color 0.15s linear, color 0.15s linear;
}
.pulse-stat.is-open-list:hover { border-bottom-color: var(--pulse-ink); }
.pulse-stat.is-open-list:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 3px; border-radius: 3px; }
.pulse-stat.is-open-list.is-on { border-bottom: 1px solid var(--pulse-ink); }
.pulse-substats { padding-top: 2px; }
.pulse-stat.is-label { color: var(--text-tertiary); }

.pulse-drawer {
  border-top: 1px solid var(--pulse-hair);
  background: rgba(0, 0, 0, 0.014);
  transition: opacity 0.2s 0.2s linear;
}
.pulse-drawer.is-stale { opacity: 0.5; }
.pulse-drawer-head {
  display: flex; align-items: center; justify-content: space-between; gap: 12px;
  padding: 11px 16px 9px;
}
.pulse-drawer-title { font-size: 13px; font-weight: 550; }
.pulse-drawer-title .is-muted { font-weight: 400; }
.pulse-drawer-title .pulse-num { margin-left: 6px; font-variant-numeric: tabular-nums; color: var(--pulse-ink-soft); }
.pulse-drawer-loading, .pulse-drawer-more {
  padding: 4px 16px 13px; font-size: 12px; color: var(--pulse-ink-soft);
}
.pulse-drawer .pulse-list { background: transparent; }

/* ---------------------------------------------------------------------------
   How long it takes
   ---------------------------------------------------------------------------
   Every other number on the board is a count. These are the only durations,
   so they get room rather than being squeezed into a stat strip. Median and
   p90 sit together on purpose: on the current data they are 95 seconds and
   nine hours, and either one alone tells a lie about the other. */
.pulse-timings { display: grid; grid-template-columns: 1fr 1fr; }
.pulse-timing { padding: 16px 18px 17px; border-right: 1px solid var(--pulse-hair); }
.pulse-timing:last-child { border-right: 0; }
.pulse-timing-label {
  font-size: 11px; font-weight: 600; letter-spacing: 0.05em; text-transform: uppercase;
  color: var(--pulse-ink-soft); margin-bottom: 8px;
}
.pulse-timing-value {
  font-size: 30px; font-weight: 500; letter-spacing: -0.02em; line-height: 1.05;
  font-variant-numeric: tabular-nums;
}
.pulse-timing-foot { margin-top: 7px; font-size: 12px; line-height: 17px; color: var(--pulse-ink-soft); }
.pulse-timing-foot b { color: var(--pulse-ink); font-weight: 550; font-variant-numeric: tabular-nums; }
.pulse-timing-hint { margin-top: 6px; font-size: 12px; line-height: 17px; color: var(--text-tertiary); }
.pulse-timing-none { font-size: 13px; color: var(--pulse-ink-soft); padding: 6px 0 2px; }

.pulse-months { display: flex; align-items: flex-end; gap: 10px; padding: 14px 18px 16px; }
.pulse-month { display: flex; flex-direction: column; align-items: center; gap: 5px; flex: 1; max-width: 76px; }
.pulse-month-bar { width: 100%; background: var(--pulse-ink); opacity: 0.86; border-radius: 2px; }
.pulse-month-n { font-size: 12px; font-variant-numeric: tabular-nums; }
.pulse-month-label { font-size: 11px; color: var(--pulse-ink-soft); }

@media (max-width: 900px) {
  .pulse-timings { grid-template-columns: 1fr; }
  .pulse-timing { border-right: 0; border-bottom: 1px solid var(--pulse-hair); }
}

/* With a platform filter on, the panels that cannot be narrowed say so rather
   than letting the filter chip imply they were. */
.pulse-scope {
  display: inline-block; margin-left: 8px; padding: 1px 7px;
  border: 1px solid var(--pulse-hair-strong); border-radius: 999px;
  font-size: 11px; color: var(--pulse-ink-soft); vertical-align: 1px;
}

/* Switching platform asks the table a different question, so the previous
   platform's people leave and this stands in until the new ones arrive. */
.pulse-sk-people { padding: 6px 16px 14px; }
.pulse-sk-people-row {
  display: flex; align-items: center; gap: 24px;
  padding: 14px 0; border-bottom: 1px solid var(--pulse-hair);
}
.pulse-sk-people-row:last-child { border-bottom: 0; }
.pulse-sk-people-row .pulse-sk-line { height: 11px; }

/* ---------------------------------------------------------------------------
   Gideon
   ---------------------------------------------------------------------------
   THE MARK is a level meter: five bars in a rounded tile, moving the way a
   signal moves. Not a circle, not a face, not the glowing orb every assistant
   already has. It is the shape of what Gideon does, which is watch numbers
   change.

   Each bar runs on its own period, and the periods are deliberately not
   multiples of one another, so the pattern never visibly repeats. Only
   `transform` animates, which keeps the whole thing on the compositor while it
   sits in the corner of the page all day. */
.pulse-gid-mark { display: inline-block; flex: none; line-height: 0; }
.gid-meter {
  display: flex; align-items: center; justify-content: center;
  gap: 6.5%; width: 100%; height: 100%; padding: 0 13%;
  border-radius: 31%;
  background: linear-gradient(150deg, #3a3a3d 0%, #1b1b1d 55%, #0f0f10 100%);
  box-sizing: border-box;
}
.gid-bar {
  flex: 1 1 0; border-radius: 999px; background: #FFFFFF;
  height: 62%; transform-origin: 50% 50%;
  animation: gid-lvl 2.6s ease-in-out infinite;
}
/* Prime-ish periods and offsets: the five never line up, so it never loops. */
.gid-bar.b1 { opacity: 0.55; animation-duration: 2.3s;  animation-delay: -0.4s; }
.gid-bar.b2 { opacity: 0.78; animation-duration: 1.7s;  animation-delay: -1.1s; }
.gid-bar.b3 { opacity: 1;    animation-duration: 2.9s;  animation-delay: -0.2s; }
.gid-bar.b4 { opacity: 0.78; animation-duration: 1.9s;  animation-delay: -1.6s; }
.gid-bar.b5 { opacity: 0.55; animation-duration: 2.2s;  animation-delay: -0.8s; }
@keyframes gid-lvl {
  0%, 100% { transform: scaleY(0.30); }
  50%      { transform: scaleY(1); }
}

/* Working: taller, faster, brighter. */
.pulse-gid-mark.is-thinking .gid-bar { animation-duration: 0.62s; opacity: 1; }
.pulse-gid-mark.is-thinking .gid-bar.b1 { animation-duration: 0.54s; }
.pulse-gid-mark.is-thinking .gid-bar.b3 { animation-duration: 0.71s; }
.pulse-gid-mark.is-thinking .gid-bar.b5 { animation-duration: 0.58s; }
.pulse-gid-mark.is-streaming .gid-bar { animation-duration: 1.15s; }

/* The corner dock. Present on every view, out of the way until wanted. */
.pulse-gid-fab {
  position: fixed; right: 24px; bottom: 24px; z-index: 60;
  display: inline-flex; align-items: center; gap: 10px;
  padding: 7px 16px 7px 7px; border: 0; border-radius: 999px;
  background: #FFFFFF; color: var(--pulse-ink); font: inherit; font-size: 13.5px; font-weight: 500;
  box-shadow: 0 1px 2px rgba(0,0,0,.06), 0 8px 26px rgba(0, 0, 0, 0.14); cursor: pointer;
  transition: box-shadow 0.18s ease, transform 0.18s ease;
}
.pulse-gid-fab:hover { box-shadow: 0 1px 2px rgba(0,0,0,.06), 0 12px 34px rgba(0, 0, 0, 0.18); transform: translateY(-1px); }
.pulse-gid-fab:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 3px; }

/* Soft, not boxy. One rounded panel, a hairline instead of a border, and the
   weight carried by shadow rather than by outline. */
.pulse-gid-dock {
  position: fixed; right: 24px; bottom: 24px; z-index: 60;
  width: 420px; max-width: calc(100vw - 32px);
  max-height: min(660px, calc(100vh - 110px));
  display: flex; flex-direction: column;
  background: #FFFFFF; border-radius: 20px;
  box-shadow: 0 0 0 1px rgba(0,0,0,.05), 0 24px 60px rgba(0, 0, 0, 0.18);
  overflow: hidden;
  animation: gid-rise 0.2s cubic-bezier(0.2, 0, 0, 1);
}
@keyframes gid-rise { from { opacity: 0; transform: translateY(12px) scale(0.985); } }
.pulse-gid-dock-head {
  display: flex; align-items: center; justify-content: space-between;
  padding: 13px 14px 12px 16px; flex: none;
}
.pulse-gid-dock-acts { display: flex; align-items: center; gap: 12px; }
.pulse-gid-x {
  border: 0; background: none; font: inherit; font-size: 19px; line-height: 1;
  color: var(--pulse-ink-soft); cursor: pointer; padding: 0 2px;
}
.pulse-gid-x:hover { color: var(--pulse-ink); }
.pulse-gid-dock-body { flex: 1 1 auto; overflow-y: auto; }
.pulse-gid-who { display: flex; align-items: center; gap: 9px; font-size: 13px; font-weight: 550; }

/* The tab version: the same thread, given room.

   Height is measured rather than guessed. A fixed min-height pushed the
   composer below the fold on shorter windows, so the first thing you had to do
   on opening the tab was scroll to find the place to type. `--gid-top` is set
   from the panel's own distance from the top of the viewport, so it always
   ends exactly at the bottom edge whatever sits above it. */
.pulse-gid-page {
  display: flex; flex-direction: column;
  height: calc(100dvh - var(--gid-top, 320px));
  min-height: 380px;
}
.pulse-gid-page-body { flex: 1 1 auto; overflow-y: auto; padding: 10px 0 0; }
.pulse-gid-page .pulse-gid-thread { max-width: 720px; margin: 0 auto; }
.pulse-gid-page .pulse-gid-form { max-width: 720px; margin: 0 auto; width: 100%; }

/* Empty state. */
.pulse-gid-empty { padding: 48px 26px 40px; text-align: center; }
.pulse-gid-empty .pulse-gid-mark { margin: 0 auto 18px; }
.pulse-gid-hi { font-size: 17px; font-weight: 550; letter-spacing: -0.01em; margin-bottom: 7px; }
.pulse-gid-sub { font-size: 13.5px; line-height: 20px; color: var(--pulse-ink-soft); max-width: 420px; margin: 0 auto 20px; }
/* A 2x2 grid, not a centred wrap. Four chips of unequal width wrapped so the
   fourth sat alone and off-centre under the other three. */
.pulse-gid-chips {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 8px; max-width: 560px; margin: 0 auto;
}
@media (max-width: 460px) { .pulse-gid-chips { grid-template-columns: 1fr; } }
.pulse-gid-chip {
  font: inherit; font-size: 12.5px; color: var(--pulse-ink); background: #FFFFFF;
  border: 1px solid var(--pulse-hair); border-radius: 12px; padding: 7px 13px; cursor: pointer;
  text-align: left; transition: background 0.15s linear, border-color 0.15s linear;
}
.pulse-gid-chip:hover { background: var(--pulse-wash); border-color: var(--pulse-hair-strong); }

/* THE THREAD. Modelled on a conversation rather than a form: Gideon's words
   sit on the page with nothing drawn around them, because a box around every
   reply makes a transcript feel like a receipt. Only the person's own lines
   get a container, and a soft one. */
.pulse-gid-thread { padding: 8px 20px 10px; }
.pulse-gid-turn { margin-bottom: 26px; }
.pulse-gid-turn:last-child { margin-bottom: 14px; }
.pulse-gid-turn.is-you { display: flex; justify-content: flex-end; }
.pulse-gid-bubble {
  background: var(--pulse-wash); color: var(--pulse-ink);
  border-radius: 18px; padding: 10px 15px;
  font-size: 14px; line-height: 21px; max-width: 84%;
  white-space: pre-wrap; word-break: break-word;
}
.pulse-gid-turn.is-gid .pulse-gid-who { margin-bottom: 10px; color: var(--pulse-ink-soft); font-weight: 500; }
.pulse-gid-say { font-size: 14.5px; line-height: 24px; letter-spacing: -0.003em; }
.pulse-gid-say p { margin: 0 0 14px; }
.pulse-gid-say p:last-child { margin-bottom: 0; }
.pulse-gid-say ul { margin: 0 0 14px; padding-left: 20px; }
.pulse-gid-say li { margin-bottom: 6px; }
.pulse-gid-say code {
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace; font-size: 12.5px;
  background: var(--pulse-wash); padding: 1px 5px; border-radius: 5px;
}
.pulse-gid-say b { font-weight: 600; }

/* A tool call while it runs. */
.pulse-gid-tools { margin-bottom: 12px; display: flex; flex-direction: column; gap: 6px; }
.pulse-gid-tool {
  display: flex; align-items: center; gap: 9px; font-size: 12.5px;
  color: var(--pulse-ink-soft);
}
/* Only a row being seen for the FIRST time animates in. These rows are
   re-created by every paint, so animating the bare class replayed the
   entrance on every rebuild — the tool name visibly flashing. */
.pulse-gid-tool.is-new {
  animation: gid-tool-in 0.24s cubic-bezier(0.2, 0, 0, 1);
}
@keyframes gid-tool-in { from { opacity: 0; transform: translateY(3px); } }
.pulse-gid-tool-dot {
  width: 6px; height: 6px; border-radius: 50%; background: var(--pulse-ink); flex: none;
  animation: gid-pulse 1.1s ease-in-out infinite;
}
.pulse-gid-tool.is-done .pulse-gid-tool-dot { animation: none; opacity: 0.28; }
@keyframes gid-pulse { 0%, 100% { opacity: 0.22; transform: scale(0.75); } 50% { opacity: 1; transform: scale(1.15); } }
.pulse-gid-tool-detail { color: var(--text-tertiary); }

.pulse-gid-caret {
  display: inline-block; width: 7px; height: 15px; margin-left: 3px;
  background: var(--pulse-ink); vertical-align: -3px; border-radius: 1px;
  animation: gid-blink 1s steps(2, start) infinite;
}
@keyframes gid-blink { 50% { opacity: 0; } }

/* THE COMPOSER grows with what you type, the way a message box does, up to
   about six lines before it scrolls. The send button sits inside the field
   rather than beside it, so the whole thing reads as one control. */
.pulse-gid-form { flex: none; padding: 8px 14px 14px; background: #FFFFFF; }
.pulse-gid-form.is-big { padding: 12px 16px 18px; }
.pulse-gid-field {
  display: flex; align-items: flex-end; gap: 8px;
  border: 1px solid var(--pulse-hair-strong); border-radius: 22px;
  padding: 7px 7px 7px 16px; background: #FFFFFF;
  transition: border-color 0.15s linear, box-shadow 0.15s linear;
}
.pulse-gid-field:focus-within {
  border-color: rgba(54, 54, 54, 0.45);
  box-shadow: 0 0 0 3px rgba(54, 54, 54, 0.06);
}
.pulse-gid-input {
  flex: 1 1 auto; font: inherit; font-size: 14px; line-height: 21px; color: var(--pulse-ink);
  border: 0; outline: none; background: none; resize: none; overflow-y: auto;
  padding: 5px 0; max-height: 168px;
}
/* The console gives every textarea a blue focus ring. Here the ring belongs on
   the pill around the field, not on the field inside it, or you get a
   rectangle drawn inside a rounded control. The indicator is not removed, it
   moves: `.pulse-gid-field:focus-within` above carries it. */
.pulse-gid-input:focus,
.pulse-gid-input:focus-visible { outline: none; box-shadow: none; }
.pulse-gid-input::placeholder { color: var(--pulse-ink-soft); }
.pulse-gid-input:disabled { color: var(--pulse-ink-soft); }
.pulse-gid-send {
  flex: none; width: 32px; height: 32px; border-radius: 50%; border: 0; cursor: pointer;
  background: var(--pulse-ink); color: #FFFFFF; display: inline-flex; align-items: center; justify-content: center;
  transition: opacity 0.15s linear, transform 0.15s ease;
}
.pulse-gid-send svg { width: 16px; height: 16px; }
.pulse-gid-send:hover:not(:disabled) { transform: scale(1.06); }
.pulse-gid-send:disabled { opacity: 0.25; cursor: default; }

@media (prefers-reduced-motion: reduce) {
  .gid-bar, .pulse-gid-tool-dot,
  .pulse-gid-caret, .pulse-gid-dock, .pulse-gid-tool { animation: none; }
  /* Parked at a readable level rather than collapsed to a line. */
  .gid-bar { transform: scaleY(0.62); }
  .pulse-gid-send:hover:not(:disabled) { transform: none; }
}

/* Elapsed time on a tool row, only once there is something worth saying. */
.pulse-gid-tool-took { margin-left: auto; color: var(--text-tertiary); font-variant-numeric: tabular-nums; }

/* What an answer can contain. A heading in a reply is emphasis, not a document
   heading: an <h2> inside a chat panel outranks the page it sits on. */
.pulse-gid-h { font-weight: 600; font-size: 14.5px; margin: 16px 0 8px; letter-spacing: -0.01em; }
.pulse-gid-say > .pulse-gid-h:first-child { margin-top: 0; }
.pulse-gid-rule { border: 0; border-top: 1px solid var(--pulse-hair); margin: 16px 0; }
.pulse-gid-say ol { margin: 0 0 14px; padding-left: 22px; }
.pulse-gid-tablewrap { overflow-x: auto; margin: 0 0 14px; }
.pulse-gid-table { border-collapse: collapse; width: 100%; font-size: 13px; }
.pulse-gid-table th {
  text-align: left; font-weight: 600; font-size: 11px; letter-spacing: 0.04em;
  text-transform: uppercase; color: var(--pulse-ink-soft);
  padding: 0 14px 7px 0; white-space: nowrap;
}
.pulse-gid-table td {
  padding: 7px 14px 7px 0; border-top: 1px solid var(--pulse-hair);
  font-variant-numeric: tabular-nums; vertical-align: top;
}
.pulse-gid-table tr td:first-child { color: var(--pulse-ink); }

/* Stop, and what is waiting behind it. */
.pulse-gid-send.is-stop { background: var(--pulse-ink); }
.pulse-gid-send.is-stop:hover { transform: scale(1.06); }
.pulse-gid-queued {
  display: flex; align-items: center; gap: 7px;
  margin: 0 4px 8px; padding: 6px 12px; border-radius: 10px;
  background: var(--pulse-wash); color: var(--pulse-ink-soft);
  font-size: 12.5px; line-height: 17px;
}
.pulse-gid-queued::before {
  content: ''; width: 5px; height: 5px; border-radius: 50%;
  background: var(--pulse-ink-soft); flex: none; opacity: 0.6;
}
.pulse-gid-stopped {
  margin-top: 10px; font-size: 12.5px; color: var(--pulse-ink-soft);
}

/* HIS WORKING — folded by default. It is context for when you want it, never
   something you must read to get the answer, so it is quieter than the answer
   and never expands on its own. */
.pulse-gid-think { margin: 2px 0 6px; }
.pulse-gid-think-toggle {
  display: inline-flex; align-items: center; gap: 6px;
  background: none; border: 0; padding: 2px 0; cursor: pointer;
  font: inherit; font-size: 12px; color: var(--pulse-ink-soft);
  transition: color 0.15s ease;
}
.pulse-gid-think-toggle:hover { color: var(--pulse-ink); }
.pulse-gid-think-caret {
  width: 0; height: 0; display: inline-block;
  border-left: 4px solid currentColor;
  border-top: 3.5px solid transparent; border-bottom: 3.5px solid transparent;
  transition: transform 0.15s ease;
}
.pulse-gid-think.is-open .pulse-gid-think-caret { transform: rotate(90deg); }
.pulse-gid-think-body {
  margin-top: 6px; padding: 8px 10px;
  border-left: 2px solid var(--pulse-line);
  font-size: 12.5px; line-height: 1.55; color: var(--pulse-ink-soft);
  white-space: pre-wrap; max-height: 320px; overflow-y: auto;
}
@media (prefers-reduced-motion: reduce) {
  .pulse-gid-think-toggle, .pulse-gid-think-caret { transition: none; }
}

/* CHARTS IN AN ANSWER — drawn from a ```chart fence with the board's own
   primitives: same ink, same hairlines, same axis type. */
.pulse-gid-chart { margin: 6px 0 16px; padding: 12px 14px 10px; border: 1px solid var(--pulse-hair); border-radius: var(--pulse-radius); background: #FFFFFF; }
.pulse-gid-chart figcaption { font-size: 12.5px; font-weight: 550; color: var(--pulse-ink); margin: 0 0 8px; }
.pulse-gid-chart svg { display: block; width: 100%; height: auto; max-height: 440px; }
.pulse-gid-chart.is-donut svg { width: 160px; height: 160px; }
.pulse-gid-chart.is-drawing { border-style: dashed; color: var(--pulse-ink-soft); font-size: 12.5px; padding: 14px; }
.pulse-gid-chart-line { fill: none; stroke: var(--pulse-ink); stroke-width: 2; stroke-linejoin: round; stroke-linecap: round; }
.pulse-gid-chart-dot { fill: #FFFFFF; stroke: var(--pulse-ink); stroke-width: 2; }
.pulse-gid-chart-dot:hover { fill: var(--pulse-ink); }
.pulse-gid-slice { fill: var(--pulse-ink); }
.pulse-gid-chart-total { fill: var(--pulse-ink); font-size: 20px; font-weight: 600; font-family: var(--font-family); font-variant-numeric: tabular-nums; }
.pulse-gid-glyph.is-on { fill: var(--pulse-ink); }
.pulse-gid-glyph.is-off { fill: var(--pulse-wash-strong); }
.pulse-gid-legend { list-style: none; margin: 8px 0 0; padding: 0; display: flex; flex-wrap: wrap; gap: 6px 16px; font-size: 12.5px; color: var(--pulse-ink-soft); }
.pulse-gid-legend li { display: inline-flex; align-items: center; gap: 7px; }
.pulse-gid-legend b { color: var(--pulse-ink); font-weight: 550; font-variant-numeric: tabular-nums; }
.pulse-gid-swatch { width: 10px; height: 10px; border-radius: 3px; background: var(--pulse-ink); display: inline-block; flex: none; }
.pulse-gid-pre { margin: 0 0 14px; padding: 10px 12px; background: var(--pulse-wash); border-radius: 8px; overflow-x: auto; font-family: ui-monospace, SFMono-Regular, Menlo, monospace; font-size: 12.5px; line-height: 1.5; white-space: pre; }
.pulse-gid-pre code { background: none; padding: 0; font-size: inherit; }

/* A side door in the funnel table: reported, but visibly not a step. */
.pulse-frow-detour td { background: var(--pulse-wash); }
.pulse-frow-detour .pulse-step-name { color: var(--pulse-ink-soft); }

/* ---------------------------------------------------------------------------
 * The design split (renderDesignSplit): one group per step, new design first,
 * classic right under it. The pill carries identity with a word, never colour alone.
 * ------------------------------------------------------------------------- */
.pulse-dsplit .pulse-dgroup td {
  padding: 18px 12px 6px;
  font-size: 12px;
  font-weight: 600;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--pulse-ink-soft);
  border-bottom: 1px solid var(--pulse-hair);
}
.pulse-dsplit .pulse-drow.is-legacy td { background: var(--pulse-wash); }
.pulse-dsplit .pulse-drow.is-absent td { padding-top: 8px; padding-bottom: 8px; font-size: 13px; }
.pulse-dpill {
  display: inline-block;
  padding: 2px 8px;
  border-radius: 999px;
  font-size: 12px;
  font-weight: 600;
  line-height: 18px;
  border: 1px solid var(--pulse-hair-strong);
  color: var(--pulse-ink);
  background: transparent;
}
.pulse-dpill.is-v6 { border-color: var(--pulse-ink); }
.pulse-dpill.is-legacy { color: var(--pulse-ink-soft); }
.pulse-dhead { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; padding: 14px 16px; border-bottom: 1px solid var(--pulse-hair); }
.pulse-dhead-col { display: flex; flex-direction: column; gap: 6px; }
.pulse-dhead-col .pulse-dpill { align-self: flex-start; }
.pulse-dhead-line { font-size: 14px; color: var(--pulse-ink); }
.pulse-dhead-line .pulse-num { font-size: 18px; margin-right: 4px; }
@media (max-width: 640px) { .pulse-dhead { grid-template-columns: 1fr; } }

/* The platforms table fits the page instead of scrolling sideways (Manuel, Sep 28 2026: "I hate horizontal scroll"):
   headers wrap, names are narrower, and the three least-used columns step aside on narrower screens. */
.pulse-table th { white-space: normal; }
.pulse-plat-name { max-width: 180px; }
@media (max-width: 1280px) { .pulse-table .is-opt { display: none; } }

/* One person (renderPersonPanel): a side panel over either page, closed with Close or Escape. */
.pulse-person-link { all: unset; cursor: pointer; color: inherit; font: inherit; text-decoration: underline; text-decoration-color: var(--pulse-hair-strong); text-underline-offset: 2px; }
.pulse-person-link:hover, .pulse-person-link:focus-visible { text-decoration-color: currentColor; }
.pulse-table tbody tr.pulse-person-row { cursor: pointer; }
.pulse-table tbody tr.pulse-person-row:hover { background: rgba(0,0,0,0.035); }
.pulse-person-row:hover .pulse-person-link { text-decoration-color: currentColor; }
.pulse-pp-host { padding: 0; position: fixed; inset: 0; z-index: 60; pointer-events: none; }
.pulse-pp-host.is-open { pointer-events: auto; }
html.pulse-pp-lock, html.pulse-pp-lock body { overflow: hidden; }
.pulse-pp-backdrop { position: absolute; inset: 0; background: rgba(17, 19, 24, 0.22); opacity: 0;
  backdrop-filter: blur(2px); -webkit-backdrop-filter: blur(2px); transition: opacity 0.28s ease; }
.pulse-pp-host.is-open .pulse-pp-backdrop { opacity: 1; }
.pulse-person-panel { position: absolute; top: 0; right: 0; bottom: 0; width: min(560px, 100vw); overflow-y: auto; overscroll-behavior: contain;
  background: #FFFFFF; box-shadow: -24px 0 60px rgba(17, 19, 24, 0.14), -1px 0 0 var(--pulse-hair);
  transform: translateX(104%); transition: transform 0.34s cubic-bezier(0.22, 1, 0.36, 1); outline: none; }
.pulse-pp-host.is-open .pulse-person-panel, .pulse-person-panel.is-open { transform: none; }
@media (prefers-reduced-motion: reduce) { .pulse-person-panel, .pulse-pp-backdrop { transition: none; } }
/* The drawer takes focus on open (keyboard, Escape); it is a surface, not a control, so no ring around it. */
#pulse-person-host .pulse-person-panel:focus, #pulse-person-host .pulse-person-panel:focus-visible { outline: none; box-shadow: -24px 0 60px rgba(17, 19, 24, 0.14), -1px 0 0 var(--pulse-hair); }

.pulse-pp-head { position: sticky; top: 0; z-index: 1; display: flex; gap: 14px; align-items: flex-start; padding: 22px 24px 16px;
  background: rgba(255, 255, 255, 0.92); backdrop-filter: saturate(1.4) blur(10px); -webkit-backdrop-filter: saturate(1.4) blur(10px);
  border-bottom: 1px solid var(--pulse-hair); }
.pulse-pp-avatar { flex: none; width: 44px; height: 44px; border-radius: 50%; display: grid; place-items: center; font-size: 15px; font-weight: 600;
  letter-spacing: 0.02em; color: var(--pulse-ink); background: linear-gradient(145deg, #F2F2F4, #E6E6EA); box-shadow: inset 0 0 0 1px rgba(0, 0, 0, 0.05); }
.pulse-pp-ident { flex: 1; min-width: 0; }
.pulse-pp-name { font-size: 17px; font-weight: 600; line-height: 1.3; letter-spacing: -0.01em; overflow-wrap: anywhere; }
.pulse-pp-who { margin-top: 3px; font-size: 13px; color: var(--pulse-ink-soft); overflow-wrap: anywhere; }
.pulse-pp-plats { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 10px; }
.pulse-pp-plat { display: inline-flex; align-items: center; gap: 6px; padding: 3px 10px 3px 4px; border-radius: 999px; background: var(--pulse-wash);
  font-size: 12.5px; font-weight: 500; }
.pulse-pp-plat .pulse-plat-mark { width: 20px; height: 20px; }
.pulse-pp-plat-when { color: var(--pulse-ink-soft); font-weight: 400; }
.pulse-pp-close { flex: none; width: 32px; height: 32px; border-radius: 50%; border: 0; display: grid; place-items: center; cursor: pointer;
  background: var(--pulse-wash); color: var(--pulse-ink); transition: background 0.15s ease, transform 0.15s ease; }
.pulse-pp-close:hover { background: var(--pulse-wash-strong); }
.pulse-pp-close:active { transform: scale(0.94); }
.pulse-pp-close:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 2px; }

.pulse-pp-body { padding: 18px 24px 40px; display: grid; gap: 14px; }
.pulse-pp-stats { display: grid; grid-template-columns: repeat(4, 1fr); gap: 8px; }
.pulse-pp-stat { padding: 10px 12px; border-radius: 12px; background: var(--pulse-wash); }
.pulse-pp-stat b { display: block; font-size: 18px; font-weight: 600; font-variant-numeric: tabular-nums; letter-spacing: -0.01em; }
.pulse-pp-stat span { font-size: 12px; color: var(--pulse-ink-soft); }
.pulse-pp-sec { border: 1px solid var(--pulse-hair); border-radius: 14px; padding: 14px 16px; background: #FFFFFF; }
.pulse-pp-sec h3 { display: flex; align-items: center; gap: 8px; font-size: 11.5px; font-weight: 600; text-transform: uppercase; letter-spacing: 0.06em;
  color: var(--pulse-ink-soft); margin: 0 0 10px; }
.pulse-pp-count { font-variant-numeric: tabular-nums; color: var(--pulse-ink); }
.pulse-pp-none { font-size: 13px; color: var(--pulse-ink-soft); }
.pulse-pp-rows { list-style: none; margin: 0; padding: 0; display: grid; }
.pulse-pp-row { display: flex; gap: 12px; align-items: center; justify-content: space-between; padding: 10px 0; border-top: 1px solid var(--pulse-hair); font-size: 13.5px; }
.pulse-pp-row:first-child { border-top: 0; padding-top: 2px; }
.pulse-pp-row-main { min-width: 0; display: grid; gap: 4px; justify-items: start; }
.pulse-pp-row-side { flex: none; }
.pulse-pp-meta { font-size: 12.5px; color: var(--pulse-ink-soft); overflow-wrap: anywhere; }
.pulse-pp-when { color: var(--pulse-ink-soft); }
.pulse-pp-replay { display: inline-flex; align-items: center; gap: 6px; padding: 6px 12px; border-radius: 999px; background: var(--pulse-ink); color: #FFFFFF !important;
  font-size: 12.5px; font-weight: 500; text-decoration: none; white-space: nowrap; transition: transform 0.15s ease, opacity 0.15s ease; }
.pulse-pp-replay + .pulse-pp-replay { margin-left: 6px; }
.pulse-pp-replay:hover { opacity: 0.88; }
.pulse-pp-replay:active { transform: scale(0.97); }
.pulse-pp-replay span { opacity: 0.7; font-variant-numeric: tabular-nums; }
.pulse-pp-lead { font-size: 13.5px; margin-bottom: 8px; }
.pulse-pp-mems { list-style: none; margin: 0; padding: 0; display: grid; gap: 2px; }
.pulse-pp-mem { padding: 8px 10px; border-radius: 10px; font-size: 13.5px; line-height: 1.45; overflow-wrap: anywhere; }
.pulse-pp-mem:hover { background: var(--pulse-wash); }
.pulse-pp-mem .pulse-pp-meta { margin-top: 2px; }
.pulse-pp-more summary { cursor: pointer; font-size: 12.5px; font-weight: 500; padding: 6px 10px; color: var(--pulse-ink); list-style: none; }
.pulse-pp-more summary::-webkit-details-marker { display: none; }
.pulse-pp-more summary::before { content: "+ "; color: var(--pulse-ink-soft); }
.pulse-pp-more[open] summary::before { content: "− "; }

.pulse-pp-doc { border-top: 1px solid var(--pulse-hair); }
.pulse-pp-doc:first-child { border-top: 0; }
.pulse-pp-doc summary { cursor: pointer; list-style: none; display: flex; justify-content: space-between; gap: 12px; align-items: baseline;
  padding: 10px 0; font-size: 14px; font-weight: 600; }
.pulse-pp-doc summary::-webkit-details-marker { display: none; }
.pulse-pp-doc summary .pulse-pp-when { font-size: 12px; font-weight: 400; }
.pulse-pp-prose { font-size: 14px; line-height: 1.6; color: var(--pulse-ink); padding-bottom: 12px; overflow-wrap: anywhere; }
.pulse-pp-prose h4 { font-size: 13px; font-weight: 600; margin: 16px 0 6px; letter-spacing: -0.005em; }
.pulse-pp-prose h4:first-child { margin-top: 2px; }
.pulse-pp-prose p { margin: 0 0 10px; }
.pulse-pp-prose ul, .pulse-pp-prose ol { margin: 0 0 10px; padding-left: 20px; }
.pulse-pp-prose li { margin: 3px 0; }
.pulse-pp-prose li::marker { color: var(--pulse-ink-soft); }
.pulse-pp-prose strong { font-weight: 600; }
.pulse-pp-prose em { color: var(--pulse-ink-soft); }
.pulse-pp-prose hr { border: 0; border-top: 1px solid var(--pulse-hair); margin: 14px 0; }
.pulse-pp-prose code { font-size: 12.5px; padding: 1px 5px; border-radius: 5px; background: var(--pulse-wash); }

.pulse-pp-tech summary { cursor: pointer; list-style: none; }
.pulse-pp-tech summary::-webkit-details-marker { display: none; }
.pulse-pp-tech summary h3 { margin: 0; }
.pulse-pp-tech summary h3::after { content: "Show"; margin-left: auto; text-transform: none; letter-spacing: 0; font-weight: 500; }
.pulse-pp-tech[open] summary h3::after { content: "Hide"; }
.pulse-pp-tech[open] summary h3 { margin-bottom: 10px; }
.pulse-pp-dl { display: grid; grid-template-columns: max-content 1fr; gap: 6px 14px; font-size: 13px; margin: 0; }
.pulse-pp-dl dt { color: var(--pulse-ink-soft); }
.pulse-pp-dl dd { margin: 0; overflow-wrap: anywhere; }
.pulse-pp-skel { display: grid; gap: 10px; }
.pulse-pp-skel span { display: block; height: 58px; border-radius: 14px; background: linear-gradient(90deg, var(--pulse-wash) 0%, var(--pulse-wash-strong) 50%, var(--pulse-wash) 100%);
  background-size: 200% 100%; animation: pulse-pp-shimmer 1.2s ease-in-out infinite; }
@keyframes pulse-pp-shimmer { from { background-position: 100% 0; } to { background-position: -100% 0; } }
@media (max-width: 640px) {
  .pulse-person-panel { width: 100vw; }
  .pulse-pp-head { padding: 16px; }
  .pulse-pp-body { padding: 14px 16px 32px; }
  .pulse-pp-stats { grid-template-columns: repeat(2, 1fr); }
}
/* The arrivals chart, stacked: linked since (ink) inside the day's arrivals (soft). */
.pulse-chart-bar.is-linked { fill: var(--pulse-ink); }
.pulse-chart-legend { display: flex; gap: 16px; font-size: 12px; color: var(--pulse-ink-soft); margin: 0 0 8px; }
.pulse-chart-legend span { display: inline-flex; align-items: center; gap: 6px; }
.pulse-chart-legend i { width: 10px; height: 10px; border-radius: 3px; display: inline-block; }
.pulse-chart-legend i.is-linked { background: var(--pulse-ink); }
.pulse-chart-legend i.is-soft { background: rgba(54, 54, 54, 0.28); }
.pulse-src-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 10px; }
.pulse-src-row { display: grid; grid-template-columns: minmax(120px, 180px) 1fr auto; gap: 14px; align-items: center; font-size: 13px; }
.pulse-src-name { display: flex; align-items: center; gap: 8px; min-width: 0; }
.pulse-src-name span:last-child { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.pulse-src-bar { position: relative; height: 10px; border-radius: 5px; background: transparent; }
.pulse-src-all, .pulse-src-linked { position: absolute; left: 0; top: 0; bottom: 0; border-radius: 5px; }
.pulse-src-all { background: rgba(54, 54, 54, 0.28); }
.pulse-src-linked { background: var(--pulse-ink); }
.pulse-src-n { font-size: 12.5px; white-space: nowrap; text-align: right; }


/* The Unlinked tab's "Not counted" line: what the smaller number leaves out. */
.pulse-people-note { padding: 10px 16px; font-size: 12.5px; color: var(--text-tertiary); border-bottom: 1px solid var(--pulse-hair); }

/* Assistant marks in the person drawer (Imports, Memories): each source's own logo on a soft tile tinted
   toward its brand, so "Claude 17" reads at a glance instead of "imported from Claude" on every line. */
.pulse-src-mark { flex: none; display: inline-grid; place-items: center; width: 36px; height: 36px; border-radius: 10px;
  background: #fff; box-shadow: inset 0 0 0 1px var(--pulse-hair), 0 1px 2px rgba(0, 0, 0, 0.04); }
.pulse-src-mark svg { width: 20px; height: 20px; display: block; }
.pulse-src-mark[data-src="claude"] { background: #FAF3EE; box-shadow: inset 0 0 0 1px rgba(217, 119, 87, 0.22); }
.pulse-src-mark[data-src="chatgpt"] { background: #F4F4F4; }
.pulse-src-mark[data-src="gemini"] { background: #F1F5FF; box-shadow: inset 0 0 0 1px rgba(49, 134, 255, 0.18); }
.pulse-src-mark[data-src="perplexity"] { background: #EEF9FA; box-shadow: inset 0 0 0 1px rgba(34, 184, 205, 0.2); }
.pulse-src-mark.is-letter { font-size: 14px; font-weight: 600; color: var(--pulse-ink-soft); background: var(--pulse-wash); }
.pulse-src-mark.is-sm { width: 18px; height: 18px; border-radius: 5px; box-shadow: none; background: transparent; }
.pulse-src-mark.is-sm svg { width: 14px; height: 14px; }
.pulse-src-mark.is-sm.is-letter { font-size: 10px; background: var(--pulse-wash); }
.pulse-pp-row.pulse-pp-import { justify-content: flex-start; }
.pulse-pp-pills { display: flex; flex-wrap: wrap; gap: 6px; margin: 0 0 10px; }
.pulse-pp-pill { display: inline-flex; align-items: center; gap: 6px; padding: 3px 10px 3px 4px; border-radius: 999px;
  background: var(--pulse-wash); font-size: 12.5px; }
.pulse-pp-pill b { font-weight: 600; }
.pulse-pp-pill .pulse-plat-mark { width: 18px; height: 18px; }
.pulse-pp-from { display: inline-flex; align-items: center; gap: 4px; vertical-align: middle; }
.pulse-pp-from .pulse-plat-mark { width: 14px; height: 14px; }
.pulse-pp-from .pulse-src-mark.is-sm { width: 14px; height: 14px; }
.pulse-pp-from .pulse-src-mark.is-sm svg { width: 12px; height: 12px; }
/* The summary card: the one document shown open, in full, at reading size. */
.pulse-pp-summary { font-size: 14px; line-height: 1.6; margin-bottom: 8px; }

/* ---- Profile building / Errors and sign-in, rebuilt (Manuel, Sep 29: "this stuff is messy").
   Headline numbers are tiles; sections have a quiet label and space between them; causes and apps are
   drawn, not listed as dotted-underlined text. Spacing on the 4/8/12/16/24 scale. ---- */
.pulse-tiles { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 8px; padding: 16px; }
.pulse-tiles.is-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.pulse-tile { display: grid; align-content: start; gap: 4px; padding: 12px; border-radius: 10px; background: var(--pulse-wash);
  text-align: left; font: inherit; color: inherit; border: 0; min-width: 0; }
.pulse-tile.is-button { cursor: pointer; transition: background .15s ease, box-shadow .15s ease; }
.pulse-tile.is-button:hover { background: var(--pulse-wash-strong); }
.pulse-tile.is-button:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 2px; }
.pulse-tile.is-on { box-shadow: inset 0 0 0 1.5px var(--pulse-ink); }
.pulse-tile-n { font-size: 24px; font-weight: 600; letter-spacing: -0.02em; line-height: 1.1; display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.pulse-tile[data-tone="bad"] .pulse-tile-n { color: var(--pulse-bad); }
.pulse-tile[data-tone="warn"] .pulse-tile-n { color: var(--pulse-warn); }
.pulse-tile[data-tone="good"] .pulse-tile-n { color: var(--pulse-good); }
.pulse-tile-label { font-size: 12.5px; color: var(--text-secondary); }
.pulse-tile-sub { font-size: 12px; color: var(--text-tertiary); }
.pulse-tile-n .pulse-delta, .pulse-tile-n .pulse-chip { font-size: 12px; font-weight: 500; letter-spacing: 0; }
.pulse-sec { padding: 12px 16px 16px; border-top: 1px solid var(--pulse-hair); }
.pulse-sec-title { font-size: 11px; font-weight: 600; letter-spacing: 0.06em; text-transform: uppercase; color: var(--text-tertiary); margin-bottom: 12px; }
.pulse-sec-title.is-list { margin: 0; padding: 16px 16px 4px; border-top: 1px solid var(--pulse-hair); }
.pulse-sec-note { display: flex; flex-wrap: wrap; gap: 4px 16px; padding: 0 16px 12px; margin-top: -4px; }
.pulse-split { display: flex; height: 8px; border-radius: 999px; overflow: hidden; background: var(--pulse-wash); gap: 2px; }
.pulse-split span { display: block; height: 100%; min-width: 3px; }
.pulse-legend { display: flex; flex-wrap: wrap; gap: 4px 8px; margin-top: 12px; }
.pulse-legend-item { display: inline-flex; align-items: center; gap: 6px; padding: 4px 8px; border-radius: 8px; border: 0; background: transparent;
  font: inherit; font-size: 13px; color: var(--text-secondary); cursor: pointer; }
.pulse-legend-item:hover, .pulse-legend-item.is-on { background: var(--pulse-wash); color: var(--pulse-ink); }
.pulse-legend-item i { width: 8px; height: 8px; border-radius: 2px; flex: none; }
.pulse-legend-item b { font-weight: 600; color: var(--pulse-ink); }
.pulse-app-pills { display: flex; flex-wrap: wrap; gap: 8px; }
.pulse-app-pill { display: inline-flex; align-items: center; gap: 8px; padding: 4px 12px 4px 4px; border-radius: 999px; border: 1px solid var(--pulse-hair);
  background: #fff; font: inherit; font-size: 13px; color: var(--pulse-ink); cursor: pointer; transition: border-color .15s ease, background .15s ease; }
.pulse-app-pill:hover { border-color: var(--pulse-hair-strong); }
.pulse-app-pill.is-on { border-color: var(--pulse-ink); }
.pulse-app-pill b { font-weight: 600; }
.pulse-app-mark { flex: none; display: inline-grid; place-items: center; width: 32px; height: 32px; border-radius: 9px; background: #fff;
  box-shadow: inset 0 0 0 1px var(--pulse-hair); }
.pulse-app-mark svg { width: 18px; height: 18px; display: block; }
.pulse-app-mark.is-sm { width: 24px; height: 24px; border-radius: 999px; box-shadow: none; background: var(--pulse-wash); }
.pulse-app-mark.is-sm svg { width: 14px; height: 14px; }
.pulse-app-mark.is-letter { font-size: 13px; font-weight: 600; color: var(--text-secondary); background: var(--pulse-wash); }
.pulse-fail-list li { align-items: center; gap: 12px; padding: 12px 16px; }
.pulse-fail-who { font-size: 13.5px; font-weight: 500; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.pulse-fail-who .pulse-person-link { font-weight: 500; text-decoration: none; }
.pulse-fail-who .pulse-person-link:hover { text-decoration: underline; }
.pulse-fail-why { font-size: 13px; color: var(--pulse-bad); margin-top: 2px; }
.pulse-fail-meta { font-size: 12px; color: var(--text-tertiary); margin-top: 2px; }
.pulse-lane { display: grid; grid-template-columns: 112px minmax(0, 1fr) auto; align-items: center; gap: 12px; padding: 4px 0; font-size: 13px; }
.pulse-lane-name { color: var(--text-secondary); }
.pulse-lane-bar { height: 6px; border-radius: 999px; background: var(--pulse-wash-strong); overflow: hidden; }
.pulse-lane-bar span { display: block; height: 100%; background: var(--pulse-good); border-radius: 999px; }
.pulse-lane-n { color: var(--text-secondary); white-space: nowrap; font-variant-numeric: tabular-nums; }
.pulse-lane-n b { color: var(--pulse-ink); font-weight: 600; }
.pulse-lane-n .is-bad { color: var(--pulse-bad); }
.pulse-err-list li { padding: 10px 16px; }
.pulse-err-row { display: flex; align-items: baseline; gap: 8px; flex-wrap: wrap; }
.pulse-err-name { font-size: 13.5px; font-weight: 500; color: var(--pulse-ink); }
.pulse-err-key { font-size: 11px; color: var(--text-tertiary); background: none; padding: 0; }
.pulse-err-n { margin-left: auto; font-weight: 600; }
.pulse-err-list .pulse-errbar { margin-top: 6px; }
.pulse-pp-import .pulse-pp-row-side { margin-left: auto; }
@media (max-width: 640px) {
  .pulse-tiles, .pulse-tiles.is-3 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .pulse-lane { grid-template-columns: 1fr auto; }
  .pulse-lane-bar { grid-column: 1 / -1; grid-row: 2; }
}
.pulse-lane-note { font-size: 12px; color: var(--text-tertiary); }
/* The people behind a number: who, where they came from, and the app, each readable at a glance. */
.pulse-people-list li { align-items: center; }
.pulse-people-who .pulse-person-link { font-weight: 500; text-decoration: none; }
.pulse-people-who .pulse-person-link:hover { text-decoration: underline; }
.pulse-came-from { display: inline-flex; flex-wrap: wrap; gap: 6px; }
.pulse-came-plat { display: inline-flex; align-items: center; gap: 4px; padding: 1px 8px 1px 2px; border-radius: 999px; background: var(--pulse-wash); font-size: 12px; color: var(--text-secondary); }
.pulse-came-plat .pulse-plat-mark { width: 16px; height: 16px; }
.pulse-came-from.is-direct { font-size: 12px; color: var(--text-tertiary); }

/* ---- The hosted flow, by platform (rebuilt Sep 29). Step counts are the story: big tabular numbers, the funnel read
   left to right with the share that made it between steps, the largest loss marked. Near-monochrome; red only for the
   step that loses the most. ---- */
.pulse-jbar { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 12px; margin: 16px 0 16px; }
.pulse-pchips { display: flex; flex-wrap: wrap; gap: 8px; }
.pulse-pchip { display: inline-flex; align-items: center; gap: 8px; min-height: 36px; padding: 4px 14px 4px 6px; border-radius: 999px; border: 1px solid var(--pulse-hair);
  background: #fff; font: inherit; font-size: 13.5px; color: var(--pulse-ink); cursor: pointer; transition: border-color .15s ease, background .15s ease; }
.pulse-pchip:first-child { padding-left: 14px; }
.pulse-pchip:hover { border-color: var(--pulse-hair-strong); }
.pulse-pchip.is-on { background: var(--pulse-ink); border-color: var(--pulse-ink); color: #fff; }
.pulse-pchip .pulse-plat-mark { width: 24px; height: 24px; }
.pulse-pchip:focus-visible { outline: 2px solid var(--pulse-ink); outline-offset: 2px; }
.pulse-jtable td, .pulse-jtable th { white-space: nowrap; }
.pulse-jrow-name { display: flex; align-items: center; gap: 10px; font-weight: 500; }
.pulse-jrow-name .pulse-plat-mark { width: 28px; height: 28px; }
.pulse-rate-chip { display: inline-block; min-width: 48px; padding: 2px 8px; border-radius: 999px; background: var(--pulse-good-wash); color: var(--pulse-good); font-weight: 600; font-variant-numeric: tabular-nums; }
.pulse-rate-chip.is-low { background: var(--pulse-wash); color: var(--pulse-ink); }
.pulse-jhead { display: flex; align-items: center; gap: 16px; padding: 20px 24px; border-bottom: 1px solid var(--pulse-hair); }
.pulse-jhead .pulse-plat-mark { width: 48px; height: 48px; border-radius: 12px; }
.pulse-jhead h3 { margin: 0; font-size: 20px; font-weight: 600; letter-spacing: -0.01em; }
.pulse-jhead p { margin: 2px 0 0; font-size: 13px; color: var(--text-secondary); }
.pulse-jhead-actions { margin-left: auto; }
.pulse-jstats { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); border-bottom: 1px solid var(--pulse-hair); }
.pulse-jstats > div { display: grid; gap: 2px; padding: 16px 24px; border-left: 1px solid var(--pulse-hair); }
.pulse-jstats > div:first-child { border-left: 0; }
.pulse-jstats b { font-size: 20px; font-weight: 600; }
.pulse-jstats span { font-size: 12.5px; color: var(--text-secondary); }
.pulse-jfunnel { padding: 24px; }
.pulse-jtakeaway { margin: 0 0 20px; font-size: 16px; line-height: 1.5; color: var(--pulse-ink); max-width: 72ch; }
.pulse-fun { display: flex; align-items: stretch; gap: 0; }
.pulse-fun-step { flex: 1 1 0; min-width: 0; display: grid; grid-template-rows: auto auto auto 1fr; gap: 2px; }
.pulse-fun-label { font-size: 12.5px; font-weight: 600; letter-spacing: 0.04em; text-transform: uppercase; color: var(--text-tertiary); }
.pulse-fun-n { font-size: 34px; font-weight: 600; letter-spacing: -0.02em; line-height: 1.1; }
.pulse-fun-note { font-size: 12.5px; color: var(--text-secondary); min-height: 18px; }
.pulse-fun-bar { position: relative; height: 72px; margin-top: 12px; max-width: 132px; border-bottom: 1px solid var(--pulse-hair-strong); }
.pulse-fun-bar i, .pulse-fun-bar span { position: absolute; left: 0; right: 0; bottom: 0; display: block; border-radius: 4px 4px 0 0; }
.pulse-fun-bar i { background: var(--pulse-wash-strong); }
.pulse-fun-bar span { background: var(--pulse-ink); opacity: 0.82; }
.pulse-fun-step.is-last .pulse-fun-bar span { background: var(--pulse-good); opacity: 1; }
.pulse-fun-step.is-worst .pulse-fun-bar i { background: var(--pulse-warn-wash); box-shadow: inset 0 0 0 1px rgba(160, 98, 0, 0.35); }
.pulse-fun-step.is-worst .pulse-fun-note { color: var(--pulse-warn); font-weight: 500; }
.pulse-fun-gap { flex: 0 0 104px; display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 2px; padding-top: 8px; color: var(--text-tertiary); }
.pulse-fun-pct { font-size: 15px; font-weight: 600; color: var(--pulse-ink); font-variant-numeric: tabular-nums; }
.pulse-fun-lost { font-size: 12px; font-variant-numeric: tabular-nums; white-space: nowrap; }
.pulse-fun-cap { font-size: 11.5px; color: var(--text-tertiary); margin-top: -2px; }
.pulse-fun-share { font-size: 14px; font-weight: 600; color: var(--pulse-ink); font-variant-numeric: tabular-nums; }
.pulse-fun-share span { font-weight: 400; color: var(--text-secondary); }
.pulse-fun-gap.is-worst .pulse-fun-pct, .pulse-fun-gap.is-worst .pulse-fun-lost, .pulse-fun-gap.is-worst svg { color: var(--pulse-warn); }
.pulse-jfacts { display: flex; flex-wrap: wrap; gap: 8px 24px; margin-top: 20px; padding-top: 16px; border-top: 1px solid var(--pulse-hair); font-size: 13px; color: var(--text-secondary); }
.pulse-jfacts b { color: var(--pulse-ink); font-weight: 600; }
.pulse-exits-wrap { padding: 16px 24px; }
.pulse-exits { list-style: none; margin: 0; padding: 0; display: grid; gap: 10px; }
.pulse-exits li { display: grid; grid-template-columns: minmax(140px, 220px) minmax(80px, 240px) auto; justify-content: start; align-items: center; gap: 16px; font-size: 13.5px; }
.pulse-exit-name { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.pulse-exit-bar { height: 8px; border-radius: 999px; background: var(--pulse-wash); overflow: hidden; }
.pulse-exit-bar span { display: block; height: 100%; background: var(--pulse-ink); opacity: 0.7; border-radius: 999px; }
.pulse-exit-n { white-space: nowrap; }
.pulse-visits li { align-items: center; padding: 10px 24px; }
.pulse-visit-left { font-size: 13.5px; }
.pulse-visit-left b { font-weight: 600; }
.pulse-visit-norec { font-size: 12px; min-width: 88px; text-align: right; }
.pulse-visits .pulse-pp-replay { margin-left: 8px; }
.pulse-yes { color: var(--pulse-good); font-weight: 600; }
.pulse-jsub { font-size: 12px; margin-top: 2px; }
@media (max-width: 760px) {
  .pulse-jstats { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .pulse-fun { flex-direction: column; }
  .pulse-fun-gap { flex-direction: row; flex-basis: auto; padding: 8px 0; gap: 8px; }
  .pulse-fun-gap svg { transform: rotate(90deg); }
  .pulse-fun-bar { height: 12px; margin-top: 6px; }
  .pulse-fun-bar span { height: 100% !important; border-radius: 8px; }
  .pulse-exits li { grid-template-columns: 1fr auto; }
  .pulse-exit-bar { grid-column: 1 / -1; grid-row: 2; }
}

.pulse-stepcell b { display: block; font-weight: 600; }
.pulse-stepcell span { display: block; font-size: 11.5px; color: var(--text-tertiary); }
.pulse-stepcell { background: rgba(54, 54, 54, calc(var(--loss, 0) * 0.10)); }

/* Sentences and one-line summaries in place of split bars and progress bars (research audit, Sep 29). */
.pulse-sentence { margin: 0; font-size: 14px; line-height: 1.7; color: var(--text-secondary); }
.pulse-inline-link { border: 0; background: none; padding: 0; font: inherit; color: inherit; cursor: pointer; border-bottom: 1px dotted var(--pulse-hair-strong); }
.pulse-inline-link b { color: var(--pulse-ink); font-weight: 600; }
.pulse-inline-link:hover, .pulse-inline-link.is-on { color: var(--pulse-ink); border-bottom-color: var(--pulse-ink); }
.pulse-sec-line { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 8px 16px; font-size: 13.5px; color: var(--text-secondary); }
.pulse-err-table th, .pulse-err-table td { padding-left: 16px; padding-right: 16px; }
.pulse-times { font-size: 12px; font-weight: 600; color: var(--text-secondary); background: var(--pulse-wash); padding: 1px 6px; border-radius: 999px; }

.pulse-mline-wrap { padding: 8px 16px 16px; }
.pulse-mline { width: 100%; height: auto; display: block; }
.pulse-mline-path { fill: none; stroke: var(--pulse-ink); stroke-width: 2; stroke-linejoin: round; stroke-linecap: round; }
.pulse-mline-dot { fill: #fff; stroke: var(--pulse-ink); stroke-width: 2; }
.pulse-mline-dot.is-last { fill: var(--pulse-ink); }
.pulse-mline-foot { font-size: 12.5px; color: var(--text-tertiary); margin-top: 4px; }

.pulse-defs-wrap { margin-top: 16px; }
.pulse-defs-wrap summary { cursor: pointer; font-size: 13px; color: var(--text-tertiary); list-style: none; }
.pulse-defs-wrap summary::before { content: "+ "; }
.pulse-defs-wrap[open] summary::before { content: "\2212  "; }

/* Real charts (Sep 29): a guide at the point under the pointer, the point highlighted, the months line at its own width. */
.pulse-chart { position: relative; }
.pulse-chart-guide { stroke: var(--pulse-ink); stroke-width: 1; stroke-dasharray: 2 3; opacity: 0; pointer-events: none; }
.pulse-chart-guide.is-on { opacity: 0.35; }
.pulse-chart-tip { line-height: 1.45; }
.pulse-mline { display: block; width: 100%; height: auto; overflow: visible; }
.pulse-mline-area { fill: var(--pulse-ink); opacity: 0.05; }
.pulse-mline-dot.is-hover { r: 6; fill: var(--pulse-ink); }
.pulse-mline .pulse-chart-val { font-size: 12px; }
.pulse-mline .pulse-chart-axis { font-size: 12px; }
.pulse-src-list { max-width: 820px; }
.pulse-src-row { grid-template-columns: minmax(140px, 200px) minmax(80px, 420px) auto; padding: 6px 8px; margin: 0 -8px; border-radius: 8px; cursor: pointer; }
.pulse-src-row.is-hover, .pulse-src-row:hover { background: var(--pulse-wash); }
.pulse-src-bar { height: 12px; background: var(--pulse-wash); border-radius: 6px; overflow: hidden; }
.pulse-src-name .pulse-plat-mark { width: 22px; height: 22px; }

/* Screen pictures in the rebuilt hosted-flow tab (Sep 29). */
.pulse-jshot { display: block; width: 100%; max-width: 132px; aspect-ratio: 456 / 872; object-fit: contain; object-position: top; border-radius: 10px;
  box-shadow: 0 0 0 1px var(--pulse-hair), 0 4px 14px rgba(0,0,0,0.06); background: #fff; }
.pulse-jshot.is-missing { display: grid; place-items: center; background: var(--pulse-wash); box-shadow: inset 0 0 0 1px var(--pulse-hair); }
.pulse-jshot.is-missing span { font-size: 11px; color: var(--text-tertiary); text-align: center; padding: 8px; }
.pulse-jshot.is-mini { width: 36px; max-width: 36px; border-radius: 6px; flex: none; box-shadow: 0 0 0 1px var(--pulse-hair); }
.pulse-fun-shot { margin-top: 12px; }
.pulse-exit-cards { list-style: none; margin: 0; padding: 0; display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); gap: 16px; }
.pulse-exit-cards li { display: grid; gap: 6px; align-content: start; padding: 10px; border-radius: 12px; }
.pulse-exit-cards li.is-top { background: var(--pulse-warn-wash); }
.pulse-exit-cards li.is-finish { background: var(--pulse-good-wash); }
.pulse-exit-cards li.is-finish .pulse-exit-n b { color: var(--pulse-good); }
.pulse-exit-cards .pulse-jshot { max-width: none; }
.pulse-exit-cards .pulse-exit-name { font-size: 13.5px; font-weight: 600; }
.pulse-exit-cards .pulse-exit-n { font-size: 13px; }
/* the whole screen, bottom button included: the captures are 456x872 cards, and a 9:16 crop cut off every CTA */
.pulse-exit-cards { grid-template-columns: repeat(auto-fill, minmax(170px, 1fr)); }
.pulse-exit-cards .pulse-exit-arr { font-size: 13px; color: var(--text-secondary, #555); }
.pulse-exit-bar { height: 4px; border-radius: 2px; background: var(--pulse-wash-strong); overflow: hidden; }
.pulse-exit-bar i { display: block; height: 100%; background: var(--pulse-bad); border-radius: 2px; }
.pulse-exit-bar.is-good i { background: var(--pulse-good); }
/* The flow in its order: one row per place a visit started (journeyBoard.journeyPathsFrom). */
.pulse-paths { display: grid; gap: 22px; }
.pulse-path-head { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 12px; margin-bottom: 8px; }
.pulse-path-name { font-size: 14px; font-weight: 600; }
.pulse-path-meta { font-size: 13px; color: var(--text-secondary, #555); }
.pulse-path-note { margin: -4px 0 10px; font-size: 12.5px; color: var(--text-secondary, #555); max-width: 72ch; }
.pulse-exit-fail { font-size: 13px; color: var(--pulse-bad); }
.pulse-path .pulse-exit-name { white-space: normal; overflow: visible; }
.pulse-path .pulse-exit-cards li.is-empty { opacity: 0.55; }
.pulse-path .pulse-exit-cards { grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); }
.pulse-path.is-classic .pulse-path-name::after { content: ' (old design)'; font-weight: 400; color: var(--text-secondary, #555); }
.pulse-visits li { gap: 12px; }

/* Replay session ids, copyable (so an agent can be sent to watch them). */
.pulse-sec-row { display: flex; align-items: center; justify-content: space-between; gap: 12px; }
.pulse-copy { border: 1px solid var(--pulse-hair); background: #fff; border-radius: 999px; padding: 4px 12px; font: inherit; font-size: 12px;
  letter-spacing: 0; text-transform: none; color: var(--pulse-ink); cursor: pointer; }
.pulse-copy:hover { border-color: var(--pulse-hair-strong); }
.pulse-copy.is-small { padding: 1px 8px; font-size: 11px; }
.pulse-sid { display: flex; align-items: center; gap: 8px; margin-top: 4px; }
.pulse-sid code { font-size: 11.5px; color: var(--text-secondary); user-select: all; }
.pulse-sid-kind { font-size: 10.5px; font-weight: 600; letter-spacing: 0.02em; text-transform: uppercase; color: var(--text-tertiary, var(--text-secondary)); }

/* The trust screen A/B card (pulse.js renderTrustPanel): its picture beside its numbers; stacked on a phone. */
.pulse-trust-body { display: grid; grid-template-columns: 140px minmax(0, 1fr); gap: 20px; align-items: start; padding: 4px 0 0; }
.pulse-trust-shot .pulse-jshot { width: 140px; }
.pulse-trust-main { display: grid; gap: 12px; min-width: 0; }
.pulse-trust .is-warn b { color: var(--pulse-warn, #b25e09); }
@media (max-width: 640px) { .pulse-trust-body { grid-template-columns: 1fr; } .pulse-trust-shot .pulse-jshot { width: 120px; } }
