/* style.css — shared styles for the Artistic Swim Library site
   Theme: light airy backdrop with an animated cyan / teal / blue / indigo gradient
   Palette: #65cfe0 (cyan), #31a8bb (teal), #b2eaf3 (pale cyan), #659fe0 (blue), #656de0 (indigo)
   Notes: comments explain major sections. Mobile-first responsive layout. */

/* Display face for the "Sway" logotype only — body copy stays on Inter */
@import url('https://fonts.googleapis.com/css2?family=Pacifico&display=swap');

:root{
  --bg: #eaf9fc; /* pale cyan page wash */
  --bg2: #dcebff; /* light blue gradient stop */
  --bg3: #e7e6fb; /* light indigo gradient stop */
  --panel: #ffffff; /* card/dropdown surface */
  --muted: #4c7b84; /* dark desaturated teal, for secondary text */
  --accent: #31a8bb; /* primary accent: teal (best contrast for links/text on light bg) */
  --accent-cyan: #65cfe0;
  --accent-teal: #31a8bb;
  --accent-pale: #b2eaf3;
  --accent-blue: #659fe0;
  --accent-indigo: #656de0;
  --text: #0d2430; /* dark navy ink */
  --radius: 10px;
}

/* Page baseline */
*{box-sizing:border-box}
html,body{height:100%}
/* .bleed (homepage full-width panels) uses 100vw to stretch edge to edge,
   but 100vw includes the vertical scrollbar's own width — wider than the
   actual visible viewport whenever a scrollbar is present, which otherwise
   shows up as a few extra pixels of permanent horizontal scroll site-wide. */
html{overflow-x:hidden}
body{
  margin:0;
  font-family: 'Inter', system-ui, -apple-system, 'Segoe UI', Roboto, 'Helvetica Neue', Arial;
  background: var(--bg);
  color:var(--text);
  -webkit-font-smoothing:antialiased;
  -moz-osx-font-smoothing:grayscale;
  line-height:1.45;
}

/* subtle page load fade used on body.page--fade. Opacity-only, deliberately:
   a transform here (even briefly, even reset to none afterwards) makes body
   a containing block for its position:fixed children — including
   body::before's ambient grid — pinning them to body's own box instead of
   the viewport, so they stop tracking scroll past one viewport-height. */
.page--fade{animation:fadeIn 420ms ease both}
@keyframes fadeIn{from{opacity:0}to{opacity:1}}

.container--nav{max-width:1100px;margin:0 auto;padding:14px 16px;display:flex;align-items:center;justify-content:space-between}

/* "Sway" logotype: a display script face, a moving gradient fill, and a
   little wave-underline that draws itself in on load — a wordmark, not
   just styled body text. */
.brand{
  font-family:'Pacifico', 'Segoe Script', cursive;
  font-size:1.7rem;
  font-weight:400;
  line-height:1;
  letter-spacing:0.5px;
  text-decoration:none;
  display:inline-flex;
  flex-direction:column;
  align-items:flex-start;
  gap:2px;
  background:linear-gradient(100deg, var(--accent-teal), var(--accent-cyan) 35%, var(--accent-blue) 65%, var(--accent-indigo));
  background-size:220% auto;
  background-position:0% center;
  -webkit-background-clip:text;
  background-clip:text;
  color:transparent;
  transition:background-position 700ms ease, transform 200ms ease;
}
.brand:hover{background-position:100% center;transform:translateY(-1px)}
.brand::after{
  content:'';
  display:block;
  width:44px;
  height:6px;
  background:linear-gradient(90deg, var(--accent-teal), var(--accent-indigo));
  -webkit-mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 44 6'%3E%3Cpath d='M0 3 C 6 0, 10 6, 16 3 S 26 0, 32 3 S 42 6, 44 3' fill='none' stroke='black' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E");
  mask-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 44 6'%3E%3Cpath d='M0 3 C 6 0, 10 6, 16 3 S 26 0, 32 3 S 42 6, 44 3' fill='none' stroke='black' stroke-width='2' stroke-linecap='round'/%3E%3C/svg%3E");
  -webkit-mask-size:100% 100%;
  mask-size:100% 100%;
  opacity:0;
  transform:scaleX(0);
  transform-origin:left center;
  animation:brandWaveIn 700ms ease 350ms both;
}
@media (prefers-reduced-motion: no-preference){
  @keyframes brandWaveIn{from{opacity:0;transform:scaleX(0)}to{opacity:1;transform:scaleX(1)}}
}
@media (prefers-reduced-motion: reduce){
  .brand::after{opacity:1;transform:scaleX(1);animation:none}
}

/* Header/nav */
.site-header{background:rgba(255,255,255,0.5);backdrop-filter:blur(6px);border-bottom:1px solid rgba(13,36,48,0.06);box-shadow:0 6px 20px rgba(13,36,48,0.07);transition:all 220ms ease}
.site-header--scrolled{background:rgba(255,255,255,0.85);backdrop-filter:blur(10px);border-bottom:1px solid rgba(49,168,187,0.15);box-shadow:0 8px 26px rgba(13,36,48,0.12)}

.nav{display:flex;align-items:center;gap:18px}
.nav__list{list-style:none;margin:0;padding:0;display:flex;gap:12px;align-items:center}
.nav__list a, .dropbtn{position:relative;color:var(--text);text-decoration:none;font:inherit;letter-spacing:inherit;line-height:1.45;padding:8px 10px;border-radius:6px;background:transparent;border:none;cursor:pointer;transition:color 200ms ease}

/* Animated underline on nav links */
.nav__list a::after, .dropbtn::after{content:'';position:absolute;bottom:-2px;left:10px;width:0;height:2px;background:var(--accent);transition:width 200ms ease}
.nav__list a:hover::after, .dropbtn:hover::after{width:calc(100% - 20px)}

.nav__list a:hover, .dropbtn:hover{color:var(--accent)}

/* Dropdown menus: smooth transitions instead of instant toggle */
.dropdown{position:relative}
.dropdown__menu{position:absolute;left:0;top:100%;margin:0;min-width:180px;background:var(--panel);border-radius:8px;padding:8px 0;box-shadow:0 8px 24px rgba(13,36,48,0.14);opacity:0;visibility:hidden;transform:translateY(-8px);transition:opacity 200ms ease, transform 200ms ease, visibility 200ms ease;pointer-events:none}

/* Invisible hover bridge so the menu doesn't close while crossing the gap
   between the button and the first item */
.dropdown__menu::before{content:'';position:absolute;left:0;right:0;top:-10px;height:10px}

.dropdown:hover > .dropdown__menu, .dropdown:focus-within > .dropdown__menu{opacity:1;visibility:visible;transform:translateY(0);pointer-events:auto}

/* Nested dropdowns: make visible on submenu hover */
.submenu:hover > .dropdown__menu.nested, .submenu:focus-within > .dropdown__menu.nested{opacity:1;visibility:visible;transform:translateY(0);pointer-events:auto;display:block}
.dropdown__menu.nested{position:static;margin-top:6px;opacity:1;visibility:visible;transform:none;background:transparent;box-shadow:none;padding:0;pointer-events:auto}

/* Rotating caret */
.dropbtn{position:relative}
@media (prefers-reduced-motion: no-preference){
  .dropbtn{transition:color 200ms ease, transform 200ms ease}
  .dropdown:hover .dropbtn, .dropdown:focus-within .dropbtn{transform:scaleY(1.1)}
}

.dropdown__menu li{list-style:none}
.dropdown__menu a{display:block;padding:8px 14px;color:var(--muted);text-decoration:none;transition:color 200ms ease}
.dropdown__menu a:hover{color:var(--text);background:linear-gradient(90deg, rgba(101,207,224,0.1), transparent)}

/* Mega menu: the header's Library dropdown opens straight onto every age /
   discipline category in two columns, instead of Figures/Elements as an
   extra click each */
.dropdown--mega .dropdown__mega{
  position:absolute;left:0;top:100%;margin:0;display:flex;gap:28px;
  min-width:340px;background:var(--panel);border-radius:10px;padding:16px 20px;
  box-shadow:0 8px 24px rgba(13,36,48,0.14);
  opacity:0;visibility:hidden;transform:translateY(-8px);
  transition:opacity 200ms ease, transform 200ms ease, visibility 200ms ease;
  pointer-events:none;
}
.dropdown--mega .dropdown__mega::before{content:'';position:absolute;left:0;right:0;top:-10px;height:10px}
.dropdown--mega:hover .dropdown__mega, .dropdown--mega:focus-within .dropdown__mega{opacity:1;visibility:visible;transform:translateY(0);pointer-events:auto}
.dropdown__col{display:flex;flex-direction:column;gap:2px;min-width:150px}

/* Figures/Elements column headings double as links straight to their
   overview page — kept looking like plain section labels (not buttons) so
   they still read as headings for the columns below them, with just a
   color/underline hover to hint they're clickable */
.dropdown__col > .dropdown__heading{color:var(--accent);font-size:0.78rem;font-weight:600;text-transform:uppercase;letter-spacing:0.06em;padding:4px 6px 6px;display:inline-block;text-decoration:none;transition:color 160ms ease}
.dropdown__col > .dropdown__heading:hover{color:var(--accent-blue);text-decoration:underline}
.dropdown__col > .dropdown__heading::after{content:none}

/* opacity/visibility stay unconditional (fixes the nested-menu-invisible
   bug described above), but pointer-events must NOT — pointer-events on a
   child is honored even while an ancestor (.dropdown__mega) is
   pointer-events:none, so forcing "auto" here unconditionally left these
   links silently clickable/hoverable at all times, invisible, sitting
   right under the header, regardless of whether the mega panel was ever
   opened. Gate it behind the same hover/focus state that reveals the
   mega panel itself. */
.dropdown__col .dropdown__menu{position:static;margin:0;min-width:0;background:none;padding:0;transform:none;box-shadow:none;opacity:1;visibility:visible}
.dropdown--mega:hover .dropdown__col .dropdown__menu, .dropdown--mega:focus-within .dropdown__col .dropdown__menu{pointer-events:auto}
.dropdown__col .dropdown__menu a{padding:6px 6px;border-radius:6px}

/* Header search: compact, always visible, submits straight to the library
   search results (library.html reads ?q= on load). Wrapped in the same
   .search-form__field the library/search hero bars use, so it gets the
   shared autocomplete dropdown too — just narrower, matching the compact
   nav input instead of the hero's full-width one. */
.nav-search .search-form__field{flex:none;max-width:none}
/* The input also carries the shared .search-input class (for the icon-reveal
   selector below), but that class's own width/padding/font-size are sized
   for the full hero bar — reassert the compact nav dimensions here at
   higher specificity so they don't leak in and blow up the header box */
.nav-search .search-input{width:170px;padding:8px 34px 8px 14px;font-size:0.9rem;box-shadow:none}
.nav-search .search-input:focus{width:220px}
/* Same clear-icon-appears-once-you-type affordance as the library/search
   hero bars, just scaled down to fit the compact pill instead of the
   full-size hero input */
.nav-search .search-form__icon{width:26px;height:26px;right:4px}
/* The compact nav-search box is too narrow for the hero suggestion layout's
   side-by-side title/category columns, so give it its own fixed-width panel
   with the category stacked under the title instead of squeezed beside it */
.nav-search .search-suggest{left:0;right:auto;width:260px}
.nav-search .search-suggest__item{flex-direction:column;align-items:flex-start;gap:2px}
.nav-search .search-suggest__cat{font-size:0.72rem}
.nav-search{display:flex}
.nav-search__input{width:170px;padding:8px 14px;border-radius:999px;border:1px solid rgba(13,36,48,0.15);background:rgba(255,255,255,0.7);color:var(--text);font:inherit;font-size:0.9rem;transition:width 220ms ease, border-color 200ms ease, box-shadow 200ms ease}
.nav-search__input:hover{border-color:rgba(49,168,187,0.4)}
.nav-search__input:focus{width:220px;outline:none;border-color:rgba(101,207,224,0.6);box-shadow:0 0 0 4px rgba(101,207,224,0.16)}

/* Mobile nav toggle: hidden on desktop, becomes the way into the whole nav
   (links + search) once things get too cramped to show inline */
.nav-toggle{display:none;flex-direction:column;justify-content:center;gap:5px;width:34px;height:34px;border:none;background:transparent;cursor:pointer;padding:6px;flex-shrink:0}
.nav-toggle span{display:block;width:100%;height:2px;background:var(--text);border-radius:2px;transition:transform 200ms ease, opacity 200ms ease}
.nav-toggle[aria-expanded="true"] span:nth-child(1){transform:translateY(7px) rotate(45deg)}
.nav-toggle[aria-expanded="true"] span:nth-child(2){opacity:0}
.nav-toggle[aria-expanded="true"] span:nth-child(3){transform:translateY(-7px) rotate(-45deg)}

/* Main content */
.site-main{max-width:1100px;margin:28px auto;padding:0 16px}
.hero{padding:28px 12px}

/* Hero heading entrance animations: staggered fade + slide-up */
.hero h1{font-size:clamp(1.6rem, 3.6vw, 2.4rem);margin:0 0 8px;opacity:0;transform:translateY(12px)}
@media (prefers-reduced-motion: no-preference){
  .hero h1{animation:heroHeadingIn 600ms ease 200ms both}
  @keyframes heroHeadingIn{from{opacity:0;transform:translateY(12px)}to{opacity:1;transform:translateY(0)}}
}

.lead{color:var(--muted);margin:0 0 12px;opacity:0;transform:translateY(12px)}
@media (prefers-reduced-motion: no-preference){
  .lead{animation:heroHeadingIn 600ms ease 400ms both}
}

.cta{opacity:0;transform:translateY(12px)}
@media (prefers-reduced-motion: no-preference){
  .cta{animation:heroHeadingIn 600ms ease 600ms both}
}

/* Search area */
.search-hero{position:relative;z-index:20;padding:18px 12px 6px;text-align:center;display:flex;flex-direction:column;align-items:center}
.search-hero h1{font-size:clamp(2rem, 4.2vw, 2.8rem);margin:0 0 10px}
.search-hero .lead{margin:0 0 22px;max-width:640px;white-space:nowrap}
.search-form{display:flex;gap:10px;align-items:center;max-width:760px;width:100%;justify-content:center}
.search-form__field{position:relative;flex:1;max-width:640px}
.search-input{width:100%;padding:16px 52px 16px 20px;border-radius:999px;border:1px solid rgba(13,36,48,0.15);background:var(--panel);color:var(--text);font-size:1.02rem;box-shadow:0 6px 18px rgba(13,36,48,0.06);transition:border-color 200ms ease, box-shadow 200ms ease}
.search-input:hover{border-color:rgba(49,168,187,0.4)}
.search-input:focus{border-color:rgba(101,207,224,0.6);box-shadow:0 0 0 5px rgba(101,207,224,0.18), 0 6px 18px rgba(13,36,48,0.08)}
/* Icon-only submit, tucked into the pill's right edge — only appears once
   the visitor has actually typed something (empty input shows its
   placeholder, which :placeholder-shown targets) */
.search-form__icon{position:absolute;right:6px;top:50%;width:36px;height:36px;border:none;border-radius:50%;background:linear-gradient(135deg, var(--accent-cyan), var(--accent-indigo));color:#fff;display:flex;align-items:center;justify-content:center;cursor:pointer;opacity:0;pointer-events:none;transform:translateY(-50%) scale(0.7);transition:opacity 200ms ease, transform 200ms ease}
.search-input:not(:placeholder-shown) ~ .search-form__icon{opacity:1;pointer-events:auto;transform:translateY(-50%) scale(1)}
.search-note{color:var(--muted);font-size:0.95rem;margin-top:8px}

/* Autocomplete suggestions dropdown, attached under any .search-form__field
   (both the library hero search and the header's compact nav-search) */
.search-suggest{position:absolute;top:calc(100% + 8px);left:0;right:0;background:var(--panel);border:1px solid rgba(101,159,224,0.22);border-radius:14px;box-shadow:0 16px 34px rgba(13,36,48,0.18);max-height:200px;overflow-x:hidden;overflow-y:auto;opacity:0;visibility:hidden;transform:translateY(-6px);transition:opacity 180ms ease, transform 180ms ease, visibility 180ms ease;z-index:200;text-align:left}
.search-suggest.is-open{opacity:1;visibility:visible;transform:translateY(0)}
.search-suggest__item{display:flex;justify-content:space-between;align-items:baseline;gap:10px;padding:10px 16px;color:var(--text);text-decoration:none;font-size:0.92rem}
.search-suggest__item:hover, .search-suggest__item.is-active{background:rgba(101,207,224,0.14)}
.search-suggest__cat{color:var(--muted);font-size:0.78rem;white-space:nowrap}

/* Dedicated search-results page: compact top-left search bar (not a hero) */
.search-bar-top{display:flex;align-items:center;gap:28px;flex-wrap:wrap;padding:22px 0 20px}
.search-bar-top .search-form{justify-content:flex-start;max-width:560px}
.search-results-meta{color:var(--muted);font-size:0.9rem;margin:0 0 18px}
.gallery-grid{display:grid;grid-template-columns:repeat(auto-fill, minmax(230px, 1fr));gap:16px}

/* Cards / quick links grid */
.grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(220px,1fr));gap:12px}
.card{position:relative;padding:16px;background:linear-gradient(180deg, #ffffff, var(--bg));border-radius:10px;text-decoration:none;color:var(--text);display:block;border:1px solid rgba(101,159,224,0.18);transition:all 200ms ease;overflow:hidden}

/* Search filtering: fade-out hidden cards */
.card.search-hidden{opacity:0;pointer-events:none;visibility:hidden;transition:opacity 300ms ease, visibility 300ms ease}

/* Category label for cards rendered by the search results */
.card__category{color:var(--muted);font-size:0.9rem;margin-top:6px}

/* Shine sweep effect: pseudo-element that sweeps top-to-bottom on hover */
.card::before{content:'';position:absolute;top:-100%;left:0;width:100%;height:100%;background:linear-gradient(180deg, rgba(101,207,224,0.25), transparent);pointer-events:none;transition:top 600ms ease}

@media (prefers-reduced-motion: no-preference){
  .card:hover::before{top:100%}
}

.card:hover{
  box-shadow:0 8px 26px rgba(13,36,48,0.12), 0 0 24px rgba(101,207,224,0.35);
  transform:translateY(-4px) scale(1.02);
  border-color:rgba(101,207,224,0.5)
}

/* Buttons */
.btn{display:inline-block;background:linear-gradient(90deg,var(--accent-cyan),var(--accent-blue),var(--accent-indigo));color:#ffffff;padding:10px 14px;border-radius:8px;text-decoration:none;font-weight:600;transition:all 160ms ease;border:none;cursor:pointer}
.btn:hover{transform:translateY(-2px);transition:transform 160ms ease}
@media (prefers-reduced-motion: no-preference){
  .btn:active{transform:translateY(0) scale(0.98)}
}

/* Primary CTA button on homepage: subtle pulsing glow */
.hero .btn{position:relative}
@media (prefers-reduced-motion: no-preference){
  .hero .btn{animation:ctaPulse 2.5s ease-in-out infinite}
  @keyframes ctaPulse{
    0%, 100%{box-shadow:0 0 0 0 rgba(101,207,224,0.4)}
    50%{box-shadow:0 0 0 8px rgba(101,207,224,0)}
  }
}

.btn--search{padding:10px 14px}

@media (prefers-reduced-motion: reduce){
  .card:hover::before{transition:none}
  .hero .btn{animation:none}
}
.skill-list{padding-left:1rem;color:var(--muted)}
.skill-list li{padding:6px 0}
.skill-list li.spacer{list-style:none;padding:8px 0}
.skill-list a{color:var(--text);text-decoration:none}
.skill-list a:hover{color:var(--accent)}

/* Breadcrumb trail: Library > Figures > <hub> > <page>, replacing the old
   "<- Back to X" links. Renders instantly (no .reveal) since it's a
   wayfinding aid, not decorative content. */
.breadcrumbs{margin:0 0 14px}
.breadcrumbs__list{list-style:none;display:flex;flex-wrap:wrap;margin:0;padding:0;font-size:0.88rem;color:var(--muted)}
.breadcrumbs__item{display:flex;align-items:center}
.breadcrumbs__item a{color:var(--muted);text-decoration:none;transition:color 160ms ease}
.breadcrumbs__item a:hover{color:var(--accent);text-decoration:underline}
.breadcrumbs__item + .breadcrumbs__item::before{content:'›';margin:0 8px;color:rgba(13,36,48,0.3)}
.breadcrumbs__item--current{color:var(--text);font-weight:600}

/* Figure category hub: large animated card grid (replaces the old plain
   skill-list on figures/10u.html, 12u.html, youth-13-15.html). Each card is
   either a real photo/diagram (aspect-ratio media block) or, where no asset
   exists yet, an animated swimmer-pose SVG icon standing in for it. */
.figure-hub-intro{padding:14px 12px}
.hub-intro__meta{color:var(--muted);font-size:0.9rem;margin-top:4px}
.figure-grid{display:grid;grid-template-columns:repeat(auto-fill, minmax(230px, 1fr));gap:22px;margin-top:8px}

.figure-card{position:relative;display:flex;flex-direction:column;background:linear-gradient(180deg, #ffffff, var(--bg));border:1px solid rgba(101,159,224,0.18);border-radius:16px;overflow:hidden;text-decoration:none;color:var(--text);transition:transform 240ms ease, box-shadow 240ms ease, border-color 240ms ease}
.figure-card:hover{transform:translateY(-6px) scale(1.015);box-shadow:0 16px 36px rgba(13,36,48,0.16), 0 0 28px rgba(101,207,224,0.35);border-color:rgba(101,207,224,0.55)}

.figure-card__media{position:relative;aspect-ratio:4/3;display:flex;align-items:center;justify-content:center;background:linear-gradient(180deg, rgba(101,207,224,0.16), rgba(255,255,255,0.55));overflow:hidden}
.figure-card__media img{width:100%;height:100%;object-fit:cover;transition:transform 450ms ease}
.figure-card:hover .figure-card__media img{transform:scale(1.1)}

/* Shine sweep on hover, same language as the homepage quick-link cards */
.figure-card__media::before{content:'';position:absolute;top:-100%;left:0;width:100%;height:100%;background:linear-gradient(180deg, rgba(255,255,255,0.35), transparent);pointer-events:none;transition:top 650ms ease;z-index:1}
@media (prefers-reduced-motion: no-preference){
  .figure-card:hover .figure-card__media::before{top:100%}
}

.figure-card__icon{width:58%;height:58%;overflow:visible;animation:iconSwim 5s ease-in-out infinite}
@media (prefers-reduced-motion: no-preference){
  .figure-card:hover .figure-card__icon{animation:iconSwimHover 700ms ease-in-out infinite}
  @keyframes iconSwim{
    0%, 100%{transform:scale(1, 1) rotate(-3deg)}
    50%{transform:scale(1.05, 0.96) rotate(3deg)}
  }
  @keyframes iconSwimHover{
    0%, 100%{transform:scale(1.16, 1.1) rotate(-8deg)}
    50%{transform:scale(1.24, 1.16) rotate(8deg)}
  }
}
@media (prefers-reduced-motion: reduce){
  .figure-card__icon{animation:none}
}

/* Ripple-ring icon fallback (replaces the old swimmer-pose stick figures
   everywhere a card has no real asset) — the wiggle animation above was
   built for the stick-figure shape, so turn it off here and let the
   ripple's own expanding-rings animation (on its child circles) run
   instead */
.figure-card__icon.ripple-icon{animation:none;width:66%;height:66%}
.figure-card:hover .figure-card__icon.ripple-icon{animation:none}

.figure-grid > .figure-card:nth-child(4n+1) .figure-card__icon{color:var(--accent-cyan)}
.figure-grid > .figure-card:nth-child(4n+2) .figure-card__icon{color:var(--accent-teal)}
.figure-grid > .figure-card:nth-child(4n+3) .figure-card__icon{color:var(--accent-blue)}
.figure-grid > .figure-card:nth-child(4n) .figure-card__icon{color:var(--accent-indigo)}
.figure-grid > .figure-card:nth-child(3n+1) .figure-card__icon{animation-delay:0s}
.figure-grid > .figure-card:nth-child(3n+2) .figure-card__icon{animation-delay:-1.6s}
.figure-grid > .figure-card:nth-child(3n) .figure-card__icon{animation-delay:-3.2s}

.figure-card__title{padding:14px 16px 18px;font-weight:600;line-height:1.35}
.figure-card__code{color:var(--muted);font-weight:700;margin-right:4px}
.figure-card__dd{display:block;margin-top:4px;font-size:0.78rem;font-weight:600;color:var(--accent-teal)}

.figure-card.reveal{transition-delay:calc(var(--card-index, 0) * 70ms)}
.figure-card.reveal.is-visible{transition-delay:0}

/* Footer: distinct columns (brand+tagline / explore links / contact) rather
   than a single bare "© Sway" line, separated by a full-width divider. Each
   column fades/slides in on scroll like the rest of the site (.reveal). */
.site-footer{max-width:1100px;margin:56px auto 0;padding:0 16px 0;color:var(--muted)}
.site-footer::before{content:'';display:block;width:100%;height:1px;margin:0 0 30px;background:rgba(13,36,48,0.7)}
.site-footer__cols{display:grid;grid-template-columns:1.3fr 1fr 1fr 1.2fr;grid-template-areas:"brand explore contact photo";gap:32px 48px;padding-bottom:26px}
.site-footer__col{display:flex;flex-direction:column;gap:9px;min-width:0}
.site-footer__col--brand{grid-area:brand}
.site-footer__col--explore{grid-area:explore}
.site-footer__col--contact{grid-area:contact}
.site-footer__col--photo{grid-area:photo}
.site-footer__col .brand{font-size:1.35rem}
.site-footer__tagline{margin:0;font-size:0.88rem;max-width:230px;line-height:1.5}
.site-footer__heading{font-size:0.76rem;font-weight:600;text-transform:uppercase;letter-spacing:0.07em;color:var(--text)}
.site-footer__col a{color:var(--muted);text-decoration:none;font-size:0.92rem;transition:color 200ms ease}
.site-footer__col a:hover{color:var(--accent)}
.site-footer__col.reveal{transition-delay:calc(var(--card-index, 0) * 90ms)}
.site-footer__col.reveal.is-visible{transition-delay:0}
.site-footer__photo{width:100%;height:100%;min-height:120px;aspect-ratio:4/3;border-radius:10px;display:block;object-fit:cover;background:linear-gradient(135deg,rgba(101,159,224,0.18),rgba(13,36,48,0.1));box-shadow:0 6px 18px rgba(13,36,48,0.25)}

/* Tablet: text block on the left, photo becomes a full-height sidebar image on the right */
@media (max-width:820px){
  .site-footer__cols{
    grid-template-columns:1.15fr 1fr;
    grid-template-areas:
      "brand   photo"
      "explore photo"
      "contact photo";
    row-gap:22px;column-gap:28px;
    align-items:start;
  }
  .site-footer__col--photo{align-self:stretch}
  .site-footer__photo{aspect-ratio:auto}
}

/* Phone: photo becomes a wide banner up top, link columns sit side by side to save height */
@media (max-width:520px){
  .site-footer__cols{
    grid-template-columns:1fr 1fr;
    grid-template-areas:
      "photo   photo"
      "brand   brand"
      "explore contact";
    row-gap:20px;column-gap:20px;
  }
  .site-footer__photo{aspect-ratio:16/9}
}
.site-footer__bottom{margin:0;padding:16px 0 24px;border-top:1px solid rgba(101,159,224,0.12);font-size:0.85rem;text-align:center}

/* Library page: a real-media showcase, framed as its own clearly-marked
   section (heading + hairline top/bottom rules) so it doesn't look like a
   stray strip of images. Auto-drifts and pauses on hover; also drag-to-scroll
   (mouse or touch), driven from script.js rather than a CSS animation so the
   two can share the same transform without fighting each other. */
.media-section{margin:8px 0 30px;padding:24px 0 4px;border-top:1px solid rgba(101,159,224,0.16);border-bottom:1px solid rgba(101,159,224,0.16)}
.media-section h2{margin:0 0 4px}
.media-section .lead{margin:0 0 16px;color:var(--muted);font-size:0.95rem}
.media-strip{overflow:hidden;margin:0 0 22px;cursor:grab;-webkit-mask-image:linear-gradient(90deg, transparent, #000 8%, #000 92%, transparent);mask-image:linear-gradient(90deg, transparent, #000 8%, #000 92%, transparent)}
.media-strip.media-strip--dragging{cursor:grabbing}
.media-strip__track{display:flex;gap:18px;width:max-content;will-change:transform}
.media-strip__item{position:relative;display:block;flex-shrink:0;border-radius:12px;text-decoration:none}
.media-strip__item img{display:block;height:150px;width:auto;border-radius:12px;border:1px solid rgba(101,159,224,0.25);box-shadow:0 8px 22px rgba(13,36,48,0.14);background:#ffffff;padding:6px;transition:transform 260ms ease, box-shadow 260ms ease, filter 200ms ease;-webkit-user-drag:none;user-select:none}
/* Hover darkens the figure and surfaces its name; suppressed while the strip
   is actually being dragged so panning doesn't flicker captions everywhere */
.media-strip__caption{position:absolute;inset:6px;display:flex;align-items:flex-end;justify-content:center;padding:10px;border-radius:8px;background:linear-gradient(180deg, transparent 45%, rgba(4,26,34,0.75));color:#fff;font-size:0.82rem;font-weight:600;text-align:center;line-height:1.25;opacity:0;transition:opacity 200ms ease;pointer-events:none}
.media-strip:not(.media-strip--dragging) .media-strip__item:hover img{transform:scale(1.06) translateY(-4px);filter:brightness(0.65);box-shadow:0 16px 30px rgba(13,36,48,0.2)}
.media-strip:not(.media-strip--dragging) .media-strip__item:hover .media-strip__caption{opacity:1}

/* Ripple-ring icon: a reusable decorative motif (concentric rings expanding
   outward and fading, like a real water ripple) used on library.html's
   category cards in place of any illustrated figure */
.ripple-icon{width:100%;height:100%;overflow:visible}
.ripple-icon circle{fill:none;stroke:currentColor;stroke-width:3;transform-origin:50px 50px}
@media (prefers-reduced-motion: no-preference){
  .ripple-icon .r1{animation:rippleOut 3.6s ease-out infinite}
  .ripple-icon .r2{animation:rippleOut 3.6s ease-out infinite;animation-delay:1.2s}
  .ripple-icon .r3{animation:rippleOut 3.6s ease-out infinite;animation-delay:2.4s}
  @keyframes rippleOut{
    0%{transform:scale(0.22);opacity:0.9}
    100%{transform:scale(2.4);opacity:0}
  }
}
@media (prefers-reduced-motion: reduce){
  .ripple-icon .r1{opacity:0.7}
  .ripple-icon .r2{opacity:0.45}
  .ripple-icon .r3{opacity:0.2}
}

/* Library category cards: bigger, animated replacement for the old plain
   quick-link .card grid on library.html specifically. Hovering flips the
   card's face (icon/title/count) out and a scrollable list of every skill
   in that category in — a fixed footprint, so the grid never reflows. */
.category-grid{display:grid;grid-template-columns:repeat(auto-fill, minmax(210px, 1fr));gap:20px;margin-top:8px}
.category-card{position:relative;display:block;min-height:210px;border-radius:16px;transition:transform 240ms ease}
.category-card:hover{transform:translateY(-6px) scale(1.02);z-index:5}

/* The card's own visible face + shine-sweep are clipped to this inner layer;
   the popover list is a sibling (not a descendant) so it isn't cut off by
   that same overflow:hidden — it needs its own visible overflow to show a
   box-shadow and, unlike this clip layer, is capped at the card's height
   rather than clipped by it (see .category-card__list below). This is the
   actual <a> for the category (the outer .category-card is a plain div —
   the skill list below has its own real <a> links, and anchors can't nest). */
.category-card__clip{position:absolute;inset:0;display:block;border-radius:16px;overflow:hidden;background:linear-gradient(180deg, #ffffff, var(--bg));border:1px solid rgba(101,159,224,0.18);text-decoration:none;color:var(--text);transition:box-shadow 240ms ease, border-color 240ms ease}
.category-card:hover .category-card__clip{box-shadow:0 16px 36px rgba(13,36,48,0.16), 0 0 28px rgba(101,207,224,0.35);border-color:rgba(101,207,224,0.55)}
.category-card__clip::before{content:'';position:absolute;top:-100%;left:0;width:100%;height:100%;background:linear-gradient(180deg, rgba(101,207,224,0.22), transparent);pointer-events:none;transition:top 650ms ease}
@media (prefers-reduced-motion: no-preference){
  .category-card:hover .category-card__clip::before{top:100%}
}

.category-card__face{position:absolute;inset:0;display:flex;flex-direction:column;align-items:center;justify-content:center;text-align:center;gap:12px;padding:20px;transition:opacity 200ms ease, transform 200ms ease}
.category-card__icon{width:64px;height:64px}
.category-card__title{font-weight:600;font-size:1.05rem;line-height:1.3}
.category-card__count{color:var(--muted);font-size:0.85rem}
.category-card:hover .category-card__face{opacity:0;transform:scale(0.92);pointer-events:none}

/* Popover skill list: grows from 0, overlaying the grid below it (never
   clipped, never pushes the grid's rows around since it's out of flow).
   Capped at the same 210px the resting card face uses, so every card is
   exactly the same size hovered or not, regardless of how many tricks are
   in it — a short list just leaves empty space, a long one scrolls under
   its pinned title header rather than growing the card. */
.category-card__list{list-style:none;margin:0;padding:0 6px 10px;position:absolute;top:0;left:0;right:0;min-height:210px;z-index:1;background:var(--panel);border:1px solid rgba(101,207,224,0.45);border-radius:16px;box-shadow:0 20px 44px rgba(13,36,48,0.22);display:flex;flex-direction:column;justify-content:flex-start;gap:1px;max-height:0;overflow:hidden;opacity:0;pointer-events:none;transition:max-height 280ms ease, opacity 200ms ease}
.category-card:hover .category-card__list{max-height:210px;opacity:1;pointer-events:auto;overflow-y:auto}
.category-card__list a{display:block;padding:6px 10px;border-radius:6px;color:var(--muted);text-decoration:none;font-size:0.86rem;transition:background 150ms ease, color 150ms ease}
.category-card__list a:hover{background:rgba(101,207,224,0.16);color:var(--text)}

/* Pinned title row: stays visible (and clickable straight through to the
   category page) at the top of the list while the tricks below it scroll,
   so hovering never hides the way into the full category. Sits flush at
   top:0 with no container padding above it (padding lives on the header
   itself instead) — otherwise scrolled trick names would peek through
   that padding strip above the sticky element. */
.category-card__list-header{position:sticky;top:0;z-index:1;background:var(--panel);margin:0 -6px 4px;padding:8px 6px 6px;border-radius:16px 16px 0 0;border-bottom:1px solid rgba(101,207,224,0.3)}
.category-card__list-header a{font-weight:700;color:var(--accent);padding:4px 4px}
.category-card__list-header a:hover{background:rgba(101,207,224,0.16);color:var(--accent)}

.category-grid > .category-card:nth-child(4n+1) .category-card__icon{color:var(--accent-cyan)}
.category-grid > .category-card:nth-child(4n+2) .category-card__icon{color:var(--accent-teal)}
.category-grid > .category-card:nth-child(4n+3) .category-card__icon{color:var(--accent-blue)}
.category-grid > .category-card:nth-child(4n) .category-card__icon{color:var(--accent-indigo)}
.category-card.reveal{transition-delay:calc(var(--card-index, 0) * 70ms)}
.category-card.reveal.is-visible{transition-delay:0}

/* Category "feature rows" for figures.html/elements.html — a small grid of
   3-4 .category-card tiles looked sparse and left most of the page empty,
   so these get their own full-width row treatment instead: one big card
   per category, icon medallion + copy + a live preview of a few tricks in
   it, filling the width regardless of how few categories there are. */
.category-features{display:flex;flex-direction:column;gap:16px;margin-top:12px}
.category-feature{display:flex;align-items:center;gap:24px;padding:24px 28px;background:linear-gradient(180deg, #ffffff, var(--bg));border:1px solid rgba(101,159,224,0.18);border-radius:18px;text-decoration:none;color:var(--text);box-shadow:0 6px 20px rgba(13,36,48,0.05);position:relative;overflow:hidden;transition:transform 220ms ease, box-shadow 220ms ease, border-color 220ms ease}
.category-feature:hover{transform:translateY(-4px);box-shadow:0 16px 40px rgba(13,36,48,0.14), 0 0 30px rgba(101,207,224,0.22);border-color:rgba(101,207,224,0.5)}
.category-feature__icon{flex-shrink:0;width:84px;height:84px;border-radius:50%;display:flex;align-items:center;justify-content:center;color:#fff}
.category-feature__icon .ripple-icon{width:52%;height:52%}
.category-feature__body{flex:1;min-width:0;display:flex;flex-direction:column}
.category-feature__count{display:block;font-size:0.76rem;font-weight:700;text-transform:uppercase;letter-spacing:0.05em;color:var(--accent-teal)}
.category-feature__title{display:block;margin:2px 0 6px;font-size:1.35rem;font-weight:600}
.category-feature__blurb{display:block;margin:0;color:var(--muted);max-width:64ch}
.category-feature__preview{display:block;margin-top:8px;font-size:0.82rem;color:var(--muted);opacity:0.85}
.category-feature__cta{flex-shrink:0;font-weight:600;color:var(--accent);white-space:nowrap;transition:color 160ms ease}
.category-feature:hover .category-feature__cta{color:var(--accent-blue)}

.category-features > .category-feature:nth-child(4n+1) .category-feature__icon{background:linear-gradient(135deg, var(--accent-cyan), var(--accent-blue))}
.category-features > .category-feature:nth-child(4n+2) .category-feature__icon{background:linear-gradient(135deg, var(--accent-teal), var(--accent-cyan))}
.category-features > .category-feature:nth-child(4n+3) .category-feature__icon{background:linear-gradient(135deg, var(--accent-blue), var(--accent-indigo))}
.category-features > .category-feature:nth-child(4n) .category-feature__icon{background:linear-gradient(135deg, var(--accent-indigo), var(--accent-teal))}

@media (max-width:640px){
  .category-feature{flex-wrap:wrap;padding:20px}
  .category-feature__cta{width:100%;text-align:right}
}

/* Individual trick page hero: eyebrow + title (+ code/DD badges on element
   pages) above a media row. The media row holds 1-2 panels — the real
   asset image (these are official figure description sheets, not photos,
   so they're framed at a readable width rather than cropped to a fixed
   box) and/or an embedded YouTube video when the page has one; pages with
   neither show a decorative icon tile instead. flex + a shared max-width
   means 1 or 2 panels both end up sensibly sized and centered. */
.trick-hero{margin:8px 0 12px}
.trick-hero__eyebrow{display:inline-block;text-transform:uppercase;letter-spacing:0.06em;font-size:0.76rem;font-weight:700;color:var(--accent-teal);margin-bottom:6px}
.trick-hero__badges{display:flex;gap:8px;margin:10px 0 0}

.trick-media{display:flex;flex-wrap:wrap;gap:20px;justify-content:center;margin:22px 0}
.trick-media__panel{flex:1 1 320px;max-width:520px;display:flex;flex-direction:column;align-items:center;gap:8px}
.trick-media__panel img{display:block;width:100%;height:auto;border-radius:12px;border:1px solid rgba(13,36,48,0.1);box-shadow:0 12px 32px rgba(13,36,48,0.14)}
.trick-media__zoom{font-size:0.82rem;color:var(--muted);text-decoration:none}
.trick-media__zoom:hover{color:var(--accent)}
.trick-media__panel .media-embed__video{width:100%;aspect-ratio:16/9;border-radius:12px;overflow:hidden;box-shadow:0 12px 32px rgba(13,36,48,0.14)}
.trick-media__panel .media-embed__video iframe{position:absolute;inset:0;width:100%;height:100%;border:0}
.trick-media__icon-tile{width:100%;aspect-ratio:4/3;border-radius:16px;background:linear-gradient(180deg, rgba(101,207,224,0.18), rgba(255,255,255,0.6));border:1px solid rgba(101,159,224,0.18);display:flex;align-items:center;justify-content:center}
.trick-media__icon{width:46%;height:46%;color:var(--accent-teal);overflow:visible}

/* Responsive adjustments */
@media (max-width:760px){
  .container--nav{padding:10px;position:relative}
  .nav-toggle{display:flex}
  .nav{position:absolute;top:100%;left:0;right:0;flex-direction:column;align-items:stretch;gap:12px;background:var(--panel);padding:14px 16px 20px;box-shadow:0 12px 26px rgba(13,36,48,0.18);opacity:0;visibility:hidden;transform:translateY(-8px);transition:opacity 200ms ease, transform 200ms ease, visibility 200ms ease}
  .nav.nav--open{opacity:1;visibility:visible;transform:translateY(0)}
  .nav__list{gap:4px;flex-direction:column;align-items:stretch}
  .dropdown__menu{position:static}
  .dropdown__mega{position:static;flex-direction:column;box-shadow:none;opacity:1;visibility:visible;transform:none;pointer-events:auto;display:none;padding:4px 0 4px 14px}
  .dropdown--mega:hover .dropdown__mega, .dropdown--mega:focus-within .dropdown__mega{display:flex}
  .nav-search{order:-1}
  .nav-search__input{width:100%}
  .nav-search__input:focus{width:100%}
  .nav-search .search-input{width:100%}
  .nav-search .search-input:focus{width:100%}
  .search-form{flex-direction:column;align-items:stretch}
  .search-hero .lead{white-space:normal}
}

/* Accessibility focus styles */
a:focus, button:focus, .search-input:focus{outline:3px solid rgba(49,168,187,0.4);outline-offset:2px}

/* Link styling */
a{color:var(--accent)}
a:hover{color:var(--accent-blue)}

/* Contact page: an email card and a form card, same visual language as the
   figure/category cards elsewhere (gradient panel, soft border, hover lift) */
.contact-card{display:flex;gap:20px;align-items:flex-start;background:linear-gradient(180deg, #ffffff, var(--bg));border:1px solid rgba(101,159,224,0.18);border-radius:16px;padding:24px;margin-top:24px;box-shadow:0 6px 20px rgba(13,36,48,0.06);transition:transform 240ms ease, box-shadow 240ms ease}
.contact-card:hover{transform:translateY(-4px);box-shadow:0 16px 36px rgba(13,36,48,0.12)}
.contact-card__icon{flex-shrink:0;width:52px;height:52px;border-radius:50%;display:flex;align-items:center;justify-content:center;background:linear-gradient(135deg, var(--accent-cyan), var(--accent-indigo));color:#fff}
.contact-card__body{flex:1;min-width:0}
.contact-card__body h2{margin:0 0 6px;font-size:1.2rem}
.contact-card__body p{margin:0 0 14px;color:var(--muted)}
.contact-card--form{flex-direction:column}
.contact-card--form .contact-card__body p{margin-bottom:0}

/* Google Form embed: fixed-height frame (the form scrolls internally if
   it's taller), with a visible fallback link since a signed-in-required
   form can't render inside a third-party iframe for a signed-out visitor */
.contact-form-embed{width:100%;margin-top:18px;border-radius:14px;overflow:hidden;border:1px solid rgba(101,159,224,0.18);box-shadow:0 6px 18px rgba(13,36,48,0.06)}
.contact-form-embed iframe{display:block;width:100%;height:900px;border:none;background:#fff}
.contact-form-fallback{margin:12px 0 0;font-size:0.88rem;color:var(--muted);text-align:center}

@media (max-width:600px){
  .contact-card{flex-direction:column}
  .contact-form-embed iframe{height:700px}
}

/* Figure page: hero (title) + media row, then a tips/media/related row */
.figure-split{display:flex;flex-direction:column;gap:16px}
.figure-bottom{flex:1;display:flex;flex-direction:column;gap:12px}
.tips{padding:8px}
.tips .placeholder{color:var(--muted);background:rgba(101,207,224,0.08);padding:12px;border-radius:8px}
.media-links{padding:8px}
.media-links ul{margin:8px 0 0 0;padding-left:1rem}
.media-links a{color:var(--accent);text-decoration:none}
.media-links a:hover{text-decoration:underline}

/* Embedded YouTube video (real URL already present on every figure page) —
   standard responsive-iframe pattern, fixed 16:9 aspect ratio */
.media-embed__video{position:relative;aspect-ratio:16/9;border-radius:10px;overflow:hidden;background:rgba(13,36,48,0.06)}
.media-embed__video iframe{position:absolute;inset:0;width:100%;height:100%;border:0}

/* Cross-links to sibling tricks in the same category, shown on every
   individual page — reuses .skill-list for the link styling itself */
.related-tricks{padding:8px}

@media (min-width:900px){
  /* on wide screens keep same vertical split but allow bottom content to be a row */
  .figure-bottom{flex-direction:row;align-items:flex-start}
  .tips,.media-links,.related-tricks{flex:1}
}

/* Element page: parsed code/DD header + movement-sequence list, replacing
   the old bare heading + "coming soon" placeholder. Shares .tips,
   .media-links and .related-tricks styling with figure pages. */
.element-split{display:flex;flex-direction:column;gap:16px}
.element-header__code{display:inline-block;background:rgba(13,36,48,0.08);color:var(--muted);font-weight:700;font-size:0.82rem;padding:3px 10px;border-radius:999px}
.element-header__dd{display:inline-block;background:rgba(49,168,187,0.14);color:var(--accent-teal);font-weight:700;font-size:0.82rem;padding:3px 10px;border-radius:999px}
.element-sequence{padding:16px;background:linear-gradient(180deg, rgba(101,207,224,0.1), rgba(255,255,255,0.55));border:1px solid rgba(13,36,48,0.1);border-radius:10px}
.element-sequence__list{margin:8px 0 0;padding-left:1.3rem;color:var(--text)}
.element-sequence__list li{padding:4px 0}
.element-body{display:flex;flex-direction:column;gap:12px}

@media (min-width:900px){
  /* same row-of-equal-columns treatment .figure-bottom gets above */
  .element-body{flex-direction:row;align-items:flex-start}
}

/* Phase 1: Background & ambiance — animated gradient drift + floating particles */
body{background:linear-gradient(-45deg, var(--bg), var(--bg2), var(--bg3), var(--panel));background-size:400% 400%;background-attachment:fixed}

/* Ambient backdrop for pages without the interactive homepage canvas. */
body::before{
  content:'';
  position:fixed;
  inset:0;
  z-index:0;
  pointer-events:none;
  background:radial-gradient(ellipse at center, transparent 40%, rgba(4, 26, 34, 0.24) 100%);
}
.page--home::before{display:none}
@media (prefers-reduced-motion: no-preference){
  body{animation:gradientShift 20s ease infinite}
  @keyframes gradientShift{
    0%{background-position:0% 50%}
    50%{background-position:100% 50%}
    100%{background-position:0% 50%}
  }
}

.particles-container{position:fixed;top:0;left:0;width:100%;height:100%;pointer-events:none;z-index:1;overflow:hidden}
.particle{position:absolute;border-radius:50%;backdrop-filter:blur(2px);opacity:0.16}
.particle-1{width:200px;height:200px;background:radial-gradient(circle, var(--accent-cyan), transparent);top:10%;left:5%;animation:float 16s ease-in-out infinite}
.particle-2{width:150px;height:150px;background:radial-gradient(circle, var(--accent-blue), transparent);top:60%;right:10%;animation:float 22s ease-in-out infinite reverse}
.particle-3{width:120px;height:120px;background:radial-gradient(circle, var(--accent-teal), transparent);top:40%;left:50%;animation:float 28s ease-in-out infinite}
.particle-4{width:180px;height:180px;background:radial-gradient(circle, var(--accent-indigo), transparent);bottom:15%;right:20%;animation:float 24s ease-in-out infinite reverse}
@media (prefers-reduced-motion: no-preference){
  @keyframes float{
    0%, 100%{transform:translate(0, 0)}
    25%{transform:translate(30px, -30px)}
    50%{transform:translate(-20px, 40px)}
    75%{transform:translate(40px, 20px)}
  }
}

.site-main, .site-footer{position:relative;z-index:2}
.site-header{position:relative;z-index:3}

/* Home-only pool photo: kept soft so the shared grid and page content remain
   the visual focus while the scene still feels submerged. Opacity/saturation
   raised slightly over the original values so the real pool photo reads with
   more of its own blue/turquoise color instead of washing toward gray. */
.home-photo-bg{
  position:fixed;
  inset:-2%;
  z-index:0;
  pointer-events:none;
  opacity:0.3;
  filter:saturate(1.05) blur(1px);
  background:
    linear-gradient(180deg, rgba(255, 205, 222, 0.42), rgba(150, 205, 230, 0.24)),
    url("assets/pngtree-the-water-in-a-pool-is-very-clear-image_13349747%20(1).jpg") center / cover no-repeat;
  background-blend-mode:soft-light, normal;
}

/* Phase 2: Scroll-triggered reveals */
.reveal{opacity:0;transform:translateY(16px);transition:opacity 600ms ease, transform 600ms ease}
.reveal.is-visible{opacity:1;transform:none}
@media (prefers-reduced-motion: reduce){
  .reveal{transition:none}
  .reveal.is-visible{opacity:1;transform:none}
}

/* Staggered reveals for cards: nth-child adds delay */
.card.reveal{transition-delay:calc(var(--card-index, 0) * 80ms)}
.card.reveal.is-visible{transition-delay:0}

/* Pool backdrop (index.html only): a soft water surface with
   cursor-driven ripples rendered by script.js. Opacity raised from the
   original 0.28 so the water reads as a primary visual element rather than
   a faint watermark — safe since .site-main/.site-footer sit at z-index:2,
   above this layer's z-index:0. */
.pool-bg{position:fixed;top:0;left:0;width:100%;height:100%;overflow:hidden;pointer-events:none;z-index:0;opacity:0.48;mix-blend-mode:multiply}
.pool-water{position:absolute;top:0;left:0;width:100%;height:100%;display:block}

/* Light-shimmer sweep: a pure-CSS diagonal highlight drifting across the
   water surface, independent of the canvas ripple sim, mimicking sunlight
   moving across a pool. */
.pool-bg::after{
  content:'';
  position:absolute;
  inset:-20%;
  background:linear-gradient(115deg, transparent 30%, rgba(255,220,232,0.18) 48%, transparent 66%);
  background-size:220% 220%;
  mix-blend-mode:screen;
  pointer-events:none;
}
@media (prefers-reduced-motion: no-preference){
  .pool-bg::after{animation:shimmerSweep 22s ease-in-out infinite}
  @keyframes shimmerSweep{
    0%, 100%{background-position:0% 0%}
    50%{background-position:100% 100%}
  }
}
@media (prefers-reduced-motion: reduce){
  .pool-bg::after{background-position:50% 50%}
}


/* ============================================================
   Homepage-only sections below. These are deliberately NOT built
   from .card/.category-feature/.category-card — this page gets its
   own visual language (pool-deck signage + swim-lane rail + a
   porthole-strung gallery) rather than re-skinning the same
   components every other page already uses.
   ============================================================ */

/* Full-bleed helper: break a section out of .site-main's 1100px column
   to the full viewport width, for the two "poster" panels below. */
.bleed{width:100vw;position:relative;left:50%;right:50%;margin-left:-50vw;margin-right:-50vw}

/* --- Marquee ribbon: a diagonal, infinitely-scrolling strip of category
   names right under the hero — glassy, tilted, a bit of showy motion that
   isn't a card or a list, just texture/personality before the real content
   starts. Pure CSS loop (two copies of the content, translateX -50%). --- */
.marquee-ribbon{transform:rotate(-1.4deg);margin:8px -4vw 34px;overflow:hidden;background:linear-gradient(90deg, var(--accent-teal), var(--accent-blue) 50%, var(--accent-indigo));box-shadow:0 10px 30px rgba(13,36,48,0.18);position:relative;z-index:1}
.marquee-ribbon__track{display:flex;width:max-content;white-space:nowrap;padding:10px 0}
.marquee-ribbon__track a{display:inline-flex;align-items:center;color:#fff;text-decoration:none;font-weight:600;letter-spacing:0.04em;font-size:0.95rem;padding:0 22px;transition:color 160ms ease}
.marquee-ribbon__track a:hover, .marquee-ribbon__track a:focus-visible{color:var(--text)}
.marquee-ribbon__track a::after{content:'✺';margin-left:22px;opacity:0.6;font-size:0.8rem}
@media (prefers-reduced-motion: no-preference){
  .marquee-ribbon__track{animation:marqueeScroll 32s linear infinite}
  .marquee-ribbon:hover .marquee-ribbon__track, .marquee-ribbon:focus-within .marquee-ribbon__track{animation-play-state:paused}
}
@media (prefers-reduced-motion: reduce){
  .marquee-ribbon__track{width:auto;flex-wrap:wrap}
  .marquee-ribbon__track a[aria-hidden="true"]{display:none}
}
@keyframes marqueeScroll{
  from{transform:translateX(0)}
  to{transform:translateX(-50%)}
}

/* Shimmering gradient heading treatment — an animated version of .brand's
   gradient-text-clip trick, for the two dark poster panels' headings. */
.gradient-text{
  background:linear-gradient(100deg, var(--accent-cyan), #fff 45%, var(--accent-cyan) 90%);
  background-size:260% auto;
  -webkit-background-clip:text;
  background-clip:text;
  color:transparent;
}
@media (prefers-reduced-motion: no-preference){
  .gradient-text{animation:shineSweep 5s ease-in-out infinite}
}
@keyframes shineSweep{
  0%, 100%{background-position:0% center}
  50%{background-position:100% center}
}

/* --- Depth marker: a pool-deck signage panel standing in for the old
   plain feature list + stats band. Dark tiled "pool wall" background,
   stenciled catalog numbers like the depth numerals painted at a
   poolside, with a lane-rope stripe running through the middle. --- */
/* Translucent, not opaque: the live ripple canvas (position:fixed, behind
   everything) stays visible and blurred through this panel instead of being
   flatly covered up — scrolling past "deeper" sections should still feel
   like the same body of water, just darker/under more pressure. */
.depth-marker{background:linear-gradient(165deg, rgba(220,50,140,0.85), rgba(255,115,185,0.8) 55%, rgba(220,50,140,0.85));backdrop-filter:blur(3px) saturate(1.15);-webkit-backdrop-filter:blur(3px) saturate(1.15);color:#eaf9fc;padding:33px 16px 38px;overflow:hidden;position:relative}
.depth-marker::before{
  content:'';
  position:absolute;inset:0;
  background-image:
    repeating-linear-gradient(135deg, rgba(255,255,255,0.035) 0 2px, transparent 2px 26px),
    repeating-linear-gradient(45deg, rgba(255,255,255,0.035) 0 2px, transparent 2px 26px);
  pointer-events:none;
}
.depth-marker__inner{max-width:1100px;margin:0 auto;position:relative}
.depth-marker__watermark{position:absolute;top:-0.3em;right:-0.05em;font-size:min(38vw, 420px);font-weight:700;line-height:1;color:transparent;-webkit-text-stroke:1px rgba(255,255,255,0.06);pointer-events:none;user-select:none;z-index:-1}
.depth-marker__eyebrow{display:block;text-align:center;text-transform:uppercase;letter-spacing:0.22em;font-size:0.72rem;color:var(--accent-cyan);margin:0 0 8px}
.depth-marker__heading{text-align:center;margin:0 0 21px;font-size:clamp(1.45rem, 3.5vw, 2.05rem)}
.depth-rope{position:relative;height:2px;margin:0 0 29px;background:repeating-linear-gradient(90deg, rgba(255,255,255,0.35) 0 14px, transparent 14px 26px)}
.depth-rope::before, .depth-rope::after{content:'';position:absolute;top:50%;width:10px;height:10px;border-radius:50%;background:var(--accent-cyan);transform:translateY(-50%);box-shadow:0 0 12px rgba(101,207,224,0.7)}
.depth-rope::before{left:0}
.depth-rope::after{right:0}
.depth-grid{display:grid;grid-template-columns:repeat(auto-fit, minmax(190px, 1fr));gap:0}
.depth-stat{position:relative;text-align:center;padding:5px 12px}
.depth-stat + .depth-stat::before{content:'';position:absolute;left:0;top:10%;bottom:10%;width:1px;background:rgba(255,255,255,0.14)}
.depth-stat__num{display:block;font-size:clamp(2.05rem, 5.1vw, 3rem);font-weight:700;line-height:1;letter-spacing:-0.02em;-webkit-text-stroke:1px rgba(101,207,224,0.5);color:#eaf9fc;text-shadow:0 0 30px rgba(101,207,224,0.35)}
.depth-stat__label{display:block;margin-top:7px;font-size:0.75rem;text-transform:uppercase;letter-spacing:0.14em;color:rgba(234,249,252,0.6)}

/* Zigzag "water surface" edges bookending the depth marker, so it reads as
   a slab submerged between two waterlines rather than a plain rectangle. */
.depth-marker{clip-path:polygon(0 18px, 4% 0, 8% 18px, 12% 0, 16% 18px, 20% 0, 24% 18px, 28% 0, 32% 18px, 36% 0, 40% 18px, 44% 0, 48% 18px, 52% 0, 56% 18px, 60% 0, 64% 18px, 68% 0, 72% 18px, 76% 0, 80% 18px, 84% 0, 88% 18px, 92% 0, 96% 18px, 100% 0, 100% calc(100% - 18px), 96% 100%, 92% calc(100% - 18px), 88% 100%, 84% calc(100% - 18px), 80% 100%, 76% calc(100% - 18px), 72% 100%, 68% calc(100% - 18px), 64% 100%, 60% calc(100% - 18px), 56% 100%, 52% calc(100% - 18px), 48% 100%, 44% calc(100% - 18px), 40% 100%, 36% calc(100% - 18px), 32% 100%, 28% calc(100% - 18px), 24% 100%, 20% calc(100% - 18px), 16% 100%, 12% calc(100% - 18px), 8% 100%, 4% calc(100% - 18px), 0 100%)}
.depth-marker__inner{padding:14px 0}

/* --- Swim-lane rail: horizontal scroll-snap replacement for the category
   row list, styled like looking down a pool lengthways — alternating
   lane-stripe backgrounds, a lane-number buoy, snap-scrolls natively
   (no JS) with visible native scrollbar styling. --- */
.lane-rail-wrap{margin:36px 0}
.lane-rail-wrap > h2{margin:0 0 6px}
.lane-rail-hint{margin:0 0 16px;color:var(--muted);font-size:0.88rem}
/* Padding on the frame (not the rail) reserves dedicated gutters for the
   nav paddles so they never sit on top of card content — the rail itself
   fills the remaining width and scrolls independently. */
.lane-rail-frame{position:relative;padding:0 50px}
.lane-rail-nav{position:absolute;top:50%;transform:translateY(-50%);z-index:3;width:38px;height:76px;border-radius:14px;border:1px solid rgba(101,159,224,0.28);background:linear-gradient(180deg, rgba(255,255,255,0.95), rgba(255,255,255,0.78));backdrop-filter:blur(4px);box-shadow:0 10px 24px rgba(13,36,48,0.2);color:var(--accent-teal);display:flex;align-items:center;justify-content:center;cursor:pointer;transition:transform 160ms ease, box-shadow 160ms ease, background 160ms ease}
.lane-rail-nav svg{width:20px;height:20px}
.lane-rail-nav:hover{transform:translateY(-50%) scale(1.05);box-shadow:0 14px 30px rgba(13,36,48,0.26);color:var(--accent-blue)}
.lane-rail-nav--prev{left:0}
.lane-rail-nav--next{right:0}
@media (max-width:640px){
  .lane-rail-frame{padding:0}
  .lane-rail-nav{display:none}
}
.lane-rail{display:flex;gap:14px;overflow-x:auto;scroll-snap-type:x proximity;padding:6px 6px 18px;scrollbar-width:thin;scrollbar-color:var(--accent-cyan) transparent}
.lane-rail::-webkit-scrollbar{height:8px}
.lane-rail::-webkit-scrollbar-thumb{background:var(--accent-cyan);border-radius:999px}
.lane-rail::-webkit-scrollbar-track{background:rgba(101,159,224,0.12);border-radius:999px}
.lane-card{scroll-snap-align:start;flex:0 0 auto;width:min(78vw, 320px);border-radius:18px;padding:26px 22px 22px;color:#fff;text-decoration:none;display:flex;flex-direction:column;gap:10px;position:relative;overflow:hidden;transition:transform 220ms ease, box-shadow 220ms ease}
.lane-card::before{content:'';position:absolute;inset:0;background-image:repeating-linear-gradient(0deg, rgba(255,255,255,0.07) 0 3px, transparent 3px 34px);pointer-events:none}
.lane-card:hover{transform:translateY(-6px) rotate(-0.4deg);box-shadow:0 18px 40px rgba(13,36,48,0.28)}
.lane-card__buoy{width:44px;height:44px;border-radius:50%;background:rgba(255,255,255,0.16);border:2px solid rgba(255,255,255,0.55);display:flex;align-items:center;justify-content:center;font-weight:700;font-size:1rem}
.lane-card__title{margin:6px 0 0;font-size:1.2rem}
.lane-card__count{font-size:0.76rem;text-transform:uppercase;letter-spacing:0.1em;opacity:0.85}
.lane-card__blurb{margin:0;font-size:0.86rem;opacity:0.92;flex:1}
.lane-card__cta{font-weight:600;font-size:0.86rem}
.lane-rail > .lane-card:nth-child(7n+1){background:linear-gradient(160deg, var(--accent-cyan), var(--accent-blue))}
.lane-rail > .lane-card:nth-child(7n+2){background:linear-gradient(160deg, var(--accent-teal), var(--accent-cyan))}
.lane-rail > .lane-card:nth-child(7n+3){background:linear-gradient(160deg, var(--accent-blue), var(--accent-indigo))}
.lane-rail > .lane-card:nth-child(7n+4){background:linear-gradient(160deg, var(--accent-indigo), var(--accent-teal))}
.lane-rail > .lane-card:nth-child(7n+5){background:linear-gradient(160deg, var(--accent-cyan), var(--accent-indigo))}
.lane-rail > .lane-card:nth-child(7n+6){background:linear-gradient(160deg, var(--accent-teal), var(--accent-blue))}
.lane-rail > .lane-card:nth-child(7n){background:linear-gradient(160deg, var(--accent-blue), var(--accent-cyan))}

/* --- Porthole gallery: a modifier on the shared .media-strip (script.js's
   drag/auto-drift logic is reused as-is — that's plumbing, not the visual
   language), reskinned as circular ship-window portholes strung on a rope,
   alternating up/down like they're bobbing, instead of library.html's
   rectangular polaroid strip. --- */
.media-strip--portholes{-webkit-mask-image:linear-gradient(90deg, transparent, #000 6%, #000 94%, transparent);mask-image:linear-gradient(90deg, transparent, #000 6%, #000 94%, transparent);padding:20px 0 8px;position:relative}
.media-strip--portholes::before{content:'';position:absolute;left:0;right:0;top:50%;height:2px;transform:translateY(-1px);background:repeating-linear-gradient(90deg, rgba(101,159,224,0.4) 0 10px, transparent 10px 20px);z-index:0}
.media-strip--portholes .media-strip__track{align-items:center;gap:26px}
.media-strip--portholes .media-strip__item{width:150px;height:150px;border-radius:50%;flex-shrink:0;box-shadow:0 10px 26px rgba(13,36,48,0.22), inset 0 0 0 6px rgba(255,255,255,0.85), inset 0 0 0 9px var(--accent-teal);z-index:1}
.media-strip--portholes .media-strip__item:nth-child(odd){transform:translateY(-10px)}
.media-strip--portholes .media-strip__item:nth-child(even){transform:translateY(10px)}
.media-strip--portholes .media-strip__item img{width:100%;height:100%;border:none;border-radius:50%;padding:0;object-fit:cover}
.media-strip--portholes:not(.media-strip--dragging) .media-strip__item:nth-child(odd):hover{transform:translateY(-14px) scale(1.06)}
.media-strip--portholes:not(.media-strip--dragging) .media-strip__item:nth-child(even):hover{transform:translateY(6px) scale(1.06)}
.media-strip--portholes .media-strip__caption{inset:0;border-radius:50%;align-items:center;padding:12px}

/* --- Closing poster: same dark pool-deck slab language as .depth-marker
   (not .hero — .hero's entrance keyframes are timed from page load, so
   reusing it this far down the page would fire invisibly before anyone
   scrolls here) with its own single zigzag waterline on top only. --- */
.cta-poster{background:linear-gradient(160deg, rgba(255,115,185,0.78), rgba(220,50,140,0.86) 70%);backdrop-filter:blur(3px) saturate(1.15);-webkit-backdrop-filter:blur(3px) saturate(1.15);color:#eaf9fc;text-align:center;padding:33px 16px 36px;clip-path:polygon(0 18px, 4% 0, 8% 18px, 12% 0, 16% 18px, 20% 0, 24% 18px, 28% 0, 32% 18px, 36% 0, 40% 18px, 44% 0, 48% 18px, 52% 0, 56% 18px, 60% 0, 64% 18px, 68% 0, 72% 18px, 76% 0, 80% 18px, 84% 0, 88% 18px, 92% 0, 96% 18px, 100% 0, 100% 100%, 0 100%)}
.cta-poster h2{margin:18px 0 8px;font-size:clamp(1.5rem, 4vw, 2.1rem)}
.cta-poster .lead{margin:0 0 20px;color:rgba(234,249,252,0.75)}
.cta-poster .btn{background:linear-gradient(90deg, var(--accent-cyan), #fff, var(--accent-cyan));background-size:220% auto;color:var(--text);font-weight:700}

@media (max-width:640px){
  .depth-grid{grid-template-columns:repeat(2, 1fr)}
  .depth-stat + .depth-stat::before{display:none}
  .depth-stat:nth-child(2n)::before{content:'';position:absolute;left:0;top:10%;bottom:10%;width:1px;background:rgba(255,255,255,0.14)}
}

/* Ripple-sound mute toggle (index.html only) */
.sound-toggle{position:fixed;bottom:18px;right:18px;z-index:4;width:40px;height:40px;border:none;border-radius:50%;background:rgba(255,255,255,0.75);backdrop-filter:blur(6px);box-shadow:0 6px 18px rgba(13,36,48,0.16);font-size:1.1rem;line-height:1;cursor:pointer;transition:transform 160ms ease, box-shadow 160ms ease}
.sound-toggle:hover{transform:scale(1.08);box-shadow:0 8px 22px rgba(13,36,48,0.2)}
.sound-toggle[aria-pressed="true"]{opacity:0.6}

/* end of style.css */
