/* SpiralOS — site styles.
   Values measured off the Framer build before it was retired, so the
   rebuilt pages match it: Manrope 500 for headings and UI, Inter 400 for
   body copy, pure #000 primary / #666 secondary / #969696 muted,
   alternating white and #f0f0f0 bands, 1200px column, 80px section padding. */

@import url("fonts.css");

:root {
  --ink: #000;
  --ink-soft: #666;
  --ink-muted: #969696;
  --band: #f0f0f0;
  --pad: 80px;
  --col: 1200px;
  --ui: "Manrope", sans-serif;
  --body: "Inter", sans-serif;
}

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

/* The scroll container is <html>, so the horizontal clamp has to live here —
   clipping only <body> still lets the page be dragged sideways while the
   reveal animation is mid-flight. */
html {
  -webkit-text-size-adjust: 100%;
  overflow-x: hidden;
  overflow-x: clip;
}

body {
  margin: 0;
  background: #fff;
  color: var(--ink);
  font-family: var(--ui);
  font-weight: 500;
  -webkit-font-smoothing: antialiased;
  /* the reveal slides in from +30px; without this the page can be dragged
     sideways while it plays. `clip` where supported, `hidden` as fallback. */
  overflow-x: hidden;
  overflow-x: clip;
}

a { color: inherit; }

/* Manrope 500 is the heading weight everywhere; without this the browser's
   default bold (700) leaks into every h1-h4 and the page reads much heavier
   than the design. */
h1, h2, h3, h4, h5, h6 { font-weight: 500; }

/* ---------- shared shell ---------- */

/* Opaque white bar, 86px tall — matches the old build. It must not be
   transparent: content scrolls underneath it. */
.masthead {
  position: fixed;
  top: 0; left: 0; right: 0;
  z-index: 10;
  height: 86px;
  display: flex;
  align-items: center;
  padding: 0 var(--pad);
  background: #fff;
}
.masthead a {
  font-size: 28px;
  font-weight: 700;
  text-decoration: none;
}

.section { padding: var(--pad); }
.section--band { background: var(--band); }
.section__inner { max-width: var(--col); margin: 0 auto; }
/* grey bands run full width, left aligned — as in the original */
.section--band .section__inner { max-width: none; margin: 0; }

.eyebrow { font-size: 16px; margin: 0 0 26px; }
.section__title { font-size: 40px; line-height: 1.1; margin: 0 0 14px; max-width: 860px; }
.lead {
  font-family: var(--body);
  font-weight: 400;
  font-size: 18px;
  line-height: 1.5;
  color: var(--ink-soft);
  margin: 0 0 8px;
  max-width: 720px;
}
.section__title + *:not(.lead), .lead + * { margin-top: 48px; }

/* ---------- hero ---------- */

/* The hero owns the first screen: with this top inset the next section's first
   line lands just below the fold, as it did in the old build. A hard 100vh
   overshoots — the old hero was 753px tall and let the following section's
   padding cover the rest. */
.hero { padding: 220px var(--pad) var(--pad); }
/* flush with the padding edge, like the closing panel — not a centred column */
.hero__inner { max-width: var(--col); }
.hero h1 {
  font-size: 64px;
  line-height: 1.2;
  font-weight: 500;
  margin: 0;
}
.hero__line { display: block; }
.hero__line--muted { color: var(--ink-muted); }
.hero__sub { font-size: 32px; line-height: 1.4; font-weight: 500; margin: 60px 0 0; }
.hero__tagline { font-size: 18px; line-height: 1.4; color: var(--ink-soft); margin: 40px 0 0; }
.hero .btn { margin-top: 60px; }

/* ---------- buttons ---------- */

.btn {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin-top: 44px;
  padding: 16px 32px;
  border-radius: 64px;
  background: var(--ink);
  color: #fff;
  text-decoration: none;
  font-size: 18px;
}
.btn:hover { opacity: .85; }
.btn--invert { background: #fff; color: var(--ink); }
/* the arrow is the site's own icon, drawn from the sprite — not a text glyph,
   which renders as an emoji on some platforms */
.btn__icon { flex: none; color: currentColor; }

/* ---------- vision ---------- */

.vision { padding: 160px var(--pad); }
/* Column geometry measured off the old build once its reveal had settled:
   the label sits flush at the padding edge and the body starts at x=362
   on a 1440 viewport. */
.vision__inner { max-width: 1280px; margin: 0 auto; display: flex; gap: 16px; }
.vision__label { flex: 0 0 266px; font-size: 16px; }
.vision__body { flex: 1; min-width: 0; }
.vision__body p { font-size: 18px; line-height: 1.5; margin: 0 0 22px; max-width: 760px; }
.vision__body p + p { color: var(--ink-muted); }

/* Four equal columns, as in the original — not a left-packed row.
   minmax(0,…) and min-width:0 stop a wide cell ("PostWeb" plus its arrow)
   from pushing the grid past the viewport. */
.eras { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); margin: 46px 0 0; }
.eras__step { display: flex; align-items: flex-start; gap: 15px; min-width: 0; }
.eras__era { text-align: center; }          /* caption centres under its label */
.eras dt { font-size: 32px; line-height: 1.4; }
.eras dd { margin: 10px 0 0; font-size: 24px; line-height: 1.4; color: var(--ink-muted); }
.eras__arrow { display: flex; align-items: center; color: var(--ink); height: 45px; }
.eras__arrow svg { display: block; }

/* ---------- content blocks ---------- */

.grid3 { display: grid; grid-template-columns: repeat(3, 1fr); gap: 48px 40px; }
.grid2 { display: grid; grid-template-columns: repeat(2, 1fr); gap: 48px; }

.card__num { display: block; font-size: 24px; }
.card h3 { font-size: 24px; line-height: 1.3; margin: 10px 0; font-weight: 500; }
.card p {
  font-family: var(--body);
  font-weight: 400;
  font-size: 16px;
  line-height: 1.55;
  color: var(--ink-soft);
  margin: 0;
}
.card__list { list-style: none; padding: 0; margin: 12px 0 0; }
.card__list li {
  font-family: var(--body);
  font-weight: 400;
  font-size: 16px;
  line-height: 1.5;
  color: var(--ink-soft);
  margin: 7px 0;
  padding-left: 18px;
  position: relative;
}
.card__list li::before { content: "—"; position: absolute; left: 0; color: #999; }

/* auto-numbered statement lists */
.points { list-style: none; padding: 0; margin: 0; counter-reset: pt; }
.points li {
  display: flex;
  gap: 22px;
  align-items: baseline;
  font-size: 20px;
  line-height: 1.4;
  padding: 20px 0;
  border-bottom: 1px solid rgba(0, 0, 0, .08);
}
.points li:first-child { border-top: 1px solid rgba(0, 0, 0, .08); }
.points li::before {
  counter-increment: pt;
  content: counter(pt, decimal-leading-zero);
  color: #999;
  font-size: 16px;
  min-width: 26px;
}
.points--2col { display: grid; grid-template-columns: repeat(2, 1fr); column-gap: 56px; }
/* `.points { margin: 0 }` sits later in this file and beats the generic
   `.lead + *` rule, so a list following a lead needs its own gap. */
.lead + .points { margin-top: 48px; }

.two { display: grid; grid-template-columns: 1fr 1fr; gap: 48px; }
.two__label { display: block; font-size: 16px; color: var(--ink-soft); margin-bottom: 14px; }
.two p { font-size: 24px; line-height: 1.35; margin: 0; }

.banner { margin-top: 44px; font-size: 20px; line-height: 1.4; }

/* The site's own thin arrow, used inline in running text. A plain "→" picks
   up whichever fallback font has the glyph and renders noticeably heavier. */
.arrow-inline { vertical-align: -3px; margin: 0 2px; color: currentColor; }

/* ---------- dark closing panel ---------- */

/* The closing panel runs the full width inside its padding — it is not a
   centred 1200px column, so its content sits flush at x=80 like the original. */
.closing { background: var(--ink); color: #fff; padding: var(--pad); }
.closing__inner {
  display: flex;
  justify-content: space-between;
  gap: 40px;
}
.closing__cta { min-width: 0; }
.closing h2 { font-size: 64px; line-height: 1.2; margin: 0; max-width: 550px; }
.closing__contacts { text-align: right; }
.closing__contacts p { font-size: 64px; line-height: 1.2; margin: 0; }
.closing__links { display: flex; gap: 24px; justify-content: flex-end; margin-top: 40px; font-size: 20px; }
.closing__links a { text-decoration: none; }
.closing__links a:hover { text-decoration: underline; }
/* white at half opacity — that is how the old build rendered it: grey on black */
.copyright { margin: 40px 0 0; font-size: 16px; color: #fff; opacity: .5; }

/* ---------- news ---------- */

/* Articles set their body copy in Manrope 500 16px/1.6 — not Inter. That is
   what the old build did; Inter is only used inside the landing cards. */
.article { padding: 200px var(--pad) var(--pad); }
.article__inner { max-width: 800px; margin: 0 auto; }
.article h1 { font-size: 64px; line-height: 1.2; margin: 0 0 40px; }
.article__body p,
.article__body li {
  font-size: 16px;
  line-height: 1.6;
  font-weight: 500;
  color: var(--ink);
}
.article__body p { margin: 0 0 22px; }
.article__body ul { margin: 0 0 22px; padding-left: 20px; }
.article__body li { margin: 6px 0; }
.article__body li p { margin: 0; }
.article__body a { color: #0099ff; }
/* right-aligned, ending flush with the text column — as in the old build */
.article__next { display: block; margin-top: 40px; color: #0099ff; text-decoration: none; text-align: right; }
.article__next:hover { text-decoration: underline; }
/* article pages padded their closing panel a little tighter than the rest */
.page-article .closing { padding: 64px; }

/* the listing sits flush against the section padding, not in a centred column */
.postlist__section { padding-top: 200px; }
.postlist__section .section__inner { max-width: none; margin: 0; }
.postlist { list-style: none; padding: 0; margin: 40px 0 0; }
.postlist a { display: block; padding: 0 0 0 58px; text-decoration: none; }
.postlist li + li { margin-top: 24px; }
.postlist__title { display: block; font-size: 18px; line-height: 1.4; }
.postlist__excerpt {
  display: block;
  max-width: 800px;
  margin-top: 8px;
  font-size: 16px;
  line-height: 1.6;
  color: var(--ink-soft);
}
.postlist__date { display: block; margin-top: 10px; font-size: 16px; color: var(--ink); }
.postlist a:hover .postlist__title { color: var(--ink-soft); }

/* ---------- reveal animations ----------
   The old Framer build slid the hero in character by character and faded the
   Vision block in on scroll, both from +X. Reproduced here.

   Everything is visible by default. The hidden starting state only applies
   once reveal.js has run and set `.js-reveal` on <html>, so a JS failure
   leaves a fully readable page — which is precisely how the old site broke.  */

.split__w { display: inline-block; white-space: nowrap; }
.split__w > span { display: inline-block; }

.js-reveal .hero h1 .split__w > span {
  opacity: 0;
  transform: translateX(50px);
}
.js-reveal .hero.is-in .split__w > span {
  animation: slide-in .6s cubic-bezier(.44, 0, .56, 1) forwards;
  animation-delay: calc(var(--i) * 18ms);
}

.js-reveal .reveal { opacity: 0; transform: translateX(30px); }
.js-reveal .reveal.is-in {
  animation: slide-in .6s cubic-bezier(.44, 0, .56, 1) forwards;
}

@keyframes slide-in {
  to { opacity: 1; transform: none; }
}

@media (prefers-reduced-motion: reduce) {
  .js-reveal .hero h1 .split__w > span,
  .js-reveal .reveal {
    opacity: 1;
    transform: none;
    animation: none;
  }
}

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

@media (max-width: 900px) {
  /* --pad must stay a single length: it is used as `padding: 0 var(--pad)`
     in the masthead, where a two-value shorthand would expand to nonsense. */
  :root { --pad: 24px; }
  .section, .closing { padding: 56px 24px; }
  /* the bar is 86px and opaque, so every page's first block must clear it —
     `.section` above would otherwise flatten these back to 56px */
  .hero { padding: 120px 20px 56px; }   /* the hero insets 20px, not 24px */
  .vision { padding: 80px 24px; }
  .article { padding: 120px 10px 56px; }   /* articles inset only 10px on phones */
  .postlist__section { padding-top: 120px; }
  .hero h1, .closing h2, .closing__contacts p { font-size: 32px; }
  .article h1 { font-size: 32px; }
  .hero__sub { font-size: 22px; }
  /* the old build left a wide gap between the CTA block and the contacts */
  .closing__inner { gap: 160px; }
  .section__title { font-size: 30px; }
  .grid3, .grid2, .two, .points--2col { grid-template-columns: 1fr; gap: 32px; }
  /* no gap: the paragraph's own line box already supplies the 16px the old
     build had between the label and the text */
  .vision__inner { flex-direction: column; gap: 0; }
  /* `flex: 0 0 266px` sizes the label's WIDTH while the row is horizontal, but
     once this stacks it becomes a 266px HEIGHT — a 244px hole under "Vision".
     Reset the basis whenever the direction changes. */
  .vision__label { flex: none; padding-left: 0; }
  .vision__body p { font-size: 22px; }
  /* On phones the eras become one centred column with the arrow turned to
     point down between them — as in the old build, not a left-packed list. */
  .eras { grid-template-columns: 1fr; gap: 0; justify-items: center; }
  .eras__step { flex-direction: column; align-items: center; gap: 14px; }
  .eras__era { text-align: center; }
  .eras dt { font-size: 22px; }
  .eras dd { font-size: 20px; margin-top: 6px; }
  .eras__arrow { height: auto; transform: rotate(90deg); margin: 8px 0 22px; }
}

@media (max-width: 700px) {
  .masthead { padding: 0 24px; }
  .closing__inner { flex-direction: column; }
  .closing__contacts { text-align: left; }
  .closing__links { justify-content: flex-start; }
}
