/* ==========================================================================
   Trigon Tennis — Design tokens & custom styles
   Tailwind (CDN, utility classes) handles layout; this file covers
   things Tailwind can't: custom properties, keyframes, SVG/court motifs,
   reveal-on-scroll states, reduced-motion handling.
   ========================================================================== */

:root {
  --color-primary: #178F76;       /* brand teal — headings, primary buttons */
  --color-primary-dark: #0B3B31;  /* footer, dark sections */
  --color-accent: #D7E62A;        /* brand lime — CTA highlight */
  --color-accent-ink: #16210A;    /* text on lime */
  --color-ink: #16201A;           /* body text */
  --color-ink-soft: #4B5A50;      /* secondary text */
  --color-bg: #FAFAF7;            /* page background */
  --color-bg-alt: #F1F3EC;        /* alternate section background */
  --color-border: #E1E5DA;

  --font-display: 'Barlow Condensed', sans-serif;
  --font-body: 'Inter', sans-serif;

  --ease-out: cubic-bezier(0.16, 1, 0.3, 1);
}

html {
  scroll-behavior: smooth;
}

body {
  font-family: var(--font-body);
  color: var(--color-ink);
  background: var(--color-bg);
}

.font-display {
  font-family: var(--font-display);
}

/* ---------- Reveal-on-scroll (IntersectionObserver toggles .is-visible) ---------- */

.reveal {
  opacity: 0;
  transform: translateY(16px);
  transition: opacity 0.6s var(--ease-out), transform 0.6s var(--ease-out);
  will-change: opacity, transform;
}

.reveal.is-visible {
  opacity: 1;
  transform: translateY(0);
}

.reveal-stagger > * {
  opacity: 0;
  transform: translateY(14px);
  transition: opacity 0.5s var(--ease-out), transform 0.5s var(--ease-out);
}

.reveal-stagger.is-visible > * {
  opacity: 1;
  transform: translateY(0);
}

.reveal-stagger.is-visible > *:nth-child(1) { transition-delay: 0ms; }
.reveal-stagger.is-visible > *:nth-child(2) { transition-delay: 80ms; }
.reveal-stagger.is-visible > *:nth-child(3) { transition-delay: 160ms; }
.reveal-stagger.is-visible > *:nth-child(4) { transition-delay: 240ms; }
.reveal-stagger.is-visible > *:nth-child(5) { transition-delay: 320ms; }

/* ---------- Header ---------- */

.site-header {
  backdrop-filter: blur(10px);
  background: rgba(250, 250, 247, 0.85);
  transition: box-shadow 0.3s var(--ease-out), padding 0.3s var(--ease-out);
}

.site-header.is-scrolled {
  box-shadow: 0 1px 0 var(--color-border), 0 8px 24px -16px rgba(18, 48, 31, 0.25);
}

/* ---------- Court-line motif (hero background) ---------- */

.court-lines {
  stroke: var(--color-accent);
  stroke-width: 1.5;
  fill: none;
  opacity: 0.35;
}

.court-lines path,
.court-lines line,
.court-lines circle {
  stroke-dasharray: 1400;
  stroke-dashoffset: 1400;
  animation: draw-court 2.4s var(--ease-out) forwards;
}

@keyframes draw-court {
  to { stroke-dashoffset: 0; }
}

/* ---------- 3D tennis ball (hero decoration) ----------
   Plain CSS here, not Tailwind arbitrary-value classes — the theme's
   Tailwind build is precompiled (assets/css/tailwind.css), not a
   runtime CDN, so a new class like w-[400px] only works after
   rebuilding it with the standalone CLI. Writing real positioning here
   instead sidesteps that step entirely for a one-off placement like
   this.

   Mobile-first on purpose (small "corner" version as the unqualified
   default, large version opt-in above 1280px) rather than the other
   way round: measured live with getBoundingClientRect at several
   widths, the hero's text column (.reveal.max-w-2xl) reaches its full
   672px and sits flush against the viewport edge anywhere from ~640px
   up to just under 1280px — e.g. at 700px wide the text's right edge
   is at 668px in a 700px viewport, 32px of clearance total. A
   vertically-centered ball big enough to look intentional simply does
   not fit beside the headline in that whole range, on any screen
   narrower than 1280px, so it goes in the one place that's reliably
   clear instead: the gap between the header and the eyebrow line above
   the headline (pt-20/md:pt-28 leaves 96-133px there, measured at
   several widths in that range) — same spot requested for mobile
   ("на мобильном сделай его меньше чтобы не мешал интерфейсу"), just
   applied everywhere it's actually needed rather than only under one
   arbitrary breakpoint. Defaulting to this safe corner placement, and
   only opting into the big centered version once verified clear
   (>=1280px, 162px+ of measured clearance), means a viewport width I
   didn't explicitly test still gets the safe layout instead of a
   guessed one. */

.hero-model {
  position: absolute;
  z-index: 1;
  top: 8px;
  right: 12px;
  width: 76px;
  height: 76px;
  pointer-events: none;
  background: transparent;
  --poster-color: transparent;
  animation: hero-ball-levitate-corner 4s ease-in-out infinite;
}

@keyframes hero-ball-levitate-corner {
  0%, 100% { transform: translateY(0); }
  50% { transform: translateY(-8px); }
}

@media (min-width: 1280px) {
  /*
   * Moved in from the right edge toward the crosshair mark the client
   * pointed at (screenshot with a hand-drawn arrow), not just eyeballed
   * to match that one screenshot's pixel position — the marked spot is
   * very close to the text column's live edge in that screenshot only
   * because that particular line of description text happens to wrap
   * short of its max column width, not because there's real guaranteed
   * space there. Worked out the actual guaranteed-clear position
   * algebraically instead: .reveal.max-w-2xl's right edge, given the
   * max-w-7xl/mx-auto/px-8 container, comes out to exactly
   * `50% - 64px` of the section width at every viewport >=1280px (the
   * two viewport-dependent terms cancel — verified by measuring
   * getBoundingClientRect at 1280px and 1920px and getting the same
   * -64px offset from center both times). left: calc(50% + 100px)
   * keeps the ball's left edge a real ~36px clear of that, as close to
   * the requested spot as it can sit without floating on top of the
   * description text if it were ever a little longer.
   *
   * Size uses the same kind of algebra, not a fixed px bumped on
   * request and hoped for the best: with left pinned to 50%+100px,
   * `calc(50vw - 120px)` for the width makes left+width always equal
   * `100% - 20px` of the viewport — the sum of a viewport-dependent
   * left offset and a viewport-dependent width, arranged so the two
   * viewport terms cancel out to a constant 20px margin from the
   * right edge at every width, instead of at just the one width it
   * was tuned against. clamp()'d so it can't go below the previous
   * fixed 520px (no regression on a 1280px-ish laptop) or past 900px
   * (so it doesn't turn into something absurd on an ultra-wide
   * monitor) — client asked for it enlarged toward some hand-drawn
   * marks in a screenshot without breaking the layout, and a size that
   * scales with the viewport instead of a single guessed constant is
   * how "bigger, but still fits" holds at whatever width they're
   * actually looking at it on.
   */
  .hero-model {
    right: auto;
    left: calc(50% + 100px);
    top: 50%;
    width: clamp(520px, calc(50vw - 120px), 900px);
    height: clamp(520px, calc(50vw - 120px), 900px);
    animation: hero-ball-levitate-centered 4s ease-in-out infinite;
  }
}

@keyframes hero-ball-levitate-centered {
  0%, 100% { transform: translateY(-50%); }
  50% { transform: translateY(calc(-50% - 18px)); }
}

/* ---------- Ball bounce accent ---------- */

.ball-bounce {
  animation: ball-bounce 2.6s ease-in-out infinite;
}

@keyframes ball-bounce {
  0%, 100% { transform: translateY(0); }
  50% { transform: translateY(-14px); }
}

/* ---------- Card hover tilt ---------- */

.tilt-card {
  transition: transform 0.35s var(--ease-out), box-shadow 0.35s var(--ease-out);
}

.tilt-card:hover {
  transform: translateY(-6px);
  box-shadow: 0 20px 40px -20px rgba(18, 48, 31, 0.35);
}

/* ---------- Nav link underline ---------- */

.nav-link {
  position: relative;
}

.nav-link::after {
  content: '';
  position: absolute;
  left: 0;
  bottom: -4px;
  width: 0;
  height: 2px;
  background: var(--color-accent);
  transition: width 0.25s var(--ease-out);
}

.nav-link:hover::after {
  width: 100%;
}

/* ---------- Placeholder photo texture (until real photos land) ---------- */

.photo-placeholder {
  position: relative;
  background:
    linear-gradient(135deg, rgba(255,255,255,0.06) 25%, transparent 25%) -10px 0/20px 20px,
    linear-gradient(225deg, rgba(255,255,255,0.06) 25%, transparent 25%) -10px 0/20px 20px,
    linear-gradient(315deg, rgba(255,255,255,0.06) 25%, transparent 25%) 0 0/20px 20px,
    linear-gradient(45deg, rgba(255,255,255,0.06) 25%, transparent 25%) 0 0/20px 20px,
    linear-gradient(135deg, var(--color-primary), var(--color-primary-dark));
}

/* ---------- Marquee (address / hours ticker) ---------- */

.marquee-track {
  animation: marquee 22s linear infinite;
}

/* Pause on hover so people can actually read/select/copy the text
   (address, phone-adjacent info) instead of chasing a moving target. */
.marquee-track:hover {
  animation-play-state: paused;
}

@keyframes marquee {
  /* -25%, not -50% — the track now holds 4 identical copies (see the
     HTML), so one copy's width is a quarter of the track, not half.
     Shifting by exactly one copy's width is what makes the loop
     restart invisible: copy 2 is already sitting exactly where copy 1
     started. */
  from { transform: translateX(0); }
  to { transform: translateX(-25%); }
}

/* ---------- Tournament tabs ---------- */

.tourn-tab {
  font-size: 0.875rem;
  font-weight: 600;
  /* 0.6rem vertical padding left these under the ~44px comfortable
     touch-target size (audit-flagged small tap areas); 0.75rem clears
     it without visibly changing the pill's proportions much. */
  padding: 0.75rem 1.1rem;
  min-height: 44px;
  border-radius: 999px;
  border: 1px solid var(--color-border);
  background: #fff;
  color: var(--color-ink-soft);
  transition: background 0.2s var(--ease-out), color 0.2s var(--ease-out), border-color 0.2s var(--ease-out);
  cursor: pointer;
}

.tourn-tab:hover {
  border-color: var(--color-primary);
  color: var(--color-primary);
}

.tourn-tab.is-active {
  background: var(--color-primary);
  border-color: var(--color-primary);
  color: #fff;
}

.tourn-panel.hidden {
  display: none;
}

.tourn-details summary {
  cursor: pointer;
  font-size: 0.8125rem;
  font-weight: 600;
  color: var(--color-primary);
  list-style: none;
}

.tourn-details summary::-webkit-details-marker {
  display: none;
}

.tourn-details summary::before {
  content: '+ ';
}

.tourn-details[open] summary::before {
  content: '– ';
}

.tourn-details {
  font-size: 0.8125rem;
  color: var(--color-ink-soft);
  border-top: 1px solid var(--color-border);
  padding-top: 0.75rem;
  margin-top: 0.75rem;
}

/* ---------- Medal badges (tournament results: 1/2/3 place) ---------- */

.medal-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 1.25rem;
  height: 1.25rem;
  border-radius: 999px;
  font-size: 0.625rem;
  font-weight: 800;
  margin-right: 0.4rem;
  vertical-align: middle;
  flex-shrink: 0;
}

.medal-1 { background: #F5C542; color: #4A3400; box-shadow: 0 0 0 1px rgba(74, 52, 0, 0.15) inset; }
.medal-2 { background: #D6DBE1; color: #3A4048; box-shadow: 0 0 0 1px rgba(58, 64, 72, 0.15) inset; }
.medal-3 { background: #E3A063; color: #4A2A0A; box-shadow: 0 0 0 1px rgba(74, 42, 10, 0.15) inset; }
.medal-n { background: var(--color-border); color: var(--color-ink-soft); }

/* ---------- Pagination (tournaments, news) ---------- */

.pager-btn {
  min-width: 2.25rem;
  height: 2.25rem;
  padding: 0 0.5rem;
  border-radius: 0.6rem;
  border: 1px solid var(--color-border);
  background: #fff;
  color: var(--color-ink-soft);
  font-size: 0.875rem;
  font-weight: 600;
  cursor: pointer;
  transition: background 0.2s var(--ease-out), color 0.2s var(--ease-out), border-color 0.2s var(--ease-out);
}

.pager-btn:hover:not(:disabled) {
  border-color: var(--color-primary);
  color: var(--color-primary);
}

.pager-btn.is-active {
  background: var(--color-primary);
  border-color: var(--color-primary);
  color: #fff;
  cursor: default;
}

.pager-btn:disabled {
  opacity: 0.35;
  cursor: not-allowed;
}

.pager-ellipsis {
  display: inline-flex;
  align-items: center;
  padding: 0 0.25rem;
  color: var(--color-ink-soft);
  font-size: 0.875rem;
}

/* ---------- Gallery albums ---------- */

.gallery-album {
  width: 100%;
  cursor: pointer;
}

/* ---------- Lightbox ----------
   Written as plain CSS rather than a Tailwind opacity-modifier utility
   (e.g. bg-black/92): the CDN build's runtime JIT did not reliably
   generate that class, leaving the backdrop fully transparent — no dimming,
   no visible separation from the page, close button hard to spot. Explicit
   rgba() here always renders regardless of the CDN's JIT timing. */

.lightbox-backdrop {
  background-color: rgba(10, 14, 12, 0.94);
  cursor: pointer;
}

.lightbox-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  border-radius: 999px;
  background: rgba(255, 255, 255, 0.12);
  color: #fff;
  cursor: pointer;
  transition: background 0.2s var(--ease-out), transform 0.2s var(--ease-out);
}

.lightbox-btn:hover {
  background: rgba(255, 255, 255, 0.22);
}

.lightbox-btn:active {
  transform: scale(0.94);
}

/* ---------- Buttons ---------- */

.btn-accent {
  transition: transform 0.2s var(--ease-out), box-shadow 0.2s var(--ease-out);
}

.btn-accent:hover {
  transform: translateY(-2px);
  box-shadow: 0 12px 24px -8px rgba(214, 242, 60, 0.5);
}

.btn-accent:active {
  transform: translateY(0);
}

/* ---------- Mobile menu ---------- */

#mobile-menu {
  transition: max-height 0.35s var(--ease-out), opacity 0.3s var(--ease-out);
  max-height: 0;
  opacity: 0;
  overflow: hidden;
}

#mobile-menu.is-open {
  /* Fallback for the (JS-disabled) no-script case: fits under the
     sticky header (h-16 = 64px) rather than a fixed pixel guess. With
     JS enabled, main.js overrides this with an inline max-height
     measured from the menu's actual position — this 64px guess is
     wrong whenever the announcement bar is showing above the header
     (it stacks ~100px on top, pushing the menu's real top down with
     it), which clipped the phone number / "Записаться" button off the
     bottom of short phones (e.g. 390x667) once the announcement bar
     had pushed the menu down further than this assumed. If the menu
     is still taller than the viewport (very small landscape phones),
     it scrolls within itself instead of clipping either way. */
  max-height: calc(100vh - 64px);
  overflow-y: auto;
  opacity: 1;
}

/* While the mobile menu is open, the page behind it shouldn't scroll —
   only the menu's own content should, and only if it needs to. */
body.menu-open {
  overflow: hidden;
}

/* ---------- Reduced motion: kill everything decorative ---------- */

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }

  .reveal,
  .reveal-stagger > * {
    opacity: 1 !important;
    transform: none !important;
    transition: none !important;
  }

  .court-lines path,
  .court-lines line,
  .court-lines circle {
    animation: none;
    stroke-dashoffset: 0;
  }

  .ball-bounce,
  .marquee-track,
  .hero-model {
    animation: none !important;
  }

  /* .hero-model's centering on >=1280px is done via the levitate
     keyframes' own translateY(-50%), not a static transform (so the
     bob animation and the vertical-centering offset can be the same
     property) — animation:none above would otherwise also remove the
     centering itself, not just the motion. */
  @media (min-width: 1280px) {
    .hero-model {
      transform: translateY(-50%);
    }
  }

  .tilt-card:hover,
  .btn-accent:hover {
    transform: none;
  }
}

/* ---------- Booking widget (online-booking disabled state) ----------
   Shown instead of YCLIENTS' own floating button while online booking
   is turned off in wp-admin → Онлайн-запись (inc/booking-widget.php).
   Plain CSS rather than Tailwind utility classes on purpose: this
   theme's tailwind.css is a compiled build (see the file's own header
   comment), not a runtime JIT, so brand-new utility strings used only
   here wouldn't reliably be in it without a rebuild — same reasoning
   as the Lightbox block above. */

.booking-widget {
  position: fixed;
  right: 24px;
  bottom: 24px;
  z-index: 9000;
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 12px;
}

.booking-widget-toggle {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 64px;
  height: 64px;
  border-radius: 999px;
  background: var(--color-accent);
  color: var(--color-accent-ink);
  box-shadow: 0 10px 30px rgba(11, 59, 49, 0.35);
  cursor: pointer;
  transition: transform 0.2s var(--ease-out);
}

.booking-widget-toggle:hover {
  transform: scale(1.06);
}

.booking-widget-toggle:active {
  transform: scale(0.96);
}

.booking-widget-panel {
  width: 290px;
  max-width: calc(100vw - 48px);
  background: var(--color-bg);
  border-radius: 18px;
  box-shadow: 0 20px 50px rgba(11, 59, 49, 0.25);
  padding: 20px;
}

.booking-widget-panel-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 8px;
}

.booking-widget-panel-title {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 17px;
  color: var(--color-ink);
}

.booking-widget-close {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 28px;
  height: 28px;
  border-radius: 999px;
  color: var(--color-ink-soft);
  cursor: pointer;
  flex-shrink: 0;
  transition: background 0.2s var(--ease-out);
}

.booking-widget-close:hover {
  background: var(--color-bg-alt);
}

.booking-widget-message {
  font-size: 14px;
  line-height: 1.5;
  color: var(--color-ink-soft);
  margin-bottom: 16px;
}

.booking-widget-cta {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 100%;
  border-radius: 999px;
  background: var(--color-accent);
  color: var(--color-accent-ink);
  font-weight: 600;
  font-size: 14px;
  padding: 11px 16px;
  transition: transform 0.2s var(--ease-out);
}

.booking-widget-cta:hover {
  transform: scale(1.02);
}
