/* Site-wide overrides layered on top of the exported design CSS.
   Loaded AFTER site.css so these win the cascade. */

/* ── The page has no background of its own ──────────────────────────
   Everything you see — the blue, the grid — is painted by .bg-grid, which is
   position:fixed, z-index:-1. It floats over the document rather than being
   the document's background, so <html> and <body> are both fully transparent,
   and rubber-banding past an edge exposed blank gutters beyond that fixed layer.

   Declaring the real page colour on the canvas fixes the cause rather than the
   symptom, and demotes overscroll-behavior below from load-bearing to belt and
   braces. Value is .bg-grid's own background-color, so nothing looks different;
   every page carries that layer, so it is correct site-wide.

   This does not affect how iOS Safari tints its status bar and toolbar: it
   samples the rendered content beside each edge, which is why it can show a
   light bar at the top and a dark one at the bottom of the same screen. A flat
   canvas colour could not produce that, so it is clearly not what Safari reads.
   See BaseLayout.astro for why we deliberately ship no theme-color meta. */
html { background-color: #cfdef4; }
html, body { overscroll-behavior: none; }

/* ── Sticky footer ──────────────────────────────────────────────────
   On short pages (e.g. team bios) the content didn't fill the viewport,
   leaving the footer floating mid-screen with the grid showing below it.
   Make the main column at least viewport-tall and push the footer to the
   bottom; on long pages this is a no-op. */
.main-wrapper {
  display: flex;
  flex-direction: column;
  min-height: 100vh;
}
.main-wrapper > .section_footer { margin-top: auto; }

/* ── Homepage "Enable Real-Time Operational Command" graphic ─────────
   The purple accent tile (.feature_img-right-3) inherits .shadow's 20px
   radius, but its SVG is sized 101% and pinned top-left, so it uncovers
   the container's oversized rounded corners at the bottom. Match the
   container radius to the SVG's ~10% corner so all four corners agree. */
.feature_img-right-3.shadow { border-radius: 10%; }

/* ── Hero image swap breakpoint ─────────────────────────────────────
   Each hero slide has a wide desktop image and a tall mobile image;
   Webflow only swapped to the mobile art at ≤479px. Extend that to
   ≤500px so slightly-larger phones get the tall crop too. */
@media (max-width: 500px) {
  .hero-slide-img.hide-mobile-portrait { display: none; }
  .hero-slide-img.show-mobile-portrait { display: block; }
}

/* ── Fluid typography ───────────────────────────────────────────────
   Webflow swaps these semantic type variables at 991/767/479px
   breakpoints, so headings jump between fixed sizes. Redefining them
   with clamp() makes every .text-* class that references them scale
   smoothly with viewport width instead. Fluid between a 480px and
   1440px viewport, clamped to the original min/max at each end. */
:root {
  --_typography---h1: clamp(2.25rem, 0.875rem + 4.583vw, 5rem);        /* 36 → 80px  (text-8xl) */
  --_typography---h2: clamp(1.375rem, 0.5625rem + 2.708vw, 3rem);      /* 22 → 48px  (text-7xl) */
  --_typography---h3: clamp(1.75rem, 1.5rem + 0.833vw, 2.25rem);       /* 28 → 36px  (text-5xl/4xl) */
  --_typography---h4: clamp(1.25rem, 1.125rem + 0.417vw, 1.5rem);      /* 20 → 24px  (text-2xl) */
  --_typography---body-xl: clamp(1.25rem, 1.125rem + 0.417vw, 1.5rem); /* 20 → 24px  (text-xl) */
}

/* text-3xl uses a literal size (policy-page titles) — make it fluid too. */
.text-3xl { font-size: clamp(1.5rem, 1.3125rem + 0.625vw, 1.875rem); } /* 24 → 30px */

/* ── Anchor scrolling ───────────────────────────────────────────────
   The nav is sticky (~64px tall). Give any #anchor target top margin so
   its heading lands below the nav instead of hidden underneath it. */
:where([id]) { scroll-margin-top: 88px; }

/* webflow.js used to animate in-page anchor jumps (the Impact and How it
   works nav links), so without it they snapped instantly. CSS does the same
   job here. Wrapped in no-preference so it stays an instant jump for anyone
   who has asked for reduced motion. */
@media (prefers-reduced-motion: no-preference) {
  html { scroll-behavior: smooth; }
}

/* ── About: ZENDERS gallery ─────────────────────────────────────────
   Replace Webflow's 100vw horizontal-scroll strip (which clipped the first
   image) with a wrapping gallery grid contained to the section width, so it
   lines up with the leadership cards above and nothing is cropped. */
.team_gallery_grid {
  align-self: stretch;
  width: 100%;
  max-width: 100%;
  margin-left: 0;
  /* min(320px, 100%), not a bare 320px: a track floor wider than the container
     cannot shrink to fit, so on anything narrower than 320px the whole grid
     would push out past the page. */
  grid-template-columns: repeat(auto-fit, minmax(min(320px, 100%), 1fr));
  grid-auto-rows: auto;
  grid-column-gap: 1rem;
  grid-row-gap: 1rem;
  overflow: visible;
}
.team_gallery_grid .gallery-img {
  width: 100%;
  height: auto;
  aspect-ratio: 4 / 3;
  object-fit: cover;
  /* These two lines are what stop an image escaping its column, and they are
     load-bearing despite looking redundant next to width:100%.
     A grid item's min-width defaults to auto, which means "never shrink below
     my min-content size" — and for an <img> that is the intrinsic width of
     whichever srcset candidate was chosen. Here that is 375px inside a 345px
     track, so the item wants to be wider than the column it sits in. Webflow's
     own max-width:none removes the usual brake on that.
     Chrome currently gets away with it because a definite width clamps the
     automatic minimum, but that clamping is a subtle corner of the spec that
     engines have not always agreed on, and when it does not apply the images
     overflow their tracks: they swallow the gutters, run wider than the grid,
     and shove the row grid upward under the paragraph. Saying min-width:0 and
     max-width:100% outright removes the dependency on that behaviour. */
  min-width: 0;
  max-width: 100%;
  max-height: none;
  /* THE one that actually matters. object-fit:cover scales the picture until it
     covers the box, and the excess has to go somewhere — the spec leaves that to
     overflow, which is `visible` on an <img> by default. So the box was a tidy
     345x194 while the picture painted up to 345x539 straight over its
     neighbours: gutters swallowed, images all apparently different heights, the
     first one spilling up across the paragraph above. Every box measured
     correctly the whole time, because the boxes were never the problem. */
  overflow: hidden;
}
.team_gallery_grid .gallery-end-spacer { display: none; }

/* Phones get a little more air between the tiles, and explicit separation from
   the paragraph. No aspect-ratio change here: a 16/9 crop briefly lived here to
   make the photos "smaller", but that was chasing the overflow above rather than
   the tile size — and a shorter box only crops these sources harder, several of
   which are portrait (down to 0.64). 4:3 keeps more of each photo in frame. */
@media (max-width: 479px) {
  .team_gallery_grid {
    grid-row-gap: 1.5rem;
    /* Explicit separation from the paragraph above. The flow left only ~15px
       here, and against a photo that reads as the last line sitting on the
       image — which is exactly how this was reported. Stating the gap means it
       cannot be squeezed out by however the copy happens to wrap. */
    margin-top: 1.5rem;
  }
}

/* ── About: leadership cards are clickable across their whole face ───
   Each card is covered by an empty <a class="full-container-link"> that is
   meant to make the whole card one link, but it ships with no z-index — and
   .team_box-img is position:relative and sits after it in the DOM, so the
   photo paints on top and swallows the click. Only the name/title area was
   clickable (this is true of the live Webflow site too). Lifting the link
   above the card's other layers makes the whole card clickable as intended;
   the decorative .team_box-border is already pointer-events:none. */
.full-container-link { z-index: 4; }

/* ── Nav: "Use cases" chevron flips while the dropdown is open ───────
   navbar.js puts w--open on the toggle whenever the panel opens — on hover
   and focus at desktop, on tap in the mobile menu — so one rule covers every
   way in, and the arrow animates back down on the way out. */
.navbar_dropdown-toggle .dropdown-icon {
  transition: transform .3s ease;
}
.navbar_dropdown-toggle.w--open .dropdown-icon {
  transform: rotate(180deg);
}
@media (prefers-reduced-motion: reduce) {
  .navbar_dropdown-toggle .dropdown-icon { transition: none; }
}

/* ── Nav: slides away on scroll down, returns on scroll up ──────────
   New behaviour (Webflow's nav just sat there). The sticky header costs ~64px
   of a phone screen, so /js/navbar.js flags the scroll direction with
   .is-nav-hidden and this hides it while you're reading. Deliberately scoped
   to the mobile breakpoint — the same width at which the nav collapses to a
   hamburger — so the desktop header stays put; the script sets the class at
   every width and lets this rule decide, which means resizing just works.
   .nav_component is position:sticky, and transforming a sticky element doesn't
   disturb its stickiness, so translating it out of view is enough. */
@media (max-width: 991px) {
  .nav_component {
    transition: transform .3s ease;
    will-change: transform;
  }
  html.is-nav-hidden .nav_component {
    transform: translateY(-100%);
  }

  /* The use-case pages park a second sticky bar — the pink "ZENDA for …"
     header — directly beneath the nav, at top:3.5rem, which is the nav's own
     height. Left alone it stays pinned there once the nav slides away, so the
     nav's vacated band shows through as a gap above the pink. Close it up on
     the same timing so the two move as one. This is why the script flags <html>
     rather than the nav element: the pink bar is nowhere near it in the DOM.
     Animating `top` (not transform) is deliberate — it only has any effect
     while the bar is actually stuck, so nothing shifts when the bar is sitting
     in normal flow further down the page. */
  .sticky-section-header {
    transition: top .3s ease;
  }
  html.is-nav-hidden .sticky-section-header {
    top: 0;
  }
}
/* Keep the behaviour but drop the slide, so nobody who has asked for less
   motion gets a header animating up and down the whole way down the page. */
@media (prefers-reduced-motion: reduce) {
  .nav_component,
  .sticky-section-header { transition: none; }
}

/* ── Nav: current-page underline for the Use cases dropdown ─────────
   Page links already get Webflow's .w--current underline; the dropdown
   toggle doesn't, so mark it on use-case pages (class added by script). */
.navbar_link-text.is-current-nav {
  text-decoration: underline;
  text-underline-offset: .125rem;
  text-underline-position: under;
  text-decoration-thickness: 1px;
}

/* ── About: the Partnership block stacks on phones ──────────────────
   .horizontal-content-block is display:flex with no breakpoint of its own, so
   the heading and the paragraph stayed side by side all the way down. At 375px
   that left the text in a 158px column — about 20 characters a line — and
   squeezed the Nagarro logo to zero width. Stacking at the site's existing
   tablet-portrait breakpoint gives both the full width; above it the two
   columns still have ~450px each, which reads fine. The class is used only
   here, on About, so this affects nothing else. */
@media (max-width: 767px) {
  .horizontal-content-block {
    flex-direction: column;
  }
  /* The paragraph and the Nagarro logo are themselves a second row flex inside
     the block, so stacking only the outer one still crushed the logo into a
     34px sliver of a 300x74 image. Both have to stack. Scoped through
     .horizontal-content-block because .header_description is used site-wide. */
  .horizontal-content-block .header_description {
    flex-direction: column;
    align-items: flex-start;
  }
}
/* No max-width on the logo, deliberately. Clamping it to 100% looked like sensible
   protection but made things worse: the percentage resolves against the link wrap,
   which is itself a flex item sized by the image, so the two collapse each other
   and the logo rendered at 78px instead of 227px on desktop. Left alone it sizes
   from its 4rem height at the correct 300:74 ratio and fits the column at every
   width — 244px inside 345px once stacked, 244px inside 585px at 900px. */

/* ── Scroll-in reveals ───────────────────────────────────────────────
   Replaces Webflow's IX2 engine. Elements exported with an inline
   opacity:0 + translate3d(0,15%,0) reveal now carry a .reveal class;
   /js/scroll-reveal.js adds .is-visible via IntersectionObserver when each
   scrolls into view (once). Matches the original "fade up 15%" motion.
   The rule is gated on html.w-mod-js (set synchronously in <head>) so
   that with JS disabled the content is simply visible, never stuck. */
html.w-mod-js .reveal {
  opacity: 0;
  /* Capped, not a bare 15%. translateY percentages resolve against the
     element's OWN height, which is fine for a paragraph (~23px of travel) but
     absurd for a big block: the About photo gallery is 1627px tall, so it was
     starting 254px adrift and sliding that whole way up. Large sections
     visibly barged past their neighbours on the way in, which reads as the
     heading above them overlapping their contents. min() keeps the original
     feel on small elements and just stops the runaway on tall ones. */
  transform: translateY(min(15%, 24px));
  transition: opacity 0.6s ease, transform 0.6s ease;
  will-change: opacity, transform;
}
html.w-mod-js .reveal.is-visible {
  opacity: 1;
  transform: none;
}
@media (prefers-reduced-motion: reduce) {
  html.w-mod-js .reveal,
  html.w-mod-js .reveal.is-visible {
    opacity: 1;
    transform: none;
    transition: none;
  }
}

/* ── Sliders (see /js/sliders.js) ──────────────────────────────────
   Replaces Webflow's slider runtime. Two layouts, picked by the slider's
   own data-animation value. */

/* Fade / cross / outin: every slide shares one grid cell so they stack,
   which also keeps the mask auto-sized to the tallest slide. */
.w-slider-mask.slider-fade-mode {
  display: grid;
  white-space: normal;
}
.w-slider-mask.slider-fade-mode > .w-slide {
  grid-area: 1 / 1;
  width: 100%;
  opacity: 0;
  visibility: hidden;
  transition-property: opacity, visibility;
  transition-timing-function: ease;
  transition-delay: 0s, var(--slider-fade-duration, .5s);
  pointer-events: none;
}
.w-slider-mask.slider-fade-mode > .w-slide.slide-is-active {
  opacity: 1;
  visibility: visible;
  transition-delay: 0s, 0s;
  pointer-events: auto;
  z-index: 1;
}

/* Slide: the row is translated horizontally; the mask clips it. */
.w-slider-mask.slider-slide-mode {
  overflow: hidden;
}
.w-slider-mask.slider-slide-mode > .w-slide {
  will-change: transform;
}

@media (prefers-reduced-motion: reduce) {
  .w-slider-mask.slider-fade-mode > .w-slide,
  .w-slider-mask.slider-slide-mode > .w-slide {
    transition: none !important;
  }
}

/* Dots: .w-slider-dot is sized in em, so each nav's own font-size decides how
   big its dots are. The homepage hero's nav sets 10px; the use-case slider's
   never set one, so it inherited the page's body size and drew dots a third
   larger. Match the homepage. */
.feature-slide-nav { font-size: 10px; }

/* ── Use-case tabs: selected state ───────────────────────────────────
   The exported CSS leaves .acc_tab.w--current transparent — on the Webflow
   site the whole selected/unselected look was applied by IX2 at runtime, so
   it vanished with the engine. Values below match what IX2 set on the live
   site: selected is white / opaque / full size, unselected is transparent /
   30% / scaled to 90%. Transitioning them here (IX2 animated in JS) is what
   makes the swap smooth. */
.acc_tab {
  background-color: #0000;
  opacity: .3;
  transform: scale(.9);
  transition: background-color .3s ease, opacity .3s ease, transform .3s ease;
}
.acc_tab.w--current {
  background-color: var(--base-colors--white, #fff);
  opacity: 1;
  transform: scale(1);
}

/* Fade each pane in as it becomes active, matching the tabs' own
   data-duration-in="300". Deliberately no fill-mode: the pane's resting
   opacity stays 1, so if the animation never runs (very old browser, or the
   page not painting) the content is simply visible rather than stuck
   invisible — the same failure the reveals had to be protected against. */
.acc-content .w-tab-pane.w--tab-active {
  animation: tab-pane-fade-in .3s ease;
}
@keyframes tab-pane-fade-in {
  from { opacity: 0; }
  to   { opacity: 1; }
}

@media (prefers-reduced-motion: reduce) {
  .acc_tab { transition: none; }
  .acc-content .w-tab-pane.w--tab-active { animation: none; }
}

/* ── Mobile menu button (see /js/navbar.js) ─────────────────────────────
   Webflow's IX2 animated the three bars into an X; rebuild that in CSS off
   the .w--open class the script toggles.

   Each bar is 1px tall and they sit .25rem apart at the widths where this
   button is visible (components.css narrows the component's row-gap from .5rem to
   .25rem at <=991px), so an outer bar has to travel 1px + .25rem to land on the
   middle one. Deriving the distance from those two values is what keeps the
   strokes crossing dead centre: the root font-size is fluid, so that .25rem
   grows with the viewport, and any fixed pixel figure could only ever line up
   at a single width — which is why the X used to look slightly lopsided. */
.w-nav-button .nav-button_line {
  --nav-bar-travel: calc(1px + .25rem);
  transition: transform .3s ease, opacity .2s ease;
}
.w-nav-button.w--open .nav-button_line.is-first {
  transform: translateY(var(--nav-bar-travel)) rotate(45deg);
}
.w-nav-button.w--open .nav-button_line.is-second {
  opacity: 0;
}
.w-nav-button.w--open .nav-button_line.is-third {
  transform: translateY(calc(var(--nav-bar-travel) * -1)) rotate(-45deg);
}
/* Webflow's default open-state chrome is grey; keep the site's own look. */
.w-nav-button.w--open {
  background-color: transparent;
}
@media (prefers-reduced-motion: reduce) {
  .w-nav-button .nav-button_line { transition: none; }
}
