/* =========================================================
   CENTRED MOCKUPS
   Loaded by index.html on top of styles.css, and it is the live layout.
   classic.html loads styles.css alone and renders the previous treatment,
   kept for comparison. styles.css itself is unmodified, so reverting is a
   matter of dropping the <link> from index.html.

   The base layout sizes every phone by WIDTH (min(34vw, 66vh)) and pins it a
   fixed distance from the top of its section, so a 2.166:1 mockup renders about
   143vh tall and the section's overflow:hidden crops the bottom off. That is
   deliberate in styles.css; this file inverts it.

   Here each phone is sized by the HEIGHT available to it and centred in its
   section, so the gap above equals the gap below. Height is the binding
   constraint, so the phones necessarily render smaller.

   Centring uses top:50% + a -50% shift rather than a computed per-mockup top
   offset. The mockups do not share an aspect ratio (slide screenshots are
   2.166:1, slide6-execute is 1.835:1, the connect canvas carries an
   overflowing menu), so no single offset could balance all of them. Centring
   balances each against its own height for free.

   WHICH PROPERTY DOES THE SHIFT is load-bearing. app.js animates these
   elements with inline styles, and an inline style beats a stylesheet:
     .mission__phone app.js:352 writes style.translate  -> centre via `transform`
     .phone          app.js:366 writes style.translate  -> centre via `transform`
   Both drifts ride on the individual `translate` property, which is applied
   before `transform`, so the centring and the drift compose rather than
   overwrite each other. Anything centred here must therefore use `transform`.

   Scope: the scrolly stack and the mission phone. The hero is left as-is.
   ========================================================= */

:root {
  /* Breathing room held above AND below each phone; the phone takes the rest.
     Raise for more air and smaller phones. */
  --vgap: 56px;

  /* Tallest mockup ratio (height / width), from slide2-data.png at 590x1278.
     Widths are derived from available height through this, so the tallest
     screenshot exactly fills the space and nothing crops. */
  --phone-ratio: 2.166;

  /* The visible box is NOT the full viewport. .nav is sticky, 70px tall and
     z-index:100, so it sits on top of the pinned layer. Centring on 100vh
     tucks the phone's top corners under the nav; the base layout's top:120px
     existed precisely to clear it. Everything here centres on the space
     between the nav's bottom edge and the bottom of the viewport. */
  --vbox: calc(100vh - var(--nav-h));

  /* One width shared by the scrolly stack and the mission phone. Derived from
     the pin even though the mission section is 104vh, so a phone is the same
     size in both places instead of the mission one rendering ~4% larger.
     Mission simply gets a bigger (still equal) gap. */
  --pw-centered: min(34vw, calc((var(--vbox) - 2 * var(--vgap)) / var(--phone-ratio)));
}

/* ---------------------------------------------------------
   DESKTOP (>=1025px): the pinned stack and the mission phone.
   The mobile treatment is a separate mechanism and is handled
   in its own block at the bottom of this file.
   --------------------------------------------------------- */
@media (min-width: 1025px) {

  /* =========================================================
     1. SCROLLY — box is the full 100vh pin
     ========================================================= */
  .phone-stack {
    /* was min(34vw, 66vh), a width-first cap that overflowed the pin */
    --pw: var(--pw-centered);

    /* centre of the space below the nav: nav-h + (100vh - nav-h)/2.
       The pin is exactly 100vh, so 50% == 50vh and this reduces cleanly. */
    top: calc(50% + var(--nav-h) / 2);
    /* base rule is translateX(-50%); add the vertical half-shift */
    transform: translate(-50%, -50%);
    /* children are absolutely positioned, so the stack has no natural height to
       centre against. Give it the tallest phone's height explicitly. */
    height: calc(var(--pw) * var(--phone-ratio));
  }

  /* Centre each phone against the stack individually, so a mockup shorter than
     --phone-ratio (slide6-execute) sits centred rather than hanging from the
     stack's top edge and getting equal gaps only by accident. */
  .phone {
    top: 50%;
    transform: translateY(-50%);
  }

  /* The connect slide scales a wider canvas up so its phone body matches its
     siblings. The body sits near-symmetrically in that canvas (~0.205 of the
     width above, ~0.215 below), so centring the canvas centres the body to
     within a pixel or two at these sizes. */
  .phone--parallax {
    width: calc(var(--pw) * 1.642);
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
  }

  /* The hero is deliberately NOT touched. Its composition is different (a
     wide canvas with the prompt bubble overhanging on a second layer) and it
     reads fine bleeding downward, so it keeps the base treatment. */

  /* =========================================================
     2. MISSION — box is the section, min-height 104vh
     ========================================================= */
  .mission__phone {
    /* was min(34vw, 66vh) anchored at top:72px */
    width: var(--pw-centered);
    top: 50%;
    transform: translate(-50%, -50%);
  }
}

/* =========================================================
   MOBILE (<=1024px)
   Different mechanism from the desktop layer. There is no pinned stack here:
   each step paints its screenshot as a background on a full-bleed gray band
   (.step::after / .mission__panel), and the live chat phone gets an equivalent
   band (.step0-chatband). All three are driven by the same three variables.

   The base values crop on purpose:
     --mphone-top:  54px                          gray above the image
     --mphone-band: --mphone-h * 0.85 + top       band is 15% SHORTER than the
                                                  image, so its bottom is cut off
   That is what makes the phone look anchored low and hanging off the band.

   Here the band is sized to hold the whole image plus an equal gap top and
   bottom, so nothing crops and the image reads as centred.
   ========================================================= */
@media (max-width: 1024px) {
  :root {
    /* gray above and below the image inside the band */
    --mphone-gap: 24px;

    --mphone-top: var(--mphone-gap);
    --mphone-band: calc(var(--mphone-h) + 2 * var(--mphone-gap));
  }
}
