/* ==========================================================================
   AstroPanda, home.css
   Styles exclusive to the index page: hero, the AstroPanda panda rail,
   services rows, success stories orbit arc, testimonials, and the
   page-load boot / reveal animations that drive them. Shared site
   chrome (variables, base, typography, buttons, header, footer) lives
   in global.css instead.
   ========================================================================== */

/* hero cards parked for now, markup stays, just not shown */
[data-ap-side]{display:none !important}
/* The travel is horizontal; this is the idle bob that keeps the figure
   alive between rows. 18px on a 580px panda was under the threshold
   where it reads as floating at all. */
@keyframes apFloat{0%,100%{transform:translateY(0)}50%{transform:translateY(-34px)}}
@keyframes apPulse{0%,100%{opacity:.55}50%{opacity:1}}
@keyframes apCueBob{0%,100%{transform:translateY(0)}50%{transform:translateY(7px)}}

/* rotated scroll cue, hero left edge */
.ap-side-cue{
  position:absolute; left:46px; bottom:44px; z-index:8;
  display:flex; flex-direction:column; align-items:center; gap:14px;
  pointer-events:none;
}
.ap-side-cue span{
  writing-mode:vertical-rl; transform:rotate(180deg);
  font-family:'Space Mono',monospace; font-size:10.5px; letter-spacing:.34em;
  color:rgba(238,240,246,.55);
}
.ap-side-cue em{
  font-style:normal; color:var(--orange); font-size:15px; line-height:1;
  animation:apCueBob 2.2s ease-in-out infinite;
}
@media (max-width:1180px){ .ap-side-cue{display:none} }

/* ---------------- the hero on phones ----------------
   The hero is the exported Claude Design block and carries its styles
   inline, so overriding it needs !important. */
@media (max-width:760px){
  /* the eyebrow is a third line of small caps above an already tall
     headline, and on a phone it is the first thing in the way */
  .ap-b-head > div:first-child{display:none !important}

  /* the two actions sat side by side and ran to both edges */
  .ap-b-foot{padding-inline:22px !important}
  .ap-b-foot > div:last-child{
    flex-direction:column !important; align-items:stretch !important;
    width:100% !important; gap:12px !important;
  }
  .ap-b-foot .ap-hero-btn{width:100% !important; justify-content:center !important}

  /* "QUE IMPULSAN MARCAS" is longer than "THAT LAUNCH BRANDS": at the
     desktop clamp floor (60px) the Spanish headline broke onto a fourth
     line, and shrunk to fit two lines it left a hole above the panda. On a
     phone it breaks into three lines of its own (the .ap-br-m breaks in
     es/index.php: SOFTWARE Y / SITIOS WEB QUE / IMPULSAN MARCAS), sized so
     the longest one fits the width. */
  html[lang^="es"] .ap-b-head h1{font-size:min(60px, 13vw) !important}
  .ap-b-head .ap-br-m{display:inline}
  .ap-b-head .ap-br-d{display:none}

  /* The lead sat on the panda's suit and lost its contrast: on a phone it
     is the short version (two lines) over a dark pool of its own. */
  .ap-b-foot{isolation:isolate}
  .ap-b-foot::before{
    content:""; position:absolute; z-index:-1; pointer-events:none;
    left:-10%; right:-10%; top:-46px; bottom:-30px;
    background:radial-gradient(ellipse 62% 58% at 50% 46%, rgba(3,3,5,.86) 0%, rgba(3,3,5,.6) 52%, rgba(3,3,5,0) 82%);
  }
}
.ap-lead-short{display:none}
.ap-br-m{display:none}
@media (max-width:760px){
  .ap-lead-long{display:none}
  .ap-lead-short{display:inline}
}

/* ---------- hero ---------- */
.ap-intro{position:relative; min-height:100vh; padding:80px 0 40px; text-align:center; overflow:hidden; display:flex; align-items:center; justify-content:center}

.ap-scroll{
  margin-top:52px; display:inline-flex; flex-direction:column; align-items:center; gap:10px;
  font-family:'Space Mono',monospace; font-size:10.5px; letter-spacing:.3em;
  color:rgba(238,240,246,.45);
}
.ap-scroll i{display:block; width:1px; height:54px;
  background:linear-gradient(180deg,rgba(255,90,20,.9),rgba(255,90,20,0));
  animation:apPulse 2.4s ease-in-out infinite}

/* big planet cresting the lower-right of service row 01, behind the panda
   rail; anchored to the viewport edge with the same 50vw escape as the
   scenes, faded at its base so it never hard-cuts against the next row */
/* Every piece of per-row scenery (planet, asteroid field, whatever comes
   next) fades in and out EACH time it enters or leaves the viewport: give it
   .ap-row-art and home.js drives .is-in from an IntersectionObserver that
   toggles both ways. */
.ap-row-art{
  opacity:0;
  transition:opacity 1.1s ease;
}
.ap-row-art.is-in{opacity:1}
@media (prefers-reduced-motion: reduce){
  .ap-row-art{transition:none}
}

/* Direct children of .ap-row on purpose: .ap-space is position:relative, so
   inside it the 50vw viewport-escape resolved against the narrow column and
   flung the art off-screen. The row spans the shell, which is the box these
   offsets are written for. */
.ap-space-planet{
  position:absolute; right:calc(50% - 50vw); bottom:-160px; z-index:0;
  width:min(56vw,1150px); max-width:none;
  -webkit-mask-image:linear-gradient(180deg,#000 0,#000 74%,transparent 96%);
  mask-image:linear-gradient(180deg,#000 0,#000 74%,transparent 96%);
  pointer-events:none;
}
/* asteroid field hugging the lower-left of service row 02, same viewport
   escape and base fade as row 01's planet, mirrored */
.ap-space-asteroids{
  position:absolute; left:calc(50% - 50vw); bottom:-50px; z-index:0;
  width:min(48vw,900px); max-width:none;
  -webkit-mask-image:linear-gradient(180deg,#000 0,#000 84%,transparent 100%);
  mask-image:linear-gradient(180deg,#000 0,#000 84%,transparent 100%);
  pointer-events:none;
}
.ap-row{position:relative}
/* rows 03 and 04: the ribbon's subject sits in the right half of its canvas
   and the rocket's in the left, which is exactly the free side of each row,
   so both just anchor to their own viewport edge. Centred rather than
   bottom-pinned: unlike the planet and the asteroid field, these
   compositions are not bottom-heavy. */
.ap-space-ribbon,
.ap-space-rocket{
  position:absolute; top:50%; transform:translateY(-50%); z-index:0;
  width:min(54vw,1050px); max-width:none;
  pointer-events:none;
}
.ap-space-ribbon{right:calc(50% - 50vw)}
/* The Growth plate spans the viewport; its subject remains on the left. */
.ap-space-rocket{
  left:calc(50% - 50vw); width:100vw;
  -webkit-mask-image:linear-gradient(180deg,transparent 0,#000 12%,#000 84%,transparent 100%);
  mask-image:linear-gradient(180deg,transparent 0,#000 12%,#000 84%,transparent 100%);
}
/* the ribbon runs to the foot of its canvas; fade it so it never butts
   against the next row */
.ap-space-ribbon{
  -webkit-mask-image:linear-gradient(180deg,transparent 0,#000 10%,#000 86%,transparent 100%);
  mask-image:linear-gradient(180deg,transparent 0,#000 10%,#000 86%,transparent 100%);
}
/* Architectural cutouts keep their alpha silhouette behind the panda. */
.ap-space-workshop{
  position:absolute; top:50%; right:calc(50% - 50vw);
  transform:translateY(-50%); z-index:0;
  width:min(50vw,960px); max-width:none; pointer-events:none;
}
.ap-space-maintenance{
  width:min(54vw,1040px);
  right:calc(50% - 50vw - clamp(40px,4vw,80px));
  -webkit-mask-image:linear-gradient(180deg,#000 0,#000 78%,transparent 100%);
  mask-image:linear-gradient(180deg,#000 0,#000 78%,transparent 100%);
}
/* Blend the Home case map into the shared sky above it. */
#ap-services + .ap-stories{border-top:0}
#ap-services + .ap-stories .ap-map{background:transparent}
#ap-services + .ap-stories .ap-map-bg{
  -webkit-mask-image:linear-gradient(180deg,transparent 0,transparent 7%,#000 23%);
  mask-image:linear-gradient(180deg,transparent 0,transparent 7%,#000 23%);
}
#ap-services + .ap-stories .ap-map-veil,
#ap-services + .ap-stories .ap-map-canvas,
#ap-services + .ap-stories .ap-map-grid,
#ap-services + .ap-stories .ap-map-dust{
  -webkit-mask-image:linear-gradient(180deg,transparent 0,#000 160px);
  mask-image:linear-gradient(180deg,transparent 0,#000 160px);
}
@media (max-width:1024px){ .ap-space-planet,.ap-space-asteroids,.ap-space-ribbon,.ap-space-rocket,.ap-space-workshop{display:none} }

/* ---------- what-we-do intro extras ---------- */
/* The two hero planets of the section. Sized with clamp so the left one can
   crest half off-screen like in the art direction without eating the copy on
   laptops; both keep the shared .ap-planet parallax (data-depth). */
.ap-wwd-left{
  left:max(-90px,-6vw); top:4%;
  width:clamp(220px,23vw,400px);
  opacity:.95;
}
.ap-wwd-right{
  right:max(-120px,-7vw); top:-2%;
  width:clamp(320px,32vw,560px);
  opacity:.92;
}

/* Entry: each planet slides in from its own screen edge when the section
   comes into view (home.js toggles .is-seen, replaying like the .ap-rv
   reveals). Uses the standalone `translate` property on purpose: the
   parallax in global.js keeps rewriting style.transform every scroll, and a
   transition there would fight it. */
.ap-intro .ap-planet{transition:translate 1.7s cubic-bezier(.16,.8,.24,1), opacity 1.2s ease}
.ap-intro:not(.is-seen) .ap-wwd-left{translate:-130% 0; opacity:0}
.ap-intro:not(.is-seen) .ap-wwd-right{translate:130% 0; opacity:0}
.ap-intro:not(.is-seen) .ap-planet:not(.ap-wwd-left):not(.ap-wwd-right){translate:80% 0; opacity:0}
.ap-intro.is-seen .ap-planet{translate:0 0}

/* Big orbital arc behind the copy: a near-viewport-size circle whose lower
   half runs off below the section, its stroke fading out on the way down, so
   what reads on screen is a wide glowing semicircle. Named .ap-halo, NOT
   name let its rules override this one (same trap as .ap-glow).
   The masked stroke lives on the inner .ap-halo-ring; the beads are siblings
   OUTSIDE it, because a mask clips children and it was slicing their glow.
   Their own fade is timed in the keyframes instead. */
.ap-halo{
  /* enters a beat after the section does: hidden until home.js marks the
     intro .is-seen, then fades in after a 1s delay (replays on re-entry,
     the same toggle that drives the planet fly-in) */
  opacity:0;
  transition:opacity .9s ease 1s;
  position:absolute; left:50%; top:100px;
  width:min(1900px,150vw); aspect-ratio:1/1;
  transform:translateX(-50%);
  pointer-events:none; z-index:0;
  /* the section clips at 100vh with overflow:hidden, and a clipped stroke is
     a hard cut that betrays the section boundary. This wrapper mask fades
     EVERYTHING in the halo to black before that edge (stops are viewport
     units on purpose, the box itself is 1900px tall and runs past it). */
  -webkit-mask-image:linear-gradient(180deg,#000 0,#000 calc(100vh - 380px),transparent calc(100vh - 150px));
  mask-image:linear-gradient(180deg,#000 0,#000 calc(100vh - 380px),transparent calc(100vh - 150px));
}
.ap-intro.is-seen .ap-halo{opacity:1}
@media (prefers-reduced-motion: reduce){
  .ap-halo{transition:none}
}
.ap-halo-ring{
  position:absolute; inset:0;
  border:2px solid var(--orange);
  border-radius:50%;
  -webkit-mask-image:linear-gradient(180deg,#000 0%,#000 26%,transparent 50%);
  mask-image:linear-gradient(180deg,#000 0%,#000 26%,transparent 50%);
}
/* offset-path 0% starts at 3 o'clock and runs clockwise: 25% bottom, 50%
   left, 75% top. The opacity keyframes hide the bead through the circle's
   invisible lower half and light it while it crosses the visible arc. */
.ap-halo-dot{
  position:absolute; inset:0;
  width:10px; height:10px; border-radius:50%;
  background:#ffd9b8;
  box-shadow:0 0 18px 7px rgba(255,110,30,.85), 0 0 5px 2px rgba(255,200,150,1);
  offset-path:ellipse(50% 50% at 50% 50%);
  offset-rotate:0deg;
  animation:apHaloRide 34s linear infinite;
}
.ap-halo-dot--b{
  width:7px; height:7px;
  animation-duration:50s; animation-delay:-33s;
  box-shadow:0 0 14px 5px rgba(255,110,30,.7), 0 0 4px 1px rgba(255,200,150,.9);
}
@keyframes apHaloRide{
  0%{offset-distance:0%; opacity:0}
  46%{opacity:0}
  56%{opacity:1}
  90%{opacity:1}
  98%{opacity:0}
  100%{offset-distance:100%; opacity:0}
}

/* mission-control corners */
.ap-coords{
  position:absolute; left:clamp(20px,3.5vw,56px); bottom:84px; z-index:2;
  display:flex; align-items:center; gap:18px;
  font-family:'Space Mono',monospace; font-size:11.5px; line-height:1.75;
  letter-spacing:.14em; color:rgba(238,240,246,.55); text-align:left;
  font-variant-numeric:tabular-nums;
}
.ap-crosshair{
  position:relative; display:block; width:26px; height:26px; opacity:.5;
}
.ap-crosshair::before,.ap-crosshair::after{
  content:''; position:absolute; background:rgba(238,240,246,.75);
}
.ap-crosshair::before{left:0; right:0; top:50%; height:1px}
.ap-crosshair::after{top:0; bottom:0; left:50%; width:1px}
/* bottom = the coords block's bottom plus half the difference between its
   two-line height and the crosshair, so both crosshairs sit level */
.ap-crosshair--right{position:absolute; right:clamp(20px,3.5vw,56px); bottom:91px; z-index:2}

/* the intro CTA sits a beat under the lead */
.ap-intro-cta{margin-top:44px}

@media (prefers-reduced-motion: reduce){
  .ap-halo-dot{animation:none}
}
@media (max-width:1024px){
  .ap-halo{display:none}
  .ap-coords,.ap-crosshair--right{display:none}
  .ap-wwd-left{width:180px}
  .ap-wwd-right{width:240px}
}

/* ---------- service rows ---------- */
.ap-rows{padding:40px 0 20px}
.ap-row{
  display:grid; grid-template-columns:1fr 1fr; gap:60px; align-items:center;
  /* full-screen rows: each service owns its viewport, no hairline seams */
  min-height:100vh;
  padding:40px 0; position:relative;
}
/* Above the row's own scenery: .ap-row-art is absolutely positioned, so a
   plate wide enough to reach the copy column would otherwise paint over
   it. The Growth plate is exactly that wide. */
.ap-copy{position:relative; z-index:1}
.ap-row[data-dir="ltr"] .ap-copy{order:2}
.ap-row[data-dir="ltr"] .ap-space{order:1}

.ap-num{
  font-family:'Space Mono',monospace; font-size:14px; letter-spacing:.28em;
  color:var(--orange); margin-bottom:24px; display:flex; align-items:center; gap:16px;
}
/* the line runs orange into nothing, 2px tall */
.ap-num::after{content:''; flex:1; height:2px; max-width:220px;
  background:linear-gradient(90deg,var(--orange),rgba(255,90,20,0))}
.ap-h2{
  font-family:'Anton',sans-serif; font-weight:400; margin:0 0 24px;
  font-size:clamp(38px,4.4vw,80px); line-height:1.03; letter-spacing:.006em;
}
.ap-text{font-size:19px; line-height:1.66; color:var(--muted); text-wrap:pretty; margin:0 0 30px}
/* tag list: plain "+ label" rows under a hairline, no pills */
.ap-tags{
  display:flex; flex-wrap:wrap; column-gap:44px; row-gap:16px;
  margin-bottom:38px; padding-top:28px;
  border-top:1px solid var(--line);
}
.ap-tag{
  font-family:'Space Mono',monospace; font-size:13.5px; letter-spacing:.06em;
  color:rgba(238,240,246,.82);
  display:inline-flex; align-items:center; gap:12px;
  transition:color .25s;
}
.ap-tag::before{content:'+'; color:var(--orange); font-size:15px; font-weight:700}
.ap-tag:hover{border-color:rgba(255,90,20,.6); color:var(--paper); transform:translateY(-2px)}

/* ---------- the panda ----------
   One single element for the whole section: pinned to the middle of the screen
   while the rows scroll past, drifting side to side so it always sits opposite
   the copy. The constant float lives on the inner element so it never fights
   with the scroll-driven transform on the outer one. */
.ap-rows{position:relative}
.ap-space{position:relative; min-height:clamp(360px,42vw,500px)}

.ap-rail{
  position:sticky; top:calc(50vh + 50px); height:0; z-index:3; pointer-events:none;
}
.ap-panda{
  position:absolute; top:calc(var(--panda-h) / -2); left:0;
  width:var(--panda-w);
  transform:translate3d(var(--x,0px),var(--y,0px),0) rotate(var(--rot,0deg));
  will-change:transform;
  opacity:0; visibility:hidden;
  /* out: fast, so it never lingers over the intro copy when scrolling back up */
  transition:opacity .3s ease, visibility 0s linear .3s;
}
.ap-panda.is-live{opacity:1; visibility:visible; transition:opacity .85s ease .1s, visibility 0s}
.ap-panda::before{
  content:''; position:absolute; left:-38%; top:2%; width:176%; height:96%;
  background:radial-gradient(ellipse 50% 50% at 50% 50%,rgba(255,90,20,.16) 0%,rgba(255,90,20,0) 70%);
  pointer-events:none;
}
.ap-panda-inner{animation:apFloat 6.5s ease-in-out infinite; will-change:transform}
.ap-panda-canvas{position:relative; width:100%; height:auto; display:block;
  /* A filter on a canvas is recomputed every time the canvas is redrawn,
     and this one is redrawn on every frame of a crossing. 60px of blur was
     a quarter of the GPU time the panda cost; 34px reads the same at this
     size and is roughly half the work. */
  filter:drop-shadow(0 22px 34px rgba(0,0,0,.62))}


/* ---------- page-load boot ----------
   The camera starts above the scene: only the starfield is there, then the hero
   plate rises into frame and each layer slides up after it, top-down. Gated by
   .ap-boot on <html> so it plays exactly once. */
@keyframes apBootBg{
  from{opacity:0; transform:translateY(17%) scale(1.11)}
  to{opacity:1; transform:none}
}
@keyframes apBootUp{
  from{opacity:0; transform:translateY(64px)}
  to{opacity:1; transform:none}
}
/* the side planets sit deeper in the scene, so they travel further and slower */
@keyframes apBootPlanet{
  from{opacity:0; transform:translateY(104px) scale(.94)}
  to{opacity:1; transform:none}
}
@keyframes apBootFade{ from{opacity:0} to{opacity:1} }

/* The exported hero is mounted asynchronously by the component runtime, and that
   mount repaints its subtree before our animations can claim it, which is the
   flash. So the whole hero stays invisible until JS says the intro may begin.
   Guarded by (scripting: enabled) so a no-JS visitor still sees it. */
/* Reserve the hero's box up front: during mount the gate is momentarily empty,
   and without a reserved height the page collapses and the next section jumps
   into view for a frame. Matches the hero's own height:100vh / min-height:780px. */
#ap-hero-gate{min-height:max(100vh,780px)}
@media (scripting: enabled){
  #ap-hero-gate{visibility:hidden}
  .ap-boot #ap-hero-gate,.ap-booted #ap-hero-gate{visibility:visible}
}

/* Hidden from the very first paint so nothing can flash in before its animation
   takes over; .ap-booted (set by JS when the intro ends) pins the final state,
   and if JS never runs the animations' forwards fill leaves them visible anyway. */
.ap-b-bg,.ap-b-planet,.ap-b-nav,.ap-b-head,.ap-b-panda,.ap-b-foot,.ap-side-cue{opacity:0}
.ap-booted .ap-b-bg,.ap-booted .ap-b-planet,.ap-booted .ap-b-nav,.ap-booted .ap-b-head,
.ap-booted .ap-b-panda,.ap-booted .ap-b-foot,.ap-booted .ap-side-cue{opacity:1; animation:none}

/* Cadence borrowed from the UN reference: a held beat of empty starfield, then
   a decelerating rise of the plate, then the copy drifting up behind it. */
/* Tightened 2026-10-30: the panda used to start rising 1.85s in and land
   at ~3.75s, which read as a slow site. Same order and curves, about half
   the time; everything settles by 2.4s (home.js pins it at 2.6s). */
.ap-boot .ap-b-bg{animation:apBootBg 1.8s cubic-bezier(.14,.78,.18,1) .1s both}
.ap-boot .ap-b-planet{animation:apBootPlanet 1.6s cubic-bezier(.16,.8,.2,1) .25s both}
.ap-boot .ap-b-planet:nth-of-type(4){animation-delay:.35s}
.ap-boot .ap-b-nav{animation:apBootUp 1.1s cubic-bezier(.19,.82,.22,1) .3s both}
.ap-boot .ap-b-head{animation:apBootUp 1.2s cubic-bezier(.19,.82,.22,1) .3s both}
.ap-boot .ap-b-panda{animation:apBootUp 1.4s cubic-bezier(.17,.84,.2,1) .35s both}
.ap-boot .ap-b-foot{animation:apBootUp 1.2s cubic-bezier(.19,.82,.22,1) .7s both}
.ap-boot .ap-side-cue{animation:apBootFade 1s ease 1.4s both}
/* the fixed nav must not flash in over the hero during the intro */
.ap-boot .ap-header{animation:none}

/* The headline is on screen from the first paint, and the scene assembles
   behind it. It is the Largest Contentful Paint of the home, and inside the
   gate it could not be counted until the component runtime had fetched React,
   mounted, and the intro had waited another 1.55s and faded it in: measured on
   a throttled phone, 11.5s. So the visible headline is a static copy outside
   the component (index.php), which never unmounts and never fades, and the
   component's own copy is hidden. Letting the component's copy show through
   the gate was tried first: the runtime swaps <x-dc> for an empty #dc-root
   while React downloads, and the title vanished for two seconds. */
#ap-hero-gate{position:relative}
.ap-b-head--static{visibility:visible}
x-dc .ap-b-head, #dc-root .ap-b-head{visibility:hidden !important}
.ap-b-head, .ap-boot .ap-b-head, .ap-booted .ap-b-head{opacity:1; animation:none}

@media (prefers-reduced-motion:reduce){
  .ap-boot .ap-b-bg,.ap-boot .ap-b-nav,.ap-boot .ap-b-head,
  .ap-boot .ap-b-panda,.ap-boot .ap-b-foot,.ap-boot .ap-side-cue,
  .ap-boot .ap-b-planet{animation:none}
  .ap-b-bg,.ap-b-planet,.ap-b-nav,.ap-b-head,.ap-b-panda,.ap-b-foot,.ap-side-cue{opacity:1}
}


/* ---------- helmet hint ----------
   A one-time nudge over the helmet so people discover the reveal effect.
   Pointer-events off: it must never block the very interaction it advertises. */
@keyframes apHintIn{ from{opacity:0; transform:translateY(10px)} to{opacity:1; transform:translateY(0)} }
@keyframes apHintBob{ 0%,100%{transform:translateY(0)} 50%{transform:translateY(-6px)} }
.ap-hint{
  /* beside the helmet, not over it: percentages of the panda's own box, so
     it keeps its place next to the visor at any viewport height */
  position:absolute; left:63%; top:15%; transform:translateY(0);
  z-index:6; pointer-events:none; opacity:0;
  display:flex; align-items:center; gap:9px;
  padding:9px 15px; border-radius:999px;
  border:1px solid rgba(255,90,20,.4);
  background:rgba(3,3,5,.62); backdrop-filter:blur(8px);
  color:var(--orange-soft);
  font-family:'Space Mono',monospace; font-size:10.5px; letter-spacing:.2em; white-space:nowrap;
  box-shadow:0 10px 40px rgba(0,0,0,.5), 0 0 26px rgba(255,90,20,.14);
  transition:opacity .5s ease, transform .5s ease;
}
.ap-hint span{color:rgba(238,240,246,.9)}
/* only after the intro has settled, and only until the panda has been revealed */
/* Shows up early, while the intro is still playing: both boot classes carry the
   same declarations so swapping ap-boot → ap-booted doesn't restart it. */
.ap-boot .ap-hint,
.ap-booted .ap-hint{animation:apHintIn .7s ease 2.4s both, apHintBob 2.6s ease-in-out 3.1s infinite}
.ap-hint.is-off{opacity:0 !important; animation:none !important; transform:translateY(-14px)}
/* one label per input: a finger works too since the reveal moved to
   pointer events */
.ap-hint-touch{display:none}
@media (pointer:coarse){ .ap-hint-mouse{display:none} .ap-hint-touch{display:inline} }
/* on a phone the side of the visor is off screen: centred over the helmet */
@media (max-width:760px){ .ap-hint{left:0; right:0; margin-inline:auto; width:max-content; top:12%} }
@media (prefers-reduced-motion:reduce){ .ap-boot .ap-hint,.ap-booted .ap-hint{animation:none; opacity:1} }

/* ---------- responsive ---------- */
@media (max-width:1024px){
  .ap-row{grid-template-columns:1fr; gap:14px; padding:52px 0}
  .ap-row[data-dir="ltr"] .ap-copy,
  .ap-row[data-dir="ltr"] .ap-space{order:initial}
  .ap-rail,.ap-space{display:none}
  .ap-lang-switch--mobile{
    display:grid;
    grid-template-columns:1fr 1fr;
    width:100%;
    gap:0;

    padding:0;
    margin:0;
    border-left:0;
  }

  .ap-lang-switch--mobile a{
    width:100%;
    padding:20px 10px;
    display:flex;
    align-items:center;
    justify-content:center;

    font-size:13px;
    font-weight:700;
    letter-spacing:.09em;

    border-bottom:1px solid var(--line);
  }

  .ap-lang-switch--mobile a + a{
    border-left:1px solid var(--line);
  }
}
@media (max-width:560px){
  .ap-hero{padding:64px 0 48px}
}

@media (prefers-reduced-motion:reduce){
  .ap-panda-inner,.ap-planet img,.ap-scroll i{animation:none !important}
  .ap-panda{transform:translate3d(var(--x,0px),0,0) !important}
}
