/* ULTRABENCH — exit-intent : the Blueprint Builder promo dialog. */

/* The first fixed overlay in the app. New ceiling: .skip-link was 100, .app-header is 20.
   The panel is a plain child — a child cannot compete with its own parent's stacking
   context, so a second z-index here would only be noise. */
.xi-root {
  position: fixed;
  inset: 0;
  z-index: 200;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: var(--gap);
  background: rgba(11, 13, 17, .78); /* = --bg */
  overscroll-behavior: contain;
  opacity: 0;
  visibility: hidden;
  pointer-events: none;
}
.xi-root.xi-open {
  opacity: 1;
  visibility: visible;
  pointer-events: auto;
}

/* The panel does not scroll: the bar and the foot are fixed rows and only .xi-main
   scrolls. That is what keeps the close control AND the two real actions on screen at any
   text size — a single scrolling panel pushes the CTA off the bottom of a 390x844 phone
   the moment the system font grows. --line-strong, not --line: this surface floats over a
   scrim and is the only thing on screen, so its edge has to assert itself. */
.xi-panel {
  position: relative;
  display: flex;
  flex-direction: column;
  width: min(560px, calc(100vw - 32px));
  max-height: min(88vh, 620px);
  max-height: min(88dvh, 620px);
  overflow: hidden;
  background: var(--bg-raised);
  border: 1px solid var(--line-strong);
  border-radius: var(--radius);
}
/* Programmatic focus only — the reader never tabbed here, so a ring would read as an error. */
.xi-panel:focus { outline: none; }

.xi-panel::before {
  content: "";
  display: block;
  flex: none;
  height: 2px;
  background: var(--accent);
}

/* ---------- bar ---------- */

/* Same gutter as .xi-main and .xi-foot — the eyebrow, the headline and the CTA share one
   left edge, the way the shell's header, views and footer share --pad-x. */
.xi-bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
  flex: none;
  padding: 10px max(20px, env(safe-area-inset-right, 0px)) 10px
           max(20px, env(safe-area-inset-left, 0px));
  border-bottom: 1px solid var(--line);
}
.xi-eyebrow {
  font-family: var(--mono);
  font-size: 11px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .06em;
  color: var(--text-dim);
}
.xi-close {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 32px;
  height: 32px;
  flex: none;
  padding: 0;
  background: transparent;
  border: 1px solid var(--line);
  border-radius: var(--radius-s);
  color: var(--text-dim);
  cursor: pointer;
}
.xi-close:hover { color: var(--text); border-color: var(--line-strong); }

/* ---------- body ---------- */

.xi-main {
  flex: 1 1 auto;
  min-height: 0;
  overflow-y: auto;
  overscroll-behavior: contain;
  padding: 20px max(20px, env(safe-area-inset-right, 0px)) 20px
           max(20px, env(safe-area-inset-left, 0px));
}
.xi-title {
  font-family: var(--sans);
  font-size: 20px;
  font-weight: 600;
  line-height: 1.25;
  color: var(--text);
  margin: 0 0 8px;
}
.xi-text {
  font-size: 13px;
  line-height: 1.55;
  color: var(--text-dim);
  margin: 0;
}

/* Bare columns, the house .stat-row recipe. Nothing else in ULTRABENCH wraps a number in a
   bordered tile, and a 4-up boxed strip is the visual signature of a landing page. */
/* 2x2, not a wrapping row. The four labels are intrinsically 497px wide and the panel's
   content box is 520px, so a flex row wraps 3 + 1 and strands the last stat on its own
   line. Two fixed columns read as a spec block rather than a marketing proof strip, and
   they still fit the 390px takeover (2 x 134 + gap against a 358px box). */
.xi-stats {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 12px 18px;
  margin-top: 16px;
}
.xi-stat {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 0;
}
.xi-stat-value {
  font-family: var(--mono);
  font-variant-numeric: tabular-nums;
  font-size: 17px;
  line-height: 1.1;
  color: var(--text);
}
/* The unit is not part of the number — at 17px it breaks the numeric read of the strip. */
.xi-stat-unit {
  margin-left: 3px;
  font-size: 11px;
  color: var(--text-dim);
}
.xi-stat-label {
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .06em;
  color: var(--text-dim);
  line-height: 1.25;
}

/* ---------- foot ---------- */

.xi-foot {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10px 12px;
  flex: none;
  padding: 12px max(20px, env(safe-area-inset-right, 0px))
           calc(16px + env(safe-area-inset-bottom, 0px))
           max(20px, env(safe-area-inset-left, 0px));
  border-top: 1px solid var(--line);
}
/* The CTA and its sub-line travel together: on one row with the dismiss button they would
   wrap it onto a second, and a lone right-floating "no thanks" reads louder than it is. */
.xi-act {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 6px;
}
/* .btn + .btn-primary carry the fill, the ink, the radius and the hover; only the deltas
   an anchor-with-an-icon needs live here. */
.xi-cta {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  padding: 8px 12px;
  font-size: 13px;
  text-decoration: none;
}
.xi-cta:hover { text-decoration: none; }
/* The line that answers "what will this cost me" — not the faintest text in the dialog. */
.xi-cta-sub {
  font-family: var(--mono);
  font-size: 12px;
  color: var(--text-dim);
}
.xi-dismiss {
  margin-left: auto;
  color: var(--text-dim);
}
.xi-dismiss:hover { color: var(--text); }

/* Component-scoped, so the CTA's new-tab suffix does not depend on the visually-hidden
   recipe in a page sheet (leaderboard.css) staying globally loaded. */
.xi-sr {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
  border: 0;
}

/* ---------- motion: opt-in only ---------- */

/* At rest the dialog is instant and fully styled. Readers who ask for reduced motion lose
   nothing but the 120ms — there is no state that only the transition reveals. */
@media (prefers-reduced-motion: no-preference) {
  .xi-root { transition: opacity .12s ease, visibility .12s ease; }
  .xi-panel { transform: translateY(6px); transition: transform .12s ease; }
  .xi-root.xi-open .xi-panel { transform: translateY(0); }
  .xi-close, .xi-cta, .xi-dismiss { transition: color .12s ease, border-color .12s ease; }
}

/* ---------- responsive ---------- */

@media (max-width: 860px) {
  .xi-panel {
    width: min(560px, calc(100vw - 24px));
    max-height: 86vh;
    max-height: 86dvh;
  }
}

/* The lead sentence is the first thing a narrow panel drops — the body sentence carries
   the whole claim without it. */
@media (max-width: 640px) {
  .xi-body-lead { display: none; }
}

@media (max-width: 560px) {
  /* Bottom sheet, not a full-screen takeover. A centred card with a dark page behind it
     does read as broken on a phone — but so does a 100dvh panel holding four stats, which
     strands the actions ~700px below the copy. Anchored to the bottom edge and sized to
     its content, the sheet is the pattern a phone reader already knows, and both the close
     control and the CTA land in the thumb's reach instead of at opposite ends of the
     screen. It still grows to 92dvh if the copy ever gets long enough to need it. */
  .xi-root { padding: 0; align-items: flex-end; }
  .xi-panel {
    position: fixed;
    inset: auto 0 0 0;
    width: 100%;
    max-width: none;
    height: auto;
    max-height: 92vh;
    max-height: 92dvh;
    border: 0;
    border-top: 1px solid var(--line-strong);
    border-radius: var(--radius) var(--radius) 0 0;
  }
  /* The sheet is content-sized, so the body must not claim the slack the panel no longer
     has; it goes back to scrolling only when 92dvh actually caps it. */
  .xi-bar {
    padding-top: calc(10px + env(safe-area-inset-top, 0px));
    padding-right: max(16px, env(safe-area-inset-right, 0px));
    padding-left: max(16px, env(safe-area-inset-left, 0px));
  }
  .xi-close { min-width: 44px; min-height: 44px; }
  .xi-main {
    flex: 0 1 auto;
    padding: 16px max(16px, env(safe-area-inset-right, 0px)) 16px
             max(16px, env(safe-area-inset-left, 0px));
  }
  .xi-title { font-size: 18px; }
  .xi-stats { gap: 12px 16px; }
  .xi-foot {
    flex-direction: column;
    align-items: stretch;
    gap: 8px;
    padding: 14px max(16px, env(safe-area-inset-right, 0px))
             calc(16px + env(safe-area-inset-bottom, 0px))
             max(16px, env(safe-area-inset-left, 0px));
  }
  .xi-act { align-items: stretch; }
  /* 44px on both real actions, not only on the close control. */
  .xi-cta {
    justify-content: center;
    min-height: 44px;
    padding: 12px;
  }
  .xi-cta-sub { text-align: center; }
  .xi-dismiss {
    margin-left: 0;
    min-height: 44px;
    text-align: center;
  }
}

@media (max-width: 560px) and (prefers-reduced-motion: no-preference) {
  .xi-panel { transform: translateY(100%); }
  .xi-root.xi-open .xi-panel { transform: translateY(0); }
}
