/*
 * Laneyard — landing page.
 *
 * Same grammar as the product: monospace everywhere, characters instead of
 * icons, right angles, one-pixel rules, no shadows, no gradients. Surfaces
 * separate by value, not by depth. Colour is semantic and nothing else.
 *
 * The page is laid out as a terminal session: each section is a command and
 * its output. The one bold thing is the hero transcript; everything around it
 * stays deliberately quiet.
 */

:root {
  --ink: #0e1013;
  --bg: #14161a;
  --raised: #1b1e24;
  --rule: #262a31;

  --text: #c8ccd4;
  --bright: #e6e9ee;
  --dim: #676e7b;

  --phosphor: #7ee787;
  --amber: #e3b341;
  --red: #f8746a;
  --blue: #79c0ff;

  --mono: ui-monospace, "SF Mono", SFMono-Regular, Menlo, Consolas, "Liberation Mono", monospace;
  --gutter: clamp(20px, 5vw, 72px);
  --measure: 62ch;
}

*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  scroll-behavior: smooth;
}

body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font-family: var(--mono);
  font-size: 14px;
  line-height: 1.65;
  -webkit-font-smoothing: antialiased;
}

a {
  color: var(--text);
  text-decoration-color: var(--rule);
  text-underline-offset: 3px;
}
a:hover {
  color: var(--bright);
  text-decoration-color: var(--phosphor);
}

:focus-visible {
  outline: 1px solid var(--phosphor);
  outline-offset: 3px;
}

.dim {
  color: var(--dim);
}
.sep {
  margin: 0 0.5ch;
}
em {
  font-style: normal;
  color: var(--bright);
}

/* ── Status bar ──────────────────────────────────────────────────────── */

.statusbar {
  position: sticky;
  top: 0;
  z-index: 10;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 16px;
  padding: 10px var(--gutter);
  background: var(--raised);
  border-bottom: 1px solid var(--rule);
  font-size: 12px;
}

.wordmark {
  color: var(--bright);
  text-decoration: none;
  letter-spacing: 0.02em;
}
.wordmark .caret {
  color: var(--phosphor);
}

.statusbar nav {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 14px;
  justify-content: flex-end;
}

/* The version and licence stopped being the point of this bar once the
   commands moved in: kept, quieter, and first to fall away on a narrow screen. */
.statusbar .meta {
  font-size: 12px;
}

@media (max-width: 640px) {
  .statusbar .meta,
  .statusbar .sep {
    display: none;
  }
}

/* ── Layout ──────────────────────────────────────────────────────────── */

main {
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 var(--gutter);
}

.block {
  padding: clamp(48px, 8vw, 88px) 0;
  border-top: 1px solid var(--rule);
}

.prompt {
  margin: 0 0 20px;
  color: var(--fg);
  font-size: 15px;
  letter-spacing: 0.06em;
}
/* The anchor sits on the prompt rather than on the section: a section's top
   edge is its rule, followed by up to 88px of padding, so landing there put the
   divider under the sticky bar and left the heading somewhere below the fold.
   scroll-margin-top only ever adds space above, so it cannot climb past that
   padding — the target has to be the heading itself. */
.prompt[id] {
  scroll-margin-top: 68px;
}

.prompt::first-letter {
  color: var(--phosphor);
}

.block-lede {
  max-width: var(--measure);
  margin: 20px 0 0;
}

.footnote {
  max-width: var(--measure);
  margin: 20px 0 0;
  color: var(--dim);
  font-size: 12.5px;
}

/* ── Hero ────────────────────────────────────────────────────────────── */

.hero {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1.05fr);
  gap: clamp(28px, 5vw, 64px);
  align-items: center;
  padding: clamp(48px, 9vw, 104px) 0;
}

h1 {
  margin: 0;
  font-size: clamp(30px, 5.2vw, 52px);
  line-height: 1.1;
  letter-spacing: -0.03em;
  font-weight: 600;
  color: var(--bright);
}

.lede {
  max-width: 54ch;
  margin: 24px 0 0;
  font-size: clamp(14px, 1.5vw, 15.5px);
}

.actions {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  margin-top: 32px;
}

.button {
  display: inline-block;
  padding: 9px 18px;
  border: 1px solid var(--rule);
  color: var(--text);
  text-decoration: none;
  font-size: 13px;
  transition: border-color 120ms linear, color 120ms linear;
}
.button:hover {
  border-color: var(--dim);
  color: var(--bright);
}
.button.primary {
  border-color: var(--phosphor);
  color: var(--phosphor);
}
.button.primary:hover {
  background: rgba(126, 231, 135, 0.08);
}

/* ── The transcript: the one loud element ────────────────────────────── */

.transcript {
  margin: 0;
  border: 1px solid var(--rule);
  background: var(--ink);
  font-size: 11.5px;
  line-height: 1.6;
}

.transcript-head {
  display: flex;
  justify-content: space-between;
  gap: 12px;
  padding: 9px 12px;
  border-bottom: 1px solid var(--rule);
  background: var(--raised);
}
.transcript-head b {
  color: var(--bright);
  font-weight: 600;
}

.transcript-body {
  display: grid;
  /* Wide enough for the longest real action name — `upload_to_testflight` is
     twenty characters. A truncated step rail would undercut the one thing this
     panel is meant to demonstrate. */
  grid-template-columns: minmax(28ch, 38%) minmax(0, 1fr);
}

.steps {
  margin: 0;
  padding: 10px 12px;
  list-style: none;
  border-right: 1px solid var(--rule);
}
.steps li {
  display: flex;
  justify-content: space-between;
  gap: 8px;
  color: var(--dim);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.steps li[data-state="running"] {
  color: var(--amber);
}
.steps li[data-state="done"] {
  color: var(--text);
}

.stream {
  margin: 0;
  padding: 10px 12px;
  min-height: 244px;
  max-height: 244px;
  overflow: hidden;
  white-space: pre-wrap;
  word-break: break-word;
  color: var(--text);
}

.transcript-foot {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  padding: 10px 12px;
  border-top: 1px solid var(--rule);
}

.chip {
  border: 1px solid var(--rule);
  padding: 3px 9px;
  color: var(--dim);
  font-size: 11px;
}

.mark {
  display: inline-block;
  width: 1.2ch;
}
.mark.ok,
.ok {
  color: var(--phosphor);
}
.mark.running,
.warn {
  color: var(--amber);
}
.mark.todo {
  color: var(--dim);
}
.err {
  color: var(--red);
}

.cursor {
  color: var(--blue);
}

/* ── Reasons ─────────────────────────────────────────────────────────── */

.reasons {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(230px, 1fr));
  gap: 28px 40px;
  margin: 0;
}
.reasons dt {
  color: var(--bright);
  border-bottom: 1px solid var(--rule);
  padding-bottom: 8px;
  margin-bottom: 10px;
}
.reasons dd {
  margin: 0;
  color: var(--text);
  font-size: 13px;
}

/* ── Samples ─────────────────────────────────────────────────────────── */

.sample {
  margin: 0;
  padding: 14px 16px;
  border: 1px solid var(--rule);
  background: var(--ink);
  overflow-x: auto;
  font-size: 12px;
  line-height: 1.75;
}
.price {
  /* Wide enough for the longest line in the block; otherwise the total — the
     one line that matters — gets clipped. */
  max-width: 60ch;
}

/* ── Comparison ──────────────────────────────────────────────────────── */

.table-scroll {
  overflow-x: auto;
}

.compare {
  border-collapse: collapse;
  width: 100%;
  min-width: 560px;
  font-size: 12.5px;
}
.compare th,
.compare td {
  text-align: left;
  padding: 9px 14px 9px 0;
  border-bottom: 1px solid var(--rule);
  font-weight: 400;
}
.compare thead th {
  color: var(--dim);
  font-size: 10.5px;
  letter-spacing: 0.09em;
  text-transform: uppercase;
}
.compare tbody th {
  color: var(--dim);
  padding-right: 28px;
}
/* No emphasis rule on our own column: it would win on specificity and strip the
   semantic colour from the very cells that carry the meaning. The table earns
   attention by being accurate, not by shouting in one column. */

/* ── Status list ─────────────────────────────────────────────────────── */

.status {
  margin: 0;
  padding: 0;
  list-style: none;
  max-width: var(--measure);
}
.status li {
  display: flex;
  gap: 10px;
  padding: 6px 0;
  border-bottom: 1px solid var(--rule);
  font-size: 13px;
}

/* ── Footer ──────────────────────────────────────────────────────────── */

footer {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: 12px;
  max-width: 1180px;
  margin: 0 auto;
  padding: 28px var(--gutter) 48px;
  border-top: 1px solid var(--rule);
  color: var(--dim);
  font-size: 12px;
}

/* ── Narrow screens ──────────────────────────────────────────────────── */

@media (max-width: 860px) {
  .hero {
    grid-template-columns: minmax(0, 1fr);
  }
  .transcript-body {
    grid-template-columns: minmax(0, 1fr);
  }
  .steps {
    border-right: none;
    border-bottom: 1px solid var(--rule);
  }
  .stream {
    min-height: 190px;
    max-height: 190px;
  }
}

/* ── Light theme ─────────────────────────────────────────────────────── */
/* The transcript keeps its dark surface in both: fastlane's ANSI colours are
   made for a black background, and restating them on cream would misrepresent
   what the tool actually prints. */

@media (prefers-color-scheme: light) {
  :root {
    --bg: #f2efe6;
    --raised: #e7e2d5;
    --rule: #d9d3c4;
    --text: #2f2b25;
    --bright: #14110c;
    --dim: #857c6d;
    --phosphor: #3f7d3f;
    --amber: #a76c14;
    --red: #b03a34;
    --blue: #2f6f9e;
  }
  .transcript,
  .sample {
    /* Dark island, on purpose. */
    --text: #c8ccd4;
    --bright: #e6e9ee;
    --dim: #676e7b;
    --rule: #262a31;
    --phosphor: #7ee787;
    --amber: #e3b341;
    color: #c8ccd4;
    border-color: #262a31;
  }
  .transcript-head {
    background: #1b1e24;
    border-color: #262a31;
  }
  .steps,
  .transcript-foot {
    border-color: #262a31;
  }
}

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }
  .button {
    transition: none;
  }
}
