/* ==========================================================================
   HALLY — shop and mobile additions.

   Loaded AFTER style.css and never editing it, so the measured desktop geometry
   and tools/verify_geometry.py stay authoritative over a file this one cannot
   touch.

   Breakpoints: >=1280 asserted desktop · 1025-1279 grace band · 768-1024 tablet
   · <=767 phone. The mobile composition starts at 1024 rather than lower because
   that is the widest common touch viewport, and the desktop hero is mouse-tuned,
   fixed height and cannot scroll.
   ========================================================================== */

:root {
  /* the five fabric colours, for the mobile colour dots */
  --swatch-white:    #f2f2f4;
  --swatch-magenta:  #c0224a;
  --swatch-charcoal: #2c2c2e;
  --swatch-cream:    #e9e0be;
  --swatch-brown:    #594740;
}

/* ---------- the CTA is now the add-to-cart button ---------- */
.cta {
  min-width: 155px;                  /* the label swap must never reflow the pill */
  justify-content: center;
  cursor: pointer;
}
.cta__check { width: 0.78em; height: 0.78em; flex: none; display: none; }
.cta.is-added .cta__chev { display: none; }
.cta.is-added .cta__check { display: block; }
.cta:active { transform: scale(0.97); }

/* ---------- live cart badge ---------- */
.badge.is-pop { animation: badgePop 300ms cubic-bezier(0.22, 1, 0.36, 1); }
@keyframes badgePop {
  0%, 100% { transform: scale(1); }
  40%      { transform: scale(1.35); }
}

/* ---------- colour dots and the mobile menu are absent from the desktop reference ---------- */
.cluster { display: contents; }
.dots, .burger, .menu { display: none; }

/* ==========================================================================
   TABLET + PHONE (<= 1024px)
   The desktop stage is a fixed, absolutely positioned, non-scrolling screen.
   Here it becomes an ordinary column. `display: contents` on .lede lets its
   heading, paragraph and button be ordered independently of one another.
   ========================================================================== */
@media (max-width: 1024px) {
  body { overflow: auto; overflow-x: hidden; }

  .stage {
    display: flex;
    flex-direction: column;
    align-items: stretch;
    width: 100%;
    height: auto;
    /* svh, not vh: on mobile `vh` is the LARGEST viewport, so a vh-sized hero
       hides its bottom under the browser chrome on first paint. */
    min-height: 100svh;
    padding: 0 20px calc(24px + env(safe-area-inset-bottom));
  }

  /* release every measured desktop anchor */
  .nav, .logo, .nav__links, .nav__actions, .lede, .buy, .carousel, .shirtslot,
  .motto, .social, .thumb, .arrow, .dots {
    position: static;
    inset: auto;
    transform: none;
    width: auto;
    max-width: none;
  }

  .lede { display: contents; }
  .thumb { display: none; }          /* a phone has no corner to spare */

  /* ---------- header ---------- */
  .nav {
    order: 0;
    display: flex;
    align-items: center;
    justify-content: space-between;
    height: auto;
    min-height: 64px;
    margin: 0 -20px;
    padding: env(safe-area-inset-top) 12px 0;
  }
  .nav__links { display: none; }
  .logo { order: 2; width: 52px; min-width: 0; }
  .logo__mark { margin-bottom: -16%; }
  .logo__word { font-size: 15px; letter-spacing: 0.05em; }
  /* The micro-tagline rendered at 4.5px here, which is a smudge, not text. At any
     size a person could actually read it would crowd a 52px lockup, so on phones it
     goes. On desktop it stays at the size measured off the reference. */
  .logo__tag { display: none; }
  .nav__actions { order: 3; gap: 0; }
  .iconbtn { width: 44px; height: 44px; min-width: 0; display: grid; place-items: center; }
  .iconbtn svg { width: 24px; height: 24px; }
  .badge { top: 4px; right: 2px; font-size: 10px; }

  .burger {
    order: 1;
    display: grid;
    place-content: center;
    gap: 5px;
    width: 44px;
    height: 44px;
    color: var(--ink);
    transition: color 700ms var(--ease-tint) 100ms;
  }
  .burger span {
    display: block;
    width: 20px;
    height: 2px;
    border-radius: 2px;
    background: currentColor;
    transition: transform 220ms ease-out;
  }
  .burger[aria-expanded="true"] span:first-child { transform: translateY(3.5px) rotate(45deg); }
  .burger[aria-expanded="true"] span:last-child { transform: translateY(-3.5px) rotate(-45deg); }

  .menu {
    display: block;
    position: fixed;
    inset: 0;
    z-index: 40;
    background: var(--g2);
    padding: calc(76px + env(safe-area-inset-top)) 28px 28px;
    animation: menuIn 220ms cubic-bezier(0.22, 1, 0.36, 1) both;
  }
  .menu[hidden] { display: none; }
  @keyframes menuIn { from { opacity: 0; transform: translateY(-8px); } }
  .menu__links { display: grid; gap: 2px; }
  .menu__links a {
    font-family: var(--serif);
    font-size: clamp(28px, 8vw, 38px);
    line-height: 1.5;
    color: var(--ink);
    padding: 6px 0;
  }

  /* ---------- heading ---------- */
  .lede__h1 {
    order: 1;
    font-size: clamp(30px, 8.7vw, 44px);
    line-height: 1.22;
    margin: 12px 0 0;
  }

  /* ---------- garment ---------- */
  /* The band and the garment MUST be derived from one number.
     They were not, and the result was the worst bug of this build: the band was
     min(42svh, 58vw) = 226px on a 390x844 phone while the slot was min(86vw, 44svh)
     = 335px wide, which is a 502px tall canvas. A 502px image inside a 226px band
     spilled 138px above and below, covering the heading, the dots, the price and the
     button, and because the carousel takes pointer events for the swipe, that spill
     swallowed every tap on the page.

     --band is the visible garment plus its floor shadow. The render is 1024x1536 and
     that content spans 65.3% of the canvas height, so canvas height = band / 0.653 and
     canvas width = that / 1.5 = band x 1.02. Nothing can overflow by construction. */
  .stage { --band: min(44svh, 76vw); }

  .carousel {
    order: 2;
    position: relative;
    height: var(--band);
    margin: 14px 0 2px;
    pointer-events: auto;
    touch-action: pan-y;             /* a vertical drag still scrolls the page */
  }
  .shirtslot {
    position: absolute;
    left: 50%;
    top: 50%;
    width: calc(var(--band) * 1.02);
    max-width: 90vw;
    transform: translate(-50%, -50%);
    /* Belt as well as braces: even if the sizing above is ever wrong again, the
       garment can never intercept a tap meant for the controls around it. The swipe
       still works, because the carousel itself keeps its pointer events. */
    pointer-events: none;
  }

  /* ---------- dots and chevrons ---------- */
  .cluster {
    order: 3;
    display: flex;
    align-items: center;
    justify-content: center;
    gap: 10px;
    margin: 6px 0 2px;
  }
  .dots { display: flex; align-items: center; gap: 2px; }
  .dot {
    width: 44px;                     /* the touch target, not the visible disc */
    height: 44px;
    display: grid;
    place-items: center;
    cursor: pointer;
  }
  .dot::before {
    content: "";
    width: 12px;
    height: 12px;
    border-radius: 50%;
    background: var(--dot, #999);
    box-shadow: inset 0 0 0 1px rgba(0, 0, 0, 0.25);
    transition: width 180ms ease-out, height 180ms ease-out, box-shadow 180ms ease-out;
  }
  .dot[data-theme="white"]::before    { --dot: var(--swatch-white); }
  .dot[data-theme="magenta"]::before  { --dot: var(--swatch-magenta); }
  .dot[data-theme="charcoal"]::before { --dot: var(--swatch-charcoal); }
  .dot[data-theme="cream"]::before    { --dot: var(--swatch-cream); }
  .dot[data-theme="brown"]::before    { --dot: var(--swatch-brown); }
  .dot.is-active::before {
    width: 16px;
    height: 16px;
    box-shadow: inset 0 0 0 1px rgba(0, 0, 0, 0.25), 0 0 0 1.5px var(--ink);
  }
  .arrow {
    order: 0;
    width: 44px;
    height: 44px;
    min-width: 0;
    aspect-ratio: auto;
    flex: none;
  }
  .arrow--next { order: 2; }
  .arrow svg { width: 18px; height: 18px; }

  /* ---------- price and sizes ---------- */
  /* Two groups, not four items in a row. As a flex row these four children laid out
     side by side and ran 19px off the right edge of a 390px screen, which is what put
     a sideways scrollbar on the page. A grid states the intent: price stacked on the
     left, label over pills on the right. */
  .buy {
    order: 4;
    display: grid;
    grid-template-columns: auto 1fr;
    grid-template-areas:
      "now label"
      "was sizes";
    align-items: end;
    column-gap: 12px;
    row-gap: 2px;
    text-align: left;
    margin-top: 10px;
  }
  .buy__price { grid-area: now; font-size: clamp(22px, 6.5vw, 30px); }
  /* The size pills make row two tall, and `align-items: end` was dropping the struck
     price to the bottom of it, leaving it floating far under the current price as if it
     belonged to something else. It sits at the top of its row, right under 199 LEI. */
  .buy__price--was { grid-area: was; align-self: start;
    font-size: clamp(14px, 4.2vw, 18px); margin-top: 2px; }
  .buy__label { grid-area: label; justify-self: end; margin: 0 0 4px; font-size: 12px; }
  .sizes { grid-area: sizes; justify-self: end; margin: 0; gap: 6px; flex-wrap: wrap; }
  .size { width: 44px; height: 44px; min-width: 44px; min-height: 44px; font-size: 13px; }

  /* ---------- add to cart ---------- */
  .cta {
    order: 5;
    width: 100%;
    height: 56px;
    margin: 16px 0 0;
    padding: 0;
    font-size: 17px;
  }

  /* ---------- tagline ---------- */
  .motto {
    order: 6;
    margin: 20px 0 0;
    font-size: clamp(19px, 5.4vw, 24px);
    text-align: center;
    white-space: normal;
  }

  /* ---------- below the fold ---------- */
  .lede__p {
    order: 7;
    max-width: 60ch;
    margin: 28px auto 0;
    text-align: center;
    font-size: 15px;
  }
  .social {
    order: 8;
    display: flex;
    justify-content: center;
    gap: 6px;
    margin: 26px 0 0;
  }
  .social a { width: 44px; height: 44px; min-width: 0; display: grid; place-items: center; }
  .social svg { width: 20px; height: 20px; }

  /* hover belongs to a mouse; on touch it sticks after a tap */
  .cta:hover, .size:hover, .arrow:hover, .nav__links a:hover, .social a:hover {
    transform: none;
    opacity: 1;
  }
  .arrow:hover { background: var(--arrow-bg); }
}

/* ---------- phone ---------- */
/* On the dark colourways the muted ink measured 82% white, which is fine at desktop
   sizes but only 3.5:1 against magenta and brown once the text drops to 15px on a
   phone. Lift it on small screens only; the desktop clone keeps the measured value. */
@media (max-width: 1024px) {
  :root[data-theme="magenta"],
  :root[data-theme="charcoal"],
  :root[data-theme="brown"] { --ink-soft: rgba(255, 255, 255, 0.94); }
  :root[data-theme="white"],
  :root[data-theme="cream"] { --ink-soft: rgba(17, 17, 17, 0.86); }
}

@media (max-width: 767px) {
  /* 560px is the floor at which everything through the add-to-cart button still
     fits above the fold on an iPhone SE with chrome showing. */
  .stage { min-height: max(100svh, 560px); }
}

/* ---------- very narrow phones ----------
   The dots row is two chevrons plus five 44px touch targets plus gaps: 328px, which
   does not fit the 280px of usable width on a 320px screen and pushed the right
   chevron off the edge. Below 380px the chevrons go and the dots carry the carousel,
   together with the swipe. Every target stays at 44px. */
@media (max-width: 379px) {
  .cluster .arrow { display: none; }
}

/* ---------- short viewports ----------
   On a 320x568 phone the add-to-cart button landed at y 604, below the fold, so the
   whole point of the screen was hidden until you scrolled. Tighten the bands until the
   purchase loop fits again. */
@media (max-width: 1024px) and (max-height: 620px) {
  .stage { --band: min(30svh, 46vw); }
  .lede__h1 { font-size: clamp(24px, 7vw, 32px); margin-top: 6px; }
  .carousel { margin: 8px 0 0; }
  .cluster { margin: 4px 0 0; }
  .cta { margin-top: 10px; height: 50px; }
  .motto { margin-top: 12px; font-size: 17px; }
}

/* ---------- tablet: same structure, more room ---------- */
@media (min-width: 768px) and (max-width: 1024px) {
  .stage { padding-left: 32px; padding-right: 32px; }
  .lede__h1, .buy, .cta, .motto, .lede__p, .cluster, .carousel {
    width: 100%;
    max-width: 560px;
    margin-left: auto;
    margin-right: auto;
  }
  .stage { --band: min(46svh, 46vw); }
}

/* ---------- landscape phone: a tall column would leave nothing visible ---------- */
@media (max-width: 1024px) and (orientation: landscape) and (max-height: 520px) {
  .carousel { height: 62svh; min-height: 180px; }
  .lede__h1 { font-size: clamp(22px, 4.4vw, 30px); }
  .motto { display: none; }
}
