/* --- S34.8 · Palette "drift" — INVESTIGATED, REVERTED, DO NOT RE-OPEN ----------
 * Review 6 reported the live palette as drift from the brand spec (#F5EFE2 base,
 * #0D1B2A navy, #C9A027 gold) and this session briefly implemented it. It has been
 * reverted in full. The site is back on the canonical V2 values.
 *
 * WHY, so a 8th review does not file it a fourth time: DESIGN_SYSTEM.md marks the
 * Bricolage/Fraunces/Hanken + #F5EFE2/#C9A027 spec as "ORIGINAL SPEC — HISTORICAL
 * ONLY … Nothing below is live." Sessions 34 and 35 each independently measured
 * spec gold on spec cream at ~2.15:1 and recorded the finding as a FALSE report
 * caused by a stale brief still circulating to reviewers (TODO S35-2). Review 6
 * was handed that same stale brief and reached the same wrong conclusion.
 *
 * What the exercise did prove, and what is worth keeping if the palette is ever
 * revisited deliberately: the spec IS shippable if ornament and text are split —
 * brass #C9A027 only on dark (7.07:1 on #0D1B2A) with a darkened #7A5C3A for text
 * on light (5.36:1 on ivory). The 2.15:1 objection only holds if brass is used as
 * body text on cream, which nobody actually proposed. That is a design decision
 * for the client, not a review finding, and it is logged in TODO rather than
 * implemented here.
 *
 * The canonical tokens live in rasvo-v2-design-system.php. Nothing overrides them
 * from this file. */

/* --- S34.9 · A 147px hole under the primary CTA, on a wrapping column ---------
 * Measured at 390px: ADD TO BAG ended at y=345, the reassurance line began at
 * y=492 — while that same line sits only 38px above the accordion beneath it. The
 * largest gap in the buy box was exactly where the eye should move fastest, and it
 * read as a section that had failed to load.
 *
 * Not a margin. The PDP summary column is `flex-direction: column` AND
 * `flex-wrap: wrap`. On a wrapping column container with a definite height the
 * browser distributes items into flex lines and stretches them, which inflated the
 * add-to-cart widget's box to 265px around 157px of actual content — 108px of
 * empty space that belongs to no element, which is why every margin/padding probe
 * on the form came back 0.
 *
 * Verified: flex-wrap:nowrap → widget 265px becomes 157px, gap 147px becomes 39px,
 * matching the 38px rhythm the rest of the column already uses.
 *
 * nowrap is simply correct here: this is a single-column stack and there is no
 * second column for items to wrap into. Applied at all breakpoints because the
 * inflation is not viewport-specific. `:has(> .elementor-widget ...)` matches only
 * the widget's immediate parent container — no generated id, survives re-export. */
body.single-product .e-con:has(> .elementor-widget .elementor-add-to-cart){
  flex-wrap:nowrap;
}

/* --- S36.2 · Mobile homepage sticky price/CTA bar removed (client) ------------
 * Measured before removal at 390x844: the bar was 93px — 11% of the viewport,
 * permanently — while the hero's own "SHOP THE DROP" sits at y=388 (above the
 * fold) and the drop grid carries 4 BUY NOW buttons plus a VIEW ALL. It was
 * duplicating a CTA the user had already seen, and because it is fixed at the
 * bottom it sat ON TOP of the card grid's size pills and BUY NOW — hiding a
 * specific, high-intent CTA in order to show a generic, lower-intent one.
 *
 * It also cost the tab bar: the two cannot coexist (S34.1), so the homepage was
 * trading persistent navigation for a redundant button. Removing the bar returns
 * both the 93px and the tab bar.
 *
 * Kept as display:none rather than deleted from template 267 — the element is
 * frozen-page markup, and this is a one-line revert if a real announcement bar
 * (drop timing, urgency) is wanted in that slot later.
 *
 * Matched on `.elementor-sticky`, NOT `.elementor-sticky--active`: Elementor drops
 * the `--active` modifier once the element reaches its natural position at the
 * bottom of the page, so an `--active` selector let the bar reappear in-flow just
 * above the footer — the button was still there, only lower down. `.elementor-sticky`
 * persists for the element's lifetime. */
.elementor-hide_desktop.elementor-sticky{display:none!important}

/* --- S34.10 · Mobile hero caption/garment overlap — FIXED AT SOURCE ------------
 * Deliberately NOT patched here. rasvo-v2-custom.css already owns the mobile hero
 * framing with its own !important block, and it loads after this one, so a rule
 * here would lose on source order and leave two disagreeing declarations for the
 * next reader to untangle. See the S34.10 note in rasvo-v2-custom.css. */

/* --- S34.11 · The two most trust-critical panels used the least branded type ---
 * "Bag totals", "Your Order" and "Billing Details" render sentence-case Geist
 * while every other label on the site — PRODUCT, PRICE, SUBTOTAL, YOUR BAG — is
 * uppercase Geist Mono. The inconsistency lands precisely at cart and checkout,
 * where an unfamiliar brand is being judged on whether it looks finished.
 *
 * Longhands, not the `font` shorthand: `font:var(--rasvo-v2-mono-label)` parses
 * but Chrome does not apply the substituted shorthand here, so the family and
 * size were silently dropped while text-transform still landed — leaving
 * uppercase Geist at 25px, which is not the label style this is meant to make. */
body.woocommerce-cart .cart_totals > h2,
body.woocommerce-checkout #order_review_heading,
body.woocommerce-checkout .woocommerce-billing-fields > h3,
body.woocommerce-checkout .woocommerce-shipping-fields > h3,
body.woocommerce-checkout .woocommerce-additional-fields > h3{
  font-family:'Geist Mono',ui-monospace,monospace!important;
  font-size:13px!important;
  font-weight:400!important;
  line-height:1.6!important;
  text-transform:uppercase;
  letter-spacing:.16em;
  color:var(--rasvo-v2-ink,#141A23);
}

/* --- S34.12 · The coupon row was the one plugin-default surface on the site ----
 * "Have a coupon? Click here to enter your coupon code" shipped as raw WooCommerce
 * copy in a bare bordered box with a default underlined link — at the last step
 * before payment, on a store with no active promos. An empty promo field is also a
 * known leak: it sends shoppers off-site to hunt for a code they will not find.
 *
 * NOTE: this checkout is Elementor's Checkout widget, not the WooCommerce
 * template, so the markup is `.e-coupon-box` / `.e-woocommerce-coupon-nudge` —
 * NOT `.woocommerce-form-coupon-toggle`, which does not exist on this page at all.
 *
 * One coupon prompt per funnel: the Bag already offers the field, and at checkout
 * the shopper has committed, so a second prompt only invites them to leave and
 * hunt for a code that does not exist. */
/* !important: Elementor's widget CSS reaches this through an id selector
   (`.elementor-widget-woocommerce-checkout-page .woocommerce #customer_details …`,
   specificity 1,1,0) which outranks any class-only selector available here. */
body.woocommerce-checkout .e-coupon-box{display:none!important}

/* Cart keeps its coupon field, but brought onto the type system rather than left
   as the default bordered notice. */
body.woocommerce-cart .coupon .input-text::placeholder{
  font-family:'Geist Mono',ui-monospace,monospace;
  font-size:11px;letter-spacing:.1em;text-transform:uppercase;
}

/* --- S34.13 · Trust signals sat ~530px below the button they reassure ----------
 * PLACE ORDER rendered at y=239 and the "UPI, cards & netbanking / 7-day exchange /
 * dispatched in 2 days" row at y=773 — below the form, in the left column, while
 * the CTA is top-right. Reassurance that far from the commit action does not get
 * read at the moment of doubt. The order-summary column also ended ~400px before
 * the form, leaving a tall void beside it.
 * The summary column is ALREADY sticky — Elementor's checkout widget ships
 * `.e-sticky-right-column`, so no position:sticky is needed or added here; the
 * earlier assumption that the column "collapsed" was measuring the form, not the
 * column. What was actually wrong is only the trust row's placement.
 *
 * Attached to `.place-order` (the div that wraps the button), NOT to #order_review:
 * the button lives in #payment .place-order at y=1236 while #order_review ends at
 * y=825, so hanging the row off the review wrapper put it 400px ABOVE the CTA —
 * the same mistake in the other direction. */
body.woocommerce-checkout .woocommerce-checkout-payment .place-order{
  padding-bottom:4px;
}
body.woocommerce-checkout .woocommerce-checkout-payment .place-order::after{
  /* S39.2 · Non-breaking spaces bind each separator to the phrase BEFORE it, so a
     wrap can only ever happen AFTER a "·", never before one. `text-wrap:balance`
     below equalises the two lines but does not control WHERE they break — at
     460px the line needs ~507px and was breaking into
     "… 7-DAY SIZE EXCHANGE" / "· DISPATCHED IN 2 BUSINESS DAYS", i.e. a line
     opening with a dangling separator on the last screen before payment.
     6-digit \0000a0 (not \00a0) because the next character is a hex digit and
     would otherwise be swallowed into the escape. */
  /* S43 · dispatch → delivery, matching the funnel-wide ETA copy (dispatch ≠
     delivery was a re-audit finding; every other trust line already says 4–9). */
  content:"SECURE CHECKOUT\0000a0· 7-DAY\0000a0SIZE\0000a0EXCHANGE\0000a0· DELIVERY\0000a0IN\0000a04\2013 9\0000a0DAYS";
  display:block;
  margin-top:14px;
  font-family:'Geist Mono',ui-monospace,monospace;
  font-size:10.5px;
  line-height:1.7;
  letter-spacing:.1em;
  color:var(--rasvo-v2-muted-on-light,#4A515C);
  text-align:center;
  text-wrap:balance;
}

/* S34.14 · Scroll-reveal "residue" and "JS dependency" — BOTH FALSE, no rule shipped.
 *
 * Review 7 reported (a) 93 elements at opacity:0 "awaiting an IntersectionObserver",
 * so a JS failure would leave the homepage blank, and (b) a related-grid card stuck
 * at translateY(-6px) after its reveal finished. A fix for both was written, then
 * removed on measurement:
 *   (a) The reveal is `animation-timeline: view()` — pure CSS scroll-driven, no JS
 *       and no observer. Elements re-hide when scrolled away BY DESIGN, and browsers
 *       without scroll-timeline support simply render them visible. Already recorded
 *       in KNOWN_ISSUES (the "always scroll before trusting a screenshot" note).
 *   (b) The -6px was sampled mid-animation while the card was partially in view. It
 *       does not reproduce: after a 2.2s settle, 0 cards hold a residual transform.
 *
 * The rules written for this matched .rasvo-reveal / [data-rasvo-reveal] / .is-in /
 * .is-visible — all FOUR match 0 elements on this site. Dead CSS, deleted rather
 * than left to look load-bearing to the next reader. */

/* --- S34.15 · PDP reassurance line orphaned its last word ---------------------
 * "SECURE CHECKOUT · 7-DAY EXCHANGE · DISPATCHED IN 2 DAYS" broke after the final
 * separator, dropping a centred "DAYS" onto a line of its own, desktop and mobile.
 *
 * S33 logged this NOT FIXED on the grounds that the line "carries no
 * distinguishing class, so the only selectors that reach it also catch the product
 * <h1>". That is no longer true — the widget carries `rasvo-pdp-reassure`, which
 * is exactly the hook that was thought to be missing. One property, one selector,
 * no <h1> exposure. */
.rasvo-pdp-reassure .elementor-heading-title{text-wrap:balance}

/* --- S34.16 · Price and its reassurance line shared a row, not a baseline -----
 * "₹799" (28px) and "UPI & CARDS · SHIPS PAN-INDIA" (12px mono) sit on one row;
 * the mono line was vertically centred against the price's cap height, so it
 * floated low and read as an accident rather than a pairing. Agree on baseline
 * and give the pair a real gap. */
body.single-product .price,
body.single-product .price ~ *{vertical-align:baseline}
body.single-product .elementor-widget-woocommerce-product-price + .elementor-widget{
  align-self:baseline;
}

/* S34.17 · Fraunces accent on the manifesto — WITHDRAWN with S34.7 above.
 * The manifesto line stays Geist like the rest of the system. */

/* --- S34.18 · Cart remove control was an unlabelled 8px glyph -----------------
 * The only destructive action in the bag rendered as a bare "×" in an unheadered
 * column, at roughly a third of the 44px tap target every other control on the
 * page meets (S32.14 set that standard and this row was missed).
 * Native <a> kept, so keyboard and screen-reader behaviour is unchanged. */
body.woocommerce-cart .product-remove a.remove{
  display:inline-flex;align-items:center;justify-content:center;
  width:44px;height:44px;
  font-size:20px;line-height:1;
  color:var(--rasvo-v2-muted-on-light,#4A515C)!important;
  border-radius:0;
  transition:color .18s ease,background-color .18s ease;
}
body.woocommerce-cart .product-remove a.remove:hover,
body.woocommerce-cart .product-remove a.remove:focus-visible{
  color:var(--rasvo-terracotta,#C2542B)!important;
  background:rgba(194,84,43,.08);
}
/* "Update bag" reads as permanently dead because it is disabled until a quantity
   changes. Say so, instead of showing a broken-looking button. */
body.woocommerce-cart button[name="update_cart"]:disabled{
  opacity:.5;cursor:not-allowed;
}

/* --- S34.22 · Homepage drop grid sat 17px short of its own section -------------
 * At 390px the two-up card grid rendered with a 20px left gutter and a 37px right
 * gutter — visibly off-centre against a section whose padding is a symmetric 20px.
 * Shop (tpl 275) was correct, which is what made it look like a grid bug; it is not.
 *
 * `.rasvo-v2-drop` is `display:flex; flex-direction:column; align-items:flex-start`,
 * and the loop-grid widget carries Elementor's `elementor-widget-mobile__width-initial`
 * (the "Width: initial" setting). Together those make the widget shrink-to-fit
 * instead of filling: it resolved to 318px inside 335px of available content box,
 * and the `repeat(2, 1fr)` columns then divided 318 rather than 335. The grid was
 * doing exactly what it was told — the container was the wrong width.
 *
 * The actual pin is a HARDCODED PIXEL WIDTH in the generated page CSS:
 *   @media (max-width:767px){ .elementor-267 .elementor-element-258bffe{
 *       width:var(--container-widget-width,318px); max-width:318px; } }
 * 318 = 2x152 + 14, i.e. the card grid measured at one specific phone width and
 * frozen. That is why the defect scales with the device: on a 360px screen the
 * content box is 320 and it very nearly fits, at 390 it leaves 37px, and on a 414
 * screen it leaves ~56px. Shop (tpl 275) has no such per-element width, which is
 * why the same grid is correct there.
 *
 * Overridden rather than re-authored in Elementor so the frozen template is not
 * touched. !important because Elementor's rule is (0,3,0) via the generated id and
 * this selector is deliberately id-free — and max-width must be lifted too, or
 * width:100% is simply capped back to 318. */
.rasvo-v2-drop > .elementor-widget-loop-grid{
  align-self:stretch;
  width:100%!important;
  max-width:100%!important;
}

/* --- S36.4 · Mobile footer: left-aligned brand, three cramped columns ----------
 * Measured at 390px (375 doc width) before this block:
 *   - brand block left-aligned at x=34 while the legal lines below it were centred
 *     — two competing alignments in one footer;
 *   - the three link columns were 101px wide, so BOTH long labels wrapped to two
 *     lines ("New drop — SS26" 81px/2 lines, "Returns & exchanges" 81px/2 lines)
 *     and the three columns ended at different heights (175 / 195 / 175), so no
 *     row in the block lined up with any other;
 *   - the legal trust line broke mid-token, orphaning "DAY EXCHANGE".
 *
 * Mobile only — the desktop footer is correct and is not touched. S33.4 forces the
 * footer image left-aligned for the DESKTOP column layout; that rule is overridden
 * here rather than removed, because desktop still needs it.
 *
 * Two columns instead of three: 355px of content cannot give three columns enough
 * width for "Returns & exchanges" (needs ~145px) without dropping below the 12px
 * type floor. At 2-up each column gets ~165px and every label fits on one line. */
@media (max-width:767px){

  /* Structure, for the selectors below:
       [data-elementor-type="footer"] > .e-con          (root)
         > .e-con:first-child   — flex ROW, wraps: brand block + 3 link columns
             > .e-con           — brand (image widget + tagline + injected contact)
             > .e-con x3        — SHOP / COMPANY / HELP (heading + icon list)
         > .e-con:last-child    — legal (© line + trust line)
     Everything below is anchored on that, NOT on `:has(.elementor-icon-list-items)`,
     which also matches every ancestor container and previously leaked a 34px row-gap
     all the way up (footer block height 535 -> 876). */

  /* --- Brand block: logo, tagline and contact centred as one unit --- */
  [data-elementor-type="footer"] .e-con:has(> .elementor-widget-image){
    align-items:center;
    text-align:center;
    flex:0 0 100%;
  }
  [data-elementor-type="footer"] .elementor-widget-image{
    text-align:center!important;   /* beats S33.4, which left-aligns for DESKTOP */
  }
  [data-elementor-type="footer"] .elementor-widget-image img{
    margin-left:auto!important;
    margin-right:auto!important;
    max-width:190px;               /* was rendering 307px — too loud for a footer mark */
  }
  [data-elementor-type="footer"] .e-con:has(> .elementor-widget-image) .elementor-heading-title{
    text-align:center;
    max-width:32ch;
    margin-inline:auto;
    text-wrap:balance;
  }
  :root .rasvo-footer-contact{ align-items:center; gap:10px; margin-top:22px; }

  /* --- Link columns: 3-up, content-proportioned, LEFT-aligned inside ---
     Was briefly 2-up, which fixed the wrapping but pushed HELP onto its own row and
     made the footer a tall tower. Back to 3 across, sized to what each column
     actually holds rather than equal thirds: SHOP needs room for "New drop — SS26",
     HELP for "Returns & exchanges" (the two that used to wrap), COMPANY's longest
     label is "Contact" and needs the least. Uneven track widths are invisible to
     the reader — ragged wrapping is not.
     13px (floor is 12) buys the last few px so both long labels sit on one line. */
  [data-elementor-type="footer"] > .e-con > .e-con:first-child{
    row-gap:26px;
    column-gap:8px;
  }
  [data-elementor-type="footer"] > .e-con > .e-con:first-child > .e-con:not(:has(> .elementor-widget-image)){
    text-align:left;
    gap:12px;
  }
  /* Even thirds, now that S36.7 has shortened the two over-long labels.
     Percentages resolve against the row's CONTENT box (355 - 28px padding = 327)
     and the two 8px gaps come out of that same 327, so the tracks must total ~94%,
     not 100% — at 33/26/39 they summed to 336px inside 327 and HELP silently
     wrapped to a second row, which is exactly the tower this is meant to remove. */
  [data-elementor-type="footer"] > .e-con > .e-con:first-child > .e-con:not(:has(> .elementor-widget-image)){
    flex:0 0 31%;
    max-width:31%;
  }
  [data-elementor-type="footer"] .elementor-icon-list-text{
    font-size:13px;
  }
  /* The column label must agree with the list under it — an earlier, broader rule
     centred "any footer heading" and caught SHOP/COMPANY/HELP too.
     :not(:has(> .elementor-widget-image)) excludes the BRAND container, which is a
     sibling of the link columns: without it this rule (later in source, equal
     specificity) beat the brand-block centring above and left-aligned the tagline
     inside its centred box — centred block, left-aligned text, which reads as a
     mistake rather than a choice. */
  [data-elementor-type="footer"] > .e-con > .e-con:first-child
    > .e-con:not(:has(> .elementor-widget-image)) .elementor-heading-title{
    text-align:left;
  }
  /* Icon lists render with an icon slot that is empty here; reclaiming it is what
     lets "Returns & exchanges" sit on one line instead of breaking after "&". */
  [data-elementor-type="footer"] .elementor-icon-list-item{ margin-bottom:0; }
  [data-elementor-type="footer"] .elementor-icon-list-icon{ display:none; }
  [data-elementor-type="footer"] .elementor-icon-list-text{ padding-inline-start:0!important; }

  /* --- Legal block: centred, balanced, no orphans --- */
  [data-elementor-type="footer"] > .e-con > .e-con:last-child,
  [data-elementor-type="footer"] > .e-con > .e-con:last-child .elementor-heading-title{
    text-align:center;
    text-wrap:balance;
  }
  [data-elementor-type="footer"] > .e-con > .e-con:last-child{
    gap:8px;
    padding-top:26px;
    margin-top:8px;
  }
}

/* --- S36.6b · End-of-page CTA band (markup injected above) --------------------
 * LIGHT, deliberately. A navy band here would have given the homepage three
 * consecutive dark sections — navy newsletter, navy CTA, navy footer — which reads
 * as one undifferentiated slab. On paper it alternates instead, and the terracotta
 * button carries far more weight on a light ground than it did on navy.
 *
 * Every colour is an existing token and every pair clears AA on paper:
 *   eyebrow  #8C6D44 on #FAF9F6 = 4.55:1   (gold-on-light — the on-DARK gold
 *                                           #D8B98B would be 1.78:1 here)
 *   headline #141A23 on #FAF9F6 = 15.3:1
 *   button   #FFFEFA on #C2542B = 4.53:1
 * The hairline flips with the ground: a light rule on navy is invisible on paper. */
.rasvo-endcap{
  background:var(--rasvo-v2-paper,#FAF9F6);
  padding:52px 20px 56px;
  text-align:center;
  border-top:1px solid rgba(20,26,35,.09);
}
.rasvo-endcap__eyebrow{
  margin:0 0 12px;
  font:400 12px/1.6 'Geist Mono',ui-monospace,monospace;
  letter-spacing:.18em;
  color:var(--rasvo-v2-gold-on-light,#8C6D44);
}
.rasvo-endcap__line{
  margin:0 0 26px;
  font-family:'Geist',system-ui,sans-serif;
  font-weight:330;
  font-size:clamp(21px,5.2vw,30px);
  line-height:1.18;
  letter-spacing:-.01em;
  color:var(--rasvo-v2-ink,#141A23);
  text-wrap:balance;
}
:root .rasvo-endcap__btn{
  display:inline-block;
  padding:16px 34px;
  min-height:44px;
  background:var(--rasvo-terracotta,#C2542B);
  color:var(--rasvo-paper,#FFFEFA);
  font:400 12px/1.2 'Geist Mono',ui-monospace,monospace;
  letter-spacing:.16em;
  text-decoration:none;
  border-radius:0;
  transition:background-color .18s ease;
}
:root .rasvo-endcap__btn:hover,
:root .rasvo-endcap__btn:focus-visible{
  background:color-mix(in srgb,var(--rasvo-terracotta,#C2542B) 84%,#000);
  color:var(--rasvo-paper,#FFFEFA);
}
@media (max-width:767px){
  .rasvo-endcap{padding:40px 20px 44px}
  .rasvo-endcap__btn{display:block;width:100%;padding:17px 20px}
}

/* --- S34.21b · Footer contact block (markup injected above) ------------------- */
.rasvo-footer-contact{
  display:flex;flex-direction:column;gap:7px;
  margin-top:16px;
}
/* `:root` prefix is load-bearing. experience-polish ships
   `:root body a{color:var(--rasvo-navy)}` (0,1,2) to kill the inherited #CC3366
   link colour; a plain `.rasvo-footer-contact a` is (0,1,1) and LOSES to it —
   which painted these links #0D1B2A on the #0C141F footer, 1.06:1, invisible.
   `:root .rasvo-footer-contact a` is (0,2,2) and wins without !important. */
:root .rasvo-footer-contact a{
  font-family:'Geist Mono',ui-monospace,monospace;
  font-size:11.5px;
  line-height:1.6;
  letter-spacing:.06em;
  color:var(--rasvo-v2-muted-on-dark,#C6CDD6);
  text-decoration:none;
  width:fit-content;
  border-bottom:1px solid transparent;
  transition:color .18s ease,border-color .18s ease;
}
:root .rasvo-footer-contact a:hover,
:root .rasvo-footer-contact a:focus-visible{
  color:var(--rasvo-v2-gold,#D8B98B);
  border-bottom-color:var(--rasvo-v2-gold,#D8B98B);
}

/* --- S34.19 · Shorts cards carried a one-line spec chip, tees a two-line one ---
 * Tees show "REGULAR / 240 GSM"; shorts show only "REGULAR", because 240 GSM is a
 * tee spec and the data is correctly empty for shorts. Honest, but it leaves the
 * chip block with two different masses across one grid. Reserve the second line's
 * height so every chip occupies the same box whether or not it has a weight. */
.rasvo-card__spec,.rasvo-card__chip{min-height:2.6em}