/*
 * Chill Basket preview landing. A temporary static page: it borrows the store's design tokens
 * (src/frontend/app/assets/styles/_tokens.scss) and its brand intro (SplashIntro.vue) instead of
 * importing them, so it can be thrown away when the real store goes live.
 */

@font-face {
  font-family: 'Barlow Condensed';
  src: url('/assets/fonts/barlow-condensed-700-latin.woff2') format('woff2');
  font-weight: 700;
  font-display: swap;
}

@font-face {
  font-family: 'Barlow Condensed';
  src: url('/assets/fonts/barlow-condensed-800-latin.woff2') format('woff2');
  font-weight: 800;
  font-display: swap;
}

@font-face {
  font-family: 'Inter';
  src: url('/assets/fonts/inter-latin.woff2') format('woff2');
  font-weight: 100 900;
  font-display: swap;
}

:root {
  --orange-500: #e2723a; /* brand; navy text on it 5.70:1 */
  --orange-400: #eb8550;
  --blue-500: #4884b7;
  --blue-700: #2f6a9c; /* 5.73:1 on white */
  --blue-100: #a9d0ea;
  --blue-50: #f1f6fb;
  --navy-900: #0f172a;
  --slate-600: #475569; /* 7.58:1 on white */
  --slate-200: #e2e8f0;
  --white: #fff;
  --on-dark-muted: #c7d2e1; /* 11.68:1 on navy */

  --font-display: 'Barlow Condensed', 'Arial Narrow', 'Roboto Condensed', system-ui, sans-serif;
  --font-body: 'Inter', system-ui, -apple-system, 'Segoe UI', Roboto, Arial, sans-serif;

  --space-2: 0.5rem;
  --space-3: 0.75rem;
  --space-4: 1rem;
  --space-5: 1.5rem;
  --space-6: 2rem;
  --space-7: 3rem;
  --space-8: 4rem;

  --radius-lg: 1rem;
  --radius-pill: 999px;

  --display-1: clamp(2.75rem, 9vw, 5.5rem);
  --display-2: clamp(2rem, 5.5vw, 3.25rem);

  --ease-out: cubic-bezier(0.23, 1, 0.32, 1);
  --ease-in-out: cubic-bezier(0.77, 0, 0.175, 1);
  --duration-reveal: 620ms;

  --splash-exit-at: 1400ms;
  --splash-exit-duration: 650ms;
  --splash-reduced-duration: 900ms;
  /* The hero waits for the intro only when the intro plays (see the script in <head>). */
  --enter-delay: 0ms;
}

html:not(.intro-seen) {
  --enter-delay: calc(var(--splash-exit-at) + 150ms);
}

*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  -webkit-text-size-adjust: 100%;
  scroll-behavior: smooth;
  scroll-padding-top: 4.5rem;
}

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }
}

body {
  margin: 0;
  background: var(--white);
  color: var(--navy-900);
  font-family: var(--font-body);
  font-size: 1rem;
  line-height: 1.6;
}

img {
  display: block;
  max-width: 100%;
  height: auto;
}

h1,
h2,
h3,
p,
ul {
  margin: 0;
}

a {
  color: var(--blue-700);
  text-underline-offset: 0.2em;
}

a:focus-visible {
  outline: 3px solid var(--blue-700);
  outline-offset: 2px;
  box-shadow: 0 0 0 2px var(--white);
}

::selection {
  background: var(--blue-100);
  color: var(--navy-900);
}

.container {
  width: 100%;
  max-width: 72rem;
  margin-inline: auto;
  padding-inline: var(--space-4);
}

@media (min-width: 768px) {
  .container {
    padding-inline: var(--space-6);
  }
}

/* ---- Buttons --------------------------------------------------------------- */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: 3rem;
  padding: 0.75rem 1.5rem;
  border: 2px solid transparent;
  border-radius: var(--radius-pill);
  font-weight: 600;
  line-height: 1.2;
  text-align: center;
  text-decoration: none;
  transition:
    background-color 200ms var(--ease-out),
    color 200ms var(--ease-out),
    transform 140ms var(--ease-out);
}

.btn:active {
  transform: scale(0.97);
}

.btn--primary {
  background: var(--orange-500);
  color: var(--navy-900);
}

.btn--outline {
  border-color: var(--navy-900);
  color: var(--navy-900);
}

.btn--sm {
  min-height: 2.5rem;
  padding: 0.5rem 1rem;
  font-size: 0.9375rem;
}

.btn--block {
  width: 100%;
}

@media (hover: hover) {
  .btn--primary:hover {
    background: var(--orange-400);
  }

  .btn--outline:hover {
    background: var(--navy-900);
    color: var(--white);
  }
}

/* ---- Header ----------------------------------------------------------------- */
.site-header {
  position: sticky;
  top: 0;
  z-index: 10;
  border-bottom: 1px solid var(--slate-200);
  background: var(--white);
}

.site-header__bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  min-height: 3.75rem;
}

.site-header__brand {
  color: var(--navy-900);
  font-family: var(--font-display);
  font-size: 1.5rem;
  font-weight: 800;
  letter-spacing: -0.01em;
  text-decoration: none;
  text-transform: uppercase;
}

.site-header__brand span {
  color: var(--orange-500);
}

/* ---- Hero ------------------------------------------------------------------- */
.hero {
  position: relative;
  overflow: hidden;
  padding-block: var(--space-7);
  background: var(--blue-100);
}

@media (min-width: 992px) {
  .hero {
    padding-block: var(--space-8) 5rem;
  }
}

.hero__court {
  position: absolute;
  right: -12%;
  bottom: -8%;
  width: 19rem;
  aspect-ratio: 4 / 3;
  pointer-events: none;
}

@media (min-width: 992px) {
  .hero__court {
    right: -2%;
    bottom: -18%;
    width: min(38rem, 55%);
  }
}

.court-line {
  stroke: var(--blue-700);
  stroke-width: 2.5;
  stroke-linecap: round;
  stroke-dasharray: 1;
  vector-effect: non-scaling-stroke;
}

.court-line--soft {
  opacity: 0.5;
}

.hero__inner {
  position: relative;
}

.eyebrow {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
  margin-bottom: var(--space-5);
  padding: 0.5rem 1rem;
  border-radius: var(--radius-pill);
  background: var(--white);
  font-family: var(--font-display);
  font-size: 1rem;
  font-weight: 700;
  letter-spacing: 0.04em;
  text-transform: uppercase;
}

.eyebrow__dot {
  width: 0.5rem;
  height: 0.5rem;
  border-radius: 50%;
  background: var(--orange-500);
}

.hero__title {
  max-width: 18ch;
  margin-bottom: var(--space-4);
  font-family: var(--font-display);
  font-size: var(--display-1);
  font-weight: 800;
  line-height: 0.92;
  letter-spacing: -0.015em;
  text-transform: uppercase;
}

.line {
  display: block;
  overflow: hidden;
  /* Room for descenders and the rule under the last line inside the mask. */
  padding-bottom: 0.08em;
}

.line__inner {
  display: block;
}

.hero__title-last {
  position: relative;
  display: inline-block;
}

.hero__title-rule {
  position: absolute;
  right: 0;
  bottom: 0.06em;
  left: 0;
  height: 0.07em;
  border-radius: var(--radius-pill);
  background: var(--orange-500);
  transform-origin: left center;
}

.hero__lead {
  max-width: 38ch;
  margin-bottom: var(--space-5);
  font-size: 1.125rem;
}

.hero__actions {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-3);
}

/* Filled with the hero surface so the court line behind it does not run through the label. */
.hero .btn--outline {
  background: var(--blue-100);
}

/* Entrance. `backwards` holds the start frame through the delay and ends at the element's own
   visible state, so without animations the hero is simply there. */
@media (prefers-reduced-motion: no-preference) {
  .line__inner {
    animation: line-in var(--duration-reveal) var(--ease-out) backwards;
  }

  .line__inner--0 {
    animation-delay: var(--enter-delay);
  }

  .line__inner--1 {
    animation-delay: calc(var(--enter-delay) + 80ms);
  }

  .line__inner--2 {
    animation-delay: calc(var(--enter-delay) + 160ms);
  }

  .hero__title-rule {
    animation: rule-in 700ms var(--ease-out) calc(var(--enter-delay) + 460ms) backwards;
  }

  .court-line {
    animation: draw-in 1s var(--ease-in-out) backwards;
  }

  .court-line--0 {
    animation-delay: var(--enter-delay);
  }

  .court-line--1 {
    animation-delay: calc(var(--enter-delay) + 120ms);
  }

  .court-line--2 {
    animation-delay: calc(var(--enter-delay) + 280ms);
  }
}

@keyframes line-in {
  from {
    opacity: 0;
    transform: translateY(100%);
  }
}

@keyframes rule-in {
  from {
    transform: scaleX(0);
  }
}

@keyframes draw-in {
  from {
    stroke-dashoffset: 1;
  }
}

/* ---- Sections --------------------------------------------------------------- */
.section {
  padding-block: var(--space-7);
}

@media (min-width: 992px) {
  .section {
    padding-block: 5rem;
  }
}

.section--alt {
  background: var(--blue-50);
}

.section--dark {
  background: var(--navy-900);
  color: var(--white);
}

.section-title {
  margin-bottom: var(--space-3);
  font-family: var(--font-display);
  font-size: var(--display-2);
  font-weight: 800;
  line-height: 1;
  text-transform: uppercase;
}

.section-lead {
  max-width: 48ch;
  margin-bottom: var(--space-6);
  color: var(--slate-600);
  font-size: 1.0625rem;
}

/* ---- Products --------------------------------------------------------------- */
.product-grid {
  display: grid;
  /* auto-fit: however many models there are, they fill the row instead of leaving empty tracks. */
  grid-template-columns: repeat(auto-fit, minmax(min(100%, 15rem), 1fr));
  gap: var(--space-5);
  padding: 0;
  list-style: none;
}

.product {
  display: flex;
  flex-direction: column;
  overflow: hidden;
  border: 1px solid var(--slate-200);
  border-radius: var(--radius-lg);
  background: var(--white);
}

/* `contain`, never `cover`: a hoop cropped at the rim or the base misrepresents the product.
   White, because the product photos are shot on white and blend into it. */
.product__photo {
  width: 100%;
  aspect-ratio: 4 / 5;
  border-bottom: 1px solid var(--slate-200);
  background: var(--white);
  object-fit: contain;
}

.product__body {
  display: flex;
  flex: 1;
  flex-direction: column;
  gap: var(--space-3);
  padding: var(--space-5);
}

.product__type {
  align-self: flex-start;
  padding: 0.25rem 0.75rem;
  border-radius: var(--radius-pill);
  background: var(--blue-50);
  color: var(--blue-700);
  font-size: 0.8125rem;
  font-weight: 600;
  letter-spacing: 0.02em;
}

.product__name {
  font-family: var(--font-display);
  font-size: 1.75rem;
  font-weight: 800;
  line-height: 1;
  text-transform: uppercase;
}

.product__code {
  margin-left: var(--space-2);
  color: var(--slate-600);
  font-size: 1rem;
  font-weight: 700;
  letter-spacing: 0.04em;
}

/* The client's spec sheet as label + value rows, the way it reads on the printed sheet. */
.specs {
  margin: 0 0 var(--space-2);
}

.specs__row {
  padding-block: var(--space-2);
  border-top: 1px solid var(--slate-200);
}

.specs__row:last-child {
  border-bottom: 1px solid var(--slate-200);
}

.specs dt {
  color: var(--slate-600);
  font-size: 0.8125rem;
  font-weight: 600;
  letter-spacing: 0.02em;
  text-transform: uppercase;
}

.specs dd {
  margin: 0;
  font-size: 0.9375rem;
  line-height: 1.5;
}

.product__pending {
  margin-bottom: var(--space-2);
  color: var(--slate-600);
}

.product__body .btn {
  margin-top: auto;
}

/* ---- Terms ------------------------------------------------------------------ */
.terms {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(100%, 14rem), 1fr));
  gap: var(--space-5) var(--space-6);
  margin-top: var(--space-5);
  padding: 0;
  list-style: none;
}

.terms__item {
  padding-top: var(--space-4);
  border-top: 3px solid var(--orange-500);
}

.terms__title {
  margin-bottom: var(--space-2);
  font-family: var(--font-display);
  font-size: 1.5rem;
  font-weight: 700;
  line-height: 1.1;
  text-transform: uppercase;
}

.terms__item p {
  color: var(--slate-600);
}

/* ---- Contact ---------------------------------------------------------------- */
.contact__lead {
  max-width: 40ch;
  margin-bottom: var(--space-6);
  color: var(--on-dark-muted);
  font-size: 1.125rem;
}

.contact__actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--space-4) var(--space-6);
}

.contact__link {
  color: var(--white);
  font-weight: 600;
}

/* Written out for whoever would rather save the number or search the account by hand. */
.contact__handles {
  margin-top: var(--space-5);
  color: var(--on-dark-muted);
  font-size: 0.9375rem;
}

.section--dark a:focus-visible {
  outline-color: var(--orange-500);
  box-shadow: 0 0 0 2px var(--navy-900);
}

/* ---- Footer ----------------------------------------------------------------- */
.site-footer {
  padding-block: var(--space-6);
  border-top: 1px solid var(--slate-200);
  color: var(--slate-600);
  font-size: 0.875rem;
}

.site-footer__inner {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: var(--space-2) var(--space-5);
}

/* ---- Brand intro (port of SplashIntro.vue) ------------------------------------
 * Pure CSS: it ends on its own, off-screen and hidden, so nothing depends on JS. The disc is
 * cropped out of the logo JPEG, which has dark grey corners: centre (438, 460), crop radius 428
 * on an 875x926 image, a few pixels inside the white so the grey edge never shows.
 */
.intro-seen .splash {
  display: none;
}

.splash {
  position: fixed;
  inset: 0;
  z-index: 100;
  overflow: hidden;
  pointer-events: none;
}

.splash__curtain {
  position: absolute;
  inset: 0;
  display: grid;
  place-items: center;
  background: var(--orange-500);
  pointer-events: auto;
  will-change: transform;
  animation: splash-lift var(--splash-exit-duration) var(--ease-in-out) var(--splash-exit-at)
    forwards;
}

/* The lower edge is an arc, the same court geometry as the hero. */
.splash__curtain::after {
  position: absolute;
  top: calc(100% - 1px);
  left: -20%;
  width: 140%;
  height: min(12vh, 18vw);
  border-radius: 0 0 50% 50% / 0 0 100% 100%;
  background: inherit;
  content: '';
}

.splash__logo {
  position: relative;
  width: min(clamp(9.5rem, 36vw, 14.5rem), 34dvh);
  aspect-ratio: 1;
  overflow: hidden;
  border-radius: 50%;
  background: var(--white);
  transform-origin: 50% 100%;
  animation:
    splash-drop 950ms 100ms both,
    splash-fade-in 320ms ease-out 100ms both;
}

.splash__logo img {
  position: absolute;
  top: -3.738%; /* -(460 - 428) / 856 */
  left: -1.168%; /* -(438 - 428) / 856 */
  width: 102.22%; /* 875 / 856 */
  max-width: none;
  height: auto;
}

/* Holds the scroll from the first paint and lets go by itself when the intro ends. */
html:not(.intro-seen):has(.splash) {
  scrollbar-gutter: stable;
  animation: splash-scroll-lock calc(var(--splash-exit-at) + var(--splash-exit-duration)) step-end;
}

@keyframes splash-scroll-lock {
  from,
  to {
    overflow: hidden;
  }
}

/* One drop, round until it touches, a ~2% squash on contact and a 6px rebound. */
@keyframes splash-drop {
  0% {
    transform: translateY(-4.5rem) scale(0.96);
    animation-timing-function: cubic-bezier(0.55, 0, 0.85, 0.35);
  }

  40% {
    transform: translateY(0) scale(1);
    animation-timing-function: var(--ease-out);
  }

  47% {
    transform: translateY(0) scale(1.02, 0.975);
    animation-timing-function: cubic-bezier(0.2, 0.7, 0.4, 1);
  }

  64% {
    transform: translateY(-0.375rem) scale(0.995, 1.005);
    animation-timing-function: cubic-bezier(0.6, 0, 0.8, 0.4);
  }

  80% {
    transform: translateY(0) scale(1.006, 0.994);
    animation-timing-function: var(--ease-out);
  }

  100% {
    transform: none;
  }
}

@keyframes splash-fade-in {
  from {
    opacity: 0;
  }
}

@keyframes splash-lift {
  to {
    transform: translateY(calc(-100% - min(12vh, 18vw)));
    visibility: hidden;
  }
}

@keyframes splash-fade-out {
  to {
    opacity: 0;
    visibility: hidden;
  }
}

@media (prefers-reduced-motion: reduce) {
  html:not(.intro-seen):has(.splash) {
    animation-duration: var(--splash-reduced-duration);
  }

  .splash__logo {
    animation: none;
  }

  .splash__curtain {
    animation: splash-fade-out 250ms ease-out calc(var(--splash-reduced-duration) - 250ms)
      forwards;
  }
}
