@charset "UTF-8";

/* Fonts — self-hosted (GDPR-safe, no external dependency). latin subset. */
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 300;
  font-display: swap;
  src: url(../fonts/twiza/inter-300-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url(../fonts/twiza/inter-400-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url(../fonts/twiza/inter-500-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 600;
  font-display: swap;
  src: url(../fonts/twiza/inter-600-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url(../fonts/twiza/inter-700-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: italic;
  font-weight: 400;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-400-italic.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: italic;
  font-weight: 500;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-500-italic.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: italic;
  font-weight: 600;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-600-italic.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-400-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-500-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: normal;
  font-weight: 600;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-600-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }
@font-face {
  font-family: 'Playfair Display';
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url(../fonts/twiza/playfairdisplay-700-normal.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
 font-display:swap; }

/* ============================================================
   TWIZA — Clair  ·  PrestaShop 8 child theme (parent: classic)
   Homepage design system. Component styles scoped under .twiza-home
   so inner pages keep the classic styling untouched.
   ============================================================ */


:root{
  /* palette */
  --orange:#F0901C;
  --orange-deep:#D9790F;
  --orange-soft:#FDEFD8;
  --orange-tint:#FFF8EE;
  --green:#4C8A56;
  --green-deep:#3C7146;
  --green-soft:#E8F1E8;
  --cream:#FBF7F0;
  --cream-2:#F5ECDD;
  --white:#FFFFFF;
  --ink:#2B251E;
  --muted:#7C7167;
  --line:#ECE2D2;
  --line-2:#F2EADC;

  --accent:#F0901C;
  --accent-deep:#D9790F;
  --accent-soft:#FDEFD8;

  --font-head:'Playfair Display', Georgia, serif;
  --font-body:'Inter', system-ui, sans-serif;

  --maxw:1400px;
  --content:1240px;
  --gutter:clamp(20px, 4vw, 56px);
  /* Vertical rhythm between homepage bands. Two adjacent sections each
     contribute this, so the visible gap is DOUBLE the value: at 8vw/120px it
     read as ~230px of empty band at 1440 and the shorter sections looked
     adrift inside it. ~150px reads as one page, not a stack of posters. */
  --section-y:clamp(52px, 5.2vw, 84px);
  --radius:18px;
  --radius-sm:12px;
  --radius-lg:26px;

  --shadow-sm:0 2px 10px rgba(43,37,30,.05);
  --shadow:0 14px 36px -18px rgba(43,37,30,.18);
  --shadow-lift:0 24px 50px -24px rgba(43,37,30,.26);
  --ease:cubic-bezier(.4,.16,.18,1);

  /* the promo-code control's ticket glyph, painted through a mask so it takes
     the button's own colour on hover */
  --tw-tag-ic:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23000' stroke-width='1.8' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M20.6 13.4 13.4 20.6a2 2 0 0 1-2.83 0l-7.2-7.2A2 2 0 0 1 2.8 12V4.8a2 2 0 0 1 2-2H12a2 2 0 0 1 1.4.6l7.2 7.2a2 2 0 0 1 0 2.8Z'/%3E%3Ccircle cx='7.6' cy='7.6' r='1.3'/%3E%3C/svg%3E");

  --khatem:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='64' height='64' viewBox='0 0 64 64'%3E%3Cg fill='none' stroke='%23F0901C' stroke-width='1.1'%3E%3Crect x='20' y='20' width='24' height='24' rx='2'/%3E%3Crect x='20' y='20' width='24' height='24' rx='2' transform='rotate(45 32 32)'/%3E%3C/g%3E%3C/svg%3E");

  /* Width the vertical scrollbar takes from the layout, in px. Overwritten on
     <html> by sbw() in custom.4.js and by the identical inline snippet in
     _partials/head.tpl; see the full-bleed note below for why the
     breakout arithmetic cannot be correct without it. 0 is right for the
     overlay scrollbars of macOS/iOS/Android, so the fallback is never wrong,
     only incomplete. */
  --sbw:0px;
}

/* A vertical scrollbar that TAKES SPACE narrows the layout but NOT `vw`, and the
   full-bleed rule below is built out of both. Reserving the gutter permanently
   makes the difference a constant the script can measure once, instead of a value
   that changes the moment a short page grows past one screen — and it also stops
   the whole page jumping sideways as you navigate between the two. */
html{ scrollbar-gutter:stable; }

/* ============================================================
   HOMEPAGE WRAPPER
   ============================================================ */
.twiza-home{
  font-family:var(--font-body);
  color:var(--ink);
  background:var(--white);
  font-size:17px; line-height:1.7; font-weight:400;
  -webkit-font-smoothing:antialiased;
}
.twiza-home img{ display:block; max-width:100%; }
.twiza-home a{ color:inherit; text-decoration:none; }
.twiza-home button{ font-family:inherit; cursor:pointer; }
.twiza-home h1,.twiza-home h2,.twiza-home h3,.twiza-home h4{
  font-family:var(--font-head); font-weight:600; margin:0; line-height:1.1; letter-spacing:-.01em;
}
.twiza-home p{ margin:0; text-wrap:pretty; }

/* Full-bleed: let sections span edge-to-edge even inside a constrained layout
   container (on every twiza page that container is bootstrap's `.container`,
   ~1110px inside a 1425px viewport, so the breakout is genuinely needed).
   ⚠ AVOIDING `width:100vw` IS NOT ENOUGH TO BE SCROLLBAR-SAFE — this rule was
   written as if it were, and was wrong for two years on every browser with
   space-taking scrollbars. `50%` is half the container, which EXCLUDES the
   scrollbar; `50vw` is half the viewport, which INCLUDES it. The section
   therefore came out one whole scrollbar too wide and hung half of it past the
   right edge: a page-level horizontal scrollbar on every twiza page, at every
   desktop width, in both languages. Invisible on macOS and in headless Chrome,
   both of which use overlay scrollbars — measure with
   `probe-hoverflow.mjs`, which launches with --hide-scrollbars removed.
   Adding back half of --sbw cancels it exactly: the section then spans the
   layout viewport, edge to edge, and nothing overflows. */
.twiza-home .section,
.twiza-home .hero{
  position:relative;
  margin-left:calc(50% - 50vw + var(--sbw)/2);
  margin-right:calc(50% - 50vw + var(--sbw)/2);
}

/* ---- helpers ---- */
.twiza-home .wrap{ width:min(var(--content), 100% - var(--gutter)*2); margin-inline:auto; }
.twiza-home .wrap-wide{ width:min(var(--maxw), 100% - var(--gutter)*2); margin-inline:auto; }
.twiza-home .section{ padding-block:var(--section-y); }
.twiza-home .bg-cream{ background:var(--cream); }
.twiza-home .bg-white{ background:var(--white); }

.twiza-home .eyebrow{
  font-family:var(--font-body);
  font-size:12px; font-weight:700; letter-spacing:.18em; text-transform:uppercase;
  color:var(--accent-deep);
  display:inline-flex; align-items:center; gap:10px;
}
.twiza-home .eyebrow::before{ content:""; width:22px; height:2px; border-radius:2px; background:var(--accent); }
.twiza-home .eyebrow.center{ justify-content:center; }
.twiza-home .eyebrow.center::after{ content:""; width:22px; height:2px; border-radius:2px; background:var(--accent); }

.twiza-home .section-head{ max-width:680px; }
.twiza-home .section-head.center{ margin-inline:auto; text-align:center; }
.twiza-home .section-head h2{ font-size:clamp(28px,3.3vw,44px); margin-top:16px; }
.twiza-home .section-head p{ color:var(--muted); margin-top:16px; font-size:18px; }

.twiza-home .tlink{
  display:inline-flex; align-items:center; gap:9px;
  font-weight:600; font-size:14.5px; color:var(--accent-deep);
  transition:gap .3s var(--ease);
}
/* inline "→" arrows: SVG carries no width/height attrs → must be sized in CSS
   (without this they fall back to the 300×150 default and balloon). */
.twiza-home .arr{ width:18px; height:18px; flex:none; }
.twiza-home .tlink .arr{ transition:transform .35s var(--ease); }
.twiza-home .tlink:hover{ gap:13px; }
.twiza-home .tlink:hover .arr{ transform:translateX(4px); }

/* The same arrow inline after a label — `_partials/tw-arrow.tpl`, a <svg>
   inside the <span class="ar"> the nudge and RTL-mirror rules already target
   (§ Univers, § Territoires below). Sized in em, not px like `.arr` above, so
   one partial trails labels running from 13px (.ucard__btn) to 14.5px (.btn)
   and keeps the arrow proportional to each. `line-height:0` keeps the inline
   svg from adding a descender's worth of height to the span. */
.twiza-home .ar{ display:inline-block; line-height:0; vertical-align:middle; }
.twiza-home .ar svg{ display:block; width:1.15em; height:1.15em; }

/* ---- buttons ---- */
.twiza-home .btn{
  display:inline-flex; align-items:center; justify-content:center; gap:9px;
  padding:15px 28px; font-size:14.5px; font-weight:600; letter-spacing:.01em;
  border:1.5px solid transparent; border-radius:100px;
  transition:background .25s var(--ease), color .25s, border-color .25s, transform .2s, box-shadow .25s;
}
.twiza-home .btn:active{ transform:translateY(1px); }
.twiza-home .btn--solid{ background:var(--accent); color:#fff; box-shadow:0 10px 22px -12px var(--accent); }
.twiza-home .btn--solid:hover{ background:var(--accent-deep); box-shadow:0 14px 26px -12px var(--accent); }
.twiza-home .btn--green{ background:var(--green); color:#fff; }
.twiza-home .btn--green:hover{ background:var(--green-deep); }
.twiza-home .btn--ghost{ background:#fff; color:var(--ink); border-color:var(--line); }
.twiza-home .btn--ghost:hover{ border-color:var(--accent); color:var(--accent-deep); }

/* ============================================================
   1 · HERO
   ============================================================ */
.twiza-home .hero{ padding-top:0; background:var(--cream); overflow:hidden; }
.twiza-home .hero__grid{
  width:min(var(--maxw), 100% - var(--gutter)*2); margin-inline:auto;
  display:grid; grid-template-columns:1fr 1.04fr; align-items:stretch; gap:0;
  min-height:clamp(540px, 76vh, 720px);
}
.twiza-home .hero__text{ display:flex; flex-direction:column; justify-content:center; padding:clamp(32px,5vw,72px) clamp(28px,4vw,64px) clamp(32px,5vw,72px) 0; position:relative; z-index:2; }
.twiza-home .hero__text h1{ font-size:clamp(36px,4.6vw,62px); line-height:1.05; margin:22px 0 0; letter-spacing:-.02em; text-wrap:balance; }
.twiza-home .hero__text h1 em{ font-style:italic; color:var(--accent-deep); }
.twiza-home .hero__sub{ margin:24px 0 0; font-size:18.5px; color:var(--muted); max-width:520px; }
.twiza-home .hero__cta{ display:flex; flex-wrap:wrap; gap:14px; margin-top:34px; }
.twiza-home .hero__trust{ display:flex; align-items:center; gap:22px; margin-top:38px; flex-wrap:wrap; }
.twiza-home .hero__trust .t{ display:flex; align-items:center; gap:9px; font-size:13.5px; color:var(--muted); }
.twiza-home .hero__trust .t b{ font-family:var(--font-head); font-size:22px; color:var(--ink); font-weight:600; }
.twiza-home .hero__trust .sep{ width:1px; height:28px; background:var(--line); }
.twiza-home .hero__media{ position:relative; }
.twiza-home .hero__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; }
.twiza-home .hero__media::after{
  content:""; position:absolute; inset:0; z-index:1; pointer-events:none;
  background:linear-gradient(90deg, var(--cream) 0%, rgba(251,247,240,.35) 16%, rgba(251,247,240,0) 42%);
}
.twiza-home .hero__badge{
  position:absolute; z-index:2; left:-34px; bottom:40px;
  background:#fff; border-radius:var(--radius); box-shadow:var(--shadow);
  padding:16px 20px; display:flex; align-items:center; gap:14px; max-width:280px;
}
.twiza-home .hero__badge .dot{ width:44px; height:44px; border-radius:12px; background:var(--green-soft); color:var(--green-deep); display:flex; align-items:center; justify-content:center; flex:none; }
.twiza-home .hero__badge .dot svg{ width:24px; height:24px; }
.twiza-home .hero__badge .l{ font-size:13px; line-height:1.4; color:var(--muted); }
.twiza-home .hero__badge .l b{ display:block; font-family:var(--font-head); font-size:16px; color:var(--ink); font-weight:600; }
/* hero slider (3 crossfading photos) */
.twiza-home .hero__slider{ position:absolute; inset:0; z-index:0; }
.twiza-home .hero__slide{ opacity:0; transition:opacity 1.1s var(--ease); will-change:opacity; }
.twiza-home .hero__slide.is-active{ opacity:1; }
.twiza-home .hero__dots{ position:absolute; z-index:3; inset-inline-end:22px; bottom:22px; display:flex; gap:9px; }
.twiza-home .hero__dot{ width:9px; height:9px; padding:0; border:0; border-radius:50%; background:rgba(255,255,255,.55); box-shadow:0 1px 3px rgba(0,0,0,.25); cursor:pointer; transition:background .25s, transform .25s; }
.twiza-home .hero__dot:hover{ background:rgba(255,255,255,.85); }
.twiza-home .hero__dot.is-active{ background:#fff; transform:scale(1.3); }

/* ============================================================
   2 · MODÈLE — Band A « Pour les territoires » + 6 étapes
       + Band C « Vente solidaire » (texte + schéma HTML/CSS)
   ============================================================ */

/* shared: orange CTA button that can wrap onto two lines + note */
.twiza-home .tm-cta{ display:inline-flex; align-items:center; justify-content:flex-start; gap:12px; max-width:460px; text-align:start; white-space:normal; padding:16px 26px; border-radius:14px; font-weight:600; line-height:1.35; }
.twiza-home .tm-cta > span{ display:inline-block; }
.twiza-home .tm-cta .arr{ flex:none; transition:transform .35s var(--ease); }
.twiza-home .tm-cta:hover .arr{ transform:translateX(4px); }
.twiza-home .tm-note{ margin-top:18px; font-family:var(--font-head); font-style:italic; font-size:15.5px; line-height:1.5; color:var(--muted); max-width:440px; }
.twiza-home .tm-note--green{ color:var(--green-deep); }

/* -- Band 2: texte à gauche + schéma écosystème à droite -- */
.twiza-home .tm-terr{ margin-top:clamp(54px,6.5vw,90px); display:grid; grid-template-columns:.92fr 1.08fr; gap:clamp(34px,4.6vw,70px); align-items:center; }
.twiza-home .tm-terr__title{ font-size:clamp(28px,3.2vw,44px); line-height:1.08; margin:16px 0 0; color:var(--ink); }
.twiza-home .tm-terr__prose{ margin:22px 0 28px; }
.twiza-home .tm-terr__prose p{ color:var(--muted); font-size:16.5px; line-height:1.7; margin:0 0 14px; }
.twiza-home .tm-terr__prose p:last-child{ margin-bottom:0; }
.twiza-home .tm-terr__strong{ color:var(--ink)!important; font-weight:700; }
.twiza-home .tm-terr__media{ position:relative; border-radius:var(--radius-lg); overflow:hidden; box-shadow:var(--shadow); }
.twiza-home .tm-terr__media img{ display:block; width:100%; height:auto; }

/* -- Band 3: 6 cartes étapes -- */
.twiza-home .tm-steps{ margin-top:clamp(48px,6vw,80px); display:grid; grid-template-columns:repeat(6,1fr); gap:clamp(14px,1.4vw,20px); }
.twiza-home .tm-step{ position:relative; display:flex; flex-direction:column; background:#fff; border:1px solid var(--line); border-radius:18px; padding:22px 20px 24px; overflow:hidden; transition:transform .3s var(--ease), box-shadow .3s, border-color .3s; }
.twiza-home .tm-step::after{ content:""; position:absolute; inset-inline-start:20px; bottom:0; width:34px; height:3px; border-radius:3px; background:var(--accent); }
.twiza-home .tm-step:hover{ transform:translateY(-5px); box-shadow:var(--shadow); border-color:var(--accent-soft); }
.twiza-home .tm-step__head{ display:flex; align-items:center; justify-content:space-between; margin-bottom:16px; }
.twiza-home .tm-step__ic{ width:52px; height:52px; border-radius:14px; background:var(--accent-soft); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; }
.twiza-home .tm-step__ic svg{ width:27px; height:27px; }
.twiza-home .tm-step__n{ font-family:var(--font-head); font-size:34px; font-weight:600; color:var(--line); line-height:1; }
.twiza-home .tm-step__t{ font-family:var(--font-head); font-weight:600; font-size:19px; line-height:1.15; margin:0; color:var(--ink); }
.twiza-home .tm-step__s{ margin-top:5px; font-size:13px; font-weight:600; color:var(--accent-deep); }
.twiza-home .tm-step__d{ margin-top:11px; font-size:13.5px; color:var(--muted); line-height:1.55; }
/* alternate green / orange accents across the row */
.twiza-home .tm-step:nth-child(even) .tm-step__ic{ background:var(--green-soft); color:var(--green-deep); }
.twiza-home .tm-step:nth-child(even)::after{ background:var(--green); }
.twiza-home .tm-step:nth-child(even) .tm-step__s{ color:var(--green-deep); }

/* -- Band 1: « Vente solidaire » texte + schéma. First band in #modele, so no top margin. -- */
.twiza-home .tm-vs{ display:grid; grid-template-columns:.86fr 1.14fr; gap:clamp(34px,4.4vw,64px); align-items:center; }
.twiza-home .tm-pill{ display:inline-block; margin:14px 0 4px; padding:7px 16px; border:1px solid var(--accent); border-radius:100px; font-size:12px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; color:var(--accent-deep); }
/* pill that opens a band (no eyebrow above it to hang off) */
.twiza-home .tm-pill--lead{ margin-top:0; }
.twiza-home .tm-vs__title{ font-family:var(--font-head); font-size:clamp(27px,3vw,40px); line-height:1.1; margin:14px 0 20px; color:var(--ink); }
.twiza-home .tm-vs__text p{ color:var(--muted); font-size:16.5px; line-height:1.7; margin:0 0 14px; }

/* infographic panel */
.twiza-home .tm-vs__info{ background:#fff; border:1px solid var(--line); border-radius:var(--radius-lg); box-shadow:var(--shadow-sm); padding:clamp(22px,2.6vw,34px) clamp(20px,2.4vw,34px) clamp(20px,2.4vw,30px); }
.twiza-home .tm-info__title{ text-align:center; font-family:var(--font-body); font-weight:700; font-size:clamp(16px,1.5vw,19px); color:var(--ink); margin:0 auto 6px; max-width:32ch; }
.twiza-home .tm-info__title{ position:relative; padding-bottom:14px; }
.twiza-home .tm-info__title::after{ content:""; position:absolute; left:50%; bottom:0; transform:translateX(-50%); width:64px; height:3px; border-radius:3px; background:var(--accent); }

/* flow: 4 steps + arrows */
.twiza-home .tm-flow{ display:flex; align-items:flex-start; justify-content:center; gap:6px; margin:26px 0 8px; }
.twiza-home .tm-flow__step{ flex:1 1 0; min-width:0; display:flex; flex-direction:column; align-items:center; text-align:center; gap:10px; }
.twiza-home .tm-flow__ic{ position:relative; width:58px; height:58px; border-radius:50%; background:var(--accent-soft); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; }
.twiza-home .tm-flow__ic svg{ width:27px; height:27px; }
.twiza-home .tm-flow__step:nth-child(4n+3) .tm-flow__ic{ background:var(--green-soft); color:var(--green-deep); }
.twiza-home .tm-flow__n{ position:absolute; inset-inline-end:-4px; bottom:-4px; width:22px; height:22px; border-radius:50%; background:var(--accent); color:#fff; font-size:12px; font-weight:700; display:flex; align-items:center; justify-content:center; border:2px solid #fff; }
.twiza-home .tm-flow__step:nth-child(4n+3) .tm-flow__n{ background:var(--green); }
.twiza-home .tm-flow__t{ font-size:12.5px; line-height:1.35; color:var(--ink); font-weight:600; }
.twiza-home .tm-flow__sep{ flex:none; align-self:center; margin-top:20px; color:var(--muted); opacity:.55; }
.twiza-home .tm-flow__sep svg{ width:20px; height:20px; display:block; }

/* artisan demo cards */
.twiza-home .tm-artists{ display:grid; grid-template-columns:repeat(3,1fr); gap:clamp(12px,1.4vw,18px); margin-top:22px; align-items:end; }
.twiza-home .tm-artist{ position:relative; background:#fff; border:1px solid var(--line); border-radius:16px; overflow:hidden; box-shadow:var(--shadow-sm); }
.twiza-home .tm-artist.is-top{ border-color:var(--accent); box-shadow:0 16px 36px -18px rgba(217,121,15,.55); transform:translateY(-8px); }
.twiza-home .tm-artist__crown{ position:absolute; top:-14px; left:50%; transform:translateX(-50%); z-index:3; width:34px; height:34px; border-radius:50%; background:#fff; border:2px solid var(--accent); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; box-shadow:var(--shadow-sm); }
.twiza-home .tm-artist__crown svg{ width:19px; height:19px; }
.twiza-home .tm-artist__media{ position:relative; aspect-ratio:4/3; overflow:hidden; }
.twiza-home .tm-artist__media img{ width:100%; height:100%; object-fit:cover; }
.twiza-home .tm-artist__count{ position:absolute; top:10px; inset-inline-end:10px; background:rgba(255,255,255,.95); border-radius:12px; padding:7px 11px; text-align:center; line-height:1; box-shadow:var(--shadow-sm); }
.twiza-home .tm-artist__count b{ display:block; font-family:var(--font-head); font-size:22px; font-weight:700; color:var(--ink); }
.twiza-home .tm-artist__count i{ display:block; font-style:normal; font-size:10px; color:var(--muted); margin-top:2px; }
.twiza-home .tm-artist__foot{ padding:12px 14px 14px; }
.twiza-home .tm-artist__name{ display:block; font-weight:700; font-size:14.5px; color:var(--ink); }
.twiza-home .tm-artist__status{ display:block; margin-top:3px; font-size:12px; font-weight:600; color:var(--muted); }
.twiza-home .tm-artist__status::before{ content:"•"; margin-inline-end:5px; }
.twiza-home .tm-artist:nth-child(2) .tm-artist__status{ color:var(--accent-deep); }
.twiza-home .tm-artist:nth-child(3) .tm-artist__status{ color:var(--green-deep); }

/* impact bar */
.twiza-home .tm-impact{ display:flex; align-items:center; gap:16px; margin-top:22px; padding:16px clamp(16px,2vw,22px); background:var(--green-soft); border:1px solid rgba(76,138,86,.28); border-radius:16px; }
.twiza-home .tm-impact__ic{ flex:none; width:46px; height:46px; border-radius:50%; background:var(--green); color:#fff; display:flex; align-items:center; justify-content:center; }
.twiza-home .tm-impact__ic svg{ width:24px; height:24px; }
.twiza-home .tm-impact__txt b{ font-size:14.5px; color:var(--green-deep); }
.twiza-home .tm-impact__txt p{ margin:3px 0 0; font-size:13.5px; color:#5a5045; line-height:1.5; }

/* responsive */
@media (max-width:1080px){
  .twiza-home .tm-steps{ grid-template-columns:repeat(3,1fr); }
}
@media (max-width:900px){
  .twiza-home .tm-terr,
  .twiza-home .tm-vs{ grid-template-columns:1fr; gap:34px; }
  /* The info panel used to be pulled above the text (order:-1) back when the
     text column opened the section and carried the eyebrow. The section head
     is its own band now, so hoisting the panel put a four-step diagram and
     three "Artisan A/B/C" cards on screen before the « vente solidaire »
     label that explains them. Text first, illustration after. */
}
@media (max-width:680px){
  .twiza-home .tm-steps{ grid-template-columns:repeat(2,1fr); }
  .twiza-home .tm-flow{ flex-wrap:wrap; gap:16px 6px; }
  .twiza-home .tm-flow__step{ flex:1 1 40%; }
  .twiza-home .tm-flow__sep{ display:none; }
}
@media (max-width:460px){
  .twiza-home .tm-steps{ grid-template-columns:1fr; }
  .twiza-home .tm-artists{ grid-template-columns:1fr; align-items:stretch; }
  .twiza-home .tm-artist.is-top{ transform:none; }
  .twiza-home .tm-cta{ max-width:none; width:100%; justify-content:center; }
}

/* ============================================================
   3 · UNIVERS — the category cards live with the Univers page's
   « Explorer par univers » (.ucards / .ucard), which the homepage
   now shares; search for them there, not here.
   ============================================================ */
.twiza-home .future{ margin-top:40px; }
.twiza-home .future__head{ display:flex; align-items:center; gap:16px; margin-bottom:22px; }
.twiza-home .future__head .lbl{ font-size:12px; font-weight:700; letter-spacing:.12em; text-transform:uppercase; color:var(--green-deep); background:var(--green-soft); padding:6px 12px; border-radius:100px; }
.twiza-home .future__head .line{ flex:1; height:1px; background:var(--line); }
.twiza-home .future__grid{ display:grid; grid-template-columns:repeat(6,1fr); gap:14px; }
.twiza-home .fchip{ display:flex; flex-direction:column; align-items:center; gap:10px; padding:22px 12px; background:var(--cream); border:1px solid var(--line); border-radius:var(--radius); text-align:center; transition:transform .25s var(--ease), border-color .25s; }
.twiza-home .fchip:hover{ transform:translateY(-3px); border-color:var(--accent-soft); }
.twiza-home .fchip__ic{ width:40px; height:40px; color:var(--muted); }
.twiza-home .fchip__ic svg{ width:100%; height:100%; }
.twiza-home .fchip span{ font-size:13.5px; font-weight:600; color:var(--ink); }

/* ============================================================
   4 · PRODUCT SELECTION — and every other place a card appears

   The card rules below are prefixed `:is(.twiza-home, .products)` rather than
   `.twiza-home` alone, because since the 13 August Marketplace brief the
   category listing and the search results render the SAME partial
   (themes/twiza/templates/catalog/_partials/miniatures/product.tpl → the
   homepage's tw-product-card.tpl). Every container that holds cards — the
   homepage rails, `#js-product-list .products`, `.product-accessories
   .products` — is a `.products`, so one ancestor covers them all.

   `:is()` takes the specificity of its strongest argument, and both arguments
   are plain classes, so this rescoping did NOT change any of these rules'
   weight: the cascade battles they already won or lost are unchanged.

   The grid rules a few lines down stay on `.twiza-home .products`, because the
   listing has a grid of its own (see « LISTING » further down) with different
   breakpoints.
   ============================================================ */
.twiza-home .sel__head{ display:flex; justify-content:space-between; align-items:flex-end; gap:24px; margin-bottom:40px; }
.twiza-home .products{ display:grid; grid-template-columns:repeat(3,1fr); gap:30px 26px; }
/* Sélection, Nouveautés and Meilleures ventes run four across: each shows 8
   products (HOME_FEATURED_NBR / NEW_PRODUCTS_NBR /
   PS_BLOCK_BESTSELLERS_TO_DISPLAY), so four gives two full rows where three
   left a ragged 3+3+2. Scoped to those three ids — the other rails keep three,
   which is what « promotions » (3 products) wants. The id beats the shared
   .twiza-home .products rule, so this ladder has to restate every step down
   rather than inherit the ones below. */
.twiza-home :is(#selection,#nouveautes,#meilleures-ventes) .products{ grid-template-columns:repeat(4,1fr); gap:30px 22px; }
@media (max-width:1240px){ .twiza-home :is(#selection,#nouveautes,#meilleures-ventes) .products{ grid-template-columns:repeat(3,1fr); } }
@media (max-width:1080px){ .twiza-home :is(#selection,#nouveautes,#meilleures-ventes) .products{ grid-template-columns:repeat(2,1fr); } }
@media (max-width:640px){  .twiza-home :is(#selection,#nouveautes,#meilleures-ventes) .products{ grid-template-columns:1fr; } }
:is(.twiza-home,.products) .product{ background:#fff; border:1px solid var(--line); border-radius:var(--radius); overflow:hidden; transition:transform .3s var(--ease), box-shadow .3s, border-color .3s; }
:is(.twiza-home,.products) .product:hover{ transform:translateY(-5px); box-shadow:var(--shadow-lift); border-color:transparent; }
:is(.twiza-home,.products) .product__media{ position:relative; aspect-ratio:4/3.4; overflow:hidden; background:var(--cream); }
/* <picture> wraps the card image so a WebP source can be offered. It is
   display:inline by default, and the img's `height:100%` resolves against IT —
   an unstyled picture therefore leaves the photo at its natural height and
   breaks the card. Block + 100%/100% makes it transparent to the layout. */
:is(.twiza-home,.products) .product__media picture{ display:block; width:100%; height:100%; }
:is(.twiza-home,.products) .product__media img{ width:100%; height:100%; object-fit:cover; transition:transform .9s var(--ease); }
:is(.twiza-home,.products) .product:hover .product__media img{ transform:scale(1.06); }
/* ============================================================
   1b · RÉASSURANCE — thin strip under the hero
   ============================================================ */
.twiza-home .tw-reassure{ padding:0; border-bottom:1px solid var(--line); }
.twiza-home .tw-reassure__grid{ display:grid; grid-template-columns:repeat(3,1fr); gap:18px 30px; list-style:none; margin:0; padding:22px 0; }
.twiza-home .tw-reassure__item{ display:flex; align-items:center; gap:13px; min-width:0; }
.twiza-home .tw-reassure__ic{
  flex:none; width:42px; height:42px; border-radius:50%; display:flex; align-items:center; justify-content:center;
  background:var(--accent-soft); color:var(--accent-deep);
}
.twiza-home .tw-reassure__ic svg{ width:21px; height:21px; }
.twiza-home .tw-reassure__txt{ display:flex; flex-direction:column; min-width:0; }
.twiza-home .tw-reassure__txt b{ font-size:14.5px; font-weight:700; color:var(--ink); line-height:1.3; }
.twiza-home .tw-reassure__txt span{ font-size:13px; color:var(--muted); line-height:1.4; }
@media (max-width:860px){
  .twiza-home .tw-reassure__grid{ grid-template-columns:1fr; gap:14px; padding:18px 0; }
}

/* the counters now sit inside the « pourquoi » band rather than in a section
   of their own, so the card needs its own top separation. */
.twiza-home .tw-impact-inline{ margin-top:56px; }
.twiza-home .impact__lead{ text-align:center; color:var(--muted); font-size:16.5px; margin:0 auto 30px; max-width:60ch; }

/* ============================================================
   BANNIÈRES COMMERCIALES — one wide, two stacked beside it
   ============================================================ */
.twiza-home .tw-banners{
  display:grid; grid-template-columns:1.55fr 1fr; grid-template-rows:1fr 1fr;
  gap:22px; min-height:420px;
}
.twiza-home .tw-banner--wide{ grid-row:1 / span 2; }
.twiza-home .tw-banner{
  position:relative; overflow:hidden; border-radius:var(--radius-lg);
  display:flex; align-items:flex-end; min-height:190px; color:#fff;
  transition:transform .3s var(--ease), box-shadow .3s;
}
.twiza-home .tw-banner:hover{ transform:translateY(-4px); box-shadow:var(--shadow-lift); }
/* The card is one <a> and the title takes its colour by inheritance, so classic's
   `#main a:hover` (1,1,1) tinted the heading orange on hover while the description
   — which sets its own white — stayed white. The lift, the zoom and the CTA are
   the intended hover; the tint was not. Needs the #main prefix to win. */
#main .twiza-home .tw-banner:hover,
#main .twiza-home .tw-banner:focus{ color:#fff; }
.twiza-home .tw-banner__img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; transition:transform .9s var(--ease); }
.twiza-home .tw-banner:hover .tw-banner__img{ transform:scale(1.05); }
/* the scrim is what keeps the white type readable over any photo the editor
   uploads — it must not depend on the image being dark. */
.twiza-home .tw-banner__scrim{
  position:absolute; inset:0;
  background:linear-gradient(0deg, rgba(22,15,9,.86) 0%, rgba(22,15,9,.55) 45%, rgba(22,15,9,.12) 100%);
}
.twiza-home .tw-banner__body{ position:relative; z-index:2; display:flex; flex-direction:column; align-items:flex-start; gap:8px; padding:26px 28px; }
.twiza-home .tw-banner__t{ font-family:var(--font-head); font-size:clamp(21px,2.3vw,30px); font-weight:600; line-height:1.15; }
.twiza-home .tw-banner__d{ font-size:14.5px; line-height:1.5; color:rgba(255,255,255,.92); max-width:42ch; }
.twiza-home .tw-banner__cta{
  margin-top:8px; display:inline-flex; align-items:center; padding:9px 18px; border-radius:100px;
  background:var(--accent); color:#fff; font-size:13px; font-weight:700;
  transition:background .25s;
}
.twiza-home .tw-banner:hover .tw-banner__cta{ background:var(--accent-deep); }
@media (max-width:860px){
  .twiza-home .tw-banners{ grid-template-columns:1fr; grid-template-rows:none; min-height:0; }
  .twiza-home .tw-banner--wide{ grid-row:auto; }
  .twiza-home .tw-banner{ min-height:210px; }
}

/* ============================================================
   2 · NOTRE MODÈLE — the six value-chain steps as one strip
   ============================================================ */
.twiza-home .tm-lead{
  max-width:760px; margin:18px auto 0; text-align:center;
  font-size:17px; line-height:1.65; color:var(--muted);
}
.twiza-home .tm-strip{
  display:grid; grid-template-columns:repeat(6,1fr); gap:26px 18px;
  list-style:none; margin:44px 0 0; padding:0;
}
.twiza-home .tm-strip__item{ display:flex; flex-direction:column; align-items:center; text-align:center; gap:9px; min-width:0; }
.twiza-home .tm-strip__ic{
  width:52px; height:52px; border-radius:50%; flex:none;
  display:flex; align-items:center; justify-content:center;
  background:var(--accent-soft); color:var(--accent-deep);
}
.twiza-home .tm-strip__ic svg{ width:24px; height:24px; }
.twiza-home .tm-strip__t{ font-size:14.5px; font-weight:700; line-height:1.3; color:var(--ink); }
.twiza-home .tm-strip__s{ font-size:12.5px; line-height:1.4; color:var(--muted); }
/* the steps are peers: no numbered rail, no ordering — a divider between them
   would imply a sequence the compressed band no longer explains. */
.twiza-home .tm-actions{ display:flex; flex-wrap:wrap; justify-content:center; gap:14px; margin-top:44px; }
@media (max-width:980px){
  .twiza-home .tm-strip{ grid-template-columns:repeat(3,1fr); gap:30px 18px; }
}
@media (max-width:560px){
  .twiza-home .tm-strip{ grid-template-columns:repeat(2,1fr); }
  .twiza-home .tm-actions .btn{ width:100%; justify-content:center; }
}

/* maker info sits bottom-start (next to CooperativeMaker's own coop badge),
   leaving the top-start corner to the commercial flags below. */
:is(.twiza-home,.products) .product__tag{ position:absolute; bottom:12px; inset-inline-start:12px; z-index:2; font-size:11px; font-weight:700; letter-spacing:.04em; text-transform:uppercase; color:var(--accent-deep); background:rgba(255,255,255,.94); padding:5px 11px; border-radius:100px; }

/* commercial flags — promo amount/percentage and « Nouveau » */
:is(.twiza-home,.products) .product__flags{ position:absolute; top:12px; inset-inline-start:12px; z-index:3; display:flex; flex-direction:column; align-items:flex-start; gap:6px; }
:is(.twiza-home,.products) .product__flag{ font-size:11px; font-weight:700; letter-spacing:.03em; padding:4px 10px; border-radius:100px; color:#fff; white-space:nowrap; }
:is(.twiza-home,.products) .product__flag--sale{ background:var(--accent); }
:is(.twiza-home,.products) .product__flag--new{ background:var(--green); }
/* inset-inline-end, not `right`: the flags opposite take the inline start, so a
   physical `right` puts both in the same corner in Arabic. */
:is(.twiza-home,.products) .wish{
  position:absolute; top:11px; inset-inline-end:11px; z-index:3; width:38px; height:38px; border-radius:50%;
  background:rgba(255,255,255,.94); border:0; display:flex; align-items:center; justify-content:center; color:var(--ink);
  box-shadow:0 4px 12px -5px rgba(43,37,30,.3); transition:transform .25s var(--ease), color .25s, background .25s;
}
:is(.twiza-home,.products) .wish svg{ width:18px; height:18px; }
:is(.twiza-home,.products) .wish:hover{ transform:scale(1.1); color:var(--accent-deep); }
:is(.twiza-home,.products) .wish.active{ background:var(--accent); color:#fff; }
:is(.twiza-home,.products) .wish.active svg{ fill:currentColor; }
/* Cards in a row are equal height (grid stretch), but their contents were not:
   a title wrapping to two lines pushed that card's price and buttons ~24px
   below its neighbours'. Making the card a flex column and letting the foot
   take the slack pins price + buttons to the same line across the row,
   whatever the title does. */
:is(.twiza-home,.products) .product{ display:flex; flex-direction:column; }
:is(.twiza-home,.products) .product__media{ flex:none; }
:is(.twiza-home,.products) .product__body{ padding:18px 20px 22px; display:flex; flex-direction:column; flex:1 1 auto; }
:is(.twiza-home,.products) .product__foot{ margin-top:auto; }
:is(.twiza-home,.products) .product__name{ font-family:var(--font-head); font-size:20px; font-weight:600; line-height:1.2; }
:is(.twiza-home,.products) .product__name a{ color:inherit; }
:is(.twiza-home,.products) .product__desc{ font-size:13.5px; color:var(--muted); margin:6px 0 14px; }
:is(.twiza-home,.products) .product__foot{ display:flex; flex-direction:column; align-items:stretch; gap:13px; }
:is(.twiza-home,.products) .product__price{ font-size:17px; font-weight:700; color:var(--ink); }
:is(.twiza-home,.products) .product__price span{ font-size:13px; font-weight:500; color:var(--muted); }

/* rating, between the price and the buttons.
   The gap belongs to `.product__foot`'s flex, so an EMPTY rating box would still
   cost 13px and push the buttons down on the cards that have no stars — which is
   most of them. `:empty` cannot see it (landingpagecod's hook always emits at
   least whitespace or productcomments' placeholder), so the box is laid out only
   when it actually has a rendered rating bar inside it: `:has()` asks the real
   question. Everything else collapses to nothing. */
:is(.twiza-home,.products) .product__rating{ display:none; }
:is(.twiza-home,.products) .product__rating:has(.ps-landing-rating-bar,.grade-stars *){
  display:block; margin:-2px 0 -1px; }
:is(.twiza-home,.products) .product__rating .ps-landing-rating-bar{ padding:0; gap:6px; }
:is(.twiza-home,.products) .product__rating .ps-landing-rating-star{ font-size:14px; }
:is(.twiza-home,.products) .product__rating .ps-landing-rating-avg{ font-size:13px; color:var(--ink); }
:is(.twiza-home,.products) .product__rating .ps-landing-rating-count{ font-size:12.5px; color:var(--muted); }

/* dual CTA — real add-to-cart beside the cash-on-delivery order form.
   display:contents on the form lets its button be a direct grid item, so both
   buttons share one row and match heights. */
/* flex-wrap with a flex-basis floor, not a viewport breakpoint: the two labels
   stop fitting side by side when the CARD is narrow (3-col grid around
   1024-1160px), which no media query on the viewport describes cleanly. Below
   the floor they simply stack full-width. */
:is(.twiza-home,.products) .product__cta{ display:flex; flex-wrap:wrap; gap:8px; align-items:stretch; }
/* the form is display:contents, so the flex items are the BUTTON inside it and
   the order link — `> *` would only ever match the form box that isn't there.
   Neither button may carry width:100%, which would force its own line. */
:is(.twiza-home,.products) .product__cta .product__add,
:is(.twiza-home,.products) .product__cta .product__order{ flex:1 1 142px; }
:is(.twiza-home,.products) .product__addform{ display:contents; }
:is(.twiza-home,.products) .product__add{
  display:inline-flex; align-items:center; justify-content:center; gap:6px;
  padding:10px 11px; border-radius:100px; text-align:center; font-family:inherit; cursor:pointer;
  background:var(--accent-soft); color:var(--accent-deep); border:0; font-size:12.5px; font-weight:600;
  line-height:1.25; transition:background .25s, color .25s;
}
:is(.twiza-home,.products) .product__add svg{ width:16px; height:16px; flex:none; }
:is(.twiza-home,.products) .product__add:hover{ background:var(--accent); color:#fff; }
:is(.twiza-home,.products) .product__add.added{ background:var(--green); color:#fff; }
:is(.twiza-home,.products) .product__add[disabled]{ opacity:.5; cursor:not-allowed; }
:is(.twiza-home,.products) .product__order{
  display:inline-flex; align-items:center; justify-content:center;
  padding:10px 11px; border-radius:100px; text-align:center;
  background:var(--accent); color:#fff; font-size:12.5px; font-weight:700;
  line-height:1.25; transition:background .25s;
}
:is(.twiza-home,.products) .product__order:hover{ background:var(--accent-deep); color:#fff; }
/* CooperativeMaker positions its badge with a physical `left`, which leaves it
   on the wrong edge in Arabic. */
body.lang-rtl :is(.twiza-home,.products) .product__coop-badge{ left:auto; right:.75rem; }
/* The badge is an <a>, and `.twiza-home a{color:inherit}` (0,1,1) outranks the
   module's own `.product__coop-badge{color:#fff}` (0,1,0) — so it inherited the
   card's dark ink and printed near-black on its green pill. Restore white, and
   hold it through hover/focus. Not scoped to .twiza-home: the same badge rides
   product cards on the category and coopérative pages. */
:is(.twiza-home,.products) .product__coop-badge,
.product-miniature .product__coop-badge,
.product__coop-badge,
.product__coop-badge:hover,
.product__coop-badge:focus,
.cooperativemaker-territoire{ color:#fff; }
.twiza-home .sel__cta{ display:flex; justify-content:center; margin-top:46px; }

/* ============================================================
   5 · HUMAN STORY
   ============================================================ */
.twiza-home .story__grid{ display:grid; grid-template-columns:1.08fr .92fr; gap:clamp(36px,5vw,72px); align-items:center; }
.twiza-home .story__media{ position:relative; }
.twiza-home .story__media img{ width:100%; height:100%; min-height:420px; max-height:560px; object-fit:cover; border-radius:var(--radius-lg); box-shadow:var(--shadow); }
.twiza-home .story__media .pat{ position:absolute; inset:auto -18px -18px auto; width:120px; height:120px; background-image:var(--khatem); background-size:42px; opacity:.5; z-index:-1; border-radius:var(--radius); }
.twiza-home .story__quote{ font-family:var(--font-head); font-style:italic; font-size:clamp(22px,2.4vw,30px); line-height:1.35; color:var(--ink); margin:22px 0; }
.twiza-home .story__quote .mark{ color:var(--accent); }
.twiza-home .story__by{ display:flex; align-items:center; gap:13px; margin-bottom:26px; }
.twiza-home .story__by .av{ width:46px; height:46px; border-radius:50%; object-fit:cover; }
.twiza-home .story__by b{ display:block; font-size:15px; }
.twiza-home .story__by small{ color:var(--muted); font-size:13px; }

/* ============================================================
   6 · COOPERATIVES
   ============================================================ */
.twiza-home .coops__head{ display:flex; justify-content:space-between; align-items:flex-end; gap:24px; margin-bottom:40px; }
.twiza-home .coops{ display:grid; grid-template-columns:repeat(3,1fr); gap:26px; }
.twiza-home .coop{ background:#fff; border:1px solid var(--line); border-radius:var(--radius); overflow:hidden; transition:transform .3s var(--ease), box-shadow .3s; }
.twiza-home .coop:hover{ transform:translateY(-5px); box-shadow:var(--shadow-lift); }
/* CONTAIN, not cover — see the note above .ccoop-card__media: most cooperatives
   carry a logo here rather than a photograph, and a crop takes a bite out of a
   wordmark. The cream ground and the small inset are what make the letterboxing
   read as a frame instead of as a mistake. */
.twiza-home .coop__media{ position:relative; aspect-ratio:3/2.3; overflow:hidden; background:var(--cream); }
.twiza-home .coop__media img{ width:100%; height:100%; object-fit:contain; padding:12px; transition:transform .9s var(--ease); }
.twiza-home .coop:hover .coop__media img{ transform:scale(1.05); }
.twiza-home .coop__terr{ position:absolute; bottom:12px; left:12px; z-index:2; display:inline-flex; align-items:center; gap:6px; font-size:12px; font-weight:600; color:#fff; background:rgba(43,37,30,.55); backdrop-filter:blur(4px); padding:6px 11px; border-radius:100px; }
.twiza-home .coop__terr svg{ width:13px; height:13px; }
.twiza-home .coop__body{ padding:20px 22px 22px; }
.twiza-home .coop__body h3{ font-size:20px; }
.twiza-home .coop__spec{ display:inline-flex; align-items:center; gap:7px; margin-top:10px; font-size:13px; font-weight:600; color:var(--accent-deep); background:var(--accent-soft); padding:5px 11px; border-radius:100px; }
.twiza-home .coop__txt{ font-size:14px; color:var(--muted); margin-top:14px; line-height:1.6; }
.twiza-home .coops__cta{ display:flex; justify-content:center; margin-top:46px; }

/* ============================================================
   7 · TERRITOIRES
   ============================================================ */
/* -- Band 4: « Explorer par territoire ». Lives inside #modele, so it needs the
      same inter-band gap the other bands get, not a section of its own. -- */
.twiza-home .tm-explore{ margin-top:clamp(54px,6.5vw,90px); }
.twiza-home .terr{ display:grid; grid-template-columns:1fr 1fr 1fr; gap:24px; }
.twiza-home .tcard{ position:relative; overflow:hidden; border-radius:var(--radius-lg); min-height:300px; display:flex; align-items:flex-end; box-shadow:var(--shadow-sm); }
.twiza-home .tcard img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; transition:transform 1s var(--ease); }
.twiza-home .tcard:hover img{ transform:scale(1.05); }
.twiza-home .tcard::after{ content:""; position:absolute; inset:0; background:linear-gradient(0deg, rgba(20,15,8,.8), rgba(20,15,8,.1) 60%, transparent); }
.twiza-home .tcard__body{ position:relative; z-index:2; padding:26px; color:#fff; }
.twiza-home .tcard__body .reg{ font-size:12px; letter-spacing:.14em; text-transform:uppercase; font-weight:700; color:var(--orange); }
.twiza-home .tcard__body h3{ color:#fff; font-size:24px; margin:8px 0 4px; }
.twiza-home .tcard__body p{ font-size:14px; color:rgba(255,255,255,.86); }
.twiza-home .tcard--soon{ background:var(--cream); border:1.5px dashed var(--line); box-shadow:none; align-items:center; justify-content:center; text-align:center; }
/* The « bientôt » ghost card is a soft fill one step off the section behind it.
   #modele is cream now, so on a cream band it fills white instead — same
   relationship, rather than a card that vanishes into its own background. */
.twiza-home .bg-cream .tcard--soon{ background:var(--white); }
.twiza-home .tcard--soon::after{ display:none; }
.twiza-home .tcard--soon .tcard__body{ color:var(--muted); padding:30px; }
.twiza-home .tcard--soon .pat{ width:64px; height:64px; margin:0 auto 16px; background-image:var(--khatem); background-size:32px; opacity:.6; }
.twiza-home .tcard--soon h3{ color:var(--ink); font-size:20px; }
.twiza-home .terr__cta{ display:flex; justify-content:center; margin-top:46px; }

/* ============================================================
   8 · WHY TWIZA
   ============================================================ */
.twiza-home .why{ display:grid; grid-template-columns:repeat(4,1fr); gap:24px; }
.twiza-home .value{ background:#fff; border:1px solid var(--line); border-radius:var(--radius); padding:30px 26px; transition:transform .3s var(--ease), box-shadow .3s; }
.twiza-home .value:hover{ transform:translateY(-5px); box-shadow:var(--shadow); }
.twiza-home .value__ic{ width:54px; height:54px; border-radius:14px; background:var(--accent-soft); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; margin-bottom:20px; }
.twiza-home .value__ic svg{ width:28px; height:28px; }
.twiza-home .value:nth-child(even) .value__ic{ background:var(--green-soft); color:var(--green-deep); }
.twiza-home .value h3{ font-size:19px; }
.twiza-home .value p{ font-size:14px; color:var(--muted); margin-top:10px; line-height:1.6; }

/* ============================================================
   9 · IMPACT
   ============================================================ */
.twiza-home .impact{ position:relative; overflow:hidden; }
.twiza-home .impact__card{
  position:relative; background:var(--orange-tint);
  border:1px solid var(--orange-soft); border-radius:var(--radius-lg);
  padding:clamp(40px,5vw,64px) clamp(28px,4vw,56px); overflow:hidden;
}
.twiza-home .impact__card::before{ content:""; position:absolute; inset:0; background-image:var(--khatem); background-size:60px; opacity:.28; pointer-events:none; }
.twiza-home .impact__head{ position:relative; z-index:1; text-align:center; max-width:640px; margin:0 auto 50px; }
.twiza-home .impact__head h2{ font-size:clamp(28px,3.3vw,46px); margin-top:14px; }
.twiza-home .impact__head p{ color:var(--muted); margin-top:14px; font-size:17.5px; }
.twiza-home .stats{ position:relative; z-index:1; display:grid; grid-template-columns:repeat(4,1fr); gap:24px; }
.twiza-home .stat{ text-align:center; padding:0 16px; position:relative; }
.twiza-home .stat + .stat::before{ content:""; position:absolute; left:0; top:14%; height:72%; width:1px; background:var(--orange-soft); }
.twiza-home .stat__n{ font-family:var(--font-head); font-size:clamp(42px,5vw,66px); font-weight:600; line-height:1; color:var(--accent-deep); letter-spacing:-.02em; }
.twiza-home .stat:nth-child(even) .stat__n{ color:var(--green-deep); }
.twiza-home .stat__l{ margin-top:12px; font-size:14px; color:var(--muted); }

/* ============================================================
   10 · FINAL CTA
   ============================================================ */
.twiza-home .final__card{
  position:relative; overflow:hidden; border-radius:var(--radius-lg);
  background:linear-gradient(120deg, var(--accent) 0%, var(--accent-deep) 100%);
  padding:clamp(48px,6vw,84px) clamp(28px,5vw,64px); text-align:center; color:#fff;
}
.twiza-home .final__card::before{ content:""; position:absolute; inset:0; background-image:var(--khatem); background-size:64px; opacity:.16; filter:brightness(0) invert(1); pointer-events:none; }
.twiza-home .final__card h2{ position:relative; z-index:1; font-size:clamp(30px,4vw,54px); color:#fff; line-height:1.07; }
.twiza-home .final__card p{ position:relative; z-index:1; color:rgba(255,255,255,.92); font-size:18px; margin:20px auto 32px; max-width:560px; }
.twiza-home .final__card .btn--solid{ background:#fff; color:var(--accent-deep); box-shadow:0 14px 30px -14px rgba(0,0,0,.4); }
.twiza-home .final__card .btn--solid:hover{ background:var(--ink); color:#fff; }

/* ============================================================
   RESPONSIVE
   ============================================================ */
@media (max-width:1080px){
  .twiza-home .hero__grid{ grid-template-columns:1fr; min-height:0; }
  .twiza-home .hero__text{ padding:40px 0; }
  .twiza-home .hero__media{ min-height:380px; border-radius:var(--radius-lg); overflow:hidden; }
  .twiza-home .hero__media::after{ background:linear-gradient(0deg, var(--cream), rgba(251,247,240,0) 40%); }
  .twiza-home .hero__badge{ left:16px; }
  .twiza-home .model__grid, .twiza-home .story__grid{ grid-template-columns:1fr; gap:40px; }
  .twiza-home .flow{ grid-template-columns:repeat(2,1fr); }
  .twiza-home .products, .twiza-home .coops{ grid-template-columns:repeat(2,1fr); }
  .twiza-home .future__grid{ grid-template-columns:repeat(3,1fr); }
  .twiza-home .why{ grid-template-columns:repeat(2,1fr); }
  .twiza-home .terr{ grid-template-columns:1fr 1fr; }
}
@media (max-width:640px){
  .twiza-home{ font-size:16px; }
  .twiza-home .flow{ grid-template-columns:1fr; }
  .twiza-home .products, .twiza-home .coops{ grid-template-columns:1fr; }
  .twiza-home .future__grid{ grid-template-columns:repeat(2,1fr); }
  .twiza-home .why{ grid-template-columns:1fr; }
  .twiza-home .terr{ grid-template-columns:1fr; }
  .twiza-home .stats{ grid-template-columns:repeat(2,1fr); gap:36px 0; }
  .twiza-home .stat + .stat::before{ display:none; }
  .twiza-home .sel__head, .twiza-home .coops__head{ flex-direction:column; align-items:flex-start; gap:16px; }
}

/* ============================================================
   GLOBAL HEADER + FOOTER (all pages) — Milestone B
   ============================================================ */
:root{ --tw-header-h:76px; }

/* Fixed header needs body offset. Front only (this CSS is front-only). */
body{ padding-top:var(--tw-header-h); }
/* Neutralise the layout's wrappers around our fixed header / cream footer */
#header{ background:transparent; box-shadow:none; }
#footer{ padding:0; background:transparent; color:inherit; box-shadow:none; }
/* classic #wrapper has a grey bg + top padding; kill the grey everywhere and
   remove the top gap on the homepage so the hero butts against the header. */
#wrapper{ background:#fff; }
body#index #wrapper{ padding-top:0; background:transparent; }
/* classic renders an empty <footer class="page-footer"> inside #main and gives it
   `margin-bottom:1.563rem`. Our pages end on a full-bleed cream section and #wrapper
   is white, so those 25px paint a white band between the section and the cream
   footer. Collapse the margin while the element holds nothing — `:empty` never
   matches it (it carries whitespace and an HTML comment), and `:has` lets the
   spacing come back by itself if a module ever fills the block. */
#main > .page-footer:not(:has(*)){ margin-bottom:0; }

.tw-header{
  position:fixed; inset:0 0 auto 0; z-index:1000;
  background:rgba(255,255,255,.86);
  -webkit-backdrop-filter:saturate(140%) blur(10px);
  backdrop-filter:saturate(140%) blur(10px);
  border-bottom:1px solid transparent;
  transition:box-shadow .35s var(--ease), border-color .35s, background .35s;
  font-family:var(--font-body);
}
.tw-header.scrolled{ background:rgba(255,255,255,.96); box-shadow:0 1px 0 rgba(43,37,30,.06); border-color:var(--line-2); }
.tw-header__inner{
  width:min(var(--maxw), 100% - var(--gutter)*2); margin-inline:auto;
  display:grid; grid-template-columns:auto 1fr auto; align-items:center; gap:20px;
  height:var(--tw-header-h);
}
.tw-brand{ display:flex; align-items:center; min-width:0; }
.tw-brand__h1{ margin:0; padding:0; line-height:0; font-size:0; }
/* Override classic .logo{max-height:70px} / .img-fluid{height:auto} */
.tw-header .tw-brand img{ height:36px !important; width:auto !important; max-height:36px !important; max-width:none !important; }
.tw-brand__name{ font-family:var(--font-head); font-size:22px; font-weight:600; color:var(--ink); }

/* --- Nav (ps_mainmenu) --- */
/* ps_mainmenu wraps the <ul> in .menu#_desktop_top_menu — center through it. */
.tw-nav{ display:flex; justify-content:center; align-items:center; min-width:0; }
.tw-nav .menu,
.tw-nav #_desktop_top_menu{ display:flex; justify-content:center; width:100%; float:none; }
.tw-nav .clearfix{ display:none; }
.tw-header .tw-nav .top-menu{
  display:flex; gap:26px; justify-content:center; align-items:center;
  list-style:none; margin:0; padding:0; font-size:14.5px; font-weight:500; float:none;
}
.tw-header .tw-nav .top-menu > li{ float:none; margin:0; border:0; }
.tw-nav .top-menu .collapse-icons,
.tw-nav .top-menu .navbar-toggler{ display:none; }
.tw-header .tw-nav .top-menu > li{ position:relative; }
.tw-header .tw-nav .top-menu > li > a{
  position:relative; display:inline-block; width:auto; padding:6px 0; border:0; background:transparent;
  color:var(--ink); font-size:14.5px; font-weight:500; text-transform:none; transition:color .2s;
}
.tw-nav .top-menu > li > a::after{
  content:""; position:absolute; inset-inline-start:0; bottom:-2px; height:2px; width:0; border-radius:2px;
  background:var(--accent); transition:width .28s var(--ease);
}
.tw-nav .top-menu > li > a:hover{ color:var(--accent-deep); }
.tw-nav .top-menu > li.current > a{ color:var(--accent-deep); }
.tw-nav .top-menu > li.current > a::after,
.tw-nav .top-menu > li > a:hover::after{ width:100%; }
/* submenus */
.tw-nav .top-menu .sub-menu,
.tw-nav .top-menu .popover{
  position:absolute; top:100%; inset-inline-start:0; min-width:220px; background:#fff;
  border:1px solid var(--line); border-radius:var(--radius-sm); box-shadow:var(--shadow);
  padding:10px; margin-top:8px; display:none; z-index:10;
}
.tw-nav .top-menu li:hover > .sub-menu,
.tw-nav .top-menu li:hover > .popover{ display:block; }
.tw-nav .top-menu .sub-menu a{ display:block; padding:8px 10px; border-radius:8px; font-size:14px; color:var(--muted); }
.tw-nav .top-menu .sub-menu a:hover{ background:var(--cream); color:var(--accent-deep); }

/* --- Actions --- */
.tw-actions{ display:flex; align-items:center; gap:7px; }

/* search (ps_searchbar override .tw-searchbar) — override classic #search_widget ID rules.
   Fixed width (not min-width) so the actions cluster has a known footprint and the
   centered nav can't be squeezed into the logo. */
/* .tw-search is the fixed-width box; widget + form fill it 100% so there is no
   phantom width inflating the actions cluster (classic sizes #search_widget itself). */
.tw-search{ flex:none; width:210px; }
.tw-search #search_widget.tw-searchbar{ display:block !important; max-width:none !important; width:100% !important; min-width:0 !important; margin:0; }
.tw-search #search_widget.tw-searchbar form{
  display:flex !important; align-items:center; gap:9px; position:relative;
  background:var(--cream); border:1px solid var(--line);
  border-radius:100px; padding:9px 18px; margin:0;
  min-width:0 !important; width:100% !important;
  color:var(--muted); transition:border-color .25s, background .25s;
}
.tw-search .tw-searchbar form:focus-within{ border-color:var(--accent); background:#fff; }
.tw-search .tw-searchbar .tw-search-ico{ width:18px; height:18px; color:var(--muted); flex:none; }
.tw-search .tw-searchbar input[type="text"]{
  position:static !important; flex:1; width:auto !important; min-width:0;
  border:0 !important; outline:0; background:transparent !important; box-shadow:none !important;
  padding:0 !important; margin:0; font-family:inherit; font-size:14px; color:var(--ink);
}
.tw-search .tw-searchbar input[type="text"]::placeholder{ color:var(--muted); opacity:1; }

/* icon buttons */
.tw-iconbtn{
  position:relative; width:42px; height:42px; border:0; background:transparent; border-radius:50%;
  display:flex; align-items:center; justify-content:center; color:var(--ink);
  transition:background .2s, color .2s; flex:none;
}
.tw-iconbtn:hover{ background:var(--accent-soft); color:var(--accent-deep); }
.tw-iconbtn svg{ width:21px; height:21px; }

/* cart (overridden ps_shoppingcart) */
.tw-cart{ position:relative; }
.tw-cart .tw-cart-link{
  position:relative; width:42px; height:42px; border-radius:50%;
  display:flex; align-items:center; justify-content:center; color:var(--ink);
  transition:background .2s, color .2s;
}
.tw-cart .tw-cart-link:hover{ background:var(--accent-soft); color:var(--accent-deep); }
.tw-cart .tw-cart-link svg{ width:21px; height:21px; }
.tw-cart-srtext{ position:absolute; width:1px; height:1px; overflow:hidden; clip:rect(0 0 0 0); }
.tw-cart-badge{
  position:absolute; top:2px; inset-inline-end:0; min-width:17px; height:17px; padding:0 4px;
  background:var(--accent); color:#fff; font-family:var(--font-body); font-size:10px; font-weight:700;
  line-height:17px; text-align:center; border-radius:9px; transform:scale(0); transition:transform .3s var(--ease);
}
.tw-cart-badge.show{ transform:scale(1); }
/* cart dropdown preview — anchored to the inline end of the cart button. With a
   physical `right:0` the 320px panel opened leftwards from a button that sits at
   the LEFT edge of the Arabic header, so it fell off the viewport. */
.tw-cart .body{
  position:absolute; top:calc(100% + 10px); inset-inline-end:0; width:320px; background:#fff;
  border:1px solid var(--line); border-radius:var(--radius); box-shadow:var(--shadow); padding:16px;
  z-index:20;
  opacity:0; visibility:hidden; transform:translateY(-6px);
  transition:opacity .18s var(--ease), transform .18s var(--ease), visibility 0s .18s;
}
/* The panel hangs 10px below the button, and that gap used to be dead ground:
   the pointer left `.tw-cart` on its way down and the panel vanished before it
   could be reached. This bridges the gap — it belongs to `.tw-cart`, not to the
   panel, so the hover survives the crossing, and it only takes the pointer once
   the panel is actually open. */
.tw-cart::after{
  content:""; position:absolute; top:100%; inset-inline-end:0;
  width:320px; height:12px; pointer-events:none;
}
.tw-cart:hover::after{ pointer-events:auto; }
.tw-cart:hover .body,
.tw-cart:focus-within .body{
  opacity:1; visibility:visible; transform:none;
  transition:opacity .18s var(--ease), transform .18s var(--ease), visibility 0s;
}
/* the panel is now always in the DOM (it fades rather than switching display),
   so on a touch device — where it can never be opened — it would sit off-canvas
   for nothing. Tapping the icon goes to the cart page there. */
@media (hover:none){
  .tw-cart .body,
  .tw-cart::after{ display:none; }
}
/* The panel is a fixed 320px anchored to the cart button's inline end, and on a
   phone-width window that end sits only ~80px from the viewport edge — so the
   panel ran off the OPPOSITE side: measured at `left:-11` on a 390px viewport in
   French. Arabic escaped it only because its button sits at the other end
   (`left:66 → right:386`), which is why this never showed up in the RTL pass.
   Below 480px, anchor the panel to the viewport instead of the button.
   `fixed` rather than making `.tw-cart` static: `.tw-cart-badge` is absolutely
   positioned against `.tw-cart` and has to keep its containing block. #tw-header
   carries no transform, so `fixed` really does resolve to the viewport here.
   The ::after hover bridge follows the panel, or the pointer would cross dead
   ground again on its way down. */
@media (max-width:479.98px){
  .tw-cart .body{
    position:fixed; top:calc(var(--tw-header-h) + 6px);
    inset-inline:12px; width:auto;
  }
  .tw-cart::after{
    position:fixed; top:var(--tw-header-h);
    inset-inline:12px; width:auto; height:12px;
  }
}
.tw-cart .body ul{ list-style:none; margin:0 0 4px; padding:0; }
/* the module prints quantity, name, price and the remove link as four inline
   children, so a long name pushed the price onto its own line and « Retirer »
   read as body text. Placed on a grid they read as one line item. */
.tw-cart .body li{
  display:grid; grid-template-columns:auto 1fr auto; gap:2px 10px; align-items:center;
  padding:10px 0; border-bottom:1px solid var(--line-2);
}
.tw-cart .body li:first-child{ padding-top:0; }
.tw-cart .body .product-quantity{
  grid-area:1 / 1 / 3 / 2; align-self:center;
  min-width:22px; height:22px; padding:0 6px;
  display:flex; align-items:center; justify-content:center;
  background:var(--cream); border-radius:100px;
  font-size:12px; font-weight:700; color:var(--accent-deep);
}
.tw-cart .body .product-name{
  grid-area:1 / 2 / 2 / 3; font-family:var(--font-head); font-size:14.5px;
  line-height:1.35; color:var(--ink);
}
.tw-cart .body .product-price{
  grid-area:2 / 2 / 3 / 3; font-size:13.5px; font-weight:700; color:var(--accent-deep);
}
/* a real target instead of a word in the middle of the line — the label stays in
   the DOM for screen readers, the glyph is drawn in CSS. */
.tw-cart .body .remove-from-cart{
  grid-area:1 / 3 / 3 / 4; align-self:center;
  display:flex; align-items:center; justify-content:center;
  width:26px; height:26px; border-radius:50%;
  border:1px solid var(--line); background:#fff;
  font-size:0; line-height:0; color:var(--muted);
  transition:color .2s, border-color .2s, background .2s;
}
.tw-cart .body .remove-from-cart::before{ content:"×"; font-size:18px; line-height:1; }
.tw-cart .body .remove-from-cart:hover{ background:var(--accent-soft); border-color:var(--accent); color:var(--accent-deep); }
.tw-cart .body .cart-subtotals > div{ display:flex; justify-content:space-between; gap:12px;
  padding:3px 0; font-size:13.5px; color:var(--muted); }
.tw-cart .body .cart-subtotals .value{ color:var(--ink); }
.tw-cart .body .cart-total{ display:flex; justify-content:space-between; font-weight:700; margin-top:10px; padding-top:10px; border-top:1px solid var(--line); }

/* burger (mobile) */
.tw-burger{ display:none; width:42px; height:42px; border:0; background:transparent; border-radius:50%; align-items:center; justify-content:center; color:var(--ink); }
.tw-burger svg{ width:24px; height:24px; }

/* ---- responsive header ---- */
/* Mid widths: shrink the actions cluster so the centered nav keeps clear of the
   logo (the lang pill widened the cluster → "Accueil" was colliding at ~1280). */
@media (max-width:1366px){
  .tw-header__inner{ gap:16px; }
  .tw-header .tw-nav .top-menu{ gap:22px; }
  .tw-search{ width:180px; }
}
@media (max-width:1240px){
  .tw-search{ display:none; }              /* drop search before it crowds the nav */
  .tw-header .tw-nav .top-menu{ gap:26px; }
}
/* the drawer-only language switcher is hidden on desktop (shown inside the
   burger drawer ≤1080 — see below) */
.tw-nav__lang{ display:none; }

@media (max-width:1080px){
  .tw-search{ display:none; }
  .tw-burger{ display:flex; }

  /* The drawer nav is position:absolute, so the 3-col grid's middle 1fr track
     greedily ate all the width and collapsed the brand + actions tracks → the
     logo overlapped the action cluster. Replace the grid with a simple flex bar:
     logo left, actions right. */
  .tw-header__inner{ display:flex; align-items:center; justify-content:space-between; gap:10px; }
  .tw-brand{ flex:0 0 auto; }
  .tw-actions{ gap:4px; }

  /* Move the language switcher into the drawer — frees ~90px so the bar fits a
     320px phone. The top-bar copy is hidden on mobile. */
  .tw-actions .tw-lang{ display:none; }
  .tw-nav__lang{ display:flex; justify-content:center; padding:18px var(--gutter) 22px;
    border-top:1px solid var(--line-2); background:var(--cream); }
  .tw-nav__lang .tw-langsw{ margin:0; padding:4px; }
  /* The two switcher buttons were the only tap targets in the drawer under the
     44px floor — 35x26 and 37x26, against 375x53 for every nav link beside them.
     Scoped to .tw-nav__lang so the desktop pill in .tw-actions keeps its size. */
  .tw-nav__lang .tw-langsw__btn{
    display:inline-flex; align-items:center; justify-content:center;
    min-height:44px; min-width:56px; font-size:14px;
  }

  /* --- the slide-down drawer --- */
  .tw-nav{
    position:absolute; top:var(--tw-header-h); left:0; right:0;
    flex-direction:column; align-items:stretch; justify-content:flex-start;  /* stack menu + lang */
    background:#fff; border-bottom:1px solid var(--line); box-shadow:var(--shadow);
    max-height:0; overflow:hidden; transition:max-height .35s var(--ease);
  }
  .tw-header.menu-open .tw-nav{ max-height:calc(100vh - var(--tw-header-h)); overflow:auto; }
  /* Paired with tw-menu-lock in custom.4.js mobileMenu(). The drawer has its own
     scroll above; this stops the PAGE scrolling behind it. Both elements need it
     — html alone leaves body scrollable in this layout. */
  html.tw-menu-lock,
  html.tw-menu-lock body{ overflow:hidden; }
  /* ps_mainmenu only emits #_desktop_top_menu, which carries classic's Bootstrap
     `hidden-sm-down` → display:none!important on phones. That collapsed the open
     drawer to 1px (menu invisible). Force it visible inside our mobile drawer. */
  .tw-nav .menu,
  .tw-nav #_desktop_top_menu{ display:flex !important; width:100%; justify-content:flex-start; }
  .tw-nav .top-menu{ flex-direction:column; align-items:stretch; gap:0; padding:6px 0; width:100%; }
  .tw-nav .top-menu > li{ width:100%; }
  /* NOTE: prefix with .tw-header to beat the base desktop rule
     `.tw-header .tw-nav .top-menu>li>a{display:inline-block;width:auto}` (line ~523),
     which otherwise wins on specificity and keeps the link inline (hover bg only
     covered the text). Same specificity + later source order → these win. */
  .tw-header .tw-nav .top-menu > li > a{
    display:flex; align-items:center; justify-content:center; width:100%; padding:16px var(--gutter);
    font-family:var(--font-body); font-size:16px; font-weight:600; color:var(--ink); text-align:center;
    border-bottom:1px solid var(--line-2);
    transition:background .28s var(--ease), color .28s var(--ease);
  }
  .tw-header .tw-nav .top-menu > li:last-child > a{ border-bottom:0; }
  .tw-header .tw-nav .top-menu > li > a:hover,
  .tw-header .tw-nav .top-menu > li > a:focus,
  .tw-header .tw-nav .top-menu > li.current > a{ background:var(--cream); color:var(--accent-deep); }
  .tw-header .tw-nav .top-menu > li > a::after{ display:none; }
  /* submenus inline under their parent */
  .tw-nav .top-menu .sub-menu,
  .tw-nav .top-menu .popover{ position:static; display:block; box-shadow:none; border:0; margin:0;
    padding:0 var(--gutter) 8px; background:var(--cream); }
  .tw-nav .top-menu .sub-menu a{ padding:11px 12px; font-size:14.5px; }
}

/* ============================================================
   FOOTER (light)
   ============================================================ */
.tw-footer{ background:var(--cream); border-top:1px solid var(--line); padding-top:clamp(56px,7vw,88px); font-family:var(--font-body); color:var(--ink); }
.tw-footer__wrap{ width:min(var(--content), 100% - var(--gutter)*2); margin-inline:auto; }
.tw-footer__grid{ display:grid; grid-template-columns:1.6fr 1fr 1fr 1.5fr; gap:clamp(28px,4vw,56px); padding-bottom:48px; }
.tw-footer__brand img{ height:30px; margin-bottom:18px; width:auto; }
.tw-footer__name{ font-family:var(--font-head); font-size:22px; font-weight:600; display:block; margin-bottom:18px; }
.tw-footer__brand p{ font-size:14.5px; color:var(--muted); line-height:1.7; max-width:300px; margin:0 0 20px; }
.tw-footer__social .ps-social-follow h4{ display:none; }
.tw-footer__social .ps-social-follow ul{ display:flex; gap:10px; list-style:none; margin:0; padding:0; }
.tw-footer__social .ps-social-follow li{ margin:0; }
.tw-footer__social .ps-social-follow li a{
  width:38px; height:38px; border-radius:50%; border:1px solid var(--line);
  display:flex; align-items:center; justify-content:center; color:var(--muted);
  transition:background .22s, color .22s, border-color .22s, transform .22s; background-position:center; background-size:18px;
}
.tw-footer__social .ps-social-follow li a:hover{ background-color:var(--accent); color:#fff; border-color:var(--accent); transform:translateY(-3px); }
.tw-footer__col h4{ font-family:var(--font-body); font-size:12px; font-weight:700; letter-spacing:.14em; text-transform:uppercase; color:var(--ink); margin:0 0 18px; }
.tw-footer__col ul{ list-style:none; margin:0; padding:0; display:flex; flex-direction:column; gap:12px; }
.tw-footer__col a{ font-size:14.5px; color:var(--muted); transition:color .2s, padding-inline-start .2s; }
.tw-footer__col a:hover{ color:var(--accent-deep); padding-inline-start:4px; }
/* newsletter (ps_emailsubscription — theme override .tw-news) */
.tw-footer__news h4{ font-family:var(--font-body); font-size:12px; font-weight:700; letter-spacing:.14em; text-transform:uppercase; color:var(--ink); margin:0 0 16px; }
.tw-footer__news .tw-news-desc{ font-size:14px; color:var(--muted); line-height:1.6; margin:0 0 16px; }
.tw-footer__news .tw-news{ margin:0; padding:0; max-width:none; }
.tw-footer__news .tw-news-field{ display:flex; gap:8px; align-items:stretch; }
.tw-footer__news .tw-news-field input[type="email"]{
  flex:1; min-width:0; width:auto; border:1px solid var(--line); background:#fff; border-radius:100px;
  padding:12px 16px; font-family:inherit; font-size:14px; color:var(--ink); outline:0; transition:border-color .25s;
}
.tw-footer__news .tw-news-field input[type="email"]:focus{ border-color:var(--accent); }
/* override classic .block_newsletter button{position:absolute;right;bottom} */
.tw-footer__news .tw-news-field button[type="submit"]{
  position:static; right:auto; bottom:auto; flex:none;
  background:var(--accent); color:#fff; border:0; border-radius:100px; padding:0 22px;
  font-family:inherit; font-size:13.5px; font-weight:600; cursor:pointer; transition:background .25s; white-space:nowrap;
}
.tw-footer__news .tw-news-field button[type="submit"]:hover{ background:var(--accent-deep); }
.tw-footer__news .tw-news-conditions{ font-size:11.5px; color:var(--muted); line-height:1.5; margin:10px 0 0; }
.tw-footer__news .tw-news-note{ font-size:12.5px; margin:10px 0 0; }
.tw-footer__news .tw-news-note.is-success{ color:var(--green-deep); }
.tw-footer__news .tw-news-note.is-error{ color:#c0392b; }
.tw-footer__bottom{ border-top:1px solid var(--line); padding:22px 0; display:flex; justify-content:space-between; align-items:center; gap:16px; flex-wrap:wrap; font-size:13px; color:var(--muted); }
.tw-footer__legal{ display:flex; gap:22px; flex-wrap:wrap; }
.tw-footer__legal a{ color:var(--muted); transition:color .2s; }
.tw-footer__legal a:hover{ color:var(--accent-deep); }

@media (max-width:1080px){
  .tw-footer__grid{ grid-template-columns:1fr 1fr; }
  .tw-footer__brand{ grid-column:1 / -1; }
}
@media (max-width:640px){
  .tw-footer__grid{ grid-template-columns:1fr; }
  .tw-footer__bottom{ justify-content:flex-start; }
}

/* ============================================================
   B-2: real featured-product card tweaks
   ============================================================ */
:is(.twiza-home,.products) .product__imglink{ display:block; width:100%; height:100%; }
:is(.twiza-home,.products) .product__old{ color:var(--muted); font-size:13px; font-weight:500; text-decoration:line-through; margin-inline-end:4px; }
:is(.twiza-home,.products) .product__add{ text-decoration:none; }
:is(.twiza-home,.products) .product__name a{ color:inherit; text-decoration:none; }

/* ============================================================
   MILESTONE C — GLOBAL TWIZA BRAND SKIN (inner pages)
   Applies brand tokens to classic components site-wide.
   ============================================================ */

/* ---- base ---- */
body{ font-family:var(--font-body); color:var(--ink); background:#fff; }
#wrapper{ background:#fff; }
#main a:hover{ color:var(--accent-deep); }
.h1,.h2,.h3,h1.page-title,.page-header h1,.product-title,
#main .card-block h1,#product .product-information h1{ font-family:var(--font-head); }

/* ---- breadcrumb ---- */
.breadcrumb{ background:transparent; padding:1.25rem 0 .5rem; margin:0; }
.breadcrumb ol{ margin:0; padding:0; }
.breadcrumb a{ color:var(--muted); font-size:13.5px; }
.breadcrumb a:hover{ color:var(--accent-deep); }
.breadcrumb li::after{ color:var(--line); }

/* ---- page header / titles ---- */
.page-header{ margin-bottom:1.5rem; }
.page-header h1,.h1.page-title{ font-size:clamp(26px,3vw,40px); color:var(--ink); }

/* ---- buttons ---- */
.btn{ border-radius:100px; font-family:var(--font-body); font-weight:600; letter-spacing:.01em; transition:background .25s,color .25s,border-color .25s,box-shadow .25s; }
.btn-primary,.btn-primary:focus{ background:var(--accent); border-color:var(--accent); color:#fff; box-shadow:0 10px 22px -12px var(--accent); }
.btn-primary:hover,.btn-primary:active{ background:var(--accent-deep); border-color:var(--accent-deep); color:#fff; }
.btn-secondary,.btn-tertiary,.btn-outline-secondary{ background:#fff; border:1.5px solid var(--line); color:var(--ink); box-shadow:none; }
.btn-secondary:hover,.btn-tertiary:hover{ border-color:var(--accent); color:var(--accent-deep); background:#fff; }
.btn-unstyle{ color:inherit; }

/* ---- forms ---- */
.form-control,input[type=text],input[type=email],input[type=password],input[type=tel],input[type=number],input[type=search],select,textarea,.input-group .form-control{
  border-radius:10px; border:1px solid var(--line); color:var(--ink); box-shadow:none;
}
.form-control:focus,input:focus,select:focus,textarea:focus{ border-color:var(--accent); box-shadow:0 0 0 3px var(--accent-soft); outline:0; }
.custom-radio input:checked+span,.custom-checkbox input:checked+span{ border-color:var(--accent); background:var(--accent); }
label,.form-control-label{ color:var(--ink); }

/* ---- links column / left column blocks ---- */
#left-column .block,#right-column .block,.block-categories,.card{ border:1px solid var(--line); border-radius:var(--radius); box-shadow:none; background:#fff; }
.block .title,.block-categories .h6,.products-section-title{ font-family:var(--font-body); font-weight:700; color:var(--ink); }

/* ============================================================
   LISTING — product miniatures as Twiza cards
   ============================================================ */
#products .products,.featured-products .products,.product-accessories .products{ gap:30px 26px; }
/* Listing grid: force a deterministic 3-per-row layout (Bootstrap col-* on the
   miniatures gave only 2 across once the facet sidebar narrowed the content area).
   CSS grid ignores the col widths; children reset their bootstrap gutters.
   The row gap is deliberately the larger of the two — the brief asks for « plus
   d'espace entre les rangées », and a card is much taller than it is wide, so an
   equal gap reads as cramped vertically. */
#js-product-list .products,#products .products{ display:grid; grid-template-columns:repeat(3,1fr);
  gap:38px 26px; margin:0; }
/* FOUR per row on the category listing from 1400px up. Scoped to #category on
   purpose: that is the only listing running on the theme's page width, which
   gave the product column back the ~100px bootstrap's container was holding —
   a 4th card lands at 226px there. Search and brand listings are still on the
   narrow container, where a 4th would squeeze every card to 182px. */
@media (min-width:1400px){
  #category #js-product-list .products,#category #products .products{
    grid-template-columns:repeat(4,1fr); gap:38px 24px; }
}
/* A listing row is only as tall as its tallest card, and a card with a rating
   line is taller than one without. `stretch` (the grid default) then leaves the
   short card's button floating mid-air; the card fills the row instead and its
   `margin-top:auto` foot pins the price and the buttons to the bottom, so the
   « Ajouter au panier » buttons line up across the row whatever sits above them. */
#js-product-list .products>.product,#products .products>.product{ align-self:stretch; }
#js-product-list .products>.product,#products .products>.product,
#js-product-list .products>.js-product,#products .products>.js-product{
  width:100%; max-width:100%; flex:none; margin:0; padding:0; }
@media (max-width:900px){ #js-product-list .products,#products .products{ grid-template-columns:repeat(2,1fr); } }
@media (max-width:560px){ #js-product-list .products,#products .products{ grid-template-columns:1fr; } }
.product-miniature{ width:100%; margin:0; }
.product-miniature .thumbnail-container{ background:#fff; border:1px solid var(--line); border-radius:var(--radius); overflow:hidden; height:auto; transition:transform .3s var(--ease),box-shadow .3s,border-color .3s; }
.product-miniature:hover .thumbnail-container{ transform:translateY(-5px); box-shadow:var(--shadow-lift); border-color:transparent; }
.product-miniature .thumbnail-top{ position:relative; }
.product-miniature .product-thumbnail{ display:block; aspect-ratio:4/3.4; overflow:hidden; background:var(--cream); }
.product-miniature .product-thumbnail img,.product-miniature .product-thumbnail picture{ width:100%; height:100%; object-fit:cover; transition:transform .9s var(--ease); }
.product-miniature:hover .product-thumbnail img{ transform:scale(1.06); }
.product-miniature .product-description{ padding:16px 18px 20px; }
.product-miniature .product-title{ font-family:var(--font-head); font-size:18px; font-weight:600; line-height:1.2; margin:0 0 8px; }
.product-miniature .product-title a{ color:var(--ink); }
.product-miniature .product-title a:hover{ color:var(--accent-deep); }
.product-miniature .product-price-and-shipping{ color:var(--ink); }
.product-miniature .price{ color:var(--ink); font-weight:700; font-size:17px; }
.product-miniature .regular-price{ color:var(--muted); text-decoration:line-through; font-weight:500; font-size:14px; }
.product-miniature .discount-product,.product-flags .discount{ background:var(--accent); border-radius:100px; }
.product-miniature .highlighted-informations{ background:transparent; }
.product-miniature .quick-view{ color:var(--accent-deep); }

/* sort / filter toolbar */
.products-selection .sort-by,.products-selection .total-products{ color:var(--muted); }
.products-sort-order .select-title{ border-radius:100px; border:1px solid var(--line); background:#fff; color:var(--ink); }

/* facets */
.facet .facet-title{ color:var(--ink); font-weight:700; }
.facet .facet-label a{ color:var(--muted); }
.facet .facet-label a:hover,.active_filters .filter-block{ color:var(--accent-deep); }
.active_filters .filter-block{ background:var(--accent-soft); border-radius:100px; color:var(--accent-deep); }

/* pagination */
.pagination .page-list li a,.pagination .page-list li span{ border-radius:8px; color:var(--ink); }
.pagination .page-list li.current a,.pagination .page-list li a:hover{ background:var(--accent); color:#fff; }

/* ============================================================
   PRODUCT PAGE
   ============================================================ */
#product .product-prices .current-price span,#product .current-price-value,.product-price .current-price{ color:var(--accent-deep); font-weight:700; }
#product .product-information h1,.product-detail-name{ font-family:var(--font-head); }
.product-add-to-cart .add-to-cart{ border-radius:100px; }
.product-quantity .qty .input-group,.product-quantity input{ border-radius:10px; }
#product .tabs,.product-tabs{ border:1px solid var(--line); border-radius:var(--radius); }
.nav-tabs .nav-link.active{ color:var(--accent-deep); border-color:var(--accent); }

/* ============================================================
   CART / CHECKOUT
   ============================================================ */
.cart-summary,.cart-grid-body .card,.cart-grid-right .card,#checkout .card{ border:1px solid var(--line); border-radius:var(--radius); box-shadow:var(--shadow-sm); }
.cart-summary-line .value,.cart-total .value{ color:var(--ink); }
.checkout-step .step-title,.cart-summary .h4{ font-family:var(--font-head); }
.product-line-grid .label,.cart__card-body a{ color:var(--ink); }

/* ============================================================
   CUSTOMER / ACCOUNT
   ============================================================ */
.page-customer-account #content,.page-authentication #content,#authentication .card{ border:1px solid var(--line); border-radius:var(--radius); box-shadow:none; }
.links .link-item,.account-links .link-item{ border:1px solid var(--line); border-radius:var(--radius); transition:transform .25s var(--ease),box-shadow .25s; }
.links .link-item:hover,.account-links .link-item:hover{ transform:translateY(-3px); box-shadow:var(--shadow); color:var(--accent-deep); }

/* ============================================================
   MILESTONE C — PRODUCT PAGE refinements
   ============================================================ */
#product #content.product-container,#product .product-container{ margin-top:1rem; }
/* Fixed square frame: any photo fills it edge-to-edge (object-fit:cover), no blank
   letterboxing regardless of the source image's aspect ratio. The cover img gets a
   runtime-injected `height:auto!important` by classic core JS (see coverFrames() in
   custom.js which enforces object-fit there); this CSS is the no-JS fallback. */
#product .product-cover,#product .js-qv-product-cover{ position:relative; aspect-ratio:1/1; border-radius:var(--radius-lg); overflow:hidden; border:1px solid var(--line); background:var(--cream); }
#product .product-cover picture{ display:block; width:100%; height:100%; }
#product .product-cover img,#product .js-qv-product-cover img,#product .product-cover picture img{ border-radius:var(--radius-lg); width:100%; height:100%; object-fit:cover; object-position:center; }
#product .images-container .js-qv-product-images img,#product .product-images>li img,#product .thumb{ border-radius:12px; border:1px solid var(--line); cursor:pointer; transition:border-color .2s; }
#product .product-images>li.selected img,#product .thumb.selected,#product .product-images img:hover{ border-color:var(--accent); }

#product .product-information .h1,#product .product-information h1{ font-family:var(--font-head); font-size:clamp(24px,2.6vw,34px); line-height:1.15; }
#product .product-prices{ margin:18px 0; }
#product .current-price .price,#product .current-price span.price,#product .current-price-value{ font-size:30px; color:var(--accent-deep); font-weight:700; }
#product .has-discount .regular-price,#product .product-discount .regular-price{ color:var(--muted); text-decoration:line-through; }
#product .discount.discount-percentage,#product .product-flags .discount{ background:var(--accent); border-radius:100px; }

/* Flags = consistent pills, stacked top-start. align-items:flex-start stops the
   auto-width `on-sale` ("Promo !") flag from stretching to a full-width bar. */
#product .product-flags{ position:absolute; top:14px; inset-inline-start:14px; z-index:3; display:flex; flex-direction:column; align-items:flex-start; gap:6px; margin:0; padding:0; list-style:none; max-width:calc(100% - 28px); }
#product .product-flag{ display:inline-flex; align-items:center; width:auto; max-width:100%; margin:0; padding:5px 12px; background:var(--accent); color:#fff; border-radius:100px; font-weight:600; font-size:12px; line-height:1.2; box-shadow:0 6px 16px -8px rgba(43,37,30,.55); white-space:nowrap; }
#product .product-flag.new{ background:var(--green); }
#product .product-flag.online-only,#product .product-flag.discount,#product .product-flag.on-sale{ background:var(--accent); }

#product .product-add-to-cart{ border-top:1px solid var(--line); border-bottom:1px solid var(--line); padding:22px 0; margin:22px 0; }
#product .product-add-to-cart .add-to-cart{ padding:14px 32px; font-size:15px; border-radius:100px; }
#product .product-add-to-cart .add-to-cart .material-icons{ vertical-align:middle; }
#product .product-quantity .qty .bootstrap-touchspin,#product .product-quantity #quantity_wanted,#product .product-quantity .input-group{ border-radius:10px; }
#product .product-quantity .input-group-btn-vertical .btn{ border:1px solid var(--line); background:#fff; }

#product .product-variants>.product-variants-item{ margin:14px 0; }
#product .product-variants .control-label{ font-weight:600; color:var(--ink); }
#product .product-variants .input-color+span,#product .product-variants .color{ border-radius:50%; border:1px solid var(--line); }
#product .product-variants input.input-color:checked+span,#product .product-variants input:checked+.color{ box-shadow:0 0 0 2px var(--accent); }
#product .product-variants select.form-control{ border-radius:100px; }

#product .product-reference,#product .product-quantities,#product .product-availability{ color:var(--muted); }
#product .product-availability .product-available{ color:var(--green-deep); }

.product-tabs .nav-tabs,#product .tabs .nav-tabs{ border-bottom:1px solid var(--line); }
.product-tabs .nav-tabs .nav-link,#product .tabs .nav-link{ color:var(--muted); font-weight:600; border:0; background:transparent; }
.product-tabs .nav-tabs .nav-link.active,#product .tabs .nav-link.active{ color:var(--accent-deep); border-bottom:2px solid var(--accent); background:transparent; }
#product .tabs{ border:1px solid var(--line); border-radius:var(--radius); padding:1.5rem; }

#product .product-accessories .h3,#product .featured-products .h3{ font-family:var(--font-head); }

/* ============================================================
   MILESTONE C — CART / CHECKOUT / ACCOUNT refinements
   ============================================================ */
/* cart */
.cart-grid-body .card,.cart-grid-right .card,.cart-summary{ border:1px solid var(--line); border-radius:var(--radius); box-shadow:var(--shadow-sm); }
.cart-item{ border-bottom:1px solid var(--line); }
.cart-items .cart-item:last-child{ border-bottom:0; }
.product-line-grid .product-line-info .label,.cart-summary-products .label{ font-family:var(--font-head); color:var(--ink); }
.cart-summary-line.cart-total .value,.cart-detailed-totals .cart-total .value{ color:var(--accent-deep); font-weight:700; }
.cart-grid-right .checkout a.btn,.checkout .btn-primary{ width:100%; }
.product-price,.cart-line-product-actions .remove-from-cart{ color:var(--muted); }
.cart-line-product-actions .remove-from-cart:hover{ color:var(--accent-deep); }

/* checkout */
#checkout .checkout-step{ border:1px solid var(--line); border-radius:var(--radius); margin-bottom:1rem; background:#fff; }
#checkout .checkout-step .step-title{ font-family:var(--font-head); color:var(--ink); }
#checkout .checkout-step.-current .step-title,#checkout .step-title:hover{ color:var(--accent-deep); }
#checkout .checkout-step .step-number,#checkout .checkout-step .done{ background:var(--accent); color:#fff; }
.payment-options .payment-option,.delivery-options .delivery-option{ border:1px solid var(--line); border-radius:var(--radius-sm); padding:.75rem 1rem; margin-bottom:.5rem; }
.payment-options .custom-radio input:checked~.delivery-option,.delivery-option:hover{ border-color:var(--accent); }
#conditions-to-approve label,.condition-label label{ color:var(--ink); }

/* order confirmation */
.order-confirmation-table,.order-confirmation .card{ border:1px solid var(--line); border-radius:var(--radius); }
#order-confirmation .h1,.page-order-confirmation h3{ font-family:var(--font-head); }

/* account */
.page-customer-account .page-content,.page-addresses .address,.page-my-account .links{ }
.page-my-account .links a.link-item{ border:1px solid var(--line); border-radius:var(--radius); box-shadow:none; transition:transform .25s var(--ease),box-shadow .25s,color .25s; }
.page-my-account .links a.link-item:hover{ transform:translateY(-4px); box-shadow:var(--shadow); color:var(--accent-deep); }
.page-my-account .links a.link-item i,.page-my-account .links a.link-item .material-icons{ color:var(--accent-deep); }
.address{ border:1px solid var(--line); border-radius:var(--radius); box-shadow:none; }
table.table thead th{ color:var(--ink); border-bottom:1px solid var(--line); }
.table tbody td{ border-color:var(--line-2); }

/* notifications / alerts */
.alert-success{ background:var(--green-soft); color:var(--green-deep); border:0; border-radius:var(--radius-sm); }
.alert-warning,.alert-info{ border-radius:var(--radius-sm); }
.alert-danger{ border-radius:var(--radius-sm); }

/* ============================================================
   UI CORRECTIONS (user feedback) — pagination, category, product, cart
   ============================================================ */

/* ---- 4) PAGINATION: robust flex layout + padded, clickable buttons ---- */
nav.pagination{ display:flex; justify-content:space-between; align-items:center; flex-wrap:wrap; gap:16px;
  margin:2rem 0 1rem; padding-top:1.5rem; border-top:1px solid var(--line); }
nav.pagination > div{ width:auto !important; max-width:none; margin:0 !important; padding:0 !important; float:none; flex:0 1 auto; }
nav.pagination .col-md-4{ color:var(--muted); font-size:14px; }
.pagination .page-list{ display:flex; flex-wrap:wrap; gap:8px; justify-content:flex-end; align-items:center;
  margin:0; padding:0; list-style:none; }
.pagination .page-list li{ margin:0; padding:0; float:none; }
.pagination .page-list li a,
.pagination .page-list li span{ display:inline-flex; align-items:center; justify-content:center;
  min-width:44px; height:44px; padding:0 14px; border:1px solid var(--line); border-radius:12px;
  color:var(--ink); font-weight:600; font-size:14px; background:#fff; line-height:1; transition:all .2s var(--ease); }
.pagination .page-list li a:hover{ border-color:var(--accent); color:var(--accent-deep); background:var(--accent-soft); }
.pagination .page-list li.current a{ background:var(--accent); border-color:var(--accent); color:#fff; }
.pagination .page-list li .disabled{ opacity:.4; pointer-events:none; }
.pagination .page-list .spacer{ border:0; background:transparent; min-width:auto; }
.pagination .page-list .previous,.pagination .page-list .next{ padding:0 16px; }
.pagination .page-list .material-icons{ font-size:18px; }

/* ---- 3) CATEGORY PAGE: theme the header, sidebar, sort, subcategories ---- */
#category #content-wrapper,.page-category #content-wrapper{ padding-top:.5rem; }
#js-product-list-header .h1,.page-category h1.h1,#category h1{ font-family:var(--font-head); font-size:clamp(26px,3vw,40px); color:var(--ink); margin-bottom:.5rem; }
#category-description,.category-description{ color:var(--muted); font-size:15px; line-height:1.7; }

/* ---- Listing width: the filter panel sits at the PAGE edge, not bootstrap's.
   The band behind the listing is the theme's own page width (--maxw/--gutter,
   the same expression .tw-header__inner uses), so #search_filters_wrapper now
   starts exactly under the header logo instead of 100px inside it — and the
   product column gains that width back. Only from 992px up: below that the
   sidebar is classic's mobile drawer and bootstrap's fluid container is right.
   The +30px is bootstrap's own gutter arithmetic — .container pads 15px, .row
   pulls 15px back, so the CONTENT box has to be the target width. */
@media (min-width:992px){
  #category #wrapper > .container{
    width:calc(min(var(--maxw), 100% - var(--gutter)*2) + 30px); max-width:none; }
}
/* ---- The breadcrumb sits directly above the filter panel, so it reads as that
   column's caption rather than a line across the page: give it the sidebar's own
   box and centre the text in it. The box has to be the COLUMN's, not a plain
   percentage of the container — col-lg-3 is 25% of the .row, and the row is the
   container plus the 30px it pulls back with its negative margins, hence
   (100% + 30px)/4 offset by -15px. Get that wrong and the centre lands ~11px off.
   Same breakpoints as the sidebar itself (col-md-4 / col-lg-3); below 768 the
   sidebar is classic's drawer and the breadcrumb goes back to a normal
   full-width line. No physical side is named, so in Arabic the block lands on
   the right with the columns. */
@media (min-width:768px){
  #category .breadcrumb{ width:calc((100% + 30px) / 3); margin-inline-start:-15px;
    padding-inline:15px; text-align:center; }
}
@media (min-width:992px){
  #category .breadcrumb{ width:calc((100% + 30px) / 4); }
}
/* « Masquer les filtres » takes the column away — with nothing left to sit over,
   the breadcrumb returns to the full band and its normal start alignment. */
body#category.tw-filters-off .breadcrumb{ width:auto; margin-inline-start:0;
  padding-inline:0; text-align:start; }
/* ---- Category HERO: a FULL-BLEED band — the cover image is the background and
   the title + description sit on a directional scrim (same language as the
   .uni / .tw-subcat cover cards, no box: a box read as "stuck on").
   The block is rendered as a direct child of #wrapper, OUTSIDE the container
   (see templates/catalog/listing/category.tpl), so it is already the full
   document width — no 100vw breakout, which would overshoot by the scrollbar
   and add a horizontal scrollbar. The filter sidebar and the grid start under it.
   The colours are prefixed with the #js-product-list-header ID because
   #category-description{color:muted} and the heading rules would otherwise win
   and render the text in dark ink on a dark photo. */
.tw-cat-hero{ position:relative; overflow:hidden; isolation:isolate; border-radius:0;
  /* edge to edge, and it climbs into classic #wrapper's 1.563rem top padding so
     the band butts up under the header the way the CMS heroes do */
  margin:-1.563rem 0 2rem; padding-block:clamp(26px,3.2vw,46px); }
/* The copy lines up with the PAGE GRID, not the viewport edge: the inline
   padding resolves to the container's own content edge at each bootstrap
   breakpoint ((100% − container)/2 + the column's 15px gutter). */
.tw-cat-hero{ padding-inline:15px; }
@media (min-width:576px){  .tw-cat-hero{ padding-inline:calc((100% - 540px)/2 + 15px); } }
@media (min-width:768px){  .tw-cat-hero{ padding-inline:calc((100% - 720px)/2 + 15px); } }
@media (min-width:992px){
  /* from here up the listing runs on the theme's own page width (see the
     .container rule above), so the hero copy has to follow THAT edge, not
     bootstrap's — same expression as .tw-header__inner resolves to. */
  .tw-cat-hero{ padding-inline:max(var(--gutter), calc((100% - var(--maxw))/2)); }
}
/* plain variant (no cover image uploaded): clean cream band. Edge to edge, so
   only the bottom rule survives — side borders would run off the screen. */
.tw-cat-hero--plain{ background:linear-gradient(180deg,#fff, var(--cream));
  border:0; border-bottom:1px solid var(--line); }
/* photo variant: image fills the band, text sits on top. Full-bleed, so it can
   carry real hero height. */
.tw-cat-hero--photo{ display:flex; align-items:center; min-height:clamp(300px,33vw,460px); }
.tw-cat-hero__media{ position:absolute; inset:0; z-index:0; }
/* object-fit:cover adapts ANY photo (portrait/landscape/square) to fill the band —
   no distortion, no PrestaShop letterbox padding (we use img/c/{id}.jpg directly). */
.tw-cat-hero__bg{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; object-position:center; display:block; }
/* scrim: a directional darkening that keeps the text side readable while the
   photo breathes on the far side, plus a soft bottom vignette that grounds the
   band. Two layers, topmost first. */
.tw-cat-hero__scrim{ position:absolute; inset:0; z-index:1;
  background:
    linear-gradient(0deg, rgba(22,15,9,.42) 0%, rgba(22,15,9,0) 48%),
    linear-gradient(90deg, rgba(22,15,9,.92) 0%, rgba(22,15,9,.84) 34%, rgba(22,15,9,.56) 62%, rgba(22,15,9,.12) 100%); }
/* Arabic reads from the right, so the dark side has to start there. */
.tw-cat-hero--photo[dir="rtl"] .tw-cat-hero__scrim{
  background:
    linear-gradient(0deg, rgba(22,15,9,.42) 0%, rgba(22,15,9,0) 48%),
    linear-gradient(270deg, rgba(22,15,9,.92) 0%, rgba(22,15,9,.84) 34%, rgba(22,15,9,.56) 62%, rgba(22,15,9,.12) 100%); }
/* text block — no box, just a max-width so it stays over the dark side */
.tw-cat-hero--photo .tw-cat-hero__frame{
  position:relative; z-index:2; max-width:min(620px,46%); background:none; border:0; padding:0; }
/* colours: prefix with the #js-product-list-header ID so they beat
   #category-description{color:muted} + the heading colour rules */
#js-product-list-header .tw-cat-hero--photo .tw-cat-hero__title{ color:#fff;
  font-size:clamp(34px,4vw,58px); line-height:1.05; letter-spacing:-.015em;
  text-shadow:0 2px 18px rgba(0,0,0,.55); }
#js-product-list-header .tw-cat-hero--photo .tw-cat-hero__desc,
#js-product-list-header .tw-cat-hero--photo .tw-cat-hero__desc p{
  color:rgba(255,255,255,.92); text-shadow:0 1px 10px rgba(0,0,0,.5); }
#js-product-list-header .tw-cat-hero--photo .tw-cat-hero__desc{ margin-top:.9rem; font-size:16.5px; }
.tw-cat-hero__title{ margin:0; }
.tw-cat-hero__desc{ margin:.55rem 0 0; color:var(--ink); font-size:14.5px; line-height:1.68; }
.tw-cat-hero__desc :where(p):last-child{ margin-bottom:0; }
@media (max-width:991px){
  .tw-cat-hero--photo{ min-height:clamp(240px,34vw,330px); }
  .tw-cat-hero--photo .tw-cat-hero__frame{ max-width:min(560px,68%); }
}
@media (max-width:640px){
  .tw-cat-hero{ margin-bottom:1.5rem; }
  .tw-cat-hero--photo{ min-height:clamp(210px,50vw,270px); }
  .tw-cat-hero--photo .tw-cat-hero__frame{ max-width:100%; }
  #js-product-list-header .tw-cat-hero--photo .tw-cat-hero__desc{ font-size:14.5px; }
}
/* left column blocks */
#left-column .block-categories,#left-column .ps-block,#search_filters,#search_filters_wrapper{
  border:1px solid var(--line); border-radius:var(--radius); background:#fff; box-shadow:none; padding:1.25rem; }
#left-column .block-categories .category-top-menu a,#search_filters .h6,#left-column h4,.block-categories h4{
  color:var(--ink); font-family:var(--font-body); font-weight:700; }
#left-column .category-sub-menu a,#left-column .block-categories a{ color:var(--muted); }
#left-column .category-sub-menu a:hover,#left-column .block-categories a:hover{ color:var(--accent-deep); }
/* subcategories: see "SUBCATEGORY cover cards" block below */
/* sort toolbar */
.products-sort-order .select-title{ border:1px solid var(--line); border-radius:100px; background:#fff; color:var(--ink); padding:.5rem 1rem; }
.products-sort-order .dropdown-menu{ border:1px solid var(--line); border-radius:var(--radius-sm); box-shadow:var(--shadow); }
.total-products{ color:var(--muted); }
.sort-by-row{ align-items:center; }

/* ---- 2) PRODUCT PAGE: stronger polish ---- */
#product .product-information{ padding-inline-start:.5rem; }
#product .product-information .h1,#product .product-prices,#product .product-actions{ font-family:var(--font-body); }
#product .product-prices .current-price,#product .current-price{ font-family:var(--font-head); }
#product .product-description-short,#product .product-description{ color:var(--muted); font-size:15px; line-height:1.75; }
#product .product-information .product-manufacturer{ color:var(--muted); }
#product .h4,#product .product-information .h4{ font-family:var(--font-head); color:var(--ink); }
#product .social-sharing li{ border:1px solid var(--line); border-radius:50%; }
#product .product-features dt.name,#product .data-sheet dt{ color:var(--ink); font-weight:600; }
#product .product-features dd.value,#product .data-sheet dd{ color:var(--muted); }

/* ---- 5) CART: font sizes + button styles ---- */
.cart-grid .cart-summary .h1,#cart .cart-overview .h1,.cart-grid-body .h1{ font-family:var(--font-head); font-size:clamp(24px,2.6vw,34px); }
.cart-summary-products,.cart-item .product-line-info{ font-size:15px; }
.cart-item .product-line-info .label,.product-line-info a.label{ font-family:var(--font-head); font-size:16px; color:var(--ink); }
.cart-summary .cart-total .value,.cart-detailed-totals .label,.cart-summary-line .value{ font-weight:600; }
.cart-detailed-actions .btn,.checkout a.btn,#cart .btn-primary{ border-radius:100px; font-weight:600; }
.cart-grid-right .card-block{ font-size:14.5px; }
.product-quantity .input-group .form-control,.cart-item .qty .form-control{ border-radius:10px; }

/* ============================================================
   UI CORRECTIONS v2 (from live screenshots)
   ============================================================ */

/* --- CATEGORY: kill the empty faceted-search box; only show it when it has facets --- */
#left-column #search_filters_wrapper,#left-column #search_filters,#left-column #search_filter_controls{
  border:0 !important; border-radius:0; padding:0; background:transparent; box-shadow:none; }
#left-column #search_filters_wrapper:has(.facet){
  border:1px solid var(--line) !important; border-radius:var(--radius); padding:1.25rem; background:#fff; margin-top:1rem; }
#left-column #search_filter_controls:empty{ display:none; }
/* category nav block heading */
#left-column .block-categories .category-top-menu>li>a{ font-family:var(--font-body); font-weight:700; color:var(--ink); }

/* --- LISTING: product flags as small pills top-start, themed colours ---
   inset-inline-start, so in Arabic they take the top-RIGHT corner. blockwishlist
   already moves its heart to the left there; a physical `left` left both in the
   same corner, one printed over the other. */
.product-miniature .thumbnail-top{ position:relative; }
.product-miniature .product-flags{ position:absolute; top:12px; inset-inline-start:12px; z-index:3; margin:0; padding:0;
  list-style:none; display:flex; flex-direction:column; align-items:flex-start; gap:6px; max-width:70%; }
.product-miniature .product-flag{ display:inline-block; width:auto; margin:0; padding:5px 11px; font-size:11px; font-weight:700;
  letter-spacing:.03em; line-height:1.2; border-radius:100px; color:#fff; background:var(--accent); box-shadow:none; }
.product-miniature .product-flag.new{ background:var(--green); }
.product-miniature .product-flag.on-sale{ background:var(--accent); }
.product-miniature .product-flag.discount{ background:var(--ink); }
.product-miniature .product-flag.online-only,.product-miniature .product-flag.pack{ background:var(--muted); }

/* --- PRODUCT PAGE: clean up orphaned "Quantité" label left by quickorder replace-cart mode --- */
#product .product-add-to-cart .control-label{ display:none !important; }
#product .product-add-to-cart{ border:0 !important; padding:0 !important; margin:0 !important; min-height:0 !important; }
/* the COD form (quickorder) becomes the primary CTA — give it a little breathing room */
#product .product-additional-info,#product .js-product-additional-info{ margin-top:1rem; }

/* --- LANDING: theme the turquoise section-title underline to orange --- */
.ps-landing-section-title::after,.ps-landing-section-title:after{ background:var(--accent) !important; }
.ps-landing-section-title{ border-bottom-color:var(--accent) !important; }
.ps-landing-features-grid .ps-landing-feature-card{ border-radius:var(--radius); border:1px solid var(--line); }

/* --- SUBCATEGORY cover cards (theme override: templates/catalog/_partials/subcategories.tpl) ---
   image fills the card (object-fit:cover, no khatem-border bug), name overlaid
   on a bottom scrim, hover zooms the photo + reveals an accent arrow.
   NOTE: classic theme.css targets `#subcategories ul` / `#subcategories ul li`
   (ID selectors: flex, min-width:200px, text-align:center) — so the structural
   rules MUST carry the `#subcategories` prefix to win specificity, else the
   grid collapses to classic's flex layout (was rendering flex/centered/1-col). */
#subcategories.tw-subcats{ margin:0 0 1.75rem; padding:0; border:0; border-top:0; background:none; box-shadow:none; }
#subcategories .tw-subcats__heading{ font-family:var(--font-head); font-size:clamp(20px,2.2vw,28px); color:var(--ink); margin:0 0 1.1rem; font-weight:600; }
/* Brief pt.4 — HORIZONTAL cards: square thumbnail, then name + short
   description, arrow pinned at the end.
   ONE PER ROW, deliberately. An auto-fit grid gave two per row in the ~977px
   product column, and the shop has THREE sub-categories: the third sat alone in
   a half-empty row, which reads as a broken grid — and as that card being
   bigger, though every box measures the same. One column widows nothing at any
   item count, lines every card up with the product grid's edges, and lets the
   description run on one line instead of being clamped at two.
   The min-height is the second half of the promise: without it a row whose
   description wraps is taller than its neighbours. */
#subcategories .tw-subcats__grid{ display:grid; grid-template-columns:1fr; gap:14px;
  list-style:none; margin:0; padding:0; flex-wrap:nowrap; justify-content:stretch; }
#subcategories .tw-subcat{ width:auto; min-width:0; margin:0; padding:0; float:none; text-align:start; }
#subcategories .tw-subcat__link{ position:relative; display:flex; align-items:stretch; min-height:104px;
  background:#fff; border:1px solid var(--line); border-radius:var(--radius-lg); overflow:hidden;
  box-shadow:none; text-decoration:none; padding:0;
  transition:border-color .3s var(--ease), box-shadow .3s var(--ease), transform .3s var(--ease); }
#subcategories .tw-subcat__link:hover{ border-color:var(--accent); box-shadow:var(--shadow-sm); transform:translateY(-2px); }
#subcategories .tw-subcat__media{ position:relative; inset:auto; z-index:0;
  flex:0 0 clamp(94px,11vw,130px); align-self:stretch; overflow:hidden; }
#subcategories .tw-subcat__img{ position:absolute; inset:0; width:100%; height:100%; max-width:none;
  object-fit:cover; object-position:center; transition:transform .9s var(--ease); }
#subcategories .tw-subcat__ph{ position:absolute; inset:0; background-color:var(--cream); background-image:var(--khatem); background-size:38px; }
#subcategories .tw-subcat__body{ flex:1 1 auto; min-width:0; display:flex; flex-direction:column;
  justify-content:center; gap:.22rem; padding:clamp(13px,1.5vw,18px) clamp(14px,1.6vw,20px); }
#subcategories .tw-subcat__name{ position:static; z-index:auto; padding:0; max-width:none;
  font-family:var(--font-head); font-size:clamp(16px,1.4vw,19px); font-weight:600; color:var(--ink);
  line-height:1.25; text-transform:none; text-shadow:none; }
#subcategories .tw-subcat__desc{ font-family:var(--font-body); font-size:13px; line-height:1.5; color:var(--muted);
  display:-webkit-box; -webkit-line-clamp:2; -webkit-box-orient:vertical; overflow:hidden; }
#subcategories .tw-subcat__go{ position:relative; inset:auto; z-index:auto; flex:0 0 auto; align-self:center;
  margin-inline-end:clamp(12px,1.4vw,18px); width:34px; height:34px; display:grid; place-items:center;
  border-radius:50%; background:var(--cream); color:var(--accent-deep); opacity:1; transform:none;
  transition:background .3s var(--ease), color .3s var(--ease), transform .3s var(--ease); }
#subcategories .tw-subcat__go .arr{ width:15px; height:15px; }
#subcategories .tw-subcat__link:hover .tw-subcat__img{ transform:scale(1.06); }
#subcategories .tw-subcat__link:hover .tw-subcat__go{ background:var(--accent); color:#fff; }
.tw-subcats[dir="rtl"] .tw-subcat__go .arr{ transform:scaleX(-1); }
@media (max-width:560px){ #subcategories .tw-subcats__grid{ gap:12px; } }

/* ============================================================
   LANDING (hide_chrome) products — match PRS01001 clean COD landing:
   hide social sharing + product comments (they shouldn't show on the landing).
   body.lp-chrome-hidden is added by landingpagecod when hide_chrome is on.
   ============================================================ */
body.lp-chrome-hidden .social-sharing,
body.lp-chrome-hidden #product-comments-list-header,
body.lp-chrome-hidden #product-comments-list,
body.lp-chrome-hidden #product-comments-list-footer,
body.lp-chrome-hidden #empty-product-comment,
body.lp-chrome-hidden .comments-nb,
body.lp-chrome-hidden #post-product-comment,
body.lp-chrome-hidden .product-comments,
body.lp-chrome-hidden .comments,
body.lp-chrome-hidden .product-comments-additional-info,
body.lp-chrome-hidden .blockreassurance_product,
body.lp-chrome-hidden .block-reassurance,
body.lp-chrome-hidden #block-reassurance,
body.lp-chrome-hidden .reassurance{ display:none !important; }

/* ============================================================
   SEARCHBAR override: size icon + pill EVERYWHERE it renders
   (fixes giant magnifier in empty-category / no-results blocks).
   Header keeps its own (more specific) sizing under .tw-search.
   ============================================================ */
.tw-searchbar .tw-search-ico{ width:18px !important; height:18px !important; flex:none; color:var(--muted); }
.tw-searchbar form{ display:flex; align-items:center; gap:9px; background:var(--cream);
  border:1px solid var(--line); border-radius:100px; padding:10px 18px; max-width:380px; }
.tw-searchbar form:focus-within{ border-color:var(--accent); background:#fff; }
.tw-searchbar input[type="text"]{ flex:1; min-width:0; border:0; outline:0; background:transparent;
  font-family:inherit; font-size:14px; color:var(--ink); }
/* centre the search inside the empty-category / no-products block */
#products .search-widget,#js-product-list .search-widget,.page-not-found .tw-searchbar{ margin:1rem auto 0; }
#products .search-widget form,.page-not-found .tw-searchbar form{ margin-inline:auto; }
/* the big "no products" icon, if any, kept reasonable */
#products .no-products svg,#js-product-list svg.icon-no-result{ width:80px; height:80px; }

/* ============================================================
   Footer tweaks (user feedback): kill newsletter white box, hide social
   ============================================================ */
.tw-footer__news .block_newsletter.tw-news,
.tw-footer__news .tw-news{
  background:transparent !important; padding:0 !important; margin:0 !important;
  max-width:none !important; border:0 !important; box-shadow:none !important; float:none !important;
}
.tw-footer__news .tw-news input{ box-shadow:none; }
/* hide footer social icons */
.tw-footer__social{ display:none !important; }

/* ============================================================
   Recolor classic's turquoise (#24b9d7) links to Twiza orange.
   Base element selector — higher-specificity component rules
   (.product-title a, .breadcrumb a, .tw-nav a, footer, .twiza-home a) win.
   ============================================================ */
a{ color:var(--accent-deep); }
a:hover{ color:var(--accent); }
.btn-link,.page-link{ color:var(--accent-deep); }
/* keep utility/neutral contexts from going orange unintentionally */
.breadcrumb a,.tw-footer__col a,.tw-footer__legal a,.product-miniature .product-title a,
#product .product-information h1 a,.tw-nav a,.cart-item a,.product-line-info a.label{ color:inherit; }
.breadcrumb a:hover,.tw-footer__col a:hover,.tw-footer__legal a:hover,
.product-miniature .product-title a:hover{ color:var(--accent-deep); }

/* ============================================================
   UI FIX (2026-06) — header turquoise + hero button merge
   ------------------------------------------------------------
   The twiza header (#tw-header) is rendered INSIDE classic's
   <header id="header">, so classic's #header a:hover{color:#24b9d7}
   (specificity 1,1,1) beat every .tw-* class override → turquoise.
   These #header #tw-header (2,1,1) rules decisively win it back.
   ============================================================ */
#header #tw-header a:hover,
#header #tw-header a:focus,
#header #tw-header .tw-iconbtn:hover,
#header #tw-header .tw-nav .top-menu a:hover,
#header #tw-header .tw-nav .top-menu .sub-menu a:hover,
#header #tw-header .tw-cart a:hover,
#header #tw-header .tw-cart .tw-cart-link:hover{ color:var(--accent-deep); }
/* preserve the soft-orange hover pill on the icon/cart buttons */
#header #tw-header .tw-iconbtn:hover,
#header #tw-header .tw-cart .tw-cart-link:hover{ background:var(--accent-soft); }

/* Hero/CTA solid+green buttons kept legible on hover.
   #main a:hover{color:var(--accent-deep)} (1,1,1) was tinting the
   label the same deep-orange as the hover background → text merged in. */
#main .twiza-home .btn--solid:hover,
#main .twiza-home .btn--green:hover,
#main a.btn-primary:hover,
#main a.btn-primary:active,
#main .twiza-territory .tp-btn:hover,
#main .twiza-territory .tp-btn:focus,
#main .twiza-territory .tp-btn:active,
#main :is(.twiza-home,.products) .product__order:hover,
#main :is(.twiza-home,.products) .product__order:focus,
#main :is(.twiza-home,.products) .product__order:active,
#main .twiza-home a.product__add:hover,
#main .twiza-home a.product__add:focus{ color:#fff; }

/* ════════════════════════════════════════════════════════════════════════
   NOTRE MODÈLE  (CMS id 10)  ·  page components + Arabic webfont + RTL
   Wrapper: <section class="twiza-home twiza-model">  → reuses home primitives.
   Added 2026-06-11 (new-pages integration, page 1/3).
   ════════════════════════════════════════════════════════════════════════ */

/* ---- suppress default breadcrumb + page-header title (own hero handles it) ---- */
body.cms-id-10 .breadcrumb,
body.cms-id-10 .page-header,
body.cms-id-13 .breadcrumb,
body.cms-id-13 .page-header,
body.cms-id-14 .breadcrumb,
body.cms-id-14 .page-header{ display:none !important; }
/* own hero must butt up under the fixed header — drop classic #wrapper's top
   padding (~1.563rem) that otherwise leaves a gap where the breadcrumb was */
body.cms-id-13 #wrapper,
body.cms-id-14 #wrapper{ padding-top:0; }

/* ---- Arabic self-hosted webfonts (headings: El Messiri · body: Cairo) ---- */
@font-face{ font-family:'Cairo'; font-style:normal; font-weight:400; font-display:swap;
  src:url(../fonts/twiza/cairo-400-normal.woff2) format('woff2');
  unicode-range:U+0600-06FF,U+0750-077F,U+0870-088E,U+0890-0891,U+0898-08E1,U+08E3-08FF,U+200C-200E,U+2010-2011,U+204F,U+2E41,U+FB50-FDFF,U+FE70-FE74,U+FE76-FEFC; }
@font-face{ font-family:'Cairo'; font-style:normal; font-weight:500; font-display:swap;
  src:url(../fonts/twiza/cairo-500-normal.woff2) format('woff2');
  unicode-range:U+0600-06FF,U+0750-077F,U+0870-088E,U+0890-0891,U+0898-08E1,U+08E3-08FF,U+200C-200E,U+2010-2011,U+204F,U+2E41,U+FB50-FDFF,U+FE70-FE74,U+FE76-FEFC; }
@font-face{ font-family:'Cairo'; font-style:normal; font-weight:600; font-display:swap;
  src:url(../fonts/twiza/cairo-600-normal.woff2) format('woff2');
  unicode-range:U+0600-06FF,U+0750-077F,U+0870-088E,U+0890-0891,U+0898-08E1,U+08E3-08FF,U+200C-200E,U+2010-2011,U+204F,U+2E41,U+FB50-FDFF,U+FE70-FE74,U+FE76-FEFC; }
@font-face{ font-family:'Cairo'; font-style:normal; font-weight:700; font-display:swap;
  src:url(../fonts/twiza/cairo-700-normal.woff2) format('woff2');
  unicode-range:U+0600-06FF,U+0750-077F,U+0870-088E,U+0890-0891,U+0898-08E1,U+08E3-08FF,U+200C-200E,U+2010-2011,U+204F,U+2E41,U+FB50-FDFF,U+FE70-FE74,U+FE76-FEFC; }
@font-face{ font-family:'El Messiri'; font-style:normal; font-weight:600; font-display:swap;
  src:url(../fonts/twiza/elmessiri-600-normal.woff2) format('woff2');
  unicode-range:U+0600-06FF,U+0750-077F,U+0870-088E,U+0890-0891,U+0898-08E1,U+08E3-08FF,U+200C-200E,U+2010-2011,U+204F,U+2E41,U+FB50-FDFF,U+FE70-FE74,U+FE76-FEFC; }
@font-face{ font-family:'El Messiri'; font-style:normal; font-weight:700; font-display:swap;
  src:url(../fonts/twiza/elmessiri-700-normal.woff2) format('woff2');
  unicode-range:U+0600-06FF,U+0750-077F,U+0870-088E,U+0890-0891,U+0898-08E1,U+08E3-08FF,U+200C-200E,U+2010-2011,U+204F,U+2E41,U+FB50-FDFF,U+FE70-FE74,U+FE76-FEFC; }

/* ────────────────────────────────────────────────────────────────────────
   Page components. Rebuilt 2026-08-07 against the nine mockups
   (shots/notre-modele-section-*). The previous set (.mhero__grid / .why4 /
   .timeline / .profiles / .partners / .vision) is gone with the seven-section
   template it dressed.

   House rules that apply throughout:
   · every band is a .section, so it is full-bleed and pays --section-y;
   · two-column bands are grids with minmax(0,…) tracks — an auto track's
     minimum is its content's width, and a long Arabic word would otherwise
     widen the band instead of wrapping;
   · rules between cells use border-inline-start so they mirror in Arabic,
     and every max-width query drops them (an inline border on a wrapped
     grid draws in the middle of a row).
   ──────────────────────────────────────────────────────────────────────── */

.twiza-model{
  /* the mockups' panels are far darker than --green, which is a UI green */
  --mgreen:#22432F;
  /* h2s across the nine sections read dark-green rather than the warm --ink */
  --mhead:#1F3B2B;
}

/* ---- shared type + ornaments ---- */
.twiza-model h2{ color:var(--mhead); }
.twiza-model h1 em,.twiza-model h2 em{ font-style:normal; color:var(--accent); }
.twiza-model .mlead{ margin-top:22px; font-size:17.5px; line-height:1.85; }
.twiza-model .mbody{ margin-top:18px; color:var(--muted); font-size:16px; line-height:1.75; }
.twiza-model .mbody b,.twiza-model .mlead b{ color:var(--ink); font-weight:600; }
.twiza-model .mcap{ margin-top:12px; font-size:13px; color:var(--muted); }
.twiza-model .mcta{ margin-top:30px; }

/* line · two-tone diamond · line — the divider under most headings */
.twiza-model .orn{ display:flex; align-items:center; gap:10px; margin-top:20px; }
.twiza-model .orn::before,.twiza-model .orn::after{ content:""; width:34px; height:2px; border-radius:2px; }
.twiza-model .orn::before{ background:var(--green); }
.twiza-model .orn::after{ background:var(--accent); }
.twiza-model .orn > span{ width:11px; height:11px; border-radius:2px; transform:rotate(45deg);
  background:linear-gradient(135deg, var(--green) 0 50%, var(--accent) 50% 100%); }

/* eyebrow variants. These land AFTER .twiza-home .eyebrow::before at the same
   specificity (0,2,1), so they win on source order — do not move them above it. */
.twiza-model .eyebrow--dia::before{ width:11px; height:11px; border-radius:2px; transform:rotate(45deg);
  background:linear-gradient(135deg, var(--green) 0 50%, var(--accent) 50% 100%); }
.twiza-model .eyebrow--stack{ display:block; }
.twiza-model .eyebrow--stack::before{ display:none; }
/* A stalk fading downward. The mockup hangs a small diamond off its end; that
   needs a rotated box, and both pseudo-elements are already spoken for here
   (::before is the eyebrow's own rule, hidden above), so the stalk carries the
   ornament alone rather than degrading into a smudge. */
.twiza-model .eyebrow--stack::after{ content:""; display:block; width:2px; height:30px;
  margin-top:10px; margin-inline-start:5px; border-radius:2px;
  background:linear-gradient(var(--accent), rgba(240,144,28,.1)); }

/* figures: the five placeholder slots and the photographs share this base */
.twiza-model .mfig{ margin:0; min-width:0; }
.twiza-model .mfig img{ width:100%; height:auto; border-radius:var(--radius); }

/* ---- 1 · HERO ---- */
.twiza-model .mhero__grid{ display:grid; grid-template-columns:minmax(0,1fr) minmax(0,1.05fr);
  gap:clamp(30px,4vw,64px); align-items:center; }
.twiza-model .mhero__text h1{ font-size:clamp(36px,4.5vw,62px); line-height:1.05; margin-top:20px;
  letter-spacing:-.02em; text-wrap:balance; color:var(--ink); }

.twiza-model .mstats{ margin-top:clamp(34px,4vw,56px); display:grid; grid-template-columns:repeat(4,1fr);
  background:#fff; border:1px solid var(--line); border-radius:var(--radius);
  box-shadow:var(--shadow-sm); overflow:hidden; }
.twiza-model .mstat{ display:flex; align-items:center; gap:16px; padding:22px clamp(16px,1.8vw,24px); min-width:0; }
.twiza-model .mstat + .mstat{ border-inline-start:1px solid var(--line); }
.twiza-model .mstat__ph{ width:56px; height:56px; flex:none; border-radius:50%; overflow:hidden; background:var(--cream); }
.twiza-model .mstat__ph img{ width:100%; height:100%; object-fit:cover; }
.twiza-model .mstat__body{ min-width:0; }
.twiza-model .mstat__n{ font-family:var(--font-head); font-size:clamp(24px,2.2vw,30px); font-weight:600; line-height:1; }
.twiza-model .mstat__l{ font-size:13.5px; font-weight:600; margin-top:6px; }
.twiza-model .mstat__s{ font-size:12px; color:var(--muted); margin-top:3px; line-height:1.45; }

/* ---- 2 · L'ESPRIT DE TWIZA ---- */
.twiza-model .msoul__grid{ display:grid; grid-template-columns:minmax(0,.95fr) minmax(0,1.1fr);
  gap:clamp(30px,5vw,72px); align-items:center; }
.twiza-model .msoul__media{ position:relative; margin:0; border-radius:var(--radius); overflow:hidden; aspect-ratio:4/5; }
.twiza-model .msoul__media img{ width:100%; height:100%; object-fit:cover; }
.twiza-model .msoul__text{ min-width:0; }
.twiza-model .msoul__text h2{ font-size:clamp(28px,3.4vw,46px); margin-top:16px; line-height:1.12; }

.twiza-model .mrows{ list-style:none; padding:0; margin:26px 0 0; }
.twiza-model .mrows li{ display:grid; grid-template-columns:48px minmax(0,1fr); gap:18px;
  align-items:start; padding:18px 0; }
.twiza-model .mrows li + li{ border-top:1px solid var(--line); }
.twiza-model .mrows__ic{ width:48px; height:48px; border-radius:50%; background:var(--cream);
  border:1px solid var(--line); display:flex; align-items:center; justify-content:center; color:var(--ink); }
.twiza-model .mrows__ic svg{ width:23px; height:23px; }
.twiza-model .mrows p{ font-size:15px; color:var(--muted); line-height:1.7; }
.twiza-model .mrows p b{ color:var(--ink); font-weight:600; }

.twiza-model .mquote{ margin:26px 0 0; padding-inline-start:22px; border-inline-start:3px solid var(--accent); }
.twiza-model .mquote::before{ content:"\201C"; display:block; font-family:var(--font-head);
  font-size:46px; line-height:.7; color:var(--accent); }
.twiza-model .mquote p{ margin-top:10px; font-family:var(--font-head); font-style:italic;
  font-size:19px; line-height:1.5; color:var(--mhead); }
.twiza-model .mquote cite{ display:block; margin-top:12px; font-style:normal; font-size:11px; font-weight:700;
  letter-spacing:.14em; text-transform:uppercase; color:var(--accent-deep); }

/* ---- shared: highlight cards (§3 §4 §5 §6) ---- */
.twiza-model .mhl{ display:flex; gap:14px; align-items:flex-start; margin:0;
  border-radius:var(--radius); padding:22px clamp(18px,2vw,24px); }
.twiza-model .mhl p{ font-size:14.5px; line-height:1.65; color:var(--muted); }
.twiza-model .mhl p b{ color:var(--ink); font-weight:600; }
.twiza-model .mhl--soft{ background:var(--orange-tint); border:1px solid var(--accent-soft); }
.twiza-model .mhl--green{ background:var(--mgreen); }
.twiza-model .mhl--green p,.twiza-model .mhl--green p b{ color:#fff; }
.twiza-model .mhl__ic{ width:44px; height:44px; flex:none; border-radius:12px; background:#fff;
  border:1px solid var(--accent-soft); color:var(--accent-deep);
  display:flex; align-items:center; justify-content:center; }
.twiza-model .mhl__ic svg{ width:22px; height:22px; }
.twiza-model .mhl--green .mhl__ic{ background:rgba(255,255,255,.12); border-color:rgba(255,255,255,.24); color:#fff; }
/* the icon slot as the brand mark rather than a glyph. A rotated inner box —
   --khatem is a hairline outline and reads as a dot at this size. */
.twiza-model .mhl__ic--dia{ position:relative; }
.twiza-model .mhl__ic--dia::before{ content:""; position:absolute; top:50%; left:50%;
  width:16px; height:16px; margin:-8px 0 0 -8px; border-radius:2px; transform:rotate(45deg);
  background:linear-gradient(135deg, var(--green) 0 50%, var(--accent) 50% 100%); }
/* the icon-less variant: a quote box (§4) */
.twiza-model .mhl--quote{ position:relative; padding-inline-start:56px; }
.twiza-model .mhl--quote::before{ content:"\201C"; position:absolute; inset-inline-start:22px; top:16px;
  font-family:var(--font-head); font-size:40px; line-height:1; color:var(--accent); }

/* ---- shared: divided icon columns (§4 three-up, §7 four-up) ---- */
.twiza-model .mcols{ list-style:none; margin:30px 0 0; padding:0; display:grid; }
.twiza-model .mcols--3{ grid-template-columns:repeat(3,minmax(0,1fr)); }
.twiza-model .mcols--4{ grid-template-columns:repeat(4,minmax(0,1fr)); }
.twiza-model .mcols li{ padding:4px clamp(12px,1.4vw,18px); min-width:0; }
.twiza-model .mcols li:first-child{ padding-inline-start:0; }
.twiza-model .mcols li + li{ border-inline-start:1px solid var(--line); }
.twiza-model .mcols__ic{ display:flex; width:40px; height:40px; align-items:center;
  justify-content:center; color:var(--green-deep); }
.twiza-model .mcols li:nth-child(even) .mcols__ic{ color:var(--accent-deep); }
.twiza-model .mcols__ic svg{ width:32px; height:32px; }
.twiza-model .mcols h3{ font-family:var(--font-body); font-size:12px; font-weight:700;
  letter-spacing:.1em; text-transform:uppercase; margin:12px 0 8px; color:var(--ink); }
.twiza-model .mcols p{ font-size:12.5px; color:var(--muted); line-height:1.6; }

/* ---- shared: the dark-green panel laid over a photograph (§4 §7) ---- */
.twiza-model .mpanel{ position:absolute; inset-inline-end:0; bottom:8%; width:min(74%,346px);
  background:var(--mgreen); color:#fff; padding:16px clamp(16px,1.8vw,22px);
  border-start-start-radius:var(--radius); border-end-start-radius:var(--radius); }
.twiza-model .mpanel__row{ display:flex; align-items:center; gap:14px; padding:11px 0; }
.twiza-model .mpanel__row + .mpanel__row{ border-top:1px solid rgba(255,255,255,.16); }
.twiza-model .mpanel__ic{ width:40px; height:40px; flex:none; border-radius:50%;
  border:1px solid rgba(255,255,255,.3); display:flex; align-items:center; justify-content:center; }
.twiza-model .mpanel__ic svg{ width:20px; height:20px; }
.twiza-model .mpanel__row > div{ min-width:0; }
.twiza-model .mpanel__row strong{ display:block; font-family:var(--font-head); font-size:23px;
  font-weight:600; color:var(--accent); line-height:1.1; }
/* name the label, not "any span in the row": a bare `span` here is one component
   more specific than `.mpanel__ic`, so it stole the icon's display:flex and the
   glyph fell to the top-left of its ring instead of centring in it. */
.twiza-model .mpanel__row > div span{ display:block; margin-top:2px; font-size:12px; line-height:1.45; opacity:.92; }

/* ---- 3 · LA VENTE SOLIDAIRE ---- */
.twiza-model .msolid__grid{ display:grid; grid-template-columns:minmax(0,.85fr) minmax(0,1.15fr);
  gap:clamp(28px,4vw,56px); align-items:center; }
.twiza-model .msolid__text{ min-width:0; }
.twiza-model .msolid__text h2{ font-size:clamp(29px,3.6vw,48px); margin-top:14px; line-height:1.1; }
/* the mockup sets this line in a script face; the house has none, so it takes
   the brand serif in italic — the most expressive voice the theme owns */
.twiza-model .mscript{ margin-top:18px; font-family:var(--font-head); font-style:italic;
  font-size:clamp(18px,1.9vw,25px); line-height:1.45; color:var(--ink); }
.twiza-model .mscript em{ font-style:italic; color:var(--accent); }

.twiza-model .msolid__after{ margin-top:clamp(32px,4vw,52px); display:grid;
  grid-template-columns:minmax(0,.36fr) minmax(0,1fr); gap:22px; align-items:start; }
.twiza-model .mchange{ background:#fff; border:1px solid var(--line); border-radius:var(--radius);
  padding:24px clamp(16px,2vw,28px) 28px; }
.twiza-model .mchange__h{ display:flex; align-items:center; justify-content:center; gap:14px;
  font-family:var(--font-head); font-size:14.5px; font-weight:700; letter-spacing:.16em;
  text-transform:uppercase; color:var(--mhead); }
.twiza-model .mchange__h::before,.twiza-model .mchange__h::after{ content:""; width:26px; height:1px;
  background:var(--accent); opacity:.65; }
.twiza-model .mchange__grid{ list-style:none; margin:24px 0 0; padding:0;
  display:grid; grid-template-columns:repeat(5,minmax(0,1fr)); }
.twiza-model .mchange__grid li{ padding:4px clamp(10px,1.2vw,18px); min-width:0; }
.twiza-model .mchange__grid li:first-child{ padding-inline-start:0; }
.twiza-model .mchange__grid li + li{ border-inline-start:1px solid var(--line); }
.twiza-model .mchange__ic{ display:flex; width:38px; height:38px; align-items:center;
  justify-content:center; color:var(--accent-deep); }
.twiza-model .mchange__ic svg{ width:30px; height:30px; }
.twiza-model .mchange h4{ font-family:var(--font-body); font-size:12px; font-weight:700;
  letter-spacing:.1em; text-transform:uppercase; margin:12px 0 8px; color:var(--ink); }
.twiza-model .mchange p{ font-size:12.5px; color:var(--muted); line-height:1.6; }

/* ---- shared: full-width bars (§3 accent CTA, §7 soft quote) ---- */
.twiza-model .mbar{ display:grid; align-items:center; border-radius:var(--radius);
  margin-top:clamp(26px,3vw,40px); }
.twiza-model .mbar--accent{ grid-template-columns:auto minmax(0,1fr) auto auto; gap:clamp(14px,1.8vw,22px);
  background:var(--accent); color:#fff; padding:22px clamp(20px,2.6vw,34px);
  box-shadow:0 16px 34px -20px var(--accent); transition:background .25s var(--ease); }
.twiza-model .mbar--accent:hover{ background:var(--accent-deep); }
/* The whole band is one <a>, so classic's `#main a:hover{color:var(--accent-deep)}`
   (1,1,1) beats the band's own `color:#fff` (0,2,0) and paints the label the exact
   colour the background moves to — the text vanishes into the fill. Needs the #main
   prefix to win. Fourth time this rule has bitten; see the handoff. */
#main .twiza-model .mbar--accent:hover,
#main .twiza-model .mbar--accent:focus{ color:#fff; }
.twiza-model .mbar__ic{ width:44px; height:44px; flex:none; display:flex; align-items:center; justify-content:center; }
.twiza-model .mbar__ic svg{ width:32px; height:32px; }
.twiza-model .mbar__t{ font-family:var(--font-head); font-size:clamp(18px,2.1vw,26px);
  font-weight:600; line-height:1.3; }
.twiza-model .mbar__arr{ width:22px; height:22px; flex:none; }
.twiza-model .mbar__s{ max-width:280px; padding-inline-start:clamp(16px,2vw,24px);
  border-inline-start:1px solid rgba(255,255,255,.36); font-size:13px; line-height:1.5; opacity:.94; }

.twiza-model .mbar--soft{ grid-template-columns:auto minmax(0,1fr) auto; gap:clamp(16px,2.4vw,34px);
  background:var(--cream-2); padding:24px clamp(20px,2.6vw,34px); }
.twiza-model .mbar__q{ width:58px; height:58px; flex:none; border-radius:50%; background:var(--accent-soft);
  color:var(--accent); display:flex; align-items:center; justify-content:center;
  font-family:var(--font-head); font-size:44px; line-height:1; padding-top:20px; }
.twiza-model .mbar--soft .mbar__t{ color:var(--mhead); font-size:clamp(17px,2vw,24px); line-height:1.4; }
.twiza-model .mbar--soft .mbar__t b{ color:var(--accent-deep); font-weight:600; }
.twiza-model .mbar__end{ text-align:center; padding-inline-start:clamp(16px,2.4vw,34px);
  border-inline-start:1px solid var(--line); }

/* ---- 4 · POURQUOI TWIZA ---- */
.twiza-model .mterr__grid{ display:grid; grid-template-columns:minmax(0,.92fr) minmax(0,1.08fr);
  gap:clamp(28px,4vw,60px); align-items:center; }
.twiza-model .mterr__text{ min-width:0; }
.twiza-model .mterr__text h2{ font-size:clamp(29px,3.6vw,48px); margin-top:14px; line-height:1.1; }
.twiza-model .mterr__text .mhl--quote{ margin-top:28px; }
.twiza-model .mterr__media{ position:relative; margin:0; border-radius:var(--radius);
  overflow:hidden; aspect-ratio:4/5; }
.twiza-model .mterr__media img{ width:100%; height:100%; object-fit:cover; }

.twiza-model .mbridge{ margin-top:clamp(24px,3vw,38px); display:flex; align-items:center;
  gap:18px; flex-wrap:wrap; background:#fff; border:1px solid var(--line);
  border-radius:var(--radius); box-shadow:var(--shadow-sm); padding:20px clamp(20px,2.4vw,32px); }
.twiza-model .mbridge__dia{ width:11px; height:11px; flex:none; border-radius:2px;
  transform:rotate(45deg);
  background:linear-gradient(135deg, var(--green) 0 50%, var(--accent) 50% 100%); }
.twiza-model .mbridge p{ flex:1 1 320px; font-family:var(--font-head);
  font-size:clamp(17px,2vw,23px); color:var(--mhead); }
.twiza-model .mbridge p b{ color:var(--accent-deep); font-weight:600; }

/* ---- 5 · UN MODÈLE INTÉGRÉ ---- */
.twiza-model .mloop__grid{ display:grid; grid-template-columns:minmax(0,.85fr) minmax(0,1.15fr);
  gap:clamp(28px,4vw,56px); align-items:center; }
.twiza-model .mloop__text{ min-width:0; }
.twiza-model .mloop__text h2{ font-size:clamp(29px,3.6vw,48px); margin-top:14px; line-height:1.1; }
.twiza-model .mloop__text .mhl{ margin-top:26px; }
.twiza-model .mtraits{ list-style:none; margin:clamp(28px,3.4vw,44px) 0 0;
  padding:24px clamp(16px,2.2vw,28px); display:grid; grid-template-columns:repeat(4,minmax(0,1fr));
  gap:clamp(16px,2vw,30px); background:#fff; border:1px solid var(--line); border-radius:var(--radius); }
.twiza-model .mtraits li{ display:grid; grid-template-columns:52px minmax(0,1fr); gap:16px; align-items:start; }
.twiza-model .mtraits__ic{ width:52px; height:52px; border-radius:14px; color:#fff;
  display:flex; align-items:center; justify-content:center; }
/* The mockup tinted these four olive and violet, which belong to no other part
   of the site. They take the house palette instead — the two greens and the two
   oranges, alternated so no two neighbours read as the same colour. */
.twiza-model .mtraits__ic--1{ background:var(--mgreen); }
.twiza-model .mtraits__ic--2{ background:var(--accent); }
.twiza-model .mtraits__ic--3{ background:var(--green); }
.twiza-model .mtraits__ic--4{ background:var(--accent-deep); }
.twiza-model .mtraits__ic svg{ width:26px; height:26px; }
.twiza-model .mtraits h3{ font-family:var(--font-body); font-size:12px; font-weight:700;
  letter-spacing:.1em; text-transform:uppercase; color:var(--ink); }
.twiza-model .mtraits p{ margin-top:8px; font-size:12.5px; color:var(--muted); line-height:1.6; }

/* ---- 6 · NOS UNIVERS ---- */
.twiza-model .muniv__grid{ display:grid; grid-template-columns:minmax(0,.9fr) minmax(0,1.1fr);
  gap:clamp(30px,5vw,72px); align-items:center; }
.twiza-model .muniv__text{ min-width:0; }
.twiza-model .muniv__text h2{ font-size:clamp(29px,3.6vw,48px); margin-top:16px; line-height:1.12; }
.twiza-model .muniv__text .mhl{ margin-top:26px; }

/* ---- 7 · NOS PARTENAIRES ---- */
.twiza-model .mpart__grid{ display:grid; grid-template-columns:minmax(0,1fr) minmax(0,1fr);
  gap:clamp(28px,4vw,56px); align-items:center; }
.twiza-model .mpart__text{ min-width:0; }
.twiza-model .mpart__text h2{ font-size:clamp(28px,3.4vw,46px); margin-top:16px; line-height:1.12; }
/* No fixed ratio at all. Every ratio tried here — square, then the mockup's
   5/4 — was a box the photograph had to be cut down to fit, and each one was
   still visibly a crop. Nothing overlays this figure any more, so it has no
   reason to hold a shape of its own: it takes the shape of whatever the shop
   uploads and loses no pixel of it. */
.twiza-model .mpart__media{ position:relative; margin:0; border-radius:var(--radius);
  overflow:hidden; }
.twiza-model .mpart__media img{ width:100%; height:auto; }

.twiza-model .mlogos{ margin-top:clamp(26px,3vw,42px); }
.twiza-model .mlogos__h{ display:flex; align-items:center; gap:16px; font-family:var(--font-body);
  font-size:11px; font-weight:700; letter-spacing:.16em; text-transform:uppercase; color:var(--muted); }
.twiza-model .mlogos__h::before,.twiza-model .mlogos__h::after{ content:""; flex:1; height:1px; background:var(--line); }
/* named cards, not a logo strip — the partners' artwork does not exist yet */
.twiza-model .partners{ display:grid; grid-template-columns:repeat(6,minmax(0,1fr));
  gap:18px; margin-top:18px; }
.twiza-model .plogo{ display:flex; align-items:center; justify-content:center; background:#fff;
  border:1px solid var(--line); border-radius:var(--radius); padding:30px 16px; min-height:104px;
  text-align:center; transition:transform .25s var(--ease), box-shadow .25s, border-color .25s; }
.twiza-model .plogo:hover{ transform:translateY(-3px); box-shadow:var(--shadow-sm);
  border-color:var(--accent-soft); }
.twiza-model .plogo__img{ max-width:100%; max-height:60px; width:auto; height:auto; object-fit:contain; }
.twiza-model .plogo__name{ font-family:var(--font-head); font-size:19px; font-weight:600;
  color:var(--ink); letter-spacing:.01em; }
.twiza-model .plogo:nth-child(3n+1) .plogo__name{ color:var(--green-deep); }
.twiza-model .plogo:nth-child(3n+2) .plogo__name{ color:var(--accent-deep); }
.twiza-model .plogo__name small{ display:block; font-family:var(--font-body); font-size:10.5px;
  font-weight:600; letter-spacing:.1em; text-transform:uppercase; color:var(--muted); margin-top:4px; }

/* ---- 8 · NOTRE IMPACT ---- */
.twiza-model .mimpact__grid{ display:grid; grid-template-columns:minmax(0,1fr) minmax(0,1.15fr);
  gap:clamp(28px,4vw,56px); align-items:center; }
.twiza-model .mimpact__text{ min-width:0; }
.twiza-model .mimpact__text h2{ font-size:clamp(30px,3.8vw,50px); margin-top:16px; line-height:1.1; }
/* The mockup does not float this photograph inside the wrap: it runs off the
   page, curved on the side that faces the text and cut straight by the edge of
   the screen. Reproduced here rather than approximated, because the floating
   version had to be a closed shape, and a closed organic shape at these radii
   renders as a plain ellipse.
   The breakout distance is the wrap's own side margin — max(gutter, half the
   slack left over from --maxw) — and it is scrollbar-safe for the same reason
   the .section rule at the top of this file is: `vw` counts the scrollbar and
   the layout does not, so --sbw is taken back out. Getting that wrong here
   costs a page-level horizontal scrollbar. */
.twiza-model .mimpact__media{ margin:0; min-width:0;
  margin-inline-end:calc(-1 * max(var(--gutter), (100vw - var(--sbw) - var(--maxw)) / 2)); }
/* No fixed ratio and no height cap: this slot is filled from the back office
   and takes whatever shape the shop uploads, at full height. 16/10 was a
   landscape box and the portrait photograph that arrived in it lost two thirds
   of its height to the centre crop — enough to cut the head off the woman the
   picture is about. A cap was the first answer and it was still a crop, just a
   smaller one, so the cap is gone too. The band grows with a tall photograph
   instead of trimming it; the text column beside it centres on its own. */
.twiza-model .mimpact__media img{ width:100%; height:auto;
  border-radius:54% 0 0 46% / 58% 0 0 42%; }

.twiza-model .mfigures{ list-style:none; margin:clamp(28px,3.4vw,46px) 0 0; padding:0;
  display:grid; grid-template-columns:repeat(6,minmax(0,1fr)); }
.twiza-model .mfigures li{ text-align:center; padding:8px clamp(8px,1.2vw,16px); min-width:0; }
.twiza-model .mfigures li + li{ border-inline-start:1px solid var(--line); }
.twiza-model .mfigures__ic{ display:flex; justify-content:center; color:var(--accent); }
.twiza-model .mfigures__ic svg{ width:34px; height:34px; }
.twiza-model .mfigures__n{ font-family:var(--font-head); font-size:clamp(22px,2.4vw,32px);
  font-weight:600; margin-top:12px; line-height:1.1; color:var(--mhead); }
.twiza-model .mfigures li:nth-child(even) .mfigures__n{ color:var(--accent); }
.twiza-model .mfigures__u{ font-size:.6em; }
.twiza-model .mfigures__l{ margin-top:8px; font-size:12.5px; color:var(--muted); line-height:1.5; }

.twiza-model .mmore{ display:inline-flex; align-items:center; gap:20px; margin-top:clamp(24px,3vw,40px); }
.twiza-model .mmore__ic{ width:56px; height:56px; flex:none; border-radius:50%;
  border:1.5px solid var(--accent); color:var(--accent); display:flex; align-items:center;
  justify-content:center; transition:background .25s var(--ease), color .25s; }
.twiza-model .mmore:hover .mmore__ic{ background:var(--accent); color:#fff; }
.twiza-model .mmore__ic .arr{ width:22px; height:22px; }
.twiza-model .mmore__body strong{ display:block; font-family:var(--font-head); font-size:18px;
  font-weight:600; color:var(--mhead); }
.twiza-model .mmore__body small{ display:block; margin-top:6px; font-size:12.5px;
  color:var(--muted); line-height:1.55; max-width:420px; }

/* ---- 9 · ENSEMBLE ---- */
/* Full-bleed on its own (it is not a .section — it pays no --section-y, the
   photograph sets the height). isolation:isolate keeps the z-index:-1 scrim
   from escaping behind the page background. The --sbw term is not optional —
   see the `.twiza-home .section` note near the top of this file. */
.twiza-model .mtogether{ position:relative; overflow:hidden; isolation:isolate; display:flex;
  align-items:center; min-height:clamp(500px,56vw,700px);
  margin-left:calc(50% - 50vw + var(--sbw)/2); margin-right:calc(50% - 50vw + var(--sbw)/2); background:var(--cream); }
.twiza-model .mtogether__bg{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; z-index:-2; }
.twiza-model .mtogether::before{ content:""; position:absolute; inset:0; z-index:-1;
  background:linear-gradient(to right, var(--cream) 0%, rgba(251,247,240,.94) 34%,
    rgba(251,247,240,.56) 56%, rgba(251,247,240,0) 82%); }
.twiza-model .mtogether__inner{ padding-block:clamp(48px,6vw,86px); }
.twiza-model .mtogether h2{ font-size:clamp(30px,4.2vw,58px); line-height:1.08; margin-top:14px; }
.twiza-model .mtogether__rule{ display:block; width:56px; height:2px; margin-top:26px;
  background:var(--accent); border-radius:2px; }
.twiza-model .mtogether .mbody{ max-width:430px; }
.twiza-model .mtogether .mbody em{ font-style:normal; font-weight:600; color:var(--accent-deep); }

.twiza-model .mpaths{ list-style:none; margin:clamp(32px,4vw,54px) 0 0; padding:0;
  display:grid; grid-template-columns:repeat(4,minmax(0,1fr)); max-width:690px; }
.twiza-model .mpaths li + li{ border-inline-start:1px solid rgba(43,37,30,.14); }
.twiza-model .mpaths a{ display:flex; flex-direction:column; align-items:center; gap:4px;
  padding:8px 10px; text-align:center; }
.twiza-model .mpaths__ic{ width:62px; height:62px; border-radius:50%; border:1.5px solid var(--accent);
  color:var(--accent); background:rgba(255,255,255,.5); display:flex; align-items:center;
  justify-content:center; transition:background .25s var(--ease), color .25s; }
.twiza-model .mpaths a:hover .mpaths__ic{ background:var(--accent); color:#fff; }
.twiza-model .mpaths__ic svg{ width:28px; height:28px; }
.twiza-model .mpaths__t{ font-family:var(--font-head); font-size:18px; font-weight:600;
  margin-top:8px; color:var(--mhead); }
.twiza-model .mpaths__s{ font-size:11px; font-weight:700; letter-spacing:.12em;
  text-transform:uppercase; color:var(--accent-deep); }
.twiza-model .mpaths__arr{ width:18px; height:18px; margin-top:4px; color:var(--ink); opacity:.5; }

/* ════════ RESPONSIVE ════════
   Every inline rule between grid cells is dropped here: once a track count
   drops, `li + li` draws a border in the middle of a row instead of between
   columns. Cards get their own outline back where they need one. */
@media (max-width:1080px){
  .twiza-model .mhero__grid,
  .twiza-model .msoul__grid,
  .twiza-model .msolid__grid,
  .twiza-model .mterr__grid,
  .twiza-model .mloop__grid,
  .twiza-model .muniv__grid,
  .twiza-model .mpart__grid,
  .twiza-model .mimpact__grid{ grid-template-columns:minmax(0,1fr); }
  /* the photograph leads on a narrow screen everywhere it led on a wide one */
  .twiza-model .msoul__media,
  .twiza-model .mterr__media{ aspect-ratio:16/11; }

  .twiza-model .mstats{ grid-template-columns:repeat(2,minmax(0,1fr)); gap:14px;
    background:transparent; border:0; box-shadow:none; overflow:visible; }
  .twiza-model .mstat{ background:#fff; border:1px solid var(--line); border-radius:var(--radius-sm); }

  .twiza-model .msolid__after{ grid-template-columns:minmax(0,1fr); }
  .twiza-model .mchange__grid{ grid-template-columns:repeat(3,minmax(0,1fr)); gap:22px 0; }
  .twiza-model .mcols--4{ grid-template-columns:repeat(2,minmax(0,1fr)); gap:22px 0; }
  .twiza-model .mtraits{ grid-template-columns:repeat(2,minmax(0,1fr)); }
  .twiza-model .mfigures{ grid-template-columns:repeat(3,minmax(0,1fr)); gap:22px 0; }
  /* The rule between cells is a COLUMN divider, drawn by `li + li`. Once these
     grids restack it lands at the start of a row instead — and on one column it
     indents every item but the first. It has to be killed in the same `li + li`
     shape: a selector one component shorter loses and does nothing, which is
     what happened here (the `gap:…px 0` above says the dividers were meant to
     be gone, since nothing else separates the columns). */
  .twiza-model .mchange__grid li, .twiza-model .mchange__grid li + li,
  .twiza-model .mcols li,         .twiza-model .mcols li + li,
  .twiza-model .mfigures li,      .twiza-model .mfigures li + li,
  .twiza-model .mpaths li,        .twiza-model .mpaths li + li{
    border-inline-start:0; padding-inline-start:clamp(12px,1.4vw,18px); }
  /* :first-child outranks the reset above, so both lists that zero it need naming */
  .twiza-model .mcols li:first-child,
  .twiza-model .mchange__grid li:first-child{ padding-inline-start:clamp(12px,1.4vw,18px); }

  /* the stats panel stops floating over the photo and becomes its own block */
  .twiza-model .mpanel{ position:static; width:auto; margin-top:14px; border-radius:var(--radius); }
  /* §7 is not in this list any more: it only needed the escape hatch because a
     panel sat inside its figure and had to break out of it here. */
  .twiza-model .mterr__media{ overflow:visible; border-radius:0; }
  .twiza-model .mterr__media img{ border-radius:var(--radius); }
  /* One column: there is no text beside it for the photograph to lean away
     from, so it stops breaking out and gives up the one-sided curve — that
     shape only reads as intentional when something cuts it off. */
  .twiza-model .mimpact__media{ margin-inline-end:0; }
  /* One column hands this figure the full width of the wrap, and a portrait
     photograph at full width is nearly 1300px tall on a tablet. Bound the
     WIDTH, never the height: the picture stays whole, it just stops being the
     size of a screen and a half. */
  .twiza-model .mimpact__media img{ width:min(100%,520px); margin-inline:auto;
    border-radius:var(--radius); }

  .twiza-model .mbar--accent{ grid-template-columns:auto minmax(0,1fr) auto; row-gap:14px; }
  .twiza-model .mbar__s{ grid-column:1/-1; max-width:none; padding-inline-start:0;
    border-inline-start:0; padding-top:14px; border-top:1px solid rgba(255,255,255,.36); }
  .twiza-model .mbar--soft{ grid-template-columns:auto minmax(0,1fr); row-gap:18px; }
  .twiza-model .mbar__end{ grid-column:1/-1; text-align:start; padding-inline-start:0;
    border-inline-start:0; padding-top:18px; border-top:1px solid var(--line); }

  .twiza-model .partners{ grid-template-columns:repeat(3,minmax(0,1fr)); }

  .twiza-model .mtogether{ min-height:0; }
  .twiza-model .mtogether::before{ background:linear-gradient(to bottom,
    rgba(251,247,240,.96) 0%, rgba(251,247,240,.9) 46%, rgba(251,247,240,.72) 100%); }
  .twiza-model .mpaths{ max-width:none; }
}

@media (max-width:620px){
  .twiza-model .mstats,
  .twiza-model .mchange__grid,
  .twiza-model .mcols--3,
  .twiza-model .mcols--4,
  .twiza-model .mtraits{ grid-template-columns:minmax(0,1fr); }
  .twiza-model .mfigures,
  .twiza-model .mpaths{ grid-template-columns:repeat(2,minmax(0,1fr)); gap:24px 0; }
  /* cards keep their column gap where the borderless lists drop theirs */
  .twiza-model .partners{ grid-template-columns:repeat(2,minmax(0,1fr)); gap:14px; }
  .twiza-model .plogo{ padding:22px 12px; min-height:88px; }
  .twiza-model .mbar--accent{ grid-template-columns:auto minmax(0,1fr); }
  .twiza-model .mbar__arr{ display:none; }
  .twiza-model .mmore{ gap:14px; }
  .twiza-model .mrows li{ grid-template-columns:40px minmax(0,1fr); gap:14px; }
  .twiza-model .mrows__ic{ width:40px; height:40px; }
  .twiza-model .mrows__ic svg{ width:20px; height:20px; }
}

/* ════════ RTL / ARABIC ════════
   The grids mirror on their own (tracks follow `direction`) and every rule
   between cells is already logical. What is left is the handful of things
   direction cannot reach: glyphs that point, and painted gradients. */
.twiza-model[dir="rtl"] .arr{ transform:scaleX(-1); }
.twiza-model[dir="rtl"] .tlink:hover .arr{ transform:scaleX(-1) translateX(4px); }
.twiza-model[dir="rtl"] .mtogether::before{ background:linear-gradient(to left,
  var(--cream) 0%, rgba(251,247,240,.94) 34%, rgba(251,247,240,.56) 56%, rgba(251,247,240,0) 82%); }
/* The breakout is logical (`margin-inline-end`) and mirrors on its own; the
   radius is four corners in writing order and cannot. */
.twiza-model[dir="rtl"] .mimpact__media img{ border-radius:0 54% 46% 0 / 0 58% 42% 0; }
/* Cairo/El Messiri have no italic — the quote and the script line take weight
   and colour instead, and Arabic needs the extra leading */
.twiza-model[dir="rtl"] .mquote p,
.twiza-model[dir="rtl"] .mscript{ font-style:normal; }
.twiza-model[dir="rtl"] .mbody,
.twiza-model[dir="rtl"] .mlead,
.twiza-model[dir="rtl"] .mrows p,
.twiza-model[dir="rtl"] .mcols p,
.twiza-model[dir="rtl"] .mchange p,
.twiza-model[dir="rtl"] .mtraits p,
.twiza-model[dir="rtl"] .mhl p{ line-height:1.9; }
.twiza-model[dir="rtl"] .eyebrow--stack::after{ background-position:right 0, right 32px; }
@media (max-width:1080px){
  .twiza-model[dir="rtl"] .mtogether::before{ background:linear-gradient(to bottom,
    rgba(251,247,240,.96) 0%, rgba(251,247,240,.9) 46%, rgba(251,247,240,.72) 100%); }
}

/* ════════════════════════════════════════════════════════════════════════
   GLOBAL RTL / ARABIC  (activates on <body class="lang-rtl">, PS adds it for AR)
   Arabic glyphs → self-hosted Cairo/El Messiri; Latin (TWIZA, prices, names)
   keeps Inter/Playfair via the fallback stack. Added 2026-06-11 (Milestone F).
   ════════════════════════════════════════════════════════════════════════ */
body.lang-rtl{
  direction:rtl;
  --font-head:'El Messiri','Playfair Display',serif;
  --font-body:'Cairo','Inter',system-ui,sans-serif;
}
body.lang-rtl,
body.lang-rtl input,
body.lang-rtl textarea,
body.lang-rtl select,
body.lang-rtl button{ font-family:var(--font-body); }
/* Arabic has no italics / negative tracking */
body.lang-rtl h1,body.lang-rtl h2,body.lang-rtl h3,body.lang-rtl h4{ letter-spacing:0; line-height:1.45; }
body.lang-rtl em{ font-style:normal; color:var(--accent-deep); }
body.lang-rtl .eyebrow{ letter-spacing:.08em; }

/* ---- Language switcher (header pill toggle) — FR / AR, height-matched to the
   42px action row so it doesn't read as cramped next to search + icons ---- */
.tw-langsw{ display:inline-flex; align-items:center; gap:2px; background:var(--cream);
  border:1px solid var(--line); border-radius:100px; padding:4px; margin-inline-end:6px; flex:none; }
.tw-langsw__btn{ border:0; background:transparent; cursor:pointer; text-decoration:none;
  font-family:var(--font-body); font-size:12.5px; font-weight:700; letter-spacing:.02em; color:var(--muted);
  padding:8px 13px; border-radius:100px; line-height:1; min-width:38px; text-align:center;
  transition:background .22s var(--ease), color .22s; }
.tw-langsw__btn.is-active{ background:#fff; color:var(--accent-deep); box-shadow:var(--shadow-sm); }
.tw-langsw__btn:not(.is-active):hover{ color:var(--ink); }
@media (max-width:1080px){ .tw-langsw button,.tw-langsw__btn{ padding:7px 10px; font-size:12px; min-width:32px; } }

/* ---- HEADER (RTL): mirror search magnifier; keep dropdowns aligned to start ---- */
body.lang-rtl .tw-search .tw-searchbar .tw-search-ico,
body.lang-rtl .tw-searchbar .tw-search-ico{ transform:scaleX(-1); }
body.lang-rtl .tw-cart .body .cart-total{ direction:rtl; }

/* ---- HOMEPAGE (.twiza-home) RTL component flips ---- */
/* hero scrim fades from the text side (now right) */
body.lang-rtl .twiza-home .hero__media::after{
  background:linear-gradient(-90deg, var(--cream) 0%, rgba(251,247,240,.35) 16%, rgba(251,247,240,0) 42%); }
@media (max-width:1080px){
  body.lang-rtl .twiza-home .hero__media::after{ background:linear-gradient(0deg, var(--cream), rgba(251,247,240,0) 40%); }
}
/* floating hero badge → opposite corner */
body.lang-rtl .twiza-home .hero__badge{ left:auto; right:-34px; }
@media (max-width:1080px){ body.lang-rtl .twiza-home .hero__badge{ left:auto; right:16px; } }
/* inline "→" arrows mirror */
body.lang-rtl .twiza-home .arr{ display:inline-block; transform:scaleX(-1); }
body.lang-rtl .twiza-home .tlink:hover .arr{ transform:scaleX(-1) translateX(4px); }
/* coop territory chip → opposite bottom corner */
body.lang-rtl .twiza-home .coop__terr{ left:auto; right:12px; }
/* stat vertical divider → opposite side */
body.lang-rtl .twiza-home .stat + .stat::before{ left:auto; right:0; }
/* decorative khatem patch (model/story/team) → opposite corner */
body.lang-rtl .twiza-home .pat,
body.lang-rtl .twiza-home .story__media .pat{ inset:auto auto -18px -18px; }
/* longer Arabic lines breathe a little more */
body.lang-rtl .twiza-home p{ line-height:1.85; }

/* ---- FOOTER (RTL): direction flip + self-hosted Arabic fonts + alignment ---- */
body.lang-rtl .tw-footer,
.tw-footer[dir="rtl"]{ direction:rtl; text-align:right; font-family:'Cairo','Inter',system-ui,sans-serif; }
body.lang-rtl .tw-footer h4,
.tw-footer[dir="rtl"] h4{ font-family:'Cairo','Inter',system-ui,sans-serif; letter-spacing:.06em; }
/* brand tagline + column links read right-to-left */
body.lang-rtl .tw-footer__brand p,
.tw-footer[dir="rtl"] .tw-footer__brand p{ margin-inline:0; }
/* newsletter field: email + button flow from the right */
body.lang-rtl .tw-footer__news .tw-news-field,
.tw-footer[dir="rtl"] .tw-news-field{ direction:rtl; }
body.lang-rtl .tw-footer__news .tw-news-field input[type="email"],
.tw-footer[dir="rtl"] .tw-news-field input[type="email"]{ text-align:right; }
/* bottom bar: copyright right, legal links wrap from the right */
body.lang-rtl .tw-footer__bottom,
.tw-footer[dir="rtl"] .tw-footer__bottom{ direction:rtl; }
body.lang-rtl .tw-footer__legal,
.tw-footer[dir="rtl"] .tw-footer__legal{ justify-content:flex-start; }

/* ════════════════════════════════════════════════════════════════════════
   TERRITOIRE  (CMS id 11 = Khémisset · id 12 = Bejaâd)  ·  page components
   Wrapper: <section class="twiza-home twiza-territory terr--{terr}"> → reuses
   home primitives (.section full-bleed, .wrap, .eyebrow) + an editorial
   "earth" register below. RTL at the end. Self-hosted fonts only.
   Adapted from Abouhtak/Twiza-new-pages (territory-page.css). Added 2026-06-11.
   ════════════════════════════════════════════════════════════════════════ */

/* ---- palette (default = Khémisset · sable/olive) ---- */
.twiza-territory{
  --sable:#E7DAC1; --sable-2:#F1E8D6; --ecru:#F7F1E5;
  --terre:#6E4B33; --terre-deep:#3A2A1D; --terre-ink:#EDE2CF; --terre-soft:#EBDDC9;
  --olive:#6C6B41; --olive-deep:#535231; --olive-soft:#E7E6D2;
  --font-label:var(--font-head); --font-italic:var(--font-head);
}
/* ---- Bejaâd · crème · terracotta · rose Boujaâd ---- */
.twiza-territory.terr--bejaad{
  --sable:#E8D3BE; --sable-2:#F3E4D2; --ecru:#FAF3E9;
  --terre:#A9492C; --terre-deep:#4E1A18; --terre-ink:#F4E2D2; --terre-soft:#E7C9B8;
  --olive:#BC5B62; --olive-deep:#8C3D49; --olive-soft:#F4DAD9;
}

/* ---- shared editorial heading ---- */
.twiza-territory .tp-head{ display:flex; align-items:baseline; gap:18px; }
.twiza-territory .tp-num{ font-family:var(--font-label); font-size:15px; letter-spacing:.06em; color:var(--terre); opacity:.7; flex:none; }
.twiza-territory .tp-kicker{ font-family:var(--font-label); font-size:13.5px; letter-spacing:.26em; text-transform:uppercase; color:var(--terre); display:inline-flex; align-items:center; gap:14px; }
.twiza-territory .tp-kicker::before{ content:""; width:30px; height:1px; background:var(--terre); opacity:.6; }
.twiza-territory .tp-h2{ font-family:var(--font-head); font-weight:500; font-size:clamp(32px,4.6vw,58px); line-height:1.04; letter-spacing:-.018em; color:var(--ink); margin:22px 0 0; text-wrap:balance; }
.twiza-territory .tp-lead{ color:var(--muted); font-size:clamp(17px,1.5vw,19px); margin-top:20px; max-width:48ch; }

/* ---- 1 · HERO (full-bleed immersive) ----
   --sbw as in `.twiza-home .section`; dropping it re-opens the page-level
   horizontal scrollbar. */
.twiza-territory .tp-hero{ position:relative; margin-left:calc(50% - 50vw + var(--sbw)/2); margin-right:calc(50% - 50vw + var(--sbw)/2);
  min-height:100svh; display:flex; flex-direction:column; justify-content:flex-end; overflow:hidden; color:#fff; isolation:isolate; }
.twiza-territory .tp-hero__img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; z-index:-2; }
.twiza-territory .tp-hero::after{ content:""; position:absolute; inset:0; z-index:-1; pointer-events:none;
  background:linear-gradient(180deg, rgba(25,17,10,.46) 0%, rgba(25,17,10,0) 26%), linear-gradient(0deg, rgba(20,13,7,.82) 0%, rgba(20,13,7,.30) 42%, rgba(20,13,7,0) 70%); }
.twiza-territory .tp-hero__top{ position:absolute; inset-block-start:0; inset-inline:0; z-index:1; padding:104px var(--gutter) 0; display:flex; align-items:center; gap:16px; }
.twiza-territory .tp-hero__loc{ font-family:var(--font-label); font-size:13px; letter-spacing:.28em; text-transform:uppercase; color:rgba(255,255,255,.92); }
.twiza-territory .tp-hero__top .rule{ flex:1; height:1px; background:rgba(255,255,255,.34); }
.twiza-territory .tp-hero__inner{ position:relative; z-index:1; width:min(var(--maxw), 100% - var(--gutter)*2); margin-inline:auto; padding-block-end:clamp(48px,7vh,96px); }
.twiza-territory .tp-hero__eyebrow{ font-family:var(--font-label); font-size:13px; letter-spacing:.3em; text-transform:uppercase; color:var(--orange); display:block; margin-bottom:6px; }
.twiza-territory .tp-hero h1{ font-family:var(--font-head); font-weight:500; font-size:clamp(72px,13vw,184px); line-height:.86; letter-spacing:-.035em; color:#fff; margin:0; }
.twiza-territory .tp-hero__sub{ font-family:var(--font-italic); font-style:italic; font-weight:500; font-size:clamp(24px,3.2vw,40px); line-height:1.15; color:#fff; margin:18px 0 0; letter-spacing:.005em; }
.twiza-territory .tp-hero__desc{ margin:22px 0 0; max-width:46ch; font-size:clamp(16px,1.4vw,18.5px); line-height:1.7; color:rgba(255,255,255,.86); }
.twiza-territory .tp-scroll{ display:inline-flex; align-items:center; gap:11px; margin-top:34px; font-family:var(--font-label); font-size:12px; letter-spacing:.22em; text-transform:uppercase; color:rgba(255,255,255,.8); }
.twiza-territory .tp-scroll .ln{ width:46px; height:1px; background:rgba(255,255,255,.6); position:relative; overflow:hidden; }
.twiza-territory .tp-scroll .ln::after{ content:""; position:absolute; inset:0; width:18px; background:#fff; animation:tpscroll 2.4s var(--ease) infinite; }
@keyframes tpscroll{ 0%{ transform:translateX(-20px) } 60%,100%{ transform:translateX(48px) } }
@media (prefers-reduced-motion: reduce){ .twiza-territory .tp-scroll .ln::after{ animation:none; } }

/* ---- 2 · HISTOIRE (écru editorial split) ---- */
.twiza-territory .tp-history{ background:var(--ecru); }
.twiza-territory .tp-history__grid{ display:grid; grid-template-columns:1.06fr .94fr; gap:clamp(40px,6vw,96px); align-items:start; margin-top:clamp(40px,5vw,64px); }
.twiza-territory .tp-prose p{ color:#4a4136; font-size:clamp(16.5px,1.45vw,18px); line-height:1.85; }
.twiza-territory .tp-prose p + p{ margin-top:22px; }
.twiza-territory .tp-prose p:first-of-type::first-letter{ font-family:var(--font-head); font-weight:600; float:inline-start; font-size:5.4em; line-height:.78; margin:6px 14px 0 0; color:var(--terre); }
.twiza-territory .tp-figure{ position:sticky; top:104px; margin:0; }
.twiza-territory .tp-figure__media{ position:relative; overflow:hidden; border-radius:6px; box-shadow:var(--shadow); }
.twiza-territory .tp-figure__media img{ width:100%; height:clamp(440px,60vh,620px); object-fit:cover; display:block; }
.twiza-territory .tp-figure__cap{ margin-top:16px; font-family:var(--font-italic); font-style:italic; font-size:18px; color:var(--terre); line-height:1.4; max-width:34ch; }
.twiza-territory .tp-figure__cap::before{ content:""; display:block; width:34px; height:1px; background:var(--olive); margin-bottom:12px; }

/* ---- 3 · FILIÈRES (white card grid) ---- */
.twiza-territory .tp-filieres{ background:#fff; }
.twiza-territory .tp-fgrid{ display:grid; grid-template-columns:repeat(4,1fr); gap:18px; margin-top:clamp(40px,5vw,60px); }
.twiza-territory .tp-fcard{ position:relative; border:1px solid var(--line); border-radius:8px; background:#fff; padding:30px 26px 28px; overflow:hidden; display:flex; flex-direction:column; gap:18px; min-height:184px; transition:transform .35s var(--ease), box-shadow .35s var(--ease), border-color .35s; }
.twiza-territory .tp-fcard:hover{ transform:translateY(-5px); box-shadow:var(--shadow); border-color:var(--terre-soft); }
.twiza-territory .tp-fcard__idx{ position:absolute; top:18px; inset-inline-end:22px; font-family:var(--font-label); font-size:13px; color:var(--line); letter-spacing:.05em; }
.twiza-territory .tp-fcard__ic{ width:52px; height:52px; border-radius:50%; flex:none; background:var(--sable-2); color:var(--terre); display:flex; align-items:center; justify-content:center; }
.twiza-territory .tp-fcard__ic svg{ width:26px; height:26px; }
.twiza-territory .tp-fcard h3{ font-family:var(--font-head); font-weight:500; font-size:21px; line-height:1.15; color:var(--ink); letter-spacing:-.01em; margin:0; }
.twiza-territory .tp-fcard--accent{ border-color:transparent; background:linear-gradient(180deg,var(--olive-soft),#fff 78%); }
.twiza-territory .tp-fcard--accent .tp-fcard__ic{ background:var(--olive); color:#fff; }
.twiza-territory .tp-fcard__tag{ display:inline-flex; align-items:center; gap:7px; align-self:flex-start; font-family:var(--font-body); font-size:11px; font-weight:600; letter-spacing:.08em; text-transform:uppercase; color:var(--olive-deep); background:#fff; border:1px solid var(--olive-soft); padding:5px 11px; border-radius:100px; margin-top:-4px; }
.twiza-territory .tp-fcard__tag::before{ content:""; width:6px; height:6px; border-radius:50%; background:var(--olive); }
/* filière cards WITH photo (Khémisset "Les filières du territoire") — photo on top, icon overlaps */
.twiza-territory .tp-fcard--photo{ padding:0; gap:0; min-height:0; }
.twiza-territory .tp-fcard__photo{ position:relative; aspect-ratio:16/10; overflow:hidden; background:var(--sable-2); }
.twiza-territory .tp-fcard__photo img{ width:100%; height:100%; object-fit:cover; transition:transform .6s var(--ease); }
.twiza-territory .tp-fcard--photo:hover .tp-fcard__photo img{ transform:scale(1.06); }
.twiza-territory .tp-fcard--photo .tp-fcard__body{ position:relative; padding:34px 24px 26px; display:flex; flex-direction:column; gap:14px; flex:1; }
.twiza-territory .tp-fcard--photo .tp-fcard__ic{ position:absolute; top:-26px; inset-inline-start:24px; border:3px solid #fff; box-shadow:0 8px 20px -8px rgba(43,37,30,.45); }
.twiza-territory .tp-fcard--photo.tp-fcard--accent{ background:#fff; }
.twiza-territory .tp-fcard--photo.tp-fcard--accent .tp-fcard__body{ background:linear-gradient(180deg,var(--olive-soft),#fff 78%); }

/* ---- 4 · FILIÈRE ACCOMPAGNÉE (deep brun-terre band, full-bleed) ----
   --sbw as in `.twiza-home .section`. */
.twiza-territory .tp-feature{ position:relative; margin-left:calc(50% - 50vw + var(--sbw)/2); margin-right:calc(50% - 50vw + var(--sbw)/2); background:var(--terre-deep); color:var(--terre-ink); overflow:hidden; }
.twiza-territory .tp-feature__grid{ display:grid; grid-template-columns:.92fr 1.08fr; align-items:stretch; width:min(var(--maxw), 100% - var(--gutter)*2); margin-inline:auto; }
.twiza-territory .tp-feature__media{ position:relative; min-height:clamp(420px,62vh,640px); }
.twiza-territory .tp-feature__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; }
.twiza-territory .tp-feature__media::after{ content:""; position:absolute; inset:0; background:linear-gradient(90deg, rgba(58,42,29,0) 60%, var(--terre-deep) 100%); }
.twiza-territory .tp-feature__body{ display:flex; flex-direction:column; justify-content:center; padding:clamp(48px,6vw,88px) clamp(32px,4.5vw,72px); }
.twiza-territory .tp-feature .tp-kicker{ color:var(--sable); }
.twiza-territory .tp-feature .tp-kicker::before{ background:var(--sable); }
.twiza-territory .tp-feature .tp-num{ color:var(--sable); }
.twiza-territory .tp-feature__h2{ font-family:var(--font-head); font-weight:500; font-size:clamp(34px,4.4vw,56px); line-height:1.02; letter-spacing:-.02em; color:#fff; margin:20px 0 0; }
.twiza-territory .tp-feature__badge{ display:inline-flex; align-items:center; gap:9px; align-self:flex-start; margin-top:22px; font-family:var(--font-label); font-size:12px; letter-spacing:.16em; text-transform:uppercase; color:var(--terre-deep); background:var(--olive-soft); padding:8px 15px; border-radius:100px; }
.twiza-territory .tp-feature__badge svg{ width:15px; height:15px; }
.twiza-territory .tp-feature__p{ margin-top:24px; }
.twiza-territory .tp-feature__p p{ color:rgba(237,226,207,.84); font-size:clamp(15.5px,1.35vw,17px); line-height:1.8; max-width:54ch; }
.twiza-territory .tp-feature__p p + p{ margin-top:16px; }
.twiza-territory .tp-feature__quote{ font-family:var(--font-italic); font-style:italic; font-size:clamp(22px,2.5vw,30px); line-height:1.35; color:#fff; margin:30px 0 0; padding-inline-start:22px; border-inline-start:2px solid var(--olive); max-width:30ch; }

/* ---- 5 · IMPACT (écru triptych) ---- */
.twiza-territory .tp-impact{ background:var(--ecru); }
.twiza-territory .tp-impact__grid{ display:grid; grid-template-columns:repeat(3,1fr); gap:clamp(28px,4vw,56px); margin-top:clamp(44px,5vw,66px); }
.twiza-territory .tp-ib{ padding-top:26px; border-top:1px solid var(--terre-soft); }
.twiza-territory .tp-ib__n{ font-family:var(--font-label); font-size:14px; letter-spacing:.1em; color:var(--terre); opacity:.65; }
.twiza-territory .tp-ib__ic{ width:46px; height:46px; color:var(--olive); margin:18px 0 20px; }
.twiza-territory .tp-ib__ic svg{ width:100%; height:100%; }
.twiza-territory .tp-ib h3{ font-family:var(--font-head); font-weight:500; font-size:clamp(24px,2.4vw,32px); color:var(--ink); letter-spacing:-.01em; margin:0; }
.twiza-territory .tp-ib p{ color:#5a5045; font-size:16px; line-height:1.7; margin-top:14px; max-width:34ch; }

/* ---- 6 · GALERIE (asymmetric) + CTA ---- */
.twiza-territory .tp-gallery{ background:#fff; }
.twiza-territory .tp-ggrid{ display:grid; grid-template-columns:repeat(12,1fr); gap:18px; margin-top:clamp(40px,5vw,60px); }
.twiza-territory .tp-gcard{ position:relative; overflow:hidden; border-radius:8px; isolation:isolate; min-height:280px; display:flex; flex-direction:column; }
.twiza-territory .tp-gcard img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; transition:transform 1.1s var(--ease); }
.twiza-territory .tp-gcard:hover img{ transform:scale(1.05); }
.twiza-territory .tp-gcard::after{ content:""; position:absolute; inset:0; z-index:1; background:linear-gradient(0deg, rgba(20,13,7,.72) 0%, rgba(20,13,7,.08) 52%, transparent 80%); }
.twiza-territory .tp-gcard__body{ position:relative; z-index:2; padding:26px; margin-top:auto; }
.twiza-territory .tp-gcard__title{ font-family:var(--font-head); font-weight:500; font-size:clamp(20px,1.9vw,26px); color:#fff; line-height:1.12; }
.twiza-territory .g-a{ grid-column:span 7; grid-row:span 2; min-height:520px; }
.twiza-territory .g-b{ grid-column:span 5; }
.twiza-territory .g-c{ grid-column:span 5; }
.twiza-territory .g-d{ grid-column:span 12; min-height:360px; }
.twiza-territory .tp-cta{ display:flex; flex-direction:column; align-items:center; text-align:center; margin-top:clamp(48px,6vw,76px); }
.twiza-territory .tp-cta p{ font-family:var(--font-italic); font-style:italic; font-size:clamp(20px,2.2vw,28px); color:var(--terre); max-width:26ch; line-height:1.3; margin-bottom:26px; }
.twiza-territory .tp-btn{ display:inline-flex; align-items:center; gap:12px; padding:18px 40px; border-radius:100px; background:var(--accent); color:#fff; font-family:var(--font-body); font-size:15px; font-weight:600; letter-spacing:.01em; box-shadow:0 16px 30px -16px var(--accent); transition:background .3s var(--ease), transform .25s var(--ease), box-shadow .3s; }
.twiza-territory .tp-btn svg{ width:18px; height:18px; transition:transform .35s var(--ease); }
.twiza-territory .tp-btn:hover{ background:var(--accent-deep); transform:translateY(-3px); box-shadow:0 22px 40px -18px var(--accent); }
.twiza-territory .tp-btn:hover svg{ transform:translateX(5px); }

/* ---- 4b · ÉTAPES DE CRÉATION (steps) + BANNIÈRE BOUTIQUE (shop CTA) ---- */
.twiza-territory .tp-craft{ background:var(--ecru); }
.twiza-territory .tp-craft__head{ text-align:center; }
.twiza-territory .tp-craft__h2{ font-family:var(--font-head); font-weight:500; font-size:clamp(26px,3.2vw,42px); line-height:1.06; letter-spacing:-.015em; color:var(--ink); margin:0; display:inline-flex; align-items:center; gap:clamp(14px,3vw,24px); max-width:100%; }
.twiza-territory .tp-craft__h2::before,.twiza-territory .tp-craft__h2::after{ content:""; flex:none; width:clamp(20px,5vw,70px); height:1px; background:var(--terre); opacity:.4; }
.twiza-territory .tp-steps{ display:grid; grid-template-columns:repeat(5,1fr); gap:18px; margin-top:clamp(34px,4.4vw,54px); }
.twiza-territory .tp-step{ display:flex; flex-direction:column; min-width:0; }
.twiza-territory .tp-step__media{ position:relative; border-radius:8px; overflow:hidden; aspect-ratio:4/3; }
.twiza-territory .tp-step__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; transition:transform 1.1s var(--ease); }
.twiza-territory .tp-step:hover .tp-step__media img{ transform:scale(1.06); }
.twiza-territory .tp-step__n{ position:absolute; inset-block-end:10px; inset-inline-start:10px; z-index:2; font-family:var(--font-label); font-size:13px; font-weight:600; letter-spacing:.04em; color:#fff; background:var(--olive-deep); padding:4px 11px; border-radius:100px; }
.twiza-territory .tp-step__t{ font-family:var(--font-head); font-weight:500; font-size:clamp(17px,1.5vw,20px); color:var(--ink); margin:16px 0 0; line-height:1.16; }
.twiza-territory .tp-step__d{ font-size:14px; line-height:1.6; color:#5a5045; margin-top:8px; }

.twiza-territory .tp-shopcta{ display:grid; grid-template-columns:.82fr 1.18fr; align-items:stretch; margin-top:clamp(44px,5.5vw,72px); border:1px solid var(--olive-soft); border-radius:14px; overflow:hidden; background:#fff; box-shadow:var(--shadow); }
.twiza-territory .tp-shopcta__media{ position:relative; min-height:220px; }
.twiza-territory .tp-shopcta__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; }
.twiza-territory .tp-shopcta__body{ display:flex; flex-direction:column; align-items:flex-start; justify-content:center; padding:clamp(28px,3.6vw,52px); }
.twiza-territory .tp-shopcta__h3{ font-family:var(--font-head); font-weight:500; font-size:clamp(24px,2.6vw,34px); color:var(--ink); line-height:1.08; letter-spacing:-.01em; margin:0; }
.twiza-territory .tp-shopcta__p{ font-size:16px; line-height:1.65; color:#5a5045; margin:14px 0 26px; max-width:42ch; }
@media (max-width:1080px){
  .twiza-territory .tp-steps{ grid-template-columns:repeat(3,1fr); }
  .twiza-territory .tp-shopcta{ grid-template-columns:1fr; }
  .twiza-territory .tp-shopcta__media{ min-height:200px; }
}
@media (max-width:560px){
  .twiza-territory .tp-steps{ grid-template-columns:repeat(2,1fr); gap:14px; }
}
.twiza-territory[dir="rtl"] .tp-craft__h2,.twiza-territory[dir="rtl"] .tp-shopcta__h3,.twiza-territory[dir="rtl"] .tp-step__t{ letter-spacing:0; line-height:1.3; }

/* ---- 2b · HISTOIRE DE L'ARTISANAT (Bejaâd) — text + framed photo ---- */
.twiza-territory .tp-arthist{ background:#fff; }
.twiza-territory .tp-arthist__grid{ display:grid; grid-template-columns:1fr 1.04fr; gap:clamp(40px,6vw,88px); align-items:center; margin-top:clamp(36px,4.6vw,58px); }
.twiza-territory .tp-arthist__prose p{ color:#4a4136; font-size:clamp(15.5px,1.4vw,17.5px); line-height:1.85; }
.twiza-territory .tp-arthist__prose p + p{ margin-top:18px; }
.twiza-territory .tp-arthist__media{ border-radius:10px; overflow:hidden; box-shadow:var(--shadow); }
.twiza-territory .tp-arthist__media img{ display:block; width:100%; height:clamp(420px,54vh,560px); object-fit:cover; }

/* ---- 3 · FILIÈRES (Bejaâd) — centred head + photo-card grid + engagement banner ---- */
.twiza-territory .tp-head--center{ justify-content:center; }
.twiza-territory .tp-head--center .tp-kicker::after{ content:""; width:30px; height:1px; background:var(--terre); opacity:.6; }
.twiza-territory .tp-h2--center{ text-align:center; }
.twiza-territory .tp-lead--center{ margin-inline:auto; text-align:center; max-width:62ch; }
.twiza-territory .tp-filieres--cards{ background:var(--ecru); }

.twiza-territory .tp-fil2grid{ display:grid; grid-template-columns:repeat(4,1fr); gap:clamp(18px,1.8vw,24px); margin-top:clamp(46px,5.2vw,68px); }
.twiza-territory .tp-fil2c{ position:relative; display:flex; flex-direction:column; background:#fff; border:1px solid var(--line); border-radius:16px; overflow:hidden; transition:transform .35s var(--ease), box-shadow .35s var(--ease), border-color .35s; }
.twiza-territory .tp-fil2c:hover{ transform:translateY(-6px); box-shadow:var(--shadow); border-color:var(--terre-soft); }
.twiza-territory .tp-fil2c__media{ position:relative; aspect-ratio:16/11; overflow:hidden; }
.twiza-territory .tp-fil2c__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; transition:transform 1.1s var(--ease); }
.twiza-territory .tp-fil2c:hover .tp-fil2c__media img{ transform:scale(1.05); }
.twiza-territory .tp-fil2c__ic{ position:absolute; left:50%; top:0; transform:translate(-50%,-50%); z-index:2; width:58px; height:58px; border-radius:50%; background:var(--sable-2); color:var(--terre); display:flex; align-items:center; justify-content:center; border:3px solid #fff; box-shadow:0 8px 20px -8px rgba(43,37,30,.5); }
.twiza-territory .tp-fil2c__ic svg{ width:28px; height:28px; }
.twiza-territory .tp-fil2c__body{ position:relative; flex:1; display:flex; flex-direction:column; align-items:center; text-align:center; padding:44px 22px 26px; }
.twiza-territory .tp-fil2c__body h3{ font-family:var(--font-head); font-weight:500; font-size:clamp(20px,1.7vw,23px); line-height:1.14; letter-spacing:-.01em; color:var(--ink); margin:0; }
.twiza-territory .tp-fil2c__rule{ position:relative; width:36px; height:1px; background:var(--terre); opacity:.45; margin:13px 0 15px; }
.twiza-territory .tp-fil2c__rule::before{ content:""; position:absolute; left:50%; top:50%; width:5px; height:5px; background:var(--terre); transform:translate(-50%,-50%) rotate(45deg); }
.twiza-territory .tp-fil2c__body p{ color:#5a5045; font-size:14.5px; line-height:1.66; }
.twiza-territory .tp-fil2c__link{ margin-top:auto; padding-top:20px; display:inline-flex; align-items:center; gap:8px; font-family:var(--font-body); font-size:12px; font-weight:600; letter-spacing:.09em; text-transform:uppercase; color:var(--accent); }
.twiza-territory .tp-fil2c__link:hover{ color:var(--accent-deep); }
.twiza-territory .tp-fil2c__link svg{ width:16px; height:16px; transition:transform .35s var(--ease); }
.twiza-territory .tp-fil2c:hover .tp-fil2c__link svg{ transform:translateX(4px); }

.twiza-territory .tp-fil2banner{ position:relative; display:flex; align-items:center; gap:clamp(18px,2.4vw,32px); margin-top:clamp(44px,5vw,64px); padding:clamp(22px,2.6vw,30px) clamp(24px,3vw,42px); padding-inline-start:clamp(66px,7vw,98px); background:var(--sable-2); border:1px solid var(--terre-soft); border-radius:18px; overflow:hidden; }
.twiza-territory .tp-fil2banner__deco{ position:absolute; inset-block:0; inset-inline-start:0; width:clamp(46px,5vw,66px); background-image:var(--khatem); background-size:34px; opacity:.4; border-inline-end:1px solid var(--terre-soft); }
.twiza-territory .tp-fil2banner__ic{ flex:none; width:52px; height:52px; color:var(--terre); }
.twiza-territory .tp-fil2banner__ic svg{ width:100%; height:100%; }
.twiza-territory .tp-fil2banner__txt{ flex:1 1 auto; min-width:0; }
.twiza-territory .tp-fil2banner__txt p{ color:#5a5045; font-size:clamp(15px,1.35vw,17px); line-height:1.55; }
.twiza-territory .tp-fil2banner__txt p.strong{ font-weight:700; color:var(--ink); margin-top:3px; }
.twiza-territory .tp-fil2banner .tp-btn{ flex:none; white-space:nowrap; }

@media (max-width:1080px){
  .twiza-territory .tp-arthist__grid{ grid-template-columns:1fr; gap:40px; }
  .twiza-territory .tp-arthist__media img{ height:clamp(320px,52vw,460px); }
  .twiza-territory .tp-fil2grid{ grid-template-columns:repeat(2,1fr); gap:28px 20px; }
  .twiza-territory .tp-fil2banner{ flex-wrap:wrap; padding-inline-start:clamp(58px,8vw,84px); }
  .twiza-territory .tp-fil2banner__txt{ flex:1 1 220px; }
  .twiza-territory .tp-fil2banner .tp-btn{ margin-inline-start:auto; }
}
@media (max-width:560px){
  .twiza-territory .tp-fil2grid{ grid-template-columns:1fr; max-width:400px; margin-inline:auto; }
  .twiza-territory .tp-fil2banner{ padding:26px 24px; }
  .twiza-territory .tp-fil2banner__deco{ display:none; }
  .twiza-territory .tp-fil2banner__ic{ width:44px; height:44px; }
  .twiza-territory .tp-fil2banner .tp-btn{ width:100%; justify-content:center; margin-inline-start:0; }
}
.twiza-territory[dir="rtl"] .tp-fil2c__body h3,.twiza-territory[dir="rtl"] .tp-h2--center{ letter-spacing:0; line-height:1.3; }

/* ---- RESPONSIVE ---- */
@media (max-width:1080px){
  .twiza-territory .tp-history__grid{ grid-template-columns:1fr; gap:48px; }
  .twiza-territory .tp-figure{ position:static; }
  .twiza-territory .tp-figure__media img{ height:clamp(360px,52vh,520px); }
  .twiza-territory .tp-fgrid{ grid-template-columns:repeat(2,1fr); }
  .twiza-territory .tp-feature__grid{ grid-template-columns:1fr; }
  .twiza-territory .tp-feature__media{ min-height:340px; }
  .twiza-territory .tp-feature__media::after{ background:linear-gradient(0deg, var(--terre-deep) 0%, rgba(58,42,29,0) 55%); }
  .twiza-territory .tp-impact__grid{ grid-template-columns:1fr; gap:0; }
  .twiza-territory .tp-ib{ padding:26px 0; }
  .twiza-territory .tp-ib + .tp-ib{ border-top:1px solid var(--terre-soft); }
  .twiza-territory .g-a,.twiza-territory .g-b,.twiza-territory .g-c,.twiza-territory .g-d{ grid-column:span 12; grid-row:auto; min-height:300px; }
  .twiza-territory .g-a{ min-height:360px; }
}
@media (max-width:560px){
  .twiza-territory .tp-hero__top{ padding-top:92px; }
  .twiza-territory .tp-fgrid{ grid-template-columns:1fr; }
  .twiza-territory .tp-feature__body{ padding:40px 24px 48px; }
}

/* ════════ RTL / Arabic layer for Territoire ════════ */
.twiza-territory[dir="rtl"]{ --font-label:var(--font-head); --font-italic:var(--font-head); }
.twiza-territory[dir="rtl"] .tp-h2,.twiza-territory[dir="rtl"] .tp-hero h1,.twiza-territory[dir="rtl"] .tp-feature__h2{ letter-spacing:0; line-height:1.3; }
.twiza-territory[dir="rtl"] .tp-hero h1{ line-height:1.05; }
.twiza-territory[dir="rtl"] .tp-hero__sub,.twiza-territory[dir="rtl"] .tp-figure__cap,.twiza-territory[dir="rtl"] .tp-feature__quote,.twiza-territory[dir="rtl"] .tp-cta p{ font-style:normal; }
.twiza-territory[dir="rtl"] .tp-prose p:first-of-type::first-letter{ margin:6px 0 0 14px; }
.twiza-territory[dir="rtl"] .tp-feature__media::after{ background:linear-gradient(270deg, rgba(58,42,29,0) 60%, var(--terre-deep) 100%); }
.twiza-territory[dir="rtl"] .tp-scroll .ln::after{ animation:none; }
@media (max-width:1080px){
  .twiza-territory[dir="rtl"] .tp-feature__media::after{ background:linear-gradient(0deg, var(--terre-deep) 0%, rgba(58,42,29,0) 55%); }
}

/* Territoire pages: hero supplies the H1 — hide the redundant CMS page-header */
body.cms-id-11 .page-header,
body.cms-id-12 .page-header{ display:none; }
body.cms-id-11 #content.twiza-territory,
body.cms-id-12 #content.twiza-territory{ margin-top:calc(-1 * var(--gutter, 24px)); }

/* ════════════════════════════════════════════════════════════════════════
   RESPONSIVE HARDENING — small screens (≤430px / iPhone SE 320px etc.)
   Added 2026-06-24. Fixes horizontal-scroll overflow found via a width audit
   (320/360px) on home, product, category, model, territoire, cart, login.
   Root causes were intrinsic min-content floors that single-column grids /
   aspect-ratio boxes couldn't shrink below. Each fix is scoped + min-impact.
   ════════════════════════════════════════════════════════════════════════ */

/* --- 1) FOOTER: the newsletter cell's email <input> + non-wrapping button gave
   the single-column footer grid a ~358px min-content floor → it overflowed at
   ≤360px on EVERY page. Let grid cells shrink, and stack the newsletter field. */
.tw-footer__grid > *{ min-width:0; }
@media (max-width:430px){
  .tw-footer__news .tw-news-field{ flex-wrap:wrap; }
  .tw-footer__news .tw-news-field input[type="email"]{ flex:1 1 100%; width:100%; }
  .tw-footer__news .tw-news-field button[type="submit"]{ flex:1 1 100%; width:100%; padding:13px 22px; }
}

/* --- 2) (was: a NOTRE MODÈLE hero-media overflow fix. Dropped 2026-08-07 with
   the seven-section page it patched — .mhero__media no longer exists, and the
   rebuilt hero carries minmax(0,…) tracks so the cell can shrink on its own.) */

/* --- 3) PRODUCT image thumbnails: the 111px thumb-strip overflowed at ≤360px.
   Allow the thumbs to wrap and keep the gallery within the viewport. */
@media (max-width:480px){
  #product .images-container{ max-width:100%; }
  #product .images-container .product-images{ display:flex; flex-wrap:wrap; gap:8px;
    max-width:100%; margin:0; padding:0; }
  #product .images-container .thumb-container{ float:none; margin:0; }
}

/* --- 4) TERRITOIRE hero H1: clamp floor of 72px overflows for longer names
   ("Khémisset") on 320px screens. Lower the floor on very small viewports. */
@media (max-width:430px){
  .twiza-territory .tp-hero h1{ font-size:clamp(52px,16vw,72px); }
}

/* --- 5) Final safety net: never allow a stray child to force horizontal scroll
   on phones. Scoped to #wrapper (page scroll container) — NOT html/body — so
   the territoire page's position:sticky figure keeps working. */
@media (max-width:560px){
  #wrapper{ overflow-x:hidden; }
}

/* ============================================================
   MODÈLE §2 — RTL mirroring for the new bands (arrows flip)
   ============================================================ */
body.lang-rtl .twiza-home .tm-cta .arr,
body.lang-rtl .twiza-home .tm-flow__sep svg{ transform:scaleX(-1); }
body.lang-rtl .twiza-home .tm-cta:hover .arr{ transform:scaleX(-1) translateX(4px); }

/* ============================================================
   NOTRE UNIVERS — experience page (CMS id 13)  ·  .twiza-univers
   ============================================================ */
.twiza-univers{ --u-green:#22412f; --u-green-2:#2c5540; }
.twiza-univers h1,.twiza-univers h2,.twiza-univers h3{ color:var(--u-green); font-family:var(--font-head); }
.twiza-univers h1 em,.twiza-univers h2 em{
  color:var(--accent-deep); font-style:normal;
  background:linear-gradient(var(--accent),var(--accent)) left bottom / 100% 3px no-repeat;
  padding-bottom:3px;
}
.twiza-univers .hd{ width:.78em; height:.78em; color:var(--accent); display:inline-block; vertical-align:baseline; margin-inline-start:.15em; }
.twiza-univers .dia{ width:14px; height:14px; color:var(--accent); flex:none; }
.twiza-univers .ar{ display:inline-block; transition:transform .3s var(--ease); }
.twiza-univers .btn:hover .ar{ transform:translateX(3px); }
.twiza-univers .eyebrow.flank::after{ content:""; width:22px; height:2px; border-radius:2px; background:var(--accent); }

/* ---- 1 · HERO ---- */
/* Not a `.section`, so it missed the full-bleed breakout at the top of this
   sheet and its gradient stopped at bootstrap's container while the four bands
   below it ran edge to edge — the same defect fixed on the Territoires hero.
   No `position:relative` here, unlike the shared rule: the band hosts no
   absolute children of its own — the photograph is positioned against
   .uhero__media, not against this. overflow:hidden STAYS: it holds the breakout
   margins in, and nothing on this page is built to hang out of the band. */
.twiza-univers .uhero{
  margin-left:calc(50% - 50vw + var(--sbw)/2);
  margin-right:calc(50% - 50vw + var(--sbw)/2);
  background:linear-gradient(180deg,#fff 0%,var(--cream) 100%); padding-block:clamp(40px,6vw,84px) clamp(30px,4vw,56px); overflow:hidden;
}
/* The photograph is framed the way the homepage hero frames its own, so this
   grid is that grid: the wider `--maxw` box (the template says wrap-wide, and
   the foot below follows it so the band keeps ONE left edge), no gap — the fade
   over the picture's inner edge is the separation — and stretched rows, so the
   picture takes whatever height the copy sets rather than a fixed one. */
.twiza-univers .uhero__grid{ display:grid; grid-template-columns:1fr 1.04fr; gap:0; align-items:stretch; min-height:clamp(460px,62vh,620px); }
/* Logical padding, unlike the homepage's physical `padding-right`: this one is
   correct on /ar/ without a mirror rule. */
.twiza-univers .uhero__text{ display:flex; flex-direction:column; justify-content:center; padding-inline-end:clamp(28px,4vw,64px); position:relative; z-index:2; }
.twiza-univers .uhero__h1{ font-size:clamp(34px,4.6vw,60px); line-height:1.06; margin:20px 0 0; letter-spacing:-.01em; }
.twiza-univers .uhero__rule{ display:flex; align-items:center; gap:8px; margin:22px 0 0; }
.twiza-univers .uhero__rule i{ width:44px; height:3px; border-radius:3px; background:var(--u-green); }
.twiza-univers .uhero__rule i.o{ background:var(--accent); }
.twiza-univers .uhero__rule svg{ width:16px; height:16px; color:var(--accent); }
.twiza-univers .uhero__p{ color:var(--muted); font-size:16.5px; line-height:1.72; margin:20px 0 0; max-width:540px; }
.twiza-univers .uhero__p b{ color:var(--ink); font-weight:700; }
.twiza-univers .uhero__p b:nth-of-type(odd){ color:var(--accent-deep); }
.twiza-univers .uhero__cta{ display:flex; flex-wrap:wrap; gap:14px; margin-top:30px; }
.twiza-univers .uhero__media{ position:relative; }
.twiza-univers .uhero__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; }
/* The band fades over the inner edge so the photograph does not cut into the
   paragraph beside it. Cream, like the homepage — the band runs white→cream top
   to bottom, and the two are four values apart, so one flat stop is enough. */
.twiza-univers .uhero__media::after{
  content:""; position:absolute; inset:0; z-index:1; pointer-events:none;
  background:linear-gradient(90deg, var(--cream) 0%, rgba(251,247,240,.35) 16%, rgba(251,247,240,0) 42%);
}

.twiza-univers .uhero__foot{ display:grid; grid-template-columns:auto 1fr; gap:clamp(20px,3vw,40px); align-items:center; margin-top:clamp(32px,4vw,52px); }
.twiza-univers .ustats{ display:flex; gap:clamp(14px,2.4vw,34px); }
.twiza-univers .ustat{ text-align:center; padding-inline:clamp(8px,1.4vw,18px); }
.twiza-univers .ustat + .ustat{ border-inline-start:1px solid var(--line); }
.twiza-univers .ustat__ic{ width:48px; height:48px; margin:0 auto 10px; border-radius:50%; background:var(--orange-tint); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; }
.twiza-univers .ustat__ic svg{ width:24px; height:24px; }
.twiza-univers .ustat__n{ font-family:var(--font-head); font-weight:700; font-size:clamp(24px,2.6vw,32px); color:var(--u-green); }
.twiza-univers .ustat__l{ font-size:13px; color:var(--muted); margin-top:2px; }
.twiza-univers .usig{ display:flex; align-items:center; gap:18px; background:#fff; border:1px solid var(--line); border-radius:var(--radius); box-shadow:var(--shadow-sm); padding:18px clamp(18px,2vw,26px); }
.twiza-univers .usig__ic{ width:34px; height:34px; color:var(--accent); flex:none; }
.twiza-univers .usig__body{ flex:none; max-width:220px; }
.twiza-univers .usig__t{ font-family:var(--font-head); font-weight:600; font-size:18px; color:var(--u-green); }
.twiza-univers .usig__s{ color:var(--accent-deep); font-size:12.5px; font-weight:600; margin-top:3px; }
.twiza-univers .usig__x{ color:var(--muted); font-size:13.5px; line-height:1.6; border-inline-start:1px solid var(--line); padding-inline-start:18px; margin:0; }

/* ---- 2 · NOTRE VISION ---- */
.twiza-univers .uvis__head h2{ font-size:clamp(30px,3.6vw,48px); }
.twiza-univers .uvis__head p b{ color:var(--accent-deep); }
.twiza-univers .uflow{ display:grid; grid-template-columns:repeat(4,1fr); gap:clamp(16px,2vw,28px); margin-top:clamp(36px,4vw,56px); }
/* The steps are equal-height grid items, but their descriptions run to two or
   three lines, so the photographs used to start wherever the copy happened to
   end. Giving the copy the one flexible row pins every photograph to the same
   line — and keeps doing it when the grid restacks to two columns or one. */
.twiza-univers .uflow__step{ position:relative; text-align:center;
  display:grid; grid-template-rows:auto auto 1fr auto; }
.twiza-univers .uflow__step:not(:last-child)::after{ content:""; position:absolute; top:38px; inset-inline-end:-14%; width:28%; height:2px; background:repeating-linear-gradient(90deg,var(--accent) 0 6px,transparent 6px 12px); }
.twiza-univers .uflow__ic{ position:relative; width:78px; height:78px; margin:0 auto; border-radius:50%; background:var(--orange-tint); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; }
.twiza-univers .uflow__step:nth-child(4) .uflow__ic{ background:var(--green-soft); color:var(--green-deep); }
.twiza-univers .uflow__ic svg{ width:34px; height:34px; }
.twiza-univers .uflow__n{ position:absolute; bottom:-6px; left:50%; transform:translateX(-50%); width:24px; height:24px; border-radius:50%; background:var(--u-green); color:#fff; font-size:12px; font-weight:700; display:flex; align-items:center; justify-content:center; }
.twiza-univers .uflow__t{ font-size:15px; font-weight:700; letter-spacing:.04em; text-transform:uppercase; margin:20px 0 0; color:var(--u-green); }
.twiza-univers .uflow__t::after{ content:""; display:block; width:26px; height:2px; background:var(--accent); border-radius:2px; margin:9px auto 0; }
.twiza-univers .uflow__d{ color:var(--muted); font-size:13.5px; line-height:1.6; margin:12px auto 18px; max-width:22ch; }
.twiza-univers .uflow__media{ border-radius:16px; overflow:hidden; aspect-ratio:5/4; box-shadow:var(--shadow-sm); }
.twiza-univers .uflow__media img{ width:100%; height:100%; object-fit:cover; }
.twiza-univers .uquote{ position:relative; display:flex; align-items:center; justify-content:center; gap:12px; text-align:center; margin-top:clamp(30px,4vw,48px); background:var(--orange-tint); border:1px solid var(--orange-soft); border-radius:var(--radius); padding:clamp(20px,3vw,30px) clamp(24px,4vw,52px); }
.twiza-univers .uquote p{ font-family:var(--font-head); font-size:clamp(17px,1.9vw,22px); line-height:1.45; color:var(--u-green); margin:0; }
.twiza-univers .uquote p::first-line{ color:var(--accent-deep); }
.twiza-univers .uquote__leaf{ width:44px; height:60px; color:var(--green-soft); flex:none; }
.twiza-univers .uquote .hd{ color:var(--accent); width:26px; height:26px; flex:none; }

/* ---- 3 · EXPLORER (dynamic category cards) ----
   Scoped to the homepage too: its « Acheter par univers » §3 draws the same
   card off the same live list, so the two pages cannot disagree about what an
   univers looks like. Keep the rules here, beside the page that owns the
   design, rather than duplicating them under .twiza-home. */
:is(.twiza-univers,.twiza-home) .ucards{ display:grid; grid-template-columns:repeat(auto-fit,minmax(240px,1fr)); gap:clamp(16px,2vw,24px); margin-top:clamp(30px,4vw,48px); }
:is(.twiza-univers,.twiza-home) .ucard{ position:relative; display:flex; flex-direction:column; align-items:center; justify-content:flex-end; min-height:270px; padding:26px 22px; border-radius:var(--radius); overflow:hidden; background-image:var(--bg); background-size:cover; background-position:center; box-shadow:var(--shadow-sm); transition:transform .3s var(--ease),box-shadow .3s; isolation:isolate; }
:is(.twiza-univers,.twiza-home) .ucard:hover{ transform:translateY(-6px); box-shadow:var(--shadow-lift); }
:is(.twiza-univers,.twiza-home) .ucard__ovl{ position:absolute; inset:0; z-index:-1; background:linear-gradient(180deg,rgba(34,45,30,.28) 0%,rgba(34,45,30,.72) 100%); }
:is(.twiza-univers,.twiza-home) .ucard__ic{ position:absolute; top:20px; left:50%; transform:translateX(-50%); width:56px; height:56px; border-radius:50%; background:rgba(255,255,255,.94); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; box-shadow:var(--shadow-sm); }
:is(.twiza-univers,.twiza-home) .ucard__ic svg{ width:26px; height:26px; }
:is(.twiza-univers,.twiza-home) .ucard__body{ display:flex; flex-direction:column; align-items:center; gap:8px; text-align:center; }
:is(.twiza-univers,.twiza-home) .ucard__t{ font-family:var(--font-head); font-size:23px; font-weight:600; color:#fff; }
:is(.twiza-univers,.twiza-home) .ucard__d{ font-size:13px; color:rgba(255,255,255,.85); line-height:1.5; max-width:24ch; }
:is(.twiza-univers,.twiza-home) .ucard__btn{ margin-top:8px; display:inline-flex; align-items:center; gap:8px; font-size:13px; font-weight:600; color:#fff; border:1.5px solid rgba(255,255,255,.6); border-radius:100px; padding:9px 18px; transition:background .25s,color .25s,border-color .25s; }
:is(.twiza-univers,.twiza-home) .ucard:hover .ucard__btn{ background:var(--accent); border-color:var(--accent); }

/* ---- CTA bands (shared by §3 & §4) ---- */
.twiza-univers .uband{ display:flex; align-items:center; gap:clamp(16px,2vw,26px); flex-wrap:wrap; margin-top:clamp(30px,4vw,44px); padding:clamp(18px,2.4vw,26px) clamp(22px,3vw,34px); border:1.5px dashed var(--orange-soft); border-radius:var(--radius); background:var(--orange-tint); }
.twiza-univers .uband--soft{ border-style:solid; border-color:var(--line); background:#fff; box-shadow:var(--shadow-sm); }
.twiza-univers .uband__ic{ width:34px; height:34px; color:var(--accent-deep); flex:none; }
.twiza-univers .uband__txt{ flex:1 1 260px; }
.twiza-univers .uband__txt b{ display:block; font-family:var(--font-head); font-size:19px; color:var(--u-green); }
.twiza-univers .uband__txt span{ color:var(--muted); font-size:14.5px; }
.twiza-univers .uband .btn{ flex:none; }

/* ---- 4 · SÉLECTION D'EXCEPTION ---- */
.twiza-home .usel{ margin-top:clamp(30px,4vw,48px); display:flex; flex-direction:column; gap:clamp(22px,3vw,36px); }
.twiza-home .usel__row{ display:grid; grid-template-columns:210px 1fr; gap:clamp(18px,2.4vw,32px); align-items:start; }
.twiza-home .usel__row + .usel__row{ border-top:1px solid var(--line); padding-top:clamp(22px,3vw,34px); }
.twiza-home .usel__ic{ width:52px; height:52px; border-radius:50%; background:var(--orange-tint); color:var(--accent-deep); display:flex; align-items:center; justify-content:center; }
.twiza-home .usel__ic svg{ width:26px; height:26px; }
.twiza-home .usel__name{ font-size:23px; font-weight:600; margin:14px 0 0; position:relative; }
.twiza-home .usel__name::after{ content:""; display:block; width:30px; height:2px; background:var(--accent); border-radius:2px; margin-top:8px; }
.twiza-home .usel__desc{ color:var(--muted); font-size:13.5px; line-height:1.6; margin:12px 0 0; }
.twiza-home .usel__all{ display:inline-flex; align-items:center; gap:7px; margin-top:14px; font-size:13.5px; font-weight:600; color:var(--accent-deep); }
.twiza-home .usel__all:hover .ar{ transform:translateX(3px); }
.twiza-home .usel__rail{ position:relative; min-width:0; }
/* The rail still scrolls — by swipe, trackpad, keyboard and the two buttons —
   it just does not draw a scrollbar. This is the only horizontal scrollbar the
   site had; the buttons replace it. */
.twiza-home .usel__track{ display:flex; gap:16px; overflow-x:auto; padding-bottom:6px; scroll-snap-type:x mandatory;
  scrollbar-width:none; -ms-overflow-style:none; scroll-behavior:smooth; }
.twiza-home .usel__track::-webkit-scrollbar{ width:0; height:0; display:none; }
.twiza-home .usel__track:focus-visible{ outline:2px solid var(--accent); outline-offset:3px; border-radius:12px; }

/* Buttons appear only once the script has wired them, so they are never dead. */
.twiza-home .usel__nav{ position:absolute; top:calc(50% - 40px); z-index:2; width:44px; height:44px; padding:0;
  display:none; align-items:center; justify-content:center;
  border:1px solid var(--line); border-radius:50%; background:#fff; color:var(--accent-deep);
  box-shadow:var(--shadow-sm); cursor:pointer; transition:background .25s,color .25s,border-color .25s,opacity .25s; }
.twiza-home .usel__rail.is-ready .usel__nav{ display:flex; }
.twiza-home .usel__nav svg{ width:20px; height:20px; }
.twiza-home .usel__nav--prev{ inset-inline-start:-14px; }
.twiza-home .usel__nav--next{ inset-inline-end:-14px; }
/* a <button>, so classic's `#main a:hover` does not reach it — no #main rule needed */
.twiza-home .usel__nav:hover{ background:var(--accent-deep); border-color:var(--accent-deep); color:#fff; }
.twiza-home .usel__nav[disabled]{ opacity:0; pointer-events:none; }
/* the chevrons point along the reading direction */
body.lang-rtl .twiza-home .usel__nav svg{ transform:scaleX(-1); }
.twiza-home .uprod{ flex:0 0 200px; scroll-snap-align:start; background:#fff; border:1px solid var(--line); border-radius:16px; overflow:hidden; display:flex; flex-direction:column; transition:transform .3s var(--ease),box-shadow .3s,border-color .3s; }
.twiza-home .uprod:hover{ transform:translateY(-5px); box-shadow:var(--shadow); border-color:transparent; }
.twiza-home .uprod__media{ aspect-ratio:1; overflow:hidden; background:var(--cream); }
.twiza-home .uprod__media img{ width:100%; height:100%; object-fit:cover; }
.twiza-home .uprod__body{ padding:12px 14px 15px; display:flex; flex-direction:column; gap:3px; }
.twiza-home .uprod__name{ font-size:13.5px; font-weight:600; color:var(--ink); line-height:1.35; display:-webkit-box; -webkit-line-clamp:2; -webkit-box-orient:vertical; overflow:hidden; min-height:2.7em; }
.twiza-home .uprod__brand{ font-size:11.5px; color:var(--muted); }
.twiza-home .uprod__price{ font-family:var(--font-head); font-weight:700; font-size:15.5px; color:var(--accent-deep); margin-top:4px; }

/* ---- 5 · REJOIGNEZ-NOUS ---- */
.twiza-univers .urej__grid{ display:grid; grid-template-columns:1.05fr .95fr; gap:clamp(28px,4vw,60px); align-items:center; }
.twiza-univers .urej__h1{ font-size:clamp(30px,4vw,52px); line-height:1.08; margin:18px 0 0; }
.twiza-univers .urej__p{ color:var(--muted); font-size:16.5px; line-height:1.72; margin:22px 0 0; max-width:520px; }
.twiza-univers .urej__p b{ color:var(--accent-deep); font-weight:700; }
.twiza-univers .urej__media{ position:relative; display:flex; justify-content:center; }
.twiza-univers .urej__circle{ width:min(100%,430px); aspect-ratio:1; border-radius:50%; overflow:hidden; border:6px solid #fff; box-shadow:var(--shadow-lift); }
.twiza-univers .urej__circle img{ width:100%; height:100%; object-fit:cover; }
.twiza-univers .urej__stamp{ position:absolute; top:8%; inset-inline-end:2%; width:118px; height:118px; border-radius:50%; background:#fff; box-shadow:var(--shadow); display:flex; flex-direction:column; align-items:center; justify-content:center; gap:5px; text-align:center; padding:10px; }
.twiza-univers .urej__stamp svg{ width:30px; height:30px; color:var(--accent-deep); }
.twiza-univers .urej__stamp span{ font-size:9px; font-weight:700; letter-spacing:.08em; text-transform:uppercase; color:var(--u-green); line-height:1.4; }
.twiza-univers .upillars{ display:grid; grid-template-columns:repeat(5,1fr); gap:clamp(10px,1.4vw,20px); margin-top:clamp(34px,4vw,54px); background:var(--cream-2); border-radius:var(--radius-lg); padding:clamp(22px,3vw,38px) clamp(18px,2.4vw,30px); }
.twiza-univers .upillar{ text-align:center; padding-inline:8px; }
.twiza-univers .upillar + .upillar{ border-inline-start:1px solid var(--line); }
.twiza-univers .upillar__ic{ width:48px; height:48px; margin:0 auto 14px; color:var(--accent-deep); display:flex; align-items:center; justify-content:center; }
.twiza-univers .upillar__ic svg{ width:30px; height:30px; }
.twiza-univers .upillar__t{ font-size:12.5px; font-weight:700; letter-spacing:.03em; text-transform:uppercase; color:var(--u-green); }
.twiza-univers .upillar__d{ font-size:12.5px; color:var(--muted); line-height:1.55; margin-top:9px; }
.twiza-univers .ufinal{ display:grid; grid-template-columns:1.15fr .85fr; margin-top:clamp(22px,2.6vw,34px); border-radius:var(--radius-lg); overflow:hidden; box-shadow:var(--shadow-sm); }
.twiza-univers .ufinal__l{ position:relative; display:flex; align-items:center; gap:18px; background:var(--cream); padding:clamp(24px,3vw,38px); }
.twiza-univers .ufinal__map{ width:60px; height:70px; color:var(--u-green); flex:none; }
.twiza-univers .ufinal__h b{ display:block; font-family:var(--font-head); font-size:clamp(19px,2vw,25px); color:var(--u-green); }
.twiza-univers .ufinal__h b.o{ color:var(--accent-deep); }
.twiza-univers .ufinal__script{ font-family:var(--font-head); font-style:italic; font-size:17px; color:var(--muted); margin-top:10px; }
.twiza-univers .ufinal__r{ background:var(--u-green); color:#fff; padding:clamp(24px,3vw,38px); display:flex; flex-direction:column; justify-content:center; gap:4px; }
.twiza-univers .ufinal__rh{ font-family:var(--font-head); font-size:clamp(19px,2vw,24px); }
.twiza-univers .ufinal__rp{ color:rgba(255,255,255,.8); font-size:14.5px; margin-bottom:16px; }
.twiza-univers .ufinal__r .btn{ align-self:flex-start; }
.twiza-univers .utrust{ display:flex; flex-wrap:wrap; justify-content:center; gap:clamp(20px,4vw,54px); margin-top:clamp(26px,3vw,40px); }
.twiza-univers .utrust__i{ display:flex; align-items:center; gap:10px; font-size:13.5px; color:var(--muted); }
.twiza-univers .utrust__i svg{ width:22px; height:22px; color:var(--accent-deep); }

/* ---- responsive ---- */
@media (max-width:1080px){
  .twiza-univers .uflow{ grid-template-columns:repeat(2,1fr); }
  .twiza-univers .uflow__step:not(:last-child)::after{ display:none; }
  .twiza-univers .upillars{ grid-template-columns:repeat(3,1fr); gap:22px 10px; }
  .twiza-univers .upillar:nth-child(3n+1){ border-inline-start:0; }
}
@media (max-width:860px){
  .twiza-univers .uhero__grid,.twiza-univers .urej__grid{ grid-template-columns:1fr; }
  /* Stacked, the row no longer gives the picture its height and the absolute
     img would collapse the box to nothing — so it gets its own floor, and
     rounded corners now that it is an object on the band rather than a half
     of it. The scrim turns bottom-up: the copy is below it, not beside it. */
  .twiza-univers .uhero__grid{ min-height:0; }
  .twiza-univers .uhero__text{ padding-inline-end:0; padding-block-start:34px; }
  .twiza-univers .uhero__media,.twiza-univers .urej__media{ order:-1; }
  .twiza-univers .uhero__media{ min-height:380px; border-radius:var(--radius-lg); overflow:hidden; }
  .twiza-univers .uhero__media::after{ background:linear-gradient(0deg, var(--cream), rgba(251,247,240,0) 40%); }
  .twiza-univers .uhero__foot{ grid-template-columns:1fr; }
  .twiza-univers .usig{ flex-wrap:wrap; }
  .twiza-univers .usig__x{ border-inline-start:0; padding-inline-start:0; }
  .twiza-home .usel__row{ grid-template-columns:1fr; }
  /* full-width rail: the buttons sit inside it rather than hanging off the
     edges, where the narrowest viewports would clip them */
  .twiza-home .usel__nav--prev{ inset-inline-start:6px; }
  .twiza-home .usel__nav--next{ inset-inline-end:6px; }
  .twiza-univers .ufinal{ grid-template-columns:1fr; }
}
@media (max-width:560px){
  .twiza-univers .uflow{ grid-template-columns:1fr; }
  .twiza-univers .upillars{ grid-template-columns:1fr; }
  .twiza-univers .upillar + .upillar{ border-inline-start:0; border-top:1px solid var(--line); padding-top:18px; }
  .twiza-univers .ustats{ justify-content:space-between; }
  .twiza-univers .uband .btn{ width:100%; }
}

/* ---- RTL ---- */
body.lang-rtl .twiza-univers .ar{ transform:scaleX(-1); }
/* the usel row also renders on the homepage, which carries `.twiza-home` but
   not `.twiza-univers` — so its arrow had a mirrored :hover state and no
   mirrored rest state, and flipped direction under the cursor. */
body.lang-rtl .twiza-home .usel__all .ar{ transform:scaleX(-1); }
body.lang-rtl .twiza-univers .btn:hover .ar,
body.lang-rtl .twiza-home .usel__all:hover .ar{ transform:scaleX(-1) translateX(3px); }
body.lang-rtl .twiza-univers .uflow__step:not(:last-child)::after{ background:repeating-linear-gradient(270deg,var(--accent) 0 6px,transparent 6px 12px); }
/* hero scrim fades from the text side (now right), like the homepage hero */
body.lang-rtl .twiza-univers .uhero__media::after{
  background:linear-gradient(-90deg, var(--cream) 0%, rgba(251,247,240,.35) 16%, rgba(251,247,240,0) 42%); }
@media (max-width:860px){
  body.lang-rtl .twiza-univers .uhero__media::after{ background:linear-gradient(0deg, var(--cream), rgba(251,247,240,0) 40%); }
}

/* ════════════════════════════════════════════════════════════════════════
   PANIER — the « ajouté au panier » dialog and the cart page
   Everything below is layout classic left us: a Bootstrap modal that assumes
   nothing on the page is pinned higher than it, a float-based product line
   sized for a desktop, and a `.card-block` whose padding classic deletes
   outright on phones. Logical properties throughout, so Arabic mirrors with
   the rest of the page.
   ════════════════════════════════════════════════════════════════════════ */

/* ---- 1 · the dialog belongs above the chrome ----------------------------
   A Bootstrap dialog tops out at z-index 1050, but landingpagecod pins its
   mini header at 9999 and its floating order button at 9998. On a landing
   product the confirmation therefore opened UNDERNEATH the bar, with its
   title and close button sliced in half. A dialog owns the screen while it
   is up: it goes over every piece of chrome, and the floating button steps
   out rather than glowing through the backdrop. */
.modal-backdrop{ z-index:10040; }
.modal{ z-index:10050; }
body.modal-open #lp-sticky-cta{ display:none !important; }

/* ---- 2 · the dialog, in the theme's voice ----
   The dialog keeps itself inside the viewport and scrolls its own body, so the
   two buttons at the end of it stay reachable on a phone — they used to fall
   past the fold behind a full-width product photo. */
#blockcart-modal .modal-dialog{ display:flex; flex-direction:column;
  max-width:900px; margin:clamp(16px,4vh,48px) auto;
  max-height:calc(100vh - 2 * clamp(16px,4vh,48px)); }
#blockcart-modal .modal-content{ max-height:100%; overflow:hidden;
  border:0; border-radius:var(--radius);
  box-shadow:0 30px 70px -20px rgba(43,37,30,.45); }
#blockcart-modal .modal-header{ position:relative; flex:0 0 auto; padding:16px 60px;
  background:var(--cream); border-bottom:1px solid var(--line);
  border-radius:var(--radius) var(--radius) 0 0; }
#blockcart-modal .modal-title{ margin:0; font-family:var(--font-body);
  font-size:16px; font-weight:600; color:var(--ink); }
/* classic writes this one down to the element too (`i.material-icons`), so a
   class-only selector loses it. The gap stays physical here on purpose: the
   glyph carries `.rtl-no-flip`, which pins it to `direction:ltr`, so its own
   inline-end is the wrong side in Arabic — rtl.css flips it. */
#blockcart-modal .modal-title i.material-icons{ color:var(--green); vertical-align:-5px;
  margin-right:8px; }
/* the close glyph is a Material Icons ligature, and the landing pages do not
   load that font — it came out as a stray chevron. Draw the cross in CSS so
   the button reads the same wherever the dialog opens. */
#blockcart-modal .modal-header .close{ position:absolute; top:50%; inset-inline-end:14px; transform:translateY(-50%);
  display:flex; align-items:center; justify-content:center; float:none;
  width:36px; height:36px; margin:0; padding:0; opacity:1;
  background:#fff; border:1px solid var(--line); border-radius:50%;
  font-size:0; line-height:0; color:var(--muted); transition:color .2s,border-color .2s; }
#blockcart-modal .modal-header .close > span{ display:none; }
#blockcart-modal .modal-header .close::before{ content:"×"; font-size:26px; line-height:1; }
#blockcart-modal .modal-header .close:hover{ color:var(--accent-deep); border-color:var(--accent); }

#blockcart-modal .modal-body{ flex:1 1 auto; overflow-y:auto; padding:26px 28px 28px; }
/* classic's divider is a physical border-right, so in Arabic it stayed on the
   wrong side of the product; border-inline-end follows the page. */
#blockcart-modal .divide-right{ border-right:0; border-inline-end:1px solid var(--line); }
#blockcart-modal .product-image{ border-radius:var(--radius-sm); }
/* classic splits the photo and the name down the middle, which at this width
   left the name in a 145px gutter and four lines tall. */
@media (min-width:768px){
  #blockcart-modal .divide-right > .row{ display:flex; align-items:center; }
  #blockcart-modal .divide-right > .row > div{ float:none; }
  #blockcart-modal .divide-right > .row > div:first-child{ flex:0 0 42%; width:42%; }
  #blockcart-modal .divide-right > .row > div:last-child{ flex:1 1 auto; width:auto; }
}
#blockcart-modal .product-name{ margin:0 0 10px; font-family:var(--font-head);
  font-size:17px; line-height:1.35; color:var(--ink); }
#blockcart-modal .product-price{ margin:0 0 8px; font-family:var(--font-head);
  font-size:18px; font-weight:700; color:var(--accent-deep); }
#blockcart-modal .product-quantity{ color:var(--muted); font-size:14.5px; }
#blockcart-modal .cart-products-count{ margin-bottom:14px; font-family:var(--font-head);
  font-size:16px; color:var(--ink); }
/* ⚠ classic writes these rules as `#blockcart-modal .cart-content …` and, for the
   buttons, down to the element (`… .cart-content-btn button`). A selector one
   class short of that loses the property outright, so every rule below repeats
   classic's own shape and wins on source order instead. */
#blockcart-modal .cart-content{ font-size:15px; }
#blockcart-modal .cart-content p.product-total{ background:var(--cream); border-radius:var(--radius-sm); padding:8px 12px; }
#blockcart-modal .cart-content p.product-total .value{ color:var(--accent-deep); font-weight:700; }
/* classic spaces the two buttons with a physical margin-right, which in Arabic
   pushed them apart on the wrong side; a flex row with a gap has no side. */
#blockcart-modal .cart-content .cart-content-btn{ display:flex; flex-wrap:wrap; gap:12px;
  justify-content:flex-end; margin-top:18px; }
#blockcart-modal .cart-content .cart-content-btn .btn,
#blockcart-modal .cart-content .cart-content-btn button.btn{ flex:1 1 auto; margin:0;
  border-radius:100px; font-weight:600; }

@media (max-width:767px){
  #blockcart-modal .modal-dialog{ margin:12px; max-height:calc(100vh - 24px); }
  #blockcart-modal .modal-header{ padding:14px 52px; }
  #blockcart-modal .modal-body{ padding:18px 16px 20px; }
  #blockcart-modal .divide-right{ border:0; border-bottom:1px solid var(--line);
    padding-bottom:16px; margin-bottom:16px; }
  /* the photo is decoration here — the confirmation is what the shopper reads */
  #blockcart-modal .product-image{ display:block; width:auto; max-height:150px; margin:0 auto 14px; }
  /* column-reverse: « commander » is the primary action, so it leads on a phone */
  #blockcart-modal .cart-content .cart-content-btn{ flex-direction:column-reverse; }
  #blockcart-modal .cart-content .cart-content-btn .btn{ width:100%; }
}

/* ---- 3 · the cart page ----
   classic sizes the title from `.cart-grid-body .card-block h1`, which outranks
   the theme's `.h1` rule — match the selector to win it back. */
.cart-grid-body .card-block h1{ margin:0; font-family:var(--font-head);
  font-size:clamp(26px,2.6vw,34px); color:var(--ink); }

/* the line reads as one sentence — photo, name, quantity, price, bin — so the
   parts line up on their middles instead of hanging from the top of the photo.
   Dropping the float also lets `direction:rtl` mirror the row on its own. */
@media (min-width:768px){
  .cart-item .product-line-grid{ display:flex; align-items:center; }
  .cart-item .product-line-grid > div{ float:none; }
}

/* « 199,00 Dh  -40,00 Dh » are two inline children of different heights, so the
   moment they wrapped — always in Arabic, where the badge is the wider of the
   two — the padded badge landed on top of the struck price. A flex row wraps
   without overlapping and carries its own gap, so the physical margins go. */
.cart-item .product-discount{ display:flex; flex-wrap:wrap; align-items:center; gap:8px; }
.cart-item .product-discount .regular-price,
.cart-item .product-discount .discount{ margin:0; }
.cart-item .product-discount .regular-price{ color:var(--muted); }
.cart-item .product-discount .discount{ padding:4px 11px; background:var(--accent);
  color:#fff; border-radius:100px; font-size:12px; font-weight:700; line-height:1.2; }
.cart-item .current-price .price{ font-family:var(--font-head); font-size:17px;
  font-weight:700; color:var(--accent-deep); }

/* the quantity spinner is a float layout that only fits its desktop column: in
   a 60px column on a phone the up/down buttons dropped under the field. One
   flex box, one border, and it holds its shape at every width. */
.cart-item .qty .bootstrap-touchspin{ display:flex; flex-wrap:nowrap; align-items:stretch;
  width:auto; max-width:100%; background:#fff; border:1px solid var(--line);
  border-radius:10px; overflow:hidden; }
.cart-item .qty .bootstrap-touchspin > input.form-control{ float:none; flex:0 0 46px;
  width:46px; height:38px; padding:0; text-align:center; background:transparent;
  border:0; border-radius:0; box-shadow:none; }
.cart-item .qty .bootstrap-touchspin .input-group-btn-vertical{ float:none; display:flex;
  flex-direction:column; border-inline-start:1px solid var(--line); }
.cart-item .qty .bootstrap-touchspin .btn-touchspin{ position:relative; display:flex;
  align-items:center; justify-content:center; flex:1 1 50%;
  width:26px; min-height:19px; padding:0; background:var(--cream);
  border:0; border-radius:0; transition:background .2s,color .2s; }
.cart-item .qty .bootstrap-touchspin .btn-touchspin + .btn-touchspin{ border-top:1px solid var(--line); }
.cart-item .qty .bootstrap-touchspin .btn-touchspin:hover{ background:var(--accent-soft); color:var(--accent-deep); }
/* classic pins the arrows with `position:absolute; left:.1875rem`, which rtl.css
   then mirrors — inside a flex button they simply centre themselves. */
.cart-item .qty .bootstrap-touchspin .btn-touchspin .material-icons{ position:static;
  font-size:15px; line-height:1; }

/* the bin gets a real target to aim at */
.cart-item .cart-line-product-actions .remove-from-cart{ display:inline-flex;
  align-items:center; justify-content:center; width:40px; height:40px;
  border-radius:50%; color:var(--muted); transition:background .2s,color .2s; }
.cart-item .cart-line-product-actions .remove-from-cart:hover{ background:var(--accent-soft); color:var(--accent-deep); }
.cart-item .cart-line-product-actions .remove-from-cart .material-icons{ float:none !important; }

/* Phone: the right-hand column is a three-level float grid whose percentages
   were picked for a desktop — the price ended up in a 30px column and the
   spinner in a 60px one. Flatten it to one flex row: quantity at the start,
   price and bin at the end, and the empty column that reserves room for the
   photo above is no longer needed. */
@media (max-width:767px){
  .cart-item .product-line-grid-right > .row{ display:flex; align-items:center; gap:12px; margin:0; }
  .cart-item .product-line-grid-right > .row > div{ float:none; width:auto; padding:0; }
  .cart-item .product-line-grid-right > .row > .hidden-md-up{ display:none !important; }
  .cart-item .product-line-grid-right > .row > .col-md-10{ flex:1 1 auto; }
  .cart-item .product-line-grid-right > .row > .col-md-10 > .row{ display:flex;
    align-items:center; justify-content:space-between; gap:12px; margin:0; }
  .cart-item .product-line-grid-right .qty,
  .cart-item .product-line-grid-right .price{ float:none; width:auto; padding:0; }
}

/* Phone: classic zeroes EVERY `.card-block` padding below 768px. The cart card
   has its own padding and survived, but the summary lost its inset, so the
   totals, the promo link and the order button sat flush against the card
   border — the one thing that made the column look broken next to the cart. */
@media (max-width:767px){
  .cart-summary .card-block{ padding:1rem 1rem .5rem; }
  .cart-summary .card-block.cart-detailed-actions{ padding:0 1rem 1.5rem; }
}

/* ---- 4 · the summary card ----
   classic leaves it a stack of undressed label/value rows: the totals carry
   grey hairlines, the promo link sits OUTSIDE the padded `.card-block` and so
   hangs flush against the card border, and the voucher form still wears the
   turquoise button of the base theme. The card now opens with a header strip
   like the « Panier » card beside it (added in the theme's own
   `cart-detailed-totals.tpl`), and every row below reads as one rhythm.
   Selectors repeat classic's `.card-block.cart-summary-totals …` shape — one
   class short and the property is lost in silence. */
/* Checkout carries the SAME parts under a different wrapper —
   `section#js-checkout-summary.card.js-cart` instead of `.card.cart-summary` —
   so every rule below names both. Skinning only the cart left the money screen
   with a bare promo link and classic's grey hairlines. Both cards now open on
   the same header strip — checkout's comes from the theme's own
   `checkout/_partials/cart-summary.tpl`. */
.cart-summary,
#js-checkout-summary{ overflow:hidden; }
.cart-summary .tw-sum__head,
#js-checkout-summary .tw-sum__head{ padding:15px 18px; background:var(--cream);
  border-bottom:1px solid var(--line); }
.cart-summary .tw-sum__title,
#js-checkout-summary .tw-sum__title{ font-family:var(--font-head); font-size:17px; color:var(--ink); }
#js-checkout-summary .cart-summary-subtotals-container{ border-color:var(--line-2); }

/* one flex row per line, so the value no longer floats and Arabic mirrors it
   without a twin rule. The shipping line carries a third child (the carrier
   detail hook) — it wraps onto its own line instead of joining the row. */
.cart-summary .cart-summary-line,
#js-checkout-summary .cart-summary-line{ display:flex; flex-wrap:wrap; align-items:baseline;
  justify-content:space-between; gap:6px 14px; margin:0; padding:6px 0; }
.cart-summary .cart-summary-line::after,
#js-checkout-summary .cart-summary-line::after{ content:none; }
.cart-summary .cart-summary-line > div,
#js-checkout-summary .cart-summary-line > div{ flex:1 1 100%; }
.cart-summary .cart-summary-line > div > small.value:empty,
#js-checkout-summary .cart-summary-line > div > small.value:empty{ display:none; }
.cart-summary .cart-summary-line .label,
#js-checkout-summary .cart-summary-line .label{ padding:0; color:var(--muted);
  font-size:14.5px; font-weight:500; }
.cart-summary .cart-summary-line .value,
#js-checkout-summary .cart-summary-line .value{ float:none; color:var(--ink);
  font-size:15px; font-weight:600; white-space:nowrap; }

/* the total is the one number that matters — it gets the cream band and the
   accent, and classic's grey rule above it goes. */
.cart-summary .card-block.cart-summary-totals,
#js-checkout-summary .card-block.cart-summary-totals{ padding-top:.75rem; }
.cart-summary .card-block.cart-detailed-subtotals{ border-bottom:1px solid var(--line-2); }
.cart-summary .card-block.cart-detailed-subtotals + .cart-summary-totals .cart-summary-line.cart-total{ border-top:0; }
.cart-summary .card-block.cart-summary-totals .cart-summary-line.cart-total,
#js-checkout-summary .card-block.cart-summary-totals .cart-summary-line.cart-total{
  margin:4px 0 2px; padding:11px 13px; background:var(--cream); border-radius:var(--radius-sm); }
.cart-summary .card-block.cart-summary-totals .cart-summary-line.cart-total .label,
#js-checkout-summary .card-block.cart-summary-totals .cart-summary-line.cart-total .label{
  color:var(--ink); font-size:15px; font-weight:700; }
.cart-summary .card-block.cart-summary-totals .cart-summary-line.cart-total .value,
#js-checkout-summary .card-block.cart-summary-totals .cart-summary-line.cart-total .value{
  font-family:var(--font-head); font-size:19px; font-weight:700; color:var(--accent-deep); }
.cart-summary .card-block.cart-summary-totals .cart-summary-line .label.sub,
.cart-summary .card-block.cart-summary-totals .cart-summary-line .value.sub,
#js-checkout-summary .card-block.cart-summary-totals .cart-summary-line .label.sub,
#js-checkout-summary .card-block.cart-summary-totals .cart-summary-line .value.sub{
  font-size:12.5px; font-weight:500; color:var(--muted); }

/* the promo link had no padding of its own — being outside the `.card-block`,
   it started at the card border while every row above it was inset by 1rem.
   It is a real control now: a soft dashed pill that fills on hover. */
.cart-summary .block-promo,
#js-checkout-summary .block-promo{ margin:0; padding:2px 18px 16px; }
.cart-summary .block-promo .promo-code-button,
#js-checkout-summary .block-promo .promo-code-button{ display:block; padding:0; margin:0; text-align:start; }
.cart-summary .block-promo .promo-code-button .collapse-button,
#js-checkout-summary .block-promo .promo-code-button .collapse-button{
  display:inline-flex; align-items:center; gap:9px; padding:9px 16px;
  background:var(--accent-soft); border:1px dashed var(--accent); border-radius:100px;
  color:var(--accent-deep); font-size:14px; font-weight:600; text-decoration:none;
  transition:background .22s var(--ease), color .22s var(--ease), border-color .22s var(--ease); }
.cart-summary .block-promo .promo-code-button .collapse-button::before,
#js-checkout-summary .block-promo .promo-code-button .collapse-button::before{
  content:""; flex:none; width:16px; height:16px; background:currentColor;
  -webkit-mask:var(--tw-tag-ic) center/contain no-repeat; mask:var(--tw-tag-ic) center/contain no-repeat; }
/* `#main a:hover{color:var(--accent-deep)}` is an ID rule and beats any number
   of classes — without the prefix the label turns the same deep orange as the
   fill it sits on and reads as an empty pill. */
#main .cart-summary .block-promo .promo-code-button .collapse-button:hover,
#main .cart-summary .block-promo .promo-code-button .collapse-button:focus,
#main #js-checkout-summary .block-promo .promo-code-button .collapse-button:hover,
#main #js-checkout-summary .block-promo .promo-code-button .collapse-button:focus{
  background:var(--accent); border-style:solid; color:#fff; }
.cart-summary .block-promo .promo-code,
#js-checkout-summary .block-promo .promo-code{ padding:14px; margin-top:12px;
  background:var(--cream); border:1px solid var(--line); border-radius:var(--radius-sm); }
.cart-summary .block-promo .promo-code form,
#js-checkout-summary .block-promo .promo-code form{ display:flex; flex-wrap:wrap; gap:8px; text-align:start; }
.cart-summary .block-promo .promo-input,
#js-checkout-summary .block-promo .promo-input{ flex:1 1 130px; width:auto; min-width:0; height:42px;
  margin:0; padding:0 15px; text-indent:0; background:#fff; border:1px solid var(--line);
  border-radius:100px; color:var(--ink); font-size:14px; }
.cart-summary .block-promo .promo-input:focus,
#js-checkout-summary .block-promo .promo-input:focus{ outline:0; border-color:var(--accent); }
/* classic paints this button turquoise, and at 2px */
.cart-summary .block-promo .promo-input + button,
#js-checkout-summary .block-promo .promo-input + button{ flex:0 0 auto; height:42px; margin:0;
  padding:0 22px; border:0; border-radius:100px; text-transform:none; font-weight:600; }
.cart-summary .block-promo .promo-code-button.cancel-promo,
#js-checkout-summary .block-promo .promo-code-button.cancel-promo{ margin-top:12px;
  color:var(--muted); font-size:13.5px; }
.cart-summary .block-promo .promo-code-button.cancel-promo:hover,
#js-checkout-summary .block-promo .promo-code-button.cancel-promo:hover{ color:var(--accent-deep); }

/* the order button is the end of the page — full width, pill, and its label
   stays white on hover (classic's `#main a:hover` otherwise tints it the same
   deep orange as its own background and the text disappears into it). */
.cart-summary .card-block.checkout .btn-primary{ padding:13px 22px; border-radius:100px;
  font-weight:700; letter-spacing:.02em; box-shadow:0 10px 22px -12px rgba(217,121,15,.9); }
#main .cart-summary .card-block.checkout .btn-primary:hover,
#main .cart-summary .card-block.checkout .btn-primary:focus{ color:#fff; }

/* ---- 5 · réassurance, in the homepage's language ----
   blockreassurance renders an icon and a title per row, with the icon colour
   as a presentation attribute and the text colour inline from its BO setting
   — a CSS `fill` outranks the former, the latter needs `!important`. The row
   is a two-column grid rather than a flex line so that a block WITH a BO
   description still stacks title over description beside one centred icon.
   Chip, sizes and weights are `.tw-reassure`'s from the homepage.

   A row is a <div> when it has no policy page behind it and an <a> when it
   has — see the theme's displayBlockProduct.tpl override — so every row rule
   selects `:is(div, a)`. Selecting `> div` alone would silently unstyle the
   card the day a block is given a link in the back office. */
.cart-grid-right .blockreassurance_product{ margin-top:14px; padding:4px 18px;
  background:#fff; border:1px solid var(--line); border-radius:var(--radius);
  box-shadow:var(--shadow-sm);
  /* The hover tint on a linked row runs edge to edge, so it has to be clipped
     to the card's radius or it squares off the top and bottom corners.
     Nothing in this card is built to hang out of it. */
  overflow:hidden; }
.cart-grid-right .blockreassurance_product > :is(div, a){ display:grid;
  grid-template-columns:42px 1fr; align-items:center; column-gap:13px;
  margin:0; padding:13px 0; }
.cart-grid-right .blockreassurance_product > :is(div, a) + :is(div, a){
  border-top:1px solid var(--line-2); }
.cart-grid-right .blockreassurance_product > :is(div, a) > .item-product{ grid-column:1;
  grid-row:1 / -1; align-self:center; float:none; display:flex; align-items:center;
  justify-content:center; width:42px; height:42px; margin:0;
  background:var(--accent-soft); border-radius:50%; }
.cart-grid-right .blockreassurance_product > :is(div, a) > .item-product svg,
.cart-grid-right .blockreassurance_product > :is(div, a) > .item-product img{ width:22px; height:22px; }
.cart-grid-right .blockreassurance_product > :is(div, a) > .item-product svg *{ fill:var(--accent-deep); }
.cart-grid-right .blockreassurance_product .block-title{ grid-column:2; margin:0;
  font-size:14.5px; font-weight:700; line-height:1.3; color:var(--ink) !important; }
.cart-grid-right .blockreassurance_product > :is(div, a) > p:not(.block-title){ grid-column:2;
  margin:2px 0 0; font-size:13px; line-height:1.45; color:var(--muted) !important; }
.cart-grid-right .blockreassurance_product > .clearfix{ display:none; }

/* ---- 5b · a linked reassurance row reads as one target ----
   The 13 August UX report: the whole line must be clickable, not the label
   alone, with a hover that says so. The row is edge-to-edge inside a card
   that is padded 18px, so the tint is pulled out by that much and given the
   padding back — a highlight that stopped short of the card's edge would
   read as a button sitting inside the row rather than as the row itself.
   `#main` prefixes the hover colour because `#main a:hover` in this sheet
   would otherwise repaint the title deep orange over its own tint. */
.blockreassurance_product > a.br-row--link{ text-decoration:none;
  transition:background-color .18s ease; }
.cart-grid-right .blockreassurance_product > a.br-row--link{
  margin-inline:-18px; padding-inline:18px; }
#main .blockreassurance_product > a.br-row--link:hover,
#main .blockreassurance_product > a.br-row--link:focus-visible{
  background:var(--accent-soft); text-decoration:none; }
#main .blockreassurance_product > a.br-row--link:hover .block-title,
#main .blockreassurance_product > a.br-row--link:focus-visible .block-title{
  color:var(--accent-deep) !important; }
/* The icon chip is --accent-soft, which is also the hover tint: left alone it
   dissolves into it and the hovered row loses the circle every other row has.
   White keeps the rhythm and reads as the row lifting. */
.cart-grid-right .blockreassurance_product > a.br-row--link:hover > .item-product,
.cart-grid-right .blockreassurance_product > a.br-row--link:focus-visible > .item-product{
  background:#fff; }
.blockreassurance_product > a.br-row--link:focus-visible{
  outline:2px solid var(--accent-deep); outline-offset:-2px; }

/* ---- 6 · the same summary, on the order page ----
   classic un-cards its own card here: `body#checkout .cart-grid-right .card
   { border:0; box-shadow:none }` is (1,2,1) and outranks BOTH `.cart-grid-right
   .card` and `#checkout .card` from §1191, so the money column was a bare white
   block sitting beside a bordered réassurance card. The rule below repeats
   classic's own shape to win it back — the same one-class-short trap as the
   dialog, one level up. It also has to survive classic's blanket
   `@media (max-width:767px){ .card{ background:inherit; border:0; box-shadow:none } }`,
   which it does on specificity alone, no media query of its own needed. */
body#checkout .cart-grid-right .card{ border:1px solid var(--line);
  border-radius:var(--radius); box-shadow:var(--shadow-sm); }
/* the header strip draws the top edge now, so the block below it starts tighter */
#js-checkout-summary > .card-block{ padding:16px 18px 8px; }
#js-checkout-summary .cart-summary-top:empty{ display:none; }

/* ---- 7 · the collapsible product list, checkout only ----
   The cart page has no equivalent: this is the list behind « afficher les
   détails ». classic leaves each line as three stacked rows — name, then
   « x1 », then a price alone on the last — because `.product-price` carries
   `.float-xs-right`. Each line is a grid here, so the price sits on the row it
   belongs to. Grid tracks follow `direction`, so Arabic mirrors the thumbnail
   and the price with no flip in `rtl.css`; the float is dropped at (1,2,0)
   `!important`, which beats that file's `.float-xs-right`. */
/* item count, then the disclosure that opens the list */
#js-checkout-summary .cart-summary-products > p{ margin:0; font-size:14.5px; color:var(--muted); }
#js-checkout-summary .cart-summary-products > p + p{ margin-top:5px; }
#js-checkout-summary .js-show-details{ display:inline-flex; align-items:center; gap:3px;
  font-size:13.5px; font-weight:600; color:var(--accent-deep); text-decoration:none; }
#main #js-checkout-summary .js-show-details:hover,
#main #js-checkout-summary .js-show-details:focus{ color:var(--accent-deep); text-decoration:underline; }
#js-checkout-summary .js-show-details .material-icons{ font-size:18px; transition:transform .2s; }
#js-checkout-summary .js-show-details[aria-expanded="true"] .material-icons{ transform:rotate(180deg); }

/* one grid per product line: thumbnail | name over (quantity · price) */
#js-checkout-summary #cart-summary-product-list.show,
#js-checkout-summary #cart-summary-product-list.collapsing{ margin-top:12px; }
#js-checkout-summary .media-list{ margin:0; padding:0; list-style:none; }
#js-checkout-summary .media-list > li.media{ display:grid;
  grid-template-columns:52px 1fr; column-gap:12px; align-items:start;
  margin:0; padding:12px 0; border-top:1px solid var(--line-2); }
#js-checkout-summary .media-list > li.media:first-child{ padding-top:0; border-top:0; }
#js-checkout-summary .media-list .media-left{ grid-column:1; float:none; padding:0; }
#js-checkout-summary .media-list .media-left img{ display:block; width:52px; height:auto;
  border:1px solid var(--line-2); border-radius:8px; }
/* ⚠ `width:auto` is the load-bearing declaration here. classic's media object is
   Bootstrap 4 ALPHA's — a table-cell faked with `.media-body{ width:10000px }` —
   and that width survives the switch to grid, so the body claimed a 10000px
   track and `.media`'s own `overflow:hidden` swallowed the price. `min-width:0`
   is the companion: a grid track's default `auto` minimum is its content's
   width, so a long product name would widen the line rather than wrap. */
#js-checkout-summary .media-list .media-body{ grid-column:2; width:auto; min-width:0;
  display:grid; grid-template-columns:minmax(0,1fr) auto; column-gap:10px; row-gap:3px; }
#js-checkout-summary .media-list .product-name{ grid-column:1 / -1; min-width:0;
  font-family:var(--font-head); font-size:14px; line-height:1.35; overflow-wrap:anywhere; }
#js-checkout-summary .media-list .product-name a{ color:var(--ink); }
#main #js-checkout-summary .media-list .product-name a:hover{ color:var(--accent-deep); }
#js-checkout-summary .media-list .product-quantity{ grid-column:1; min-width:0; align-self:center;
  font-size:13px; color:var(--muted); }
#js-checkout-summary .media-list .product-price{ grid-column:2; align-self:center;
  float:none !important; font-size:14px; font-weight:700; color:var(--accent-deep);
  text-align:end; white-space:nowrap; }
#js-checkout-summary .media-list .product-line-info{ grid-column:1 / -1; font-size:12.5px; }
#js-checkout-summary .media-list .media-body br{ display:none; }

@media (max-width:767px){
  .cart-summary .tw-sum__head,
  #js-checkout-summary .tw-sum__head{ padding:13px 1rem; }
  .cart-summary .block-promo,
  #js-checkout-summary .block-promo{ padding:2px 1rem 14px; }
  #js-checkout-summary > .card-block{ padding:14px 1rem 8px; }
}

/* ════════════════════════════════════════════════════════════════════════
   CONFIRMATION — the page after payment
   The last screen of the buy path, and the one still closest to stock classic:
   a float grid for the ordered lines, a bare <table> for the money, an <hr>
   between them and an unstyled <ul> of order details. It is rebuilt here in the
   same language as the cart and checkout summaries — one grid per line, the
   total on an accent band, hairlines instead of rules.

   The line grid deliberately repeats classic's own column split so the values
   stay under the headings that name them: classic gives the heading row
   `col-md-6` + three `col-md-2`, i.e. 50% then 3×16.666%. Both rows are grids
   with those tracks, which also means they mirror in Arabic for free.
   ════════════════════════════════════════════════════════════════════════ */
.page-order-confirmation .card-block{ padding:20px 22px; }
#content-hook_order_confirmation .card-block{ padding:16px 22px; }
/* §1275 boxes `.order-confirmation-table` — a border inside the card it already
   sits in. The card is the only box this page needs. */
.page-order-confirmation .order-confirmation-table{ border:0; border-radius:0; }

/* heading row: one section title, three quiet column labels */
#order-items > .row{ display:grid; grid-template-columns:minmax(0,1fr) 16.666% 16.666% 16.666%;
  align-items:end; gap:0 8px; margin:0 0 10px; padding-bottom:10px;
  border-bottom:1px solid var(--line); }
#order-items > .row > .card-title{ float:none; width:auto; max-width:none; padding:0; margin:0; }
#order-items > .row > .card-title:first-child{ font-family:var(--font-head); font-size:19px;
  color:var(--ink); text-transform:none; letter-spacing:0; }
#order-items > .row > ._desktop-title{ font-family:var(--font-body); font-size:11.5px; font-weight:700;
  letter-spacing:.06em; text-transform:uppercase; color:var(--muted); text-align:center; }

/* one grid per ordered line — thumbnail, name, then the three money columns */
.order-confirmation-table .order-line{ display:grid;
  grid-template-columns:84px minmax(0,1fr) 16.666% 16.666% 16.666%;
  align-items:center; gap:0 12px; margin:0; padding:14px 0;
  border-bottom:1px solid var(--line-2); }
.order-confirmation-table .order-line > div{ float:none; width:auto; max-width:none; padding:0; }
.order-confirmation-table .order-line .image{ display:block; }
.order-confirmation-table .order-line .image img{ display:block; width:84px; height:auto;
  border:1px solid var(--line-2); border-radius:10px; }
.order-confirmation-table .order-line .details{ min-width:0; font-size:14.5px;
  line-height:1.4; color:var(--ink); overflow-wrap:anywhere; }
/* classic nests the three money cells in their own `.row` inside `.qty`; that
   wrapper is dissolved so the cells become items of the LINE grid, which is
   what keeps them under their headings. */
.order-confirmation-table .order-line .qty{ display:contents; }
.order-confirmation-table .order-line .qty > .row{ display:contents; }
.order-confirmation-table .order-line .qty > .row > div{ float:none; width:auto; max-width:none;
  padding:0; text-align:center; font-size:14.5px; color:var(--ink); }
.order-confirmation-table .order-line .qty > .row > div.bold{ font-weight:700; color:var(--accent-deep); }

.order-confirmation-table hr{ display:none; }

/* the money table, in the summary card's rhythm */
.order-confirmation-table table{ width:100%; margin-top:4px; border-collapse:collapse; }
.order-confirmation-table table td{ padding:9px 0; font-size:14.5px; color:var(--muted);
  border:0; vertical-align:middle; }
.order-confirmation-table table td:last-child{ text-align:end; color:var(--ink); font-weight:600;
  white-space:nowrap; }
.order-confirmation-table table tr.total-value td{ background:var(--accent-soft);
  font-family:var(--font-head); color:var(--ink); font-size:16px; }
.order-confirmation-table table tr.total-value td:first-child{ padding-inline-start:12px;
  border-start-start-radius:8px; border-end-start-radius:8px; }
.order-confirmation-table table tr.total-value td:last-child{ padding-inline-end:12px;
  color:var(--accent-deep); font-size:17px;
  border-start-end-radius:8px; border-end-end-radius:8px; }
/* the taxes line is a footnote — classic wraps its two halves in their own
   spans, which is where the colour has to land or the label stays ink-dark. */
.order-confirmation-table table tr.sub.taxes td{ padding-top:9px; font-size:12.5px; font-weight:400; }
.order-confirmation-table table tr.sub.taxes td .label,
.order-confirmation-table table tr.sub.taxes td .value{ color:var(--muted); font-weight:400; }

/* order details — a list of facts, not a bulleted list */
/* The card's outer row stacks its two blocks instead of floating them. Leaving
   `#order-items` floated while `#order-details` is not put the latter's BOX at
   the top of the row — only its text was pushed down by the float — so its
   border-top drew as a stray hairline under the card's top edge. */
.page-order-confirmation .card-block > .row{ display:flex; flex-direction:column; }
/* keeps classic's 15px column padding — zeroing it would hang this block
   15px to the left of `#order-items`, which keeps its own. */
#order-details{ float:none; width:auto; max-width:none; margin-top:26px; padding-top:20px;
  border-top:1px solid var(--line); }
#order-details .card-title{ font-family:var(--font-head); font-size:17px; color:var(--ink);
  margin:0 0 10px; text-transform:none; }
#order-details ul{ margin:0; padding:0; list-style:none; }
#order-details li{ padding:7px 0; font-size:14.5px; color:var(--muted);
  border-top:1px solid var(--line-2); }
#order-details li:first-child{ border-top:0; }
#order-details li em{ color:var(--muted); font-size:13px; }

/* ---- « Vous aimerez aussi » ----
   The featured block, wrapped by the theme's own order-confirmation.tpl in the
   `.twiza-home` scope so it reuses the homepage card. Only the grid width and
   the heading are page-specific; four across, like « Sélection TWIZA ». */
.tw-ocsug{ margin-top:34px; }
.tw-ocsug__head{ margin-bottom:18px; }
.tw-ocsug__head h2{ font-family:var(--font-head); font-size:clamp(21px,2.2vw,27px);
  color:var(--ink); margin:0; }
.twiza-home.tw-ocsug .products{ grid-template-columns:repeat(4,1fr); gap:26px 22px; }
@media (max-width:1240px){ .twiza-home.tw-ocsug .products{ grid-template-columns:repeat(3,1fr); } }
@media (max-width:1080px){ .twiza-home.tw-ocsug .products{ grid-template-columns:repeat(2,1fr); } }
@media (max-width:640px){  .twiza-home.tw-ocsug .products{ grid-template-columns:1fr; } }

@media (max-width:767px){
  .page-order-confirmation .card-block{ padding:16px 1rem; }
  /* The three money cells drop to their own row under the name. classic hides
     the headings that named them below md, so the quantity — the only one of
     the three that is not obviously money — gets a « × » marker; it reads the
     same in French and Arabic, which a translated label would not. */
  #order-items > .row{ grid-template-columns:1fr; border-bottom:0; padding-bottom:0; }
  #order-items > .row > ._desktop-title{ display:none; }
  .order-confirmation-table .order-line{ grid-template-columns:64px minmax(0,1fr); gap:4px 12px; }
  .order-confirmation-table .order-line .image img{ width:64px; }
  .order-confirmation-table .order-line .details{ align-self:end; }
  .order-confirmation-table .order-line .qty{ display:block; grid-column:2; }
  .order-confirmation-table .order-line .qty > .row{ display:flex; justify-content:space-between;
    gap:10px; margin:0; }
  .order-confirmation-table .order-line .qty > .row > div{ text-align:start; font-size:13.5px; }
  .order-confirmation-table .order-line .qty > .row > div:nth-child(2)::before{
    content:"\00d7\00a0"; color:var(--muted); }
  .order-confirmation-table .order-line .qty > .row > div:last-child{ text-align:end; }
}

/* ════════════════════════════════════════════════════════════════════════
   MOTION — smooth scroll · scroll-reveal · gentle entrances
   Loaded globally, but the .tw-reveal classes are injected by custom.js only
   on .twiza-home pages (home + custom CMS pages + the coopératives landing),
   so standard shop pages stay untouched. Everything collapses to a no-op
   under prefers-reduced-motion, and reveal classes are never in the HTML —
   if JS is off, content is always fully visible.
   ════════════════════════════════════════════════════════════════════════ */
@media (prefers-reduced-motion: no-preference){
  html{ scroll-behavior:smooth; }
}

/* Offset in-page anchor jumps so the sticky header never covers the target.
   The JS smooth-scroller uses the live header height; this is the native
   fallback for reduced-motion / no-JS jumps. */
.twiza-home [id="content"],
.twiza-home section[id],
.twiza-home [id^="coop-"]{ scroll-margin-top:96px; }

/* Big layout blocks: fade + rise. */
.tw-reveal{
  opacity:0;
  transform:translateY(24px);
  transition:opacity .7s cubic-bezier(.22,.61,.36,1),
             transform .7s cubic-bezier(.22,.61,.36,1);
  will-change:opacity,transform;
}
.tw-reveal.is-in{ opacity:1; transform:none; }

/* Card-like items: a touch more lift + a subtle scale, staggered in JS. */
.tw-reveal.tw-reveal--card{ transform:translateY(30px) scale(.985); }
.tw-reveal.tw-reveal--card.is-in{ transform:none; }

@media (prefers-reduced-motion: reduce){
  html{ scroll-behavior:auto; }
  .tw-reveal,
  .tw-reveal.tw-reveal--card{
    opacity:1 !important;
    transform:none !important;
    transition:none !important;
  }
}

/* ============================================================
   TERRITOIRES — hub page (CMS id 14)  ·  .twiza-territoires
   The per-territory pages (11/12) keep their own "earth" register
   (.twiza-territory / .tp-*); this one is the editorial hub above them.
   ============================================================ */
.twiza-territoires{ --tx-ink:#241E18; --tx-sand:#FAF4EA; }
.twiza-territoires h1,.twiza-territoires h2,.twiza-territoires h3{ color:var(--tx-ink); font-family:var(--font-head); }
.twiza-territoires h1 em,.twiza-territoires h2 em{ color:var(--accent-deep); font-style:normal; }
.twiza-territoires .dia{ width:14px; height:14px; color:var(--accent); flex:none; }
.twiza-territoires .ar{ display:inline-block; transition:transform .3s var(--ease); }
.twiza-territoires .btn:hover .ar{ transform:translateX(3px); }
.twiza-territoires .btn__ic{ width:19px; height:19px; flex:none; margin-inline-end:2px; }
.twiza-territoires .btn{ display:inline-flex; align-items:center; gap:9px; }
.twiza-territoires .eyebrow{ color:var(--accent-deep); }

/* The section counter ("02", "03"…) — an outlined figure with a short rule
   under it, exactly as drawn. Decorative, so it is hidden from screen readers
   by being pure CSS content on an empty element in the markup. */
.twiza-territoires .txnum{
  font-family:var(--font-head); font-size:clamp(38px,4.6vw,58px); line-height:1;
  color:var(--cream-2); font-weight:700; margin-bottom:10px; user-select:none;
}
.twiza-territoires .txnum i{ display:block; width:34px; height:2px; border-radius:2px; background:var(--accent); margin-top:14px; }

/* ---- 1 · HÉRO ---- */
/* The hero is not a `.section`, so it does not inherit the full-bleed breakout
   at the top of this sheet — and without it the tinted band stopped at the
   bootstrap container while the header and every band below it ran edge to
   edge, leaving the hero sitting in a white frame. Same two margins, same
   scrollbar correction. */
.twiza-territoires .txhero{
  position:relative;
  margin-left:calc(50% - 50vw + var(--sbw)/2);
  margin-right:calc(50% - 50vw + var(--sbw)/2);
  /* flow-root, NOT overflow:hidden. The hero needs a block formatting context so
     the strip's negative bottom margin does not collapse through it — but
     overflow:hidden also CLIPS, and the strip is built to hang past the hero on
     purpose, so the figures were cut off in half across their labels. flow-root
     contains the margin and paints the overhang. */
  display:flow-root;
  /* One flat sand, not white→sand. The map is a photograph on a near-white
     ground, so against a graded band it always sat in a visible rectangle:
     wherever the band had darkened past the photo the seam showed. A single
     colour is the half of the fix the band can do; see the blend below. */
  background:var(--tx-sand); padding-block:clamp(34px,5vw,70px) 0;
}
.twiza-territoires .txhero__grid{ display:grid; grid-template-columns:.92fr 1.08fr; gap:clamp(24px,4vw,56px); align-items:center; }
.twiza-territoires .txhero__h1{ font-size:clamp(38px,5.6vw,72px); line-height:1.02; margin:18px 0 0; letter-spacing:-.015em; }
.twiza-territoires .txhero__rule{ display:flex; align-items:center; gap:8px; margin:24px 0 0; }
.twiza-territoires .txhero__rule i{ width:46px; height:2px; border-radius:2px; background:var(--accent); }
.twiza-territoires .txhero__rule i.o{ width:16px; }
.twiza-territoires .txhero__rule svg{ width:13px; height:13px; color:var(--accent); }
.twiza-territoires .txhero__p{ color:var(--muted); font-size:15.5px; line-height:1.78; margin:22px 0 0; max-width:470px; }
.twiza-territoires .txhero__quote{
  position:relative; margin:26px 0 0; padding-inline-start:30px; max-width:470px;
  font-family:var(--font-head); font-size:clamp(16px,1.6vw,18.5px); line-height:1.5; color:var(--tx-ink);
}
.twiza-territoires .txhero__quote::before{
  content:"“"; position:absolute; inset-inline-start:0; top:-10px;
  font-family:var(--font-head); font-size:44px; line-height:1; color:var(--accent);
}
.twiza-territoires .txhero__cta{ display:flex; flex-wrap:wrap; gap:12px; margin-top:30px; }
.twiza-territoires .txhero__media{ position:relative; }
/* `darken` and not a keyed-out PNG. The map arrives from the back office as a
   JPEG on a near-white ground (#fcf7f3), lighter than the band in all three
   channels — so taking the per-channel minimum against the band turns every
   one of those pixels into EXACTLY the band colour and leaves everything
   darker untouched. Measured on the current file: 80.9% of it becomes the
   band, 2% more is artwork bright enough to warm slightly (at most 21/255 in
   one channel — clouds, snow, the white strokes between regions).
   The point of doing it in CSS is that it keeps working when the shop
   uploads a NEW map: any ground lighter than the sand disappears by itself,
   where a hand-cut alpha channel would have to be cut again. It needs the
   flat band above — over a gradient the blend would track the gradient. */
.twiza-territoires .txhero__media img{ display:block; width:100%; height:auto; object-fit:contain; mix-blend-mode:darken; }

/* Key-figure strip — a raised card straddling the hero and the next band. */
.twiza-territoires .txstats{
  display:grid; grid-template-columns:repeat(4,1fr);
  background:#fff; border:1px solid var(--line); border-radius:var(--radius-lg);
  box-shadow:var(--shadow); padding:clamp(18px,2.2vw,26px) clamp(14px,2vw,22px);
  margin-block:clamp(22px,3vw,38px) calc(-1 * clamp(26px,3.4vw,46px)); position:relative; z-index:2;
}
.twiza-territoires .txstat{ display:flex; align-items:center; gap:14px; padding-inline:clamp(10px,1.6vw,20px); }
.twiza-territoires .txstat + .txstat{ border-inline-start:1px solid var(--line); }
.twiza-territoires .txstat__ic{ width:34px; height:34px; flex:none; color:var(--accent); }
.twiza-territoires .txstat__ic svg{ width:100%; height:100%; }
.twiza-territoires .txstat__body{ display:flex; flex-direction:column; min-width:0; }
.twiza-territoires .txstat__n{ font-family:var(--font-head); font-size:clamp(21px,2.4vw,30px); line-height:1.1; color:var(--tx-ink); }
.twiza-territoires .txstat__l{ font-size:11.5px; letter-spacing:.06em; text-transform:uppercase; color:var(--muted); line-height:1.4; margin-top:3px; }

/* ---- 2 · NOTRE OFFRE AUX TERRITOIRES ---- */
.twiza-territoires .txoffer{ padding-top:clamp(58px,7vw,104px); }
.twiza-territoires .txoffer__grid{ display:grid; grid-template-columns:.86fr 1.14fr; gap:clamp(28px,4vw,60px); align-items:center; }
.twiza-territoires .txoffer__h2{ font-size:clamp(30px,3.9vw,50px); line-height:1.07; margin:14px 0 0; }
.twiza-territoires .txoffer__p{ color:var(--muted); font-size:15px; line-height:1.76; margin:18px 0 0; max-width:430px; }
.twiza-territoires .txoffer__p b{ color:var(--accent-deep); font-weight:600; }
.twiza-territoires .txoffer__sep{ display:flex; align-items:center; gap:10px; margin:26px 0; }
.twiza-territoires .txoffer__sep i{ flex:1; height:1px; background:var(--line); }
.twiza-territoires .txoffer__sep svg{ width:12px; height:12px; color:var(--accent); flex:none; }
.twiza-territoires .txoffer__kick{ font-family:var(--font-head); font-size:clamp(17px,1.9vw,22px); line-height:1.45; text-align:center; }
.twiza-territoires .txoffer__kick b{ display:block; color:var(--tx-ink); font-weight:600; }
.twiza-territoires .txoffer__kick em{ display:block; color:var(--accent-deep); font-style:normal; margin-top:6px; }
.twiza-territoires .txoffer__cta{ margin-top:26px; }

/* Four slanted panels. The skew lives on the tile and is undone on the inner
   body so the type stays upright, which is what the mockup shows. */
.twiza-territoires .txoffer__media{ position:relative; }
/* §2 supplied as one drawn picture instead of the four panels. It already
   carries the médaillon and the labels, so it gets the panels' footprint and
   nothing on top of it — and it is never cropped: the composition is the
   content, and a fixed ratio would cut a label off. */
.twiza-territoires .txoffer__art{ padding-inline:22px; }
.twiza-territoires .txoffer__art img{ display:block; width:100%; height:auto; border-radius:6px; }
.twiza-territoires .txpanels{ display:grid; grid-template-columns:repeat(4,1fr); gap:10px; overflow:hidden; padding-inline:22px; }
.twiza-territoires .txpanel{
  position:relative; aspect-ratio:.5; min-height:340px; overflow:hidden; border-radius:6px;
  background:var(--bg) center/cover no-repeat, var(--cream-2);
  transform:skewX(-7deg); transition:transform .45s var(--ease);
}
.twiza-territoires .txpanel:hover{ transform:skewX(-7deg) translateY(-6px); }
.twiza-territoires .txpanel__ovl{ position:absolute; inset:0; background:linear-gradient(180deg,rgba(36,30,24,0) 38%,rgba(36,30,24,.82) 100%); }
.twiza-territoires .txpanel__body{
  position:absolute; inset-inline:0; bottom:0; padding:16px 12px 20px;
  display:flex; flex-direction:column; align-items:center; gap:6px; text-align:center;
  transform:skewX(7deg); color:#fff;
}
.twiza-territoires .txpanel__ic{ width:26px; height:26px; color:var(--accent); margin-bottom:4px; }
.twiza-territoires .txpanel__t{ font-size:11.5px; letter-spacing:.08em; text-transform:uppercase; font-weight:600; }
.twiza-territoires .txpanel__d{ font-size:12px; color:rgba(255,255,255,.82); line-height:1.4; }
.twiza-territoires .txoffer__badge{
  position:absolute; top:50%; inset-inline-start:50%; transform:translate(-50%,-50%);
  width:clamp(150px,15vw,196px); aspect-ratio:1; border-radius:50%;
  background:#fff; box-shadow:var(--shadow-lift); border:1px solid var(--line);
  display:grid; place-items:center; text-align:center; padding:18px;
}
body.lang-rtl .twiza-territoires .txoffer__badge{ transform:translate(50%,-50%); }
.twiza-territoires .txoffer__badge::after{ content:""; position:absolute; inset:8px; border:1px solid var(--orange-soft); border-radius:50%; }
.twiza-territoires .txoffer__badge span{ font-family:var(--font-head); font-size:clamp(13px,1.3vw,15.5px); line-height:1.5; color:var(--muted); }
.twiza-territoires .txoffer__badge b{ color:var(--accent-deep); font-weight:500; }

/* ---- 3 · LE MODÈLE D'ACTIVATION ---- */
.twiza-territoires .txact__head{ display:grid; grid-template-columns:1.25fr .75fr; gap:clamp(22px,3.4vw,52px); align-items:end; }
.twiza-territoires .txact__h2{ font-size:clamp(28px,3.7vw,47px); line-height:1.08; margin:12px 0 0; }
.twiza-territoires .txact__sub{ color:var(--muted); font-size:15px; line-height:1.7; margin:16px 0 0; max-width:520px; }
.twiza-territoires .txact__headr{ border-inline-start:2px solid var(--accent); padding-inline-start:20px; }
.twiza-territoires .txact__headr p{ color:var(--muted); font-size:13.5px; line-height:1.66; margin:0; }
.twiza-territoires .txact__note2{ margin-top:12px !important; }
.twiza-territoires .txact__headr b{ color:var(--accent-deep); font-weight:600; }

.twiza-territoires .txsteps{ --tx-step-gap:clamp(12px,1.6vw,22px); display:grid; grid-template-columns:repeat(5,1fr); gap:var(--tx-step-gap); margin:clamp(28px,3.6vw,50px) 0 0; padding:0; list-style:none; }
.twiza-territoires .txstep{ position:relative; display:flex; flex-direction:column; }
/* The dotted spine threading the five steps together. It spans the COLUMN GAP
   only — given a width relative to the step it would run the length of the next
   column and strike through its number. */
.twiza-territoires .txstep:not(:last-child)::after{
  content:""; position:absolute; top:26px; inset-inline-start:100%; width:var(--tx-step-gap); height:2px;
  background:repeating-linear-gradient(90deg,var(--accent) 0 5px,transparent 5px 11px);
}
body.lang-rtl .twiza-territoires .txstep:not(:last-child)::after{ background:repeating-linear-gradient(270deg,var(--accent) 0 5px,transparent 5px 11px); }
.twiza-territoires .txstep__top{ display:flex; align-items:center; gap:12px; }
.twiza-territoires .txstep__ic{
  width:52px; height:52px; flex:none; border-radius:50%; display:grid; place-items:center;
  background:#fff; border:1.5px solid var(--orange-soft); color:var(--accent-deep); position:relative; z-index:1;
}
.twiza-territoires .txstep__ic svg{ width:25px; height:25px; }
.twiza-territoires .txstep__n{ font-family:var(--font-head); font-size:clamp(24px,2.6vw,34px); color:var(--tx-ink); line-height:1; }
.twiza-territoires .txstep__t{ font-size:13.5px; letter-spacing:.05em; text-transform:uppercase; line-height:1.35; margin:16px 0 0; font-weight:700; }
.twiza-territoires .txstep__g{ color:var(--accent-deep); font-size:12.5px; font-style:italic; margin-top:6px; }
.twiza-territoires .txstep__d{ color:var(--muted); font-size:13px; line-height:1.62; margin:12px 0 0; }
.twiza-territoires .txstep__media{ margin-top:auto; padding-top:16px; }
.twiza-territoires .txstep__media img{ display:block; width:100%; aspect-ratio:1.16; object-fit:cover; border-radius:var(--radius-sm); }
.twiza-territoires .txchips{ display:flex; align-items:center; flex-wrap:wrap; gap:5px; margin-top:12px; }
.twiza-territoires .txchip{ font-size:10.5px; letter-spacing:.04em; text-transform:uppercase; color:var(--accent-deep); background:var(--orange-tint); border:1px solid var(--orange-soft); border-radius:99px; padding:3px 8px; }
.twiza-territoires .txchip__ar{ width:11px; height:11px; color:var(--accent); flex:none; }
body.lang-rtl .twiza-territoires .txchip__ar{ transform:scaleX(-1); }

.twiza-territoires .tximpact{ background:var(--orange-tint); border:1px solid var(--orange-soft); border-radius:var(--radius); padding:clamp(20px,2.6vw,32px); margin-top:clamp(28px,3.4vw,46px); }
.twiza-territoires .tximpact__t{ text-align:center; font-family:var(--font-head); font-size:clamp(16px,1.8vw,21px); letter-spacing:.04em; text-transform:uppercase; color:var(--tx-ink); margin-bottom:22px; }
.twiza-territoires .tximpact__grid{ display:grid; grid-template-columns:repeat(5,1fr); gap:clamp(10px,1.4vw,18px); }
.twiza-territoires .tximpact__i{ display:flex; align-items:flex-start; gap:12px; padding-inline:clamp(8px,1.2vw,16px); }
.twiza-territoires .tximpact__i + .tximpact__i{ border-inline-start:1px solid var(--orange-soft); }
.twiza-territoires .tximpact__ic{ width:44px; height:44px; flex:none; border-radius:50%; background:#fff; border:1px solid var(--orange-soft); display:grid; place-items:center; color:var(--accent-deep); }
.twiza-territoires .tximpact__ic svg{ width:22px; height:22px; }
.twiza-territoires .tximpact__b{ display:flex; flex-direction:column; gap:4px; }
.twiza-territoires .tximpact__b b{ font-size:12.5px; letter-spacing:.03em; text-transform:uppercase; color:var(--tx-ink); line-height:1.35; }
.twiza-territoires .tximpact__b span{ font-size:12px; color:var(--muted); line-height:1.45; }

.twiza-territoires .txquote{ display:flex; align-items:center; justify-content:center; gap:16px; margin:clamp(26px,3.2vw,44px) auto 0; max-width:900px; text-align:center; }
.twiza-territoires .txquote__m{ width:34px; height:34px; color:var(--accent); flex:none; }
.twiza-territoires .txquote p{ font-family:var(--font-head); font-size:clamp(18px,2.2vw,27px); line-height:1.36; color:var(--tx-ink); margin:0; }
.twiza-territoires .txquote em{ color:var(--accent-deep); font-style:normal; }

/* ---- 4 · DES TERRITOIRES QUI NOUS FONT CONFIANCE ---- */
.twiza-territoires .txtrust__head{ display:grid; grid-template-columns:1.3fr .7fr; gap:clamp(22px,3.4vw,56px); align-items:center; }
.twiza-territoires .txtrust__h2{ font-size:clamp(30px,4vw,52px); line-height:1.06; margin:0 0 18px; }
.twiza-territoires .txtrust__headl p{ color:var(--muted); font-size:14.5px; line-height:1.74; margin:0 0 10px; max-width:560px; }
.twiza-territoires .txtrust__quote{
  position:relative; margin:0; padding-inline-start:32px;
  font-family:var(--font-head); font-size:clamp(17px,1.9vw,22px); line-height:1.42; color:var(--tx-ink);
}
.twiza-territoires .txtrust__quote::before{ content:"“"; position:absolute; inset-inline-start:0; top:-14px; font-family:var(--font-head); font-size:52px; line-height:1; color:var(--accent); }
.twiza-territoires .txtrust__quote i{ display:block; width:120px; height:3px; border-radius:3px; background:var(--accent); margin-top:12px; }

.twiza-territoires .txcards{ display:grid; grid-template-columns:repeat(3,1fr); gap:clamp(16px,2vw,26px); margin-top:clamp(26px,3.2vw,44px); }
.twiza-territoires .txcard{
  display:flex; flex-direction:column; background:#fff; border:1px solid var(--line);
  border-radius:var(--radius); overflow:hidden; text-decoration:none; color:inherit;
  transition:transform .4s var(--ease), box-shadow .4s var(--ease), border-color .4s var(--ease);
}
.twiza-territoires a.txcard:hover{ transform:translateY(-6px); box-shadow:var(--shadow-lift); border-color:var(--orange-soft); }
.twiza-territoires .txcard__media{ display:block; aspect-ratio:1.62; overflow:hidden; background:var(--cream-2); }
.twiza-territoires .txcard__media img{ display:block; width:100%; height:100%; object-fit:cover; transition:transform .6s var(--ease); }
.twiza-territoires a.txcard:hover .txcard__media img{ transform:scale(1.05); }
.twiza-territoires .txcard__pat{ display:grid; place-items:center; width:100%; height:100%; background:#3B322A; color:rgba(255,255,255,.5); }
.twiza-territoires .txcard__pat svg{ width:78px; height:78px; }
.twiza-territoires .txcard__body{ display:flex; flex-direction:column; gap:8px; padding:clamp(16px,2vw,22px); }
.twiza-territoires .txcard__h{ display:flex; align-items:center; gap:10px; }
.twiza-territoires .txcard__ic{ width:24px; height:24px; color:var(--accent); flex:none; }
.twiza-territoires .txcard__t{ font-family:var(--font-head); font-size:clamp(19px,2.1vw,25px); letter-spacing:.02em; text-transform:uppercase; color:var(--tx-ink); }
.twiza-territoires .txcard__tags{ display:flex; flex-wrap:wrap; align-items:center; gap:6px; font-size:12.5px; color:var(--muted); }
.twiza-territoires .txcard__tags span + span::before{ content:"·"; color:var(--accent); margin-inline-end:6px; }
.twiza-territoires .txcard__d{ color:var(--muted); font-size:13.5px; line-height:1.62; }
.twiza-territoires .txcard__cta{ margin-top:6px; font-size:12.5px; letter-spacing:.05em; text-transform:uppercase; color:var(--accent-deep); font-weight:600; }
.twiza-territoires .txcard__cta.is-soon{ color:var(--muted); }
.twiza-territoires .txcard--soon{ background:var(--tx-sand); }
.twiza-territoires .txtrust__foot{ margin-top:clamp(24px,3vw,40px); display:flex; flex-direction:column; align-items:center; }
.twiza-territoires .txtrust__foot .txoffer__sep{ width:min(420px,100%); }

/* ---- 5 · LA MARKETPLACE DES TERRITOIRES ---- */
/* the homepage links straight here (#marketplace), so the section clears the
   fixed header the same way its rails do */
.twiza-territoires .txmk{ scroll-margin-top:calc(var(--tw-header-h) + 16px); }
.twiza-territoires .txmk__h2{ font-size:clamp(30px,4vw,52px); line-height:1.06; margin:12px 0 0; }
.twiza-territoires .txmk__p{ color:var(--muted); font-size:14.5px; line-height:1.74; margin:16px 0 0; max-width:620px; }
.twiza-territoires .txchipbar{ display:flex; flex-wrap:wrap; align-items:center; gap:8px; margin-top:clamp(20px,2.4vw,30px); }
.twiza-territoires .txchipbar__all{ background:var(--accent); color:#fff; border-radius:99px; padding:7px 16px; font-size:12.5px; font-weight:600; }
.twiza-territoires .txchipbar__c{ background:#fff; border:1px solid var(--line); color:var(--muted); border-radius:99px; padding:7px 16px; font-size:12.5px; text-decoration:none; transition:color .3s var(--ease), border-color .3s var(--ease); }
.twiza-territoires .txchipbar__c:hover{ color:var(--accent-deep); border-color:var(--accent); }

.twiza-territoires .txrail{ background:#fff; border:1px solid var(--line); border-radius:var(--radius); padding:clamp(16px,2vw,24px); margin-top:clamp(18px,2.2vw,28px); scroll-margin-top:calc(var(--tw-header-h) + 16px); }
.twiza-territoires .txrail__head{ display:flex; align-items:center; gap:14px; flex-wrap:wrap; padding-bottom:14px; border-bottom:1px solid var(--line-2); }
.twiza-territoires .txrail__ic{ width:44px; height:44px; flex:none; border-radius:12px; background:var(--orange-tint); border:1px solid var(--orange-soft); display:grid; place-items:center; color:var(--accent); }
.twiza-territoires .txrail__ic svg{ width:24px; height:24px; }
.twiza-territoires .txrail__body{ flex:1 1 240px; min-width:0; }
.twiza-territoires .txrail__t{ font-size:clamp(19px,2.1vw,25px); letter-spacing:.02em; text-transform:uppercase; margin:0; }
.twiza-territoires .txrail__d{ color:var(--muted); font-size:13px; line-height:1.55; margin:4px 0 0; }
.twiza-territoires .txrail__all{ font-size:12.5px; letter-spacing:.04em; text-transform:uppercase; color:var(--accent-deep); font-weight:600; text-decoration:none; }
.twiza-territoires .txrail__all:hover{ text-decoration:underline; }
/* the shared .usel rail carries its own label column; inside a txrail the head
   above already names the territory, so the column is dropped and the track
   takes the full width */
.twiza-territoires .txrail .usel__row{ grid-template-columns:1fr; }
.twiza-territoires .txrail .usel__label{ display:none; }
.twiza-territoires .txrail .usel{ margin-top:4px; }

/* ---- 6 · LES COOPÉRATIVES ---- */
.twiza-territoires .txco__h2{ font-size:clamp(28px,3.7vw,48px); line-height:1.07; margin:12px 0 0; max-width:920px; }
.twiza-territoires .txco__p{ color:var(--muted); font-size:14.5px; line-height:1.74; margin:16px 0 0; max-width:620px; }
.twiza-territoires .txco__grid{ display:grid; grid-template-columns:repeat(4,1fr); gap:clamp(14px,1.8vw,22px); margin-top:clamp(24px,3vw,38px); }
.twiza-territoires .txcoop{ display:flex; flex-direction:column; background:#fff; border:1px solid var(--line); border-radius:var(--radius); overflow:hidden; text-decoration:none; color:inherit; transition:transform .4s var(--ease), box-shadow .4s var(--ease); }
.twiza-territoires .txcoop:hover{ transform:translateY(-5px); box-shadow:var(--shadow-lift); }
/* contain, for the same reason as .ccoop-card__media: these are the same
   cooperative files, and most of them are logos. */
.twiza-territoires .txcoop__media{ position:relative; display:block; aspect-ratio:1.28; overflow:hidden; background:var(--cream-2); }
.twiza-territoires .txcoop__media img{ display:block; width:100%; height:100%; object-fit:contain; padding:12px; transition:transform .6s var(--ease); }
.twiza-territoires .txcoop:hover .txcoop__media img{ transform:scale(1.05); }
.twiza-territoires .txcoop__badge{
  position:absolute; top:10px; inset-inline-start:10px; display:inline-flex; align-items:center; gap:5px;
  background:rgba(255,255,255,.94); border-radius:99px; padding:4px 10px 4px 6px;
  font-size:10px; letter-spacing:.05em; text-transform:uppercase; font-weight:700; color:var(--green-deep);
}
.twiza-territoires .txcoop__badge svg{ width:15px; height:15px; flex:none; }
.twiza-territoires .txcoop__body{ display:flex; flex-direction:column; gap:7px; padding:clamp(13px,1.6vw,17px); }
.twiza-territoires .txcoop__t{ font-family:var(--font-head); font-size:16.5px; line-height:1.3; color:var(--tx-ink); }
.twiza-territoires .txcoop__terr{ display:inline-flex; align-items:center; gap:5px; font-size:12px; color:var(--muted); }
.twiza-territoires .txcoop__terr svg{ width:14px; height:14px; color:var(--accent); flex:none; }
.twiza-territoires .txcoop__d{ color:var(--muted); font-size:12.5px; line-height:1.6; }
/* names and excerpts differ in length, so the link is pushed to the foot of the
   card and the row of links reads as one line */
.twiza-territoires .txcoop__cta{ margin-top:auto; padding-top:8px; font-size:11.5px; letter-spacing:.05em; text-transform:uppercase; color:var(--accent-deep); font-weight:600; }
.twiza-territoires .txco__foot{ display:flex; justify-content:center; margin-top:clamp(22px,2.8vw,36px); }

/* ---- 7 · ET SI LA PROCHAINE HISTOIRE ÉTAIT LA VÔTRE ---- */
/* Not a `.section` either — same breakout as the hero, for the same reason. */
.twiza-territoires .txfinal{
  position:relative;
  margin-left:calc(50% - 50vw + var(--sbw)/2);
  margin-right:calc(50% - 50vw + var(--sbw)/2);
  background:var(--tx-sand); padding-block:0 clamp(30px,4vw,52px);
}
.twiza-territoires .txfinal__grid{ display:grid; grid-template-columns:.86fr 1.14fr; align-items:stretch; }
.twiza-territoires .txfinal__media{ position:relative; min-height:clamp(360px,44vw,620px); }
.twiza-territoires .txfinal__media img{ position:absolute; inset:0; width:100%; height:100%; object-fit:cover; }
.twiza-territoires .txfinal__flag{
  position:absolute; top:0; inset-inline-start:clamp(16px,3vw,42px); z-index:1;
  background:#2E4636; color:#fff; padding:16px 18px 24px; text-align:center;
  display:flex; flex-direction:column; align-items:center; gap:8px;
  clip-path:polygon(0 0,100% 0,100% 100%,50% 86%,0 100%);
}
.twiza-territoires .txfinal__flag svg{ width:30px; height:30px; color:rgba(255,255,255,.9); }
.twiza-territoires .txfinal__flag span{ font-family:var(--font-head); font-size:14px; line-height:1.45; }
.twiza-territoires .txfinal__text{ padding:clamp(30px,4vw,64px) var(--gutter); display:flex; flex-direction:column; justify-content:center; }
.twiza-territoires .txfinal__h2{ font-size:clamp(26px,3.4vw,44px); line-height:1.1; letter-spacing:.01em; text-transform:uppercase; margin:0; max-width:760px; }
.twiza-territoires .txfinal__sub{ font-family:var(--font-head); font-size:clamp(18px,2.1vw,26px); color:var(--accent-deep); margin:14px 0 0; }
.twiza-territoires .txfinal__text .txoffer__sep{ max-width:520px; }
.twiza-territoires .txfinal__p{ color:var(--muted); font-size:14.5px; line-height:1.78; margin:0 0 14px; max-width:560px; }
.twiza-territoires .txfinal__p b{ color:var(--tx-ink); font-weight:700; }
.twiza-territoires .txfinal__cards{ display:grid; grid-template-columns:repeat(3,1fr); gap:0; background:#fff; border:1px solid var(--line); border-radius:var(--radius); margin-top:12px; }
.twiza-territoires .txfcard{ display:flex; flex-direction:column; gap:7px; padding:clamp(15px,1.8vw,20px); }
.twiza-territoires .txfcard + .txfcard{ border-inline-start:1px solid var(--line); }
.twiza-territoires .txfcard__ic{ width:40px; height:40px; border-radius:50%; border:1px solid var(--orange-soft); background:var(--orange-tint); display:grid; place-items:center; color:var(--accent-deep); }
.twiza-territoires .txfcard__ic svg{ width:21px; height:21px; }
.twiza-territoires .txfcard__t{ font-size:12px; letter-spacing:.05em; text-transform:uppercase; color:var(--tx-ink); line-height:1.35; }
.twiza-territoires .txfcard__d{ font-size:12.5px; color:var(--muted); line-height:1.55; }
.twiza-territoires .txfinal__cta{ display:flex; flex-wrap:wrap; gap:12px; margin-top:20px; }
.twiza-territoires .txinst{ display:flex; align-items:center; gap:16px; background:#fff; border:1px solid var(--line); border-radius:var(--radius); padding:clamp(14px,1.8vw,20px); margin-top:18px; }
.twiza-territoires .txinst__ic{ width:38px; height:38px; flex:none; color:var(--green-deep); }
.twiza-territoires .txinst__ic svg{ width:100%; height:100%; }
.twiza-territoires .txinst__b{ display:flex; flex-direction:column; gap:4px; }
.twiza-territoires .txinst__b b{ font-size:13.5px; color:var(--tx-ink); }
.twiza-territoires .txinst__b span{ font-size:12.5px; color:var(--muted); line-height:1.6; }
.twiza-territoires .txinst__b b + span b{ color:var(--accent-deep); }

.twiza-territoires .txreassure{ display:grid; grid-template-columns:repeat(5,1fr); gap:clamp(10px,1.4vw,18px); margin-top:clamp(26px,3.4vw,46px); padding-top:clamp(20px,2.6vw,30px); border-top:1px solid var(--line); }
.twiza-territoires .txreassure__i{ display:flex; align-items:flex-start; gap:11px; padding-inline:clamp(6px,1vw,14px); }
.twiza-territoires .txreassure__i + .txreassure__i{ border-inline-start:1px solid var(--line); }
.twiza-territoires .txreassure__ic{ width:30px; height:30px; flex:none; color:var(--accent-deep); }
.twiza-territoires .txreassure__ic svg{ width:100%; height:100%; }
.twiza-territoires .txreassure__b{ display:flex; flex-direction:column; gap:3px; }
.twiza-territoires .txreassure__b b{ font-size:11.5px; letter-spacing:.05em; text-transform:uppercase; color:var(--tx-ink); line-height:1.35; }
.twiza-territoires .txreassure__b span{ font-size:12px; color:var(--muted); line-height:1.5; }

/* ---- responsive ---- */
@media (max-width:1080px){
  .twiza-territoires .txsteps{ grid-template-columns:repeat(3,1fr); row-gap:26px; }
  .twiza-territoires .txstep:not(:last-child)::after{ display:none; }
  .twiza-territoires .tximpact__grid{ grid-template-columns:repeat(3,1fr); row-gap:18px; }
  .twiza-territoires .tximpact__i:nth-child(3n+1){ border-inline-start:0; }
  .twiza-territoires .txco__grid{ grid-template-columns:repeat(3,1fr); }
  .twiza-territoires .txreassure{ grid-template-columns:repeat(3,1fr); row-gap:18px; }
  .twiza-territoires .txreassure__i:nth-child(3n+1){ border-inline-start:0; }
}
@media (max-width:860px){
  .twiza-territoires .txhero__grid,
  .twiza-territoires .txoffer__grid,
  .twiza-territoires .txact__head,
  .twiza-territoires .txtrust__head,
  .twiza-territoires .txfinal__grid{ grid-template-columns:1fr; }
  .twiza-territoires .txhero__media{ order:-1; }
  .twiza-territoires .txact__headr{ border-inline-start:0; border-top:2px solid var(--accent); padding-inline-start:0; padding-top:16px; }
  .twiza-territoires .txstats{ grid-template-columns:repeat(2,1fr); row-gap:18px; }
  .twiza-territoires .txstat:nth-child(odd){ border-inline-start:0; }
  .twiza-territoires .txcards{ grid-template-columns:1fr; }
  .twiza-territoires .txco__grid{ grid-template-columns:repeat(2,1fr); }
  .twiza-territoires .txpanel{ min-height:250px; }
  .twiza-territoires .txfinal__media{ min-height:300px; }
  .twiza-territoires .txfinal__text{ padding-inline:var(--gutter); }
}
@media (max-width:560px){
  .twiza-territoires .txsteps{ grid-template-columns:1fr; }
  .twiza-territoires .tximpact__grid,
  .twiza-territoires .txreassure{ grid-template-columns:1fr; }
  .twiza-territoires .tximpact__i,
  .twiza-territoires .txreassure__i{ border-inline-start:0 !important; }
  .twiza-territoires .txco__grid{ grid-template-columns:1fr; }
  .twiza-territoires .txfinal__cards{ grid-template-columns:1fr; }
  .twiza-territoires .txfcard + .txfcard{ border-inline-start:0; border-top:1px solid var(--line); }
  .twiza-territoires .txhero__cta .btn,
  .twiza-territoires .txfinal__cta .btn{ width:100%; justify-content:center; }
  /* the four skewed panels stop being a composition at this width */
  .twiza-territoires .txpanels{ grid-template-columns:repeat(2,1fr); padding-inline:0; }
  .twiza-territoires .txoffer__art{ padding-inline:0; }
  .twiza-territoires .txpanel{ transform:none; min-height:190px; }
  .twiza-territoires .txpanel:hover{ transform:translateY(-4px); }
  .twiza-territoires .txpanel__body{ transform:none; }
  /* stays `relative`, never `static`: the inner ring is an ::after pinned to it,
     and un-positioning the badge would stretch that ring over the whole grid */
  .twiza-territoires .txoffer__badge{ position:relative; top:auto; inset-inline-start:auto; transform:none; width:150px; margin:18px auto 0; }
  body.lang-rtl .twiza-territoires .txoffer__badge{ transform:none; }
}

/* ---- RTL ---- */
body.lang-rtl .twiza-territoires .ar{ transform:scaleX(-1); }
body.lang-rtl .twiza-territoires .btn:hover .ar{ transform:scaleX(-1) translateX(3px); }
/* the slant is a direction, so it mirrors with the text */
body.lang-rtl .twiza-territoires .txpanel{ transform:skewX(7deg); }
body.lang-rtl .twiza-territoires .txpanel:hover{ transform:skewX(7deg) translateY(-6px); }
body.lang-rtl .twiza-territoires .txpanel__body{ transform:skewX(-7deg); }
body.lang-rtl .twiza-territoires .txhero__quote::before,
body.lang-rtl .twiza-territoires .txtrust__quote::before{ content:"”"; }

/* ============================================================
   FAVORIS — the header drawer and the heart that fills it
   The 13 August UX report: the heart must not navigate. This is what
   opens instead, over whatever page the shopper is on.
   ============================================================ */

/* ---- the header heart's counter ---- */
.tw-iconbtn--fav{ position:relative; }
.tw-iconbtn__badge{
  position:absolute; top:-3px; inset-inline-end:-4px; min-width:17px; height:17px; padding:0 4px;
  display:flex; align-items:center; justify-content:center;
  background:var(--accent); color:#fff; border-radius:100px;
  font-size:10.5px; font-weight:700; line-height:1; font-family:var(--font-body);
  /* the badge is a count, not a target: it must never eat the heart's click */
  pointer-events:none;
}
.tw-iconbtn__badge[hidden]{ display:none; }

/* ---- shell ----
   Above landingpagecod's pinned chrome, which sits at 10030, and above the
   cart dialog's own backdrop so a favourite added from the cart page is not
   opened underneath it. */
.tw-fav{ position:fixed; inset:0; z-index:10060; }
.tw-fav[hidden]{ display:none; }
.tw-fav__backdrop{
  position:absolute; inset:0; background:rgba(43,37,30,.44);
  opacity:0; transition:opacity .24s var(--ease);
}
.tw-fav.is-open .tw-fav__backdrop{ opacity:1; }

.tw-fav__panel{
  position:absolute; inset-block:0; inset-inline-end:0;
  width:min(420px, 100%); display:flex; flex-direction:column;
  background:var(--white); box-shadow:-18px 0 44px -26px rgba(43,37,30,.5);
  /* translate along the inline axis so the panel leaves by the edge it
     entered from — in Arabic that is the left one */
  transform:translateX(100%); transition:transform .26s var(--ease);
}
body.lang-rtl .tw-fav__panel{ transform:translateX(-100%); }
.tw-fav.is-open .tw-fav__panel,
body.lang-rtl .tw-fav.is-open .tw-fav__panel{ transform:translateX(0); }

@media (prefers-reduced-motion: reduce){
  .tw-fav__backdrop, .tw-fav__panel{ transition:none; }
}

/* ---- head ----
   Cream, like the account page's RGPD row: the drawer opens over whatever the
   shopper was reading, and a white head on a white body gave it no edge. */
.tw-fav__head{
  flex:0 0 auto; display:flex; align-items:center; justify-content:space-between; gap:12px;
  padding:18px 20px; background:var(--cream); border-bottom:1px solid var(--line);
}
.tw-fav__title{
  margin:0; display:flex; align-items:center; gap:9px;
  font-family:var(--font-head); font-size:21px; font-weight:700; color:var(--ink);
}
.tw-fav__count{
  min-width:24px; height:24px; padding:0 7px; display:inline-flex; align-items:center; justify-content:center;
  background:var(--accent); color:#fff; border-radius:100px;
  font-family:var(--font-body); font-size:12px; font-weight:700;
}
.tw-fav__count[hidden]{ display:none; }
/* the 42px circle every other icon button in the header is */
.tw-fav__close{
  flex:0 0 auto; width:42px; height:42px; display:flex; align-items:center; justify-content:center;
  background:transparent; border:0; border-radius:50%; color:var(--ink); cursor:pointer;
  transition:background .2s ease, color .2s ease;
}
.tw-fav__close svg{ width:19px; height:19px; }
.tw-fav__close:hover,
.tw-fav__close:focus-visible{ background:var(--accent-soft); color:var(--accent-deep); }

/* ---- body ---- */
.tw-fav__body{ flex:1 1 auto; overflow-y:auto; -webkit-overflow-scrolling:touch; padding:6px 0 18px; }
.tw-fav__loading{ margin:0; padding:26px 20px; color:var(--muted); font-size:14px; text-align:center; }

/* ---- the two empty states (guest, and nothing saved yet) ---- */
.tw-fav__state{ padding:44px 26px; text-align:center; }
/* the halo the account pages' empty state uses, at drawer scale */
.tw-fav__state-icon{
  width:88px; height:88px; margin:0 auto 20px; display:flex; align-items:center; justify-content:center;
  background:var(--orange-tint); border-radius:50%; color:var(--accent);
}
.tw-fav__state-icon svg{ width:38px; height:38px; }
.tw-fav__state-h{
  margin:0 0 8px; font-family:var(--font-head); font-size:20px; font-weight:700; line-height:1.25; color:var(--ink);
}
.tw-fav__state-p{ margin:0 auto 22px; max-width:34ch; font-size:14px; line-height:1.65; color:var(--muted); }

/* ⚠ WHERE THE DRAWER ACTUALLY LIVES, AND WHY EVERY LINK IN IT NEEDS #tw-fav.
   _partials/header.tpl prints the drawer INSIDE `<header id="header">`, before
   #wrapper. Two consequences, and the old code had both of them backwards:

   · `#main .tw-fav__…` — how every hover here used to be written — can never
     match, because the drawer is not inside #main. All four rules were dead:
     the buttons, the product name and « Ajouter au panier » had no hover at
     all. Do not put #main back.
   · classic's `#header a{color:#232323}` and `#header a:hover{color:#24b9d7}`
     DO match, and at (1,0,1)/(1,0,2) they beat anything built from classes.
     Measured before this was scoped: the product name rested in classic's ink
     and turned CYAN under the pointer, and « Se connecter » — white text on
     the orange pill — came out dark.

   So every rule below that colours an ANCHOR carries #tw-fav, which is on the
   drawer's own root: (1,1,0) and (1,1,1) clear both. Rules on <button> and on
   non-anchors are left as classes; #header only reaches them by inheritance,
   which any explicit declaration outranks. */
#tw-fav .tw-fav__btn{
  display:block; width:100%; margin-top:9px; padding:12px 18px; border-radius:100px;
  border:1px solid var(--line); background:var(--white); color:var(--ink);
  font-size:14.5px; font-weight:600; text-align:center; text-decoration:none;
  transition:background .2s var(--ease), border-color .2s var(--ease), color .2s var(--ease), transform .2s var(--ease);
}
#tw-fav .tw-fav__btn:hover,
#tw-fav .tw-fav__btn:focus-visible{ background:var(--orange-tint); border-color:var(--accent); color:var(--accent-deep); text-decoration:none; }
#tw-fav .tw-fav__btn--solid{ background:var(--accent); border-color:var(--accent); color:#fff; }
#tw-fav .tw-fav__btn--solid:hover,
#tw-fav .tw-fav__btn--solid:focus-visible{ background:var(--accent-deep); border-color:var(--accent-deep); color:#fff; transform:translateY(-2px); }

/* ---- one saved piece ---- */
.tw-fav__list{ margin:0; padding:0; list-style:none; }
.tw-fav__row{
  display:grid; grid-template-columns:74px 1fr 32px; align-items:start; gap:13px;
  padding:15px 20px; transition:background .2s ease;
}
.tw-fav__row + .tw-fav__row{ border-top:1px solid var(--line-2); }
.tw-fav__row:hover{ background:var(--cream); }
.tw-fav__row.is-going{ opacity:.4; }

.tw-fav__thumb{ display:block; border-radius:var(--radius-sm); overflow:hidden; background:var(--cream); }
/* the same slow push-in every product photograph in this theme answers a hover with */
.tw-fav__thumb img{ display:block; width:100%; height:auto; aspect-ratio:1; object-fit:cover;
  transition:transform .6s var(--ease); }
.tw-fav__row:hover .tw-fav__thumb img{ transform:scale(1.06); }

.tw-fav__col{ min-width:0; }
/* Playfair, like the product name in the cart preview and on every card —
   this line was the drawer's loudest tell that it was not part of the theme. */
#tw-fav .tw-fav__name{
  display:block; font-family:var(--font-head); color:var(--ink); font-size:15px; font-weight:600;
  line-height:1.3; text-decoration:none; transition:color .2s ease;
}
#tw-fav .tw-fav__name:hover,
#tw-fav .tw-fav__name:focus-visible{ color:var(--accent-deep); text-decoration:none; }
.tw-fav__coop{ display:block; margin-top:3px; font-size:12px; color:var(--muted); }
.tw-fav__price{
  display:block; margin-top:5px; font-size:14.5px; font-weight:700; color:var(--accent-deep);
}
.tw-fav__price del{ margin-inline-end:5px; font-weight:500; font-size:12.5px; color:var(--muted); }

.tw-fav__addform{ margin:9px 0 0; }
/* a <button> when the piece can be added, an <a> (« Voir la pièce ») when it
   cannot — so this one is scoped too, or the anchor form loses its colour */
#tw-fav .tw-fav__add{
  display:inline-block; padding:7px 15px; border:1px solid var(--accent-soft); border-radius:100px;
  background:var(--accent-soft); color:var(--accent-deep);
  font-family:var(--font-body); font-size:13px; font-weight:700; cursor:pointer; text-decoration:none;
  transition:background .2s ease, border-color .2s ease, color .2s ease;
}
#tw-fav .tw-fav__add:hover,
#tw-fav .tw-fav__add:focus-visible{ background:var(--accent); border-color:var(--accent); color:#fff; text-decoration:none; }

/* the bordered circle the cart preview's own « Retirer » is */
.tw-fav__remove{
  width:30px; height:30px; display:flex; align-items:center; justify-content:center;
  background:var(--white); border:1px solid var(--line); border-radius:50%; color:var(--muted); cursor:pointer;
  transition:background .2s ease, border-color .2s ease, color .2s ease;
}
.tw-fav__remove svg{ width:13px; height:13px; }
.tw-fav__remove:hover,
.tw-fav__remove:focus-visible{ background:var(--accent-soft); border-color:var(--accent); color:var(--accent-deep); }

/* ---- a heart mid-request ---- */
.wish.is-busy, .tw-fav__remove.is-busy{ opacity:.5; pointer-events:none; }

/* ============================================================
   ADD-TO-CART TOAST
   The short confirmation the 13 August Marketplace brief asks for, in place of
   classic's page-sized blockcart modal (see cartToast() in custom.4.js).
   It sits above the favourites drawer's z-index on purpose: adding from the
   drawer must confirm on top of it, not behind it.
   ============================================================ */
.tw-toast{
  /* 10070 = one above the favourites drawer's 10060 */
  position:fixed; z-index:10070; inset-block-end:22px; inset-inline-end:22px;
  display:flex; align-items:center; gap:12px; width:min(360px, calc(100vw - 32px));
  padding:12px 14px; background:#fff; border:1px solid var(--line);
  border-radius:var(--radius); box-shadow:0 18px 40px -18px rgba(43,37,30,.45);
  /* Off-screen and inert until opened, so it can never eat a click on the page
     behind it — `visibility` is what removes it from hit-testing; opacity alone
     would leave an invisible 360px target parked over the corner. */
  visibility:hidden; opacity:0; transform:translateY(12px);
  transition:opacity .22s ease, transform .22s var(--ease), visibility 0s linear .22s;
}
.tw-toast.is-open{ visibility:visible; opacity:1; transform:translateY(0); transition-delay:0s; }
.tw-toast__img{ flex:none; width:46px; height:46px; object-fit:cover; border-radius:var(--radius-sm); background:var(--cream); }
.tw-toast__txt{ min-width:0; flex:1 1 auto; }
.tw-toast__title{ display:block; font-size:14px; font-weight:700; color:var(--green); }
.tw-toast__name{ display:block; font-size:12.5px; color:var(--muted); line-height:1.35;
  /* one line, then an ellipsis — a long artisan product name would otherwise
     make the toast three lines tall and change the layout every add */
  overflow:hidden; text-overflow:ellipsis; white-space:nowrap; }
.tw-toast__cta{ flex:none; font-size:12.5px; font-weight:700; color:var(--accent-deep);
  text-decoration:none; white-space:nowrap; }
.tw-toast__cta:hover{ text-decoration:underline; }
.tw-toast__close{ flex:none; width:24px; height:24px; padding:0; border:0; background:transparent;
  color:var(--muted); font-size:19px; line-height:1; cursor:pointer; }
.tw-toast__close:hover{ color:var(--ink); }
@media (max-width:560px){
  .tw-toast{ inset-inline:16px; inset-block-end:16px; width:auto; }
}
@media (prefers-reduced-motion:reduce){
  .tw-toast{ transition:opacity .01s linear, visibility 0s; transform:none; }
}

/* ============================================================
   MARKETPLACE listing — brief « Améliorations design de la Marketplace »
   pt.2 (filter panel), pt.3 (duplicate nav removed via an empty
   ps_categorytree override) and pt.5 (product control bar).
   ============================================================ */

/* ---- pt.5 · control bar: count · sort · Afficher les filtres ---- */
#js-product-list-top.tw-ctrlbar{ display:flex; align-items:center; justify-content:space-between;
  flex-wrap:wrap; gap:12px 18px; margin:0 0 1.15rem; padding:0 0 .95rem;
  border-bottom:1px solid var(--line); }
.tw-ctrlbar__count{ display:flex; align-items:center; gap:9px; color:var(--ink);
  font-size:14.5px; font-weight:600; }
.tw-ctrlbar__ico{ width:17px; height:17px; flex:none; color:var(--muted); }
.tw-ctrlbar__tools{ display:flex; align-items:center; gap:12px; flex-wrap:wrap; margin-inline-start:auto; }
/* classic prints the sort control inside .products-sort-order wrapped in bootstrap
   columns — unwrap it so it sits on our flex row without a stray 100% width */
.tw-ctrlbar .products-sort-order{ padding:0; margin:0; width:auto; max-width:none; flex:0 0 auto; }
.tw-ctrlbar .products-sort-order .select-title{ display:inline-flex; align-items:center; gap:8px;
  background:#fff; border:1px solid var(--line); border-radius:100px; padding:9px 14px;
  color:var(--ink); font-size:14px; box-shadow:none; min-width:0; }
.tw-ctrlbar .products-sort-order .select-title:hover{ border-color:var(--accent); }
/* THE OPEN STATE was never dressed. Only the closed pill had been: click it and
   bootstrap's own panel came up on classic's #f6f6f6 ground with #232323 text,
   16px rows, no hover, and — worst of the four — nothing at all to say which
   line is the sort currently applied, on a menu whose whole job is to answer
   that. Scoped to .products-sort-order rather than the control bar, because the
   same control opens on search results and on the new-products listing.
   The current row is marked with weight and a tint, not an icon: a tick or a
   chevron would have to be mirrored for Arabic and would sit on the wrong side
   of a label that already reads from the other edge. */
.products-sort-order.dropdown .dropdown-menu{
  margin-top:8px; padding:6px; min-width:244px;
  background:#fff; border:1px solid var(--line); border-radius:16px;
  box-shadow:0 18px 40px -22px rgba(43,37,30,.34); }
.products-sort-order.dropdown .dropdown-menu .select-list{
  display:block; padding:9px 14px; border-radius:11px; text-align:start;
  color:var(--ink); font-size:14.5px; line-height:1.35; text-decoration:none;
  transition:background .2s var(--ease), color .2s var(--ease); }
.products-sort-order.dropdown .dropdown-menu .select-list:hover,
.products-sort-order.dropdown .dropdown-menu .select-list:focus{
  background:var(--orange-tint); color:var(--accent-deep); text-decoration:none; }
.products-sort-order.dropdown .dropdown-menu .select-list.current{
  background:var(--line-2); color:var(--ink); font-weight:600; }
.tw-ctrlbar__filters{ display:inline-flex; align-items:center; gap:8px;
  background:#fff; border:1px solid var(--line); border-radius:100px; padding:9px 16px;
  color:var(--ink); font-size:14px; font-weight:600; line-height:1; cursor:pointer;
  box-shadow:none; text-transform:none; letter-spacing:0;
  transition:border-color .25s var(--ease), background .25s var(--ease), color .25s var(--ease); }
.tw-ctrlbar__filters:hover,.tw-ctrlbar__filters:focus{ border-color:var(--accent); background:var(--orange-tint); color:var(--accent-deep); }
.tw-ctrlbar__filters .tw-ctrlbar__ico{ color:currentColor; }
.tw-ctrlbar__showing{ flex:1 0 100%; color:var(--muted); font-size:13px; text-align:center; }

/* From 768px up — classic's own drawer owns everything below, so this is
   exactly where our collapse takes over. The button hides the sidebar and the
   gallery runs the full width. */
@media (min-width:768px){
  body.tw-filters-off #left-column{ display:none; }
  body.tw-filters-off #content-wrapper{ flex:0 0 100%; max-width:100%; }
}

/* ---- pt.2 · filter panel: compact, one head, always-placed Réinitialiser ---- */
#left-column #search_filters.tw-facets{ padding:clamp(14px,1.5vw,18px); }
.tw-facets__head{ display:flex; align-items:center; justify-content:space-between; gap:10px;
  margin:0 0 .35rem; padding:0 0 .7rem; border-bottom:1px solid var(--line); }
#left-column .tw-facets .tw-facets__title{ display:inline-flex; align-items:center; gap:8px;
  font-family:var(--font-body); font-size:13px; font-weight:700; letter-spacing:.08em;
  text-transform:uppercase; color:var(--ink); }
.tw-facets__ico{ width:16px; height:16px; flex:none; color:var(--muted); }
.tw-facets .clear-all-wrapper{ margin:0; padding:0; }
#left-column .tw-facets .tw-facets__reset{ background:none; border:0; padding:0; box-shadow:none;
  font-family:var(--font-body); font-size:13px; font-weight:600; line-height:1;
  color:var(--accent-deep); text-transform:none; letter-spacing:0; cursor:pointer; }
#left-column .tw-facets .tw-facets__reset:hover{ color:var(--accent); text-decoration:underline; }
#left-column .tw-facets .tw-facets__reset--off{ color:var(--line); cursor:default; pointer-events:none; }
#left-column .tw-facets .tw-facets__reset i{ display:none; }

.tw-facets .tw-facet{ margin:0; padding:.85rem 0 0; border:0; }
.tw-facets .tw-facet + .tw-facet{ border-top:1px solid var(--line-2); }
#left-column .tw-facets .tw-facet__title{ display:flex; align-items:center; justify-content:space-between;
  margin:0 0 .4rem; padding:0; cursor:default; }
#left-column .tw-facets .tw-facet__title .facet-title{ margin:0; font-family:var(--font-body);
  font-size:13.5px; font-weight:700; color:var(--ink); text-transform:none; letter-spacing:0; }
#left-column .tw-facets .tw-facet__list{ margin:0; padding:0; list-style:none; }
#left-column .tw-facets .tw-facet__list > li{ margin:0; padding:0; }
#left-column .tw-facets .facet-label{ display:flex; align-items:center; gap:8px; margin:0; padding:3px 0; }
#left-column .tw-facets .facet-label a{ font-size:13.5px; line-height:1.45; color:var(--muted); }
#left-column .tw-facets .facet-label a:hover,
#left-column .tw-facets .facet-label.active a{ color:var(--accent-deep); }
#left-column .tw-facets .magnitude{ color:var(--line); font-size:12.5px; }
/* the collapse toggler is a mobile affordance only — desktop keeps facets open */
@media (min-width:992px){
  #left-column .tw-facets .tw-facet__list.collapse{ display:block; height:auto; visibility:visible; }
  #left-column .tw-facets .navbar-toggler{ display:none; }
}

/* ============================================================
   COMPTE CLIENT — « Votre compte » dashboard
   Brief « Modifications UX Compte Client » (13 août 2026) §1.
   Six equal cards, each saying what it holds, then a shopping card and the
   way out. The old screen was seven bare links in a bootstrap row; the rules
   at .page-my-account .links above still dress whatever a module adds to the
   hook, which is why they stay.
   ============================================================ */

.tw-acct-hero{ display:flex; align-items:center; gap:clamp(20px,4vw,56px);
  padding:clamp(18px,2.6vw,34px) 0 clamp(22px,3vw,38px); }
.tw-acct-hero__txt{ flex:1 1 auto; min-width:0; }
.tw-acct-hero__hi{ margin:0 0 12px; font-family:var(--font-head); font-weight:700;
  font-size:clamp(28px,3.4vw,44px); line-height:1.16; color:var(--ink); }
.tw-acct-hero__wave{ display:inline-block; width:clamp(26px,2.6vw,36px); height:clamp(26px,2.6vw,36px); margin-inline-start:10px; vertical-align:-4px; color:var(--accent); }

/* Cards on one row keep one height, whatever their description costs. */
.tw-acct__grid > li{ display:flex; }
.tw-acct__grid > li > .tw-acct__tile{ height:100%; }
.tw-acct-hero__sub{ margin:0; color:var(--muted); font-size:clamp(14px,1.1vw,16px); line-height:1.7; }

/* The validated mockup puts a still-life in a cream halo here. That photograph
   is not in the repo, so the halo carries the theme's own khatem instead of a
   stand-in product shot; drop a background-image on it the day the asset lands. */
.tw-acct-hero__seal{ flex:0 0 auto; width:clamp(120px,17vw,220px); aspect-ratio:1; border-radius:50%;
  background:var(--orange-tint) var(--khatem) center/45% no-repeat; }

.tw-acct__grid{ display:grid; grid-template-columns:1fr; gap:clamp(12px,1.4vw,20px);
  margin:0; padding:0; list-style:none; }
@media (min-width:640px){ .tw-acct__grid{ grid-template-columns:repeat(2,1fr); } }
@media (min-width:992px){ .tw-acct__grid{ grid-template-columns:repeat(3,1fr); } }

.tw-acct__tile,.tw-acct__rgpd,.tw-acct__shop{ display:flex; align-items:center; gap:16px; width:100%;
  padding:clamp(16px,1.6vw,22px); background:var(--white); border:1px solid var(--line-2);
  border-radius:var(--radius); color:var(--ink); text-align:start; font:inherit; cursor:pointer;
  transition:transform .25s var(--ease),box-shadow .25s var(--ease),border-color .25s var(--ease); }
.tw-acct__tile:hover,.tw-acct__rgpd:hover,.tw-acct__shop:hover,
.tw-acct__tile:focus-visible,.tw-acct__rgpd:focus-visible,.tw-acct__shop:focus-visible{
  transform:translateY(-3px); box-shadow:var(--shadow); border-color:var(--accent-soft); color:var(--ink); }

.tw-acct__ico{ flex:0 0 auto; display:grid; place-items:center; width:54px; height:54px; border-radius:50%;
  background:var(--orange-soft); color:var(--accent); }
.tw-acct__ico svg{ width:25px; height:25px; }
.tw-acct__ico--sm{ width:44px; height:44px; }
.tw-acct__ico--sm svg{ width:21px; height:21px; }
.tw-acct__ico--plain{ background:transparent; color:var(--ink); }

.tw-acct__body{ display:flex; flex-direction:column; gap:5px; min-width:0; }
.tw-acct__name{ font-family:var(--font-head); font-weight:700; font-size:clamp(16px,1.3vw,19px);
  line-height:1.25; color:var(--ink); }
.tw-acct__desc{ color:var(--muted); font-size:14px; line-height:1.45; max-width:24ch; }
.tw-acct__desc--accent{ color:var(--accent); max-width:none; }

.tw-acct__go{ flex:0 0 auto; margin-inline-start:auto; color:var(--accent); display:inline-flex; }
.tw-acct__go .arr{ width:20px; height:20px; transition:transform .25s var(--ease); }
.tw-acct__tile:hover .tw-acct__go .arr,
.tw-acct__rgpd:hover .tw-acct__go .arr,
.tw-acct__shop:hover .tw-acct__go .arr{ transform:translateX(4px); }
.tw-acct[dir="rtl"] .tw-acct__go .arr{ transform:scaleX(-1); }
.tw-acct[dir="rtl"] .tw-acct__tile:hover .tw-acct__go .arr,
.tw-acct[dir="rtl"] .tw-acct__rgpd:hover .tw-acct__go .arr,
.tw-acct[dir="rtl"] .tw-acct__shop:hover .tw-acct__go .arr{ transform:scaleX(-1) translateX(4px); }

/* §6 asks that the profile and the RGPD desk stop looking like the same thing.
   A full-width row on cream, under the grid rather than inside it. */
.tw-acct__rgpd{ margin-top:clamp(12px,1.4vw,20px); background:var(--cream); border-color:var(--line); }

.tw-acct__more{ margin-top:clamp(12px,1.4vw,20px); }

.tw-acct__foot{ display:flex; align-items:center; justify-content:space-between; flex-wrap:wrap;
  gap:clamp(12px,1.4vw,20px); margin-top:clamp(18px,2.4vw,32px); }
.tw-acct__shop{ flex:1 1 340px; max-width:520px; }
.tw-acct__logout{ flex:0 0 auto; display:inline-flex; align-items:center; gap:10px;
  padding:15px 26px; border:1px solid var(--line); border-radius:var(--radius);
  background:var(--white); color:var(--accent); font-weight:600;
  transition:background .25s var(--ease),border-color .25s var(--ease); }
.tw-acct__logout svg{ width:20px; height:20px; }
.tw-acct__logout:hover,.tw-acct__logout:focus-visible{ background:var(--orange-tint); border-color:var(--accent); color:var(--accent-deep); }
.tw-acct[dir="rtl"] .tw-acct__logout svg{ transform:scaleX(-1); }

@media (max-width:639px){
  .tw-acct-hero{ gap:16px; }
  .tw-acct-hero__seal{ width:96px; }
  .tw-acct__foot{ flex-direction:column; align-items:stretch; }
  /* stacked, the shopping card must not grow to fill what is left of the column */
  .tw-acct__shop{ flex:0 0 auto; max-width:none; }
  .tw-acct__logout{ justify-content:center; }
}

/* ---- account sub-pages: the introduction line and the empty state ----
   Brief « Modifications UX Compte Client » §5. Classic answered an empty page
   with a grey alert and no way forward; this is a card, a glyph, one sentence
   of explanation and the Marketplace. */

.tw-acctpage__intro{ margin:0 0 clamp(16px,2vw,26px); color:var(--muted); font-size:15px; line-height:1.65; }

.tw-empty{ display:flex; flex-direction:column; align-items:center; text-align:center;
  padding:clamp(34px,5vw,64px) clamp(20px,4vw,48px);
  border:1px solid var(--line); border-radius:var(--radius-lg); background:var(--white); }

.tw-empty__halo{ position:relative; display:grid; place-items:center; width:132px; height:132px;
  margin-bottom:22px; border-radius:50%; background:var(--orange-tint); color:var(--accent); }
.tw-empty__glyph{ width:62px; height:62px; }

/* the three little sparks the mockup scatters around the halo */
.tw-empty__spark{ position:absolute; width:9px; height:9px; opacity:.55;
  background:
    linear-gradient(var(--accent),var(--accent)) center/100% 1.6px no-repeat,
    linear-gradient(var(--accent),var(--accent)) center/1.6px 100% no-repeat; }
.tw-empty__spark--a{ inset-block-start:12px; inset-inline-end:14px; }
.tw-empty__spark--b{ inset-block-start:34px; inset-inline-end:-6px; width:7px; height:7px; opacity:.4; }
.tw-empty__spark--c{ inset-block-end:38px; inset-inline-start:-4px; width:7px; height:7px; opacity:.4; }

.tw-empty__title{ margin:0 0 10px; font-family:var(--font-head); font-weight:700;
  font-size:clamp(19px,1.8vw,24px); color:var(--ink); }
.tw-empty__text{ margin:0 0 26px; max-width:46ch; color:var(--muted); font-size:15px; line-height:1.7; }

.tw-empty__cta{ display:inline-flex; align-items:center; justify-content:center;
  padding:14px 30px; border-radius:999px; background:var(--accent); color:#fff; font-weight:600;
  transition:background .25s var(--ease),transform .25s var(--ease); }
.tw-empty__cta:hover,.tw-empty__cta:focus-visible{ background:var(--accent-deep); color:#fff; transform:translateY(-2px); }

/* The empty state is the card; the page must not draw a second one around it.
   classic dresses #content.page-content as a panel on every account screen,
   which left « Mes avoirs » showing a box inside a box. */
body.page-order-slip #content.page-content{ padding:0; border:0; background:transparent; box-shadow:none; }

/* ============================================================
   CONTACT (« Contactez-nous ») — body#contact
   The last page still wearing classic's form clothes: captions pinned to the
   right edge by the blanket `.label, label { text-align:right }`, a select and
   an e-mail field 361px wide beside a 556px textarea, and a browser-blue
   « Choisir un fichier » that belongs to no palette on this site. The markup
   is themes/twiza/modules/contactform/…/widget/contactform.tpl; the page itself
   drops the second copy of the shop's address (contact.tpl).
   #content already carries classic's .card, so nothing here draws a second box.
   ============================================================ */
body#contact #content.page-content{ padding:clamp(22px,3vw,40px); }
/* Same shape as the filter panel's own title one column over — this is the
   sidebar's convention, and « Informations » had no reason to invent another. */
body#contact #left-column .contact-rich h4{ font-family:var(--font-body); font-size:13px;
  font-weight:700; letter-spacing:.08em; text-transform:uppercase;
  color:var(--ink); margin:0 0 16px; }
/* The information column. Left alone it read as three misdrawn pills, and the
   cause is one broad sidebar rule of ours: `#left-column .block` paints every
   module block in the sidebar white with a border — written for panels like the
   category tree, but ps_contactinfo calls each ROW of its rich block a .block
   too. With padding:0 the text touched the border on all four sides, the 2rem
   material glyph overhung the corner, and classic's own <hr> drew a line
   BETWEEN two boxes that already had edges.
   So: one card, three rows inside it. The reset has to be at least as specific
   as the rule it undoes, hence the full body#contact chain. */
body#contact #left-column .contact-rich{
  background:#fff; border:1px solid var(--line); border-radius:var(--radius-lg);
  padding:22px 20px; margin:0 0 28px; color:var(--muted); }
body#contact #left-column .contact-rich .block{
  display:flex; align-items:flex-start; gap:12px;
  background:none; border:0; border-radius:0; padding:0; height:auto; overflow:visible; }
body#contact #left-column .contact-rich hr{
  border:0; border-top:1px solid var(--line-2); margin:15px 0; }
/* classic floats the icon and gives it 3.5rem of gutter; the flex row above
   already owns the geometry, so the float has to go or it takes the row with it. */
body#contact #left-column .contact-rich .block .icon{
  float:none; flex:0 0 32px; width:32px; height:32px; display:flex;
  align-items:center; justify-content:center; border-radius:50%;
  background:var(--orange-tint); }
body#contact #left-column .contact-rich .block .icon i{ font-size:19px; color:var(--accent-deep); }
body#contact #left-column .contact-rich .block .data{
  width:auto; overflow:visible; padding-top:1px;
  font-size:14px; line-height:1.5; color:var(--ink); }
body#contact #left-column .contact-rich .block .data.email{ padding-top:1px; }
body#contact #left-column .contact-rich .block .data a{ color:var(--accent-deep); font-weight:600;
  text-decoration:none; word-break:break-word; }
body#contact #left-column .contact-rich .block .data a:hover{ text-decoration:underline; }
/* ⚠ The mail address is NOT inside .data. ps_contactinfo prints it with Smarty's
   {mailto encode="javascript"}, so a <script> sits as a SIBLING of the text and
   document.write drops the <a> right there — a third child of the flex row,
   which took width from the label beside it and then hung off the card. Give it
   the whole next line, indented past the icon, and both problems go at once.
   Written as a child selector so it cannot also catch a mail link that really
   is inside .data on some other shop's address format. */
body#contact #left-column .contact-rich .block{ flex-wrap:wrap; }
body#contact #left-column .contact-rich .block .data{ flex:1 1 0; }
body#contact #left-column .contact-rich .block > a[href^="mailto:"]{
  flex:0 0 100%; box-sizing:border-box; padding-left:44px; margin:2px 0 0; clear:none;
  font-size:14px; font-weight:600; color:var(--accent-deep);
  text-decoration:none; word-break:break-word; }
body#contact #left-column .contact-rich .block > a[href^="mailto:"]:hover{ text-decoration:underline; }
/* ⚠ …and in Arabic that indent lands on the WRONG SIDE. rtl.css:265 pins every
   mailto link to `direction:ltr` (so a Latin address reads forwards inside
   Arabic prose — correct, and worth keeping), which also makes the LINK the
   thing a LOGICAL property resolves against instead of the column around it —
   `padding-inline-start` follows the element, not its parent. So the indent is
   written physically, on both sides, and only here. */
body#contact.lang-rtl #left-column .contact-rich .block > a[href^="mailto:"]{
  padding-left:0; padding-right:44px; text-align:right; }

.tw-cf__head{ margin:0 0 26px; }
.tw-cf__title{ font-family:var(--font-head); font-size:clamp(26px,3vw,38px); line-height:1.1;
  color:var(--ink); margin:0; font-weight:600; }
.tw-cf__lede{ color:var(--muted); font-size:16px; margin:12px 0 0; max-width:58ch; }

/* One column, one width. The stock form let each control size itself, so the
   fields ended on three different right edges down a single card. */
.tw-cf__form{ display:grid; gap:18px; max-width:620px; }
.tw-cf__field{ display:block; min-width:0; }

/* A CLASS, not `.tw-cf__field > label` — see the same note on the partner form:
   a descendant form outranks a component class and quietly wins arguments it
   should not be in. This one only has to beat classic's bare `label` selector. */
.tw-cf__label{ display:block; text-align:start; font-weight:600; font-size:14px;
  color:var(--ink); margin:0 0 7px; }

.tw-cf__control{ width:100%; box-sizing:border-box; display:block;
  font-family:var(--font-body); font-size:15px; color:var(--ink);
  background:#fff; border:1px solid var(--line); border-radius:14px;
  padding:12px 15px; box-shadow:none; -webkit-appearance:none; appearance:none;
  transition:border-color .25s var(--ease), box-shadow .25s var(--ease); }
.tw-cf__control::placeholder{ color:var(--muted); opacity:.85; }
.tw-cf__control:focus{ outline:none; border-color:var(--accent);
  box-shadow:0 0 0 3px rgba(240,144,28,.16); }

select.tw-cf__control{ padding-inline-end:40px; cursor:pointer;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%237C7167' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E");
  background-repeat:no-repeat; background-size:18px; background-position:right 14px center; }
.tw-cf--rtl select.tw-cf__control{ background-position:left 14px center; }

textarea.tw-cf__control{ min-height:150px; resize:vertical; line-height:1.55; }

/* The attachment row is bootstrap-filestyle, bundled in the parent theme's
   theme.js: it clips the native input away (`clip:rect(0,0,0,0)` — in place, so
   RTL keeps its page width) and puts a disabled text field plus a <label>
   button in its place. That indirection is what lets the button carry OUR
   wording in French and Arabic, instead of whatever language the visitor's
   browser INTERFACE happens to be in — a French page reading « Choose File »
   is the kind of seam this page had too many of. With JavaScript off the plugin
   never runs and the native control shows, styled as any other field. */
.tw-cf .bootstrap-filestyle{ display:flex; align-items:stretch; overflow:hidden;
  background:#fff; border:1px solid var(--line); border-radius:14px; }
.tw-cf .bootstrap-filestyle .form-control{ flex:1 1 auto; min-width:0; height:auto;
  border:0; background:transparent; box-shadow:none; padding:12px 15px;
  font-family:var(--font-body); font-size:15px; color:var(--ink); }
/* A disabled input is greyed by the UA in its own way in every browser; say it. */
.tw-cf .bootstrap-filestyle .form-control:disabled{ opacity:1; color:var(--muted);
  -webkit-text-fill-color:var(--muted); }
.tw-cf .group-span-filestyle{ display:flex; align-items:center; }
/* `label.btn` inside the input-group: classic reaches it with an element in the
   selector and paints it white, uppercase and 11px, so a bare component class
   loses the tie. Matching its shape here is the fix — the button is a pill in
   the page's own words, not a shout. */
.tw-cf .group-span-filestyle label.tw-cf__filebtn{
  display:inline-flex; align-items:center; white-space:nowrap; cursor:pointer;
  margin:5px; padding:8px 18px; border-radius:100px;
  font-family:var(--font-body); font-weight:600; font-size:14px;
  text-transform:none; letter-spacing:0; line-height:1.2;
  color:var(--ink); background:var(--line-2); border:1px solid var(--line); box-shadow:none;
  transition:border-color .25s var(--ease), color .25s var(--ease); }
.tw-cf .group-span-filestyle label.tw-cf__filebtn .buttonText{
  color:inherit; font-size:inherit; text-transform:none; letter-spacing:inherit; }
.tw-cf .group-span-filestyle:hover label.tw-cf__filebtn,
.tw-cf .group-span-filestyle:focus-within label.tw-cf__filebtn{
  border-color:var(--accent); color:var(--accent); }
.tw-cf__hint{ color:var(--muted); font-size:13px; margin:7px 0 0; }

.tw-cf__note{ border:1px solid var(--line); border-inline-start:3px solid var(--accent);
  border-radius:14px; background:#fff; padding:14px 18px; margin:0 0 24px; }
.tw-cf__note--err{ border-inline-start-color:#C7472F; background:#FFF7F5; }
.tw-cf__note ul{ list-style:none; margin:0; padding:0; color:var(--ink); }

.tw-cf__foot{ margin-top:4px; }
.tw-cf__send{ min-width:180px; padding:13px 30px; font-size:15px; }

@media (max-width:767px){
  .tw-cf__form{ max-width:none; }
  .tw-cf__send{ width:100%; }
}

/* ════════════════════════════════════════════════════════════════════════
   « LES CRÉATIONS TWIZA » — CMS 16
   The pre-territorial catalogue's own page. Built on the homepage primitives
   (.twiza-home .section / .wrap / .eyebrow / .section-head / .btn--*); only
   what the mockup adds lives here. RTL lives in rtl.css.
   ════════════════════════════════════════════════════════════════════════ */

/* Own hero, so the default breadcrumb + page title go (same call as CMS 10/13/14). */
body.cms-id-16 .breadcrumb,
body.cms-id-16 .page-header{ display:none !important; }
body.cms-id-16 #wrapper{ padding-top:0; }

/* The page speaks the Univers page's palette — it is the page that card opens,
   and headings four shades apart were the loudest thing telling the two apart. */
.twiza-creations{ --u-green:#22412f; }
.twiza-creations h1,.twiza-creations h2,.twiza-creations h3{ color:var(--u-green); font-family:var(--font-head); }
.twiza-creations h1 em,.twiza-creations h2 em{
  color:var(--accent-deep); font-style:normal;
  background:linear-gradient(var(--accent),var(--accent)) left bottom / 100% 3px no-repeat;
  padding-bottom:3px;
}
.twiza-creations .dia{ width:14px; height:14px; color:var(--accent); flex:none; }

/* ---- 1 · HERO ------------------------------------------------------- */
/* Neither the hero nor §5 is a `.section`, so neither inherits the full-bleed
   breakout at the top of this sheet — the same trap the Territoires and Univers
   heroes fell into. Without it both stop at bootstrap's ~1110px container while
   every band between them runs edge to edge. Same two margins, same scrollbar
   correction as the shared rule. */
.twiza-creations .chero,
.twiza-creations .cfut{
  margin-left:calc(50% - 50vw + var(--sbw)/2);
  margin-right:calc(50% - 50vw + var(--sbw)/2); }

/* The Univers hero's band, grid and framing, to the value: white→cream, the
   wider `wrap-wide` box, no gap, and the band fading over the picture's inner
   edge. The slanted cream panel it replaces was this page's alone. */
.twiza-creations .chero{ background:linear-gradient(180deg,#fff 0%,var(--cream) 100%);
  padding-block:clamp(40px,6vw,84px) clamp(34px,4.5vw,64px); overflow:hidden; }
.twiza-creations .chero__grid{ display:grid; grid-template-columns:1fr 1.04fr; gap:0;
  align-items:center; }
.twiza-creations .chero__text{ display:flex; flex-direction:column; justify-content:center;
  padding-inline-end:clamp(28px,4vw,64px); position:relative; z-index:2; }
.twiza-creations .chero__h1{ font-size:clamp(34px,4.4vw,58px); line-height:1.06;
  margin:20px 0 0; letter-spacing:-.01em; }
.twiza-creations .chero__rule{ display:flex; align-items:center; gap:8px; margin:22px 0 0; }
.twiza-creations .chero__rule i{ width:44px; height:3px; border-radius:3px; background:var(--u-green); }
.twiza-creations .chero__rule i.o{ background:var(--accent); }
.twiza-creations .chero__rule svg{ width:16px; height:16px; color:var(--accent); }
.twiza-creations .chero__lead{ font-family:var(--font-head); font-weight:600; color:var(--u-green);
  font-size:clamp(18px,1.7vw,23px); line-height:1.32; margin:22px 0 0; max-width:28ch; }
.twiza-creations .chero__p{ color:var(--muted); font-size:16px; line-height:1.72;
  margin:16px 0 0; max-width:540px; }
.twiza-creations .chero__cta{ display:flex; flex-wrap:wrap; gap:14px; margin-top:30px; }

/* The mosaic is ONE photograph already cut into eight tiles: cropping it to
   whatever height the copy sets — which is what a stretched row does — ate the
   outer column and the bottom row. It keeps its own 1600:853 instead and sits
   centred in its half, so every tile prints. A replacement photo of another
   shape crops to that frame, like every other hero on the site. */
.twiza-creations .chero__media{ display:flex; flex-direction:column; justify-content:center; }
.twiza-creations .chero__frame{ position:relative; display:block; }
.twiza-creations .chero__frame img{ display:block; width:100%; aspect-ratio:1600/853;
  object-fit:cover; }
.twiza-creations .chero__frame::after{ content:""; position:absolute; inset:0; z-index:1;
  pointer-events:none;
  background:linear-gradient(90deg, var(--cream) 0%, rgba(251,247,240,.35) 16%, rgba(251,247,240,0) 42%); }

/* the hand-written closing line: the house has no script face (see .mscript) */
.twiza-creations .chero__script{ margin-top:18px; display:flex; flex-direction:column;
  align-items:flex-end; gap:2px; font-family:var(--font-head); font-style:italic;
  color:var(--accent); font-size:clamp(14px,1.25vw,17px); line-height:1.5; text-align:end; }
.twiza-creations .chero__swash{ position:relative; padding-bottom:12px; }
.twiza-creations .chero__swash svg{ position:absolute; inset-inline-start:0; bottom:0;
  width:100%; height:9px; color:var(--accent); }

/* ---- 2 · LA TRANSITION ---------------------------------------------- */
.twiza-creations .ctrans__grid{ display:grid; grid-template-columns:minmax(0,.85fr) minmax(0,1.15fr);
  gap:clamp(28px,5vw,72px); align-items:center; }
.twiza-creations .ctrans__h{ font-family:var(--font-head); font-size:clamp(19px,2vw,25px);
  line-height:1.28; margin:0 0 20px; }
.twiza-creations .ctrans__h b{ display:block; font-weight:700; text-transform:uppercase;
  letter-spacing:.01em; }
.twiza-creations .ctrans__h b.o{ color:var(--accent); }
.twiza-creations .ctrans__text p{ color:var(--muted); font-size:15px; line-height:1.75; margin:0 0 14px; }
.twiza-creations .ctrans__link{ display:inline-flex; align-items:center; gap:8px; margin-top:6px;
  color:var(--accent); font-weight:600; font-size:14.5px; }
.twiza-creations .ctrans__link:hover{ color:var(--accent-deep); }

/* the four-step axis: a dashed rule with a dot per step, arrows between icons */
.twiza-creations .cflow{ list-style:none; margin:0; padding:0;
  display:grid; grid-template-columns:repeat(4, minmax(0,1fr)); }
.twiza-creations .cflow__i{ display:grid; grid-template-rows:auto auto 1fr;
  justify-items:center; text-align:center; }
.twiza-creations .cflow__ic{ position:relative; display:grid; place-items:center;
  width:64px; height:64px; color:var(--accent); }
.twiza-creations .cflow__ic > svg{ width:44px; height:44px; }
.twiza-creations .cflow__arr{ position:absolute; inset-inline-end:100%; top:50%;
  transform:translateY(-50%); width:26px; height:26px; color:var(--muted);
  display:grid; place-items:center; }
.twiza-creations .cflow__arr svg{ width:20px; height:20px; }

.twiza-creations .cflow__ax{ position:relative; display:block; width:100%; height:26px; }
.twiza-creations .cflow__ax::before{ content:""; position:absolute; inset-inline:0; top:50%;
  border-top:1px dashed var(--line); }
/* the axis stops at the first and last dot rather than running off the row */
.twiza-creations .cflow__i:first-child .cflow__ax::before{ inset-inline-start:50%; }
.twiza-creations .cflow__i:last-child .cflow__ax::before{ inset-inline-end:50%; }
.twiza-creations .cflow__ax::after{ content:""; position:absolute; inset-inline-start:calc(50% - 5px);
  top:calc(50% - 5px); width:10px; height:10px; border-radius:50%; background:var(--accent); }

/* the four captions sit in adjacent grid cells with no column gap (the dashed
   axis has to run through unbroken), so the breathing room is padding on the
   caption itself — without it « … partout au Maroc » touches « Espace … ». */
.twiza-creations .cflow__t{ margin-top:12px; padding-inline:12px; font-size:13.5px;
  line-height:1.55; color:var(--muted); }
.twiza-creations .cflow__t b{ color:var(--ink); font-weight:600; }

/* ---- 3 · DÉCOUVREZ LEURS CRÉATIONS ---------------------------------- */
/* The mockup underlines the emphasised half of the heading, and so does the
   house — the shared `h2 em` rule above draws it now, at the house's weight. */
.twiza-creations .cchips{ display:flex; flex-wrap:wrap; justify-content:center; gap:10px;
  margin:34px 0 0; }
.twiza-creations .cchip{ display:inline-flex; align-items:center; padding:9px 20px;
  border-radius:100px; border:1px solid var(--line); background:#fff;
  color:var(--ink); font-size:14px; font-weight:500; line-height:1.2;
  transition:border-color .25s var(--ease), color .25s var(--ease), background .25s var(--ease); }
.twiza-creations .cchip:hover{ border-color:var(--accent); color:var(--accent-deep); }
.twiza-creations .cchip.is-on{ background:var(--accent); border-color:var(--accent); color:#fff;
  box-shadow:0 10px 22px -14px var(--accent); }
.twiza-creations .cchip.is-on:hover{ background:var(--accent-deep); border-color:var(--accent-deep); color:#fff; }

.twiza-creations .cgrid{ display:grid; grid-template-columns:repeat(4, minmax(0,1fr));
  gap:22px; margin-top:30px; }
.twiza-creations .ccrea__cta,
.twiza-creations .ccoop__cta{ display:flex; justify-content:center; margin-top:34px; }
.twiza-creations .cempty{ text-align:center; color:var(--muted); margin:34px 0 0; }

/* ---- 4 · DÉCOUVREZ LES COOPÉRATIVES --------------------------------- */
.twiza-creations .ccoops{ display:grid; grid-template-columns:repeat(4, minmax(0,1fr));
  gap:22px; margin-top:34px; }
.twiza-creations .ccoop-card{ display:flex; flex-direction:column; background:#fff;
  border:1px solid var(--line); border-radius:var(--radius); overflow:hidden; color:inherit;
  transition:transform .3s var(--ease), box-shadow .3s, border-color .3s; }
.twiza-creations .ccoop-card:hover{ transform:translateY(-5px); box-shadow:var(--shadow-lift);
  border-color:transparent; }
/* 3/2, the ratio CooperativeMaker's own cards already use: several of these
   images are logos rather than photographs, and a taller box crops them more.

   And they are not cropped AT ALL any more. `cover` was cutting the top and
   bottom off nearly every one of them — the MAASSOULA bee, the Afaq wordmark,
   ENNAJAH's name — because 186 of the 195 files are 250×250 squares dropped
   into a 3/2 box. A crop is a reasonable default for a photograph and a wrong
   one for a logo, which has to be seen whole or not at all. `contain` on the
   cream ground, with a small inset so nothing touches the frame edge. */
.twiza-creations .ccoop-card__media{ position:relative; display:block; aspect-ratio:3/2;
  overflow:hidden; background:var(--cream); }
.twiza-creations .ccoop-card__media img{ width:100%; height:100%; object-fit:contain; display:block;
  padding:14px; transition:transform .9s var(--ease); }
.twiza-creations .ccoop-card:hover .ccoop-card__media img{ transform:scale(1.06); }
.twiza-creations .ccoop-card__ribbon{ position:absolute; top:12px; inset-inline-start:12px;
  padding:5px 11px; border-radius:6px; background:var(--accent); color:#fff;
  font-size:10.5px; font-weight:700; letter-spacing:.07em; text-transform:uppercase; }
.twiza-creations .ccoop-card__body{ display:flex; flex-direction:column; gap:7px; flex:1 1 auto;
  padding:16px 18px 18px; }
.twiza-creations .ccoop-card__n{ font-family:var(--font-head); font-size:18px; font-weight:600;
  line-height:1.25; color:var(--ink); }
.twiza-creations .ccoop-card__c{ font-size:13.5px; color:var(--muted); }
.twiza-creations .ccoop-card__go{ margin-top:auto; padding-top:8px; display:inline-flex;
  align-items:center; gap:8px; color:var(--accent); font-size:14px; font-weight:600; }
.twiza-creations .ccoop-card:hover .ccoop-card__go{ color:var(--accent-deep); }

/* ---- 5 · LES FUTURS UNIVERS ----------------------------------------- */
.twiza-creations .cfut{ position:relative; background:var(--cream-2); overflow:hidden;
  border-block:1px solid var(--line); }
.twiza-creations .cfut__grid{ display:grid; grid-template-columns:minmax(0,.5fr) minmax(0,1.32fr) minmax(0,.68fr);
  align-items:center; min-height:clamp(260px,26vw,360px); }
.twiza-creations .cfut__media{ position:relative; height:100%; min-height:inherit; }
.twiza-creations .cfut__media img{ position:absolute; inset:0; width:100%; height:100%;
  object-fit:cover; display:block; }
/* the photograph dissolves into the band rather than butting against it */
.twiza-creations .cfut__media::after{ content:""; position:absolute; inset:0;
  background:linear-gradient(to right, transparent 35%, var(--cream-2)); }
.twiza-creations[dir="rtl"] .cfut__media::after{ background:linear-gradient(to left, transparent 35%, var(--cream-2)); }

.twiza-creations .cfut__body{ position:relative; z-index:2; text-align:center;
  padding:clamp(30px,4vw,52px) clamp(14px,2vw,30px); display:flex; flex-direction:column;
  align-items:center; gap:0; }
.twiza-creations .cfut__h{ font-family:var(--font-head); font-size:clamp(26px,3.1vw,40px);
  font-weight:700; margin:14px 0 0; }
.twiza-creations .cfut__p{ color:var(--muted); font-size:15px; line-height:1.75;
  margin:14px 0 0; max-width:62ch; }
.twiza-creations .cfut__p b{ color:var(--accent); font-weight:600; }
.twiza-creations .cfut__strong{ margin:12px 0 0; font-weight:700; color:var(--ink); font-size:15.5px; }
.twiza-creations .cfut__body .btn{ margin-top:20px; }

/* The territoires hub's own hero map — a Morocco composed of photographs,
   not the drawn outline that used to sit here. It arrives from the back
   office as a JPEG on a near-white ground, so it is dropped onto the band the
   way the hub drops it: `darken` takes the per-channel minimum against the
   cream painted below, which turns every pixel lighter than the band into
   EXACTLY the band and leaves the artwork untouched. Measured on the current
   file against #F5ECDD: 82.2% of it becomes the band, 1.1% more is artwork
   bright enough to warm slightly (at most 34/255 in one channel — the white
   strokes between regions, and the brightest highlights). Done in CSS rather
   than with a keyed-out PNG so it keeps working when the shop uploads a NEW
   map — a hand-cut alpha channel would have to be cut again. It needs the
   flat band above: over a gradient the blend would track the gradient.
   NOT mirrored in RTL: the grid moves it to the other column, which is all
   that should move. */
.twiza-creations .cfut__map{ height:100%; min-height:inherit;
  display:grid; place-items:center; padding:clamp(10px,1.6vw,22px); }
.twiza-creations .cfut__map img{ display:block; width:100%; height:auto;
  max-height:min(86%,300px); object-fit:contain; mix-blend-mode:darken; }

/* ---- responsive ------------------------------------------------------ */
@media (max-width:1199px){
  .twiza-creations .cgrid,
  .twiza-creations .ccoops{ grid-template-columns:repeat(3, minmax(0,1fr)); }
}
@media (max-width:991px){
  /* The hero stacks, photograph first — the Univers hero's own order. The
     media column dissolves (display:contents) so its two children order
     independently: the closing note belongs AFTER the copy it closes, not
     between the photograph and the headline. */
  .twiza-creations .chero__grid{ grid-template-columns:1fr; }
  .twiza-creations .chero__text{ padding-inline-end:0; padding-block-start:32px; order:1; }
  .twiza-creations .chero__media{ display:contents; }
  .twiza-creations .chero__frame{ order:0; border-radius:var(--radius-lg); overflow:hidden; }
  /* stacked, the picture has no neighbour to fade into */
  .twiza-creations .chero__frame::after{ display:none; }
  .twiza-creations .chero__script{ order:2; margin-top:26px;
    align-items:flex-start; text-align:start; }

  .twiza-creations .ctrans__grid{ grid-template-columns:1fr; }

  .twiza-creations .cfut__grid{ grid-template-columns:1fr; min-height:0; }
  .twiza-creations .cfut__media{ min-height:0; aspect-ratio:16/7; }
  .twiza-creations .cfut__media::after{ background:linear-gradient(to bottom, transparent 30%, var(--cream-2)); }
  .twiza-creations[dir="rtl"] .cfut__media::after{ background:linear-gradient(to bottom, transparent 30%, var(--cream-2)); }
  .twiza-creations .cfut__map{ display:none; }
}
@media (max-width:767px){
  .twiza-creations .cgrid,
  .twiza-creations .ccoops{ grid-template-columns:repeat(2, minmax(0,1fr)); gap:14px; }
  /* four steps do not fit a phone row; two by two, and the axis goes with them */
  .twiza-creations .cflow{ grid-template-columns:repeat(2, minmax(0,1fr)); row-gap:26px; }
  .twiza-creations .cflow__ax{ display:none; }
  .twiza-creations .cflow__arr{ display:none; }
  .twiza-creations .cflow__t{ margin-top:6px; }
  .twiza-creations .cchips{ justify-content:flex-start; flex-wrap:nowrap; overflow-x:auto;
    scrollbar-width:none; margin-inline:calc(var(--gutter) * -1); padding-inline:var(--gutter); }
  .twiza-creations .cchips::-webkit-scrollbar{ display:none; }
  .twiza-creations .cchip{ flex:0 0 auto; }
}
@media (max-width:479px){
  .twiza-creations .cgrid,
  .twiza-creations .ccoops{ grid-template-columns:1fr; }
}

/* ---- « Les créations TWIZA » · RTL ---- */
/* Everything that could be expressed logically already was (inset-inline,
   margin-inline, border-inline). What is left is what has no logical form:
   drawn arrows, and the hero fade whose gradient angle is physical. The map is
   deliberately absent: a mirrored Morocco is a wrong Morocco. */
body.lang-rtl .twiza-creations .ar,
body.lang-rtl .twiza-creations .cflow__arr svg{ transform:scaleX(-1); }
body.lang-rtl .twiza-creations .btn:hover .ar,
body.lang-rtl .twiza-creations .ctrans__link:hover .ar,
body.lang-rtl .twiza-creations .ccoop-card:hover .ccoop-card__go .ar{ transform:scaleX(-1) translateX(3px); }
/* the grid mirrors on its own, so the picture's inner edge moves to its right */
body.lang-rtl .twiza-creations .chero__frame::after{
  background:linear-gradient(270deg, var(--cream) 0%, rgba(251,247,240,.35) 16%, rgba(251,247,240,0) 42%); }

/* ============================================================
   CONNEXION · INSCRIPTION — the two doors into the account area
   customer/authentication.tpl and customer/registration.tpl.

   Classic laid both out as a full-width `.card.card-block` holding bootstrap's
   3/6/3 form grid: a 1240px slab with a 130px fixed-width label beside every
   field. Two things follow from that grid, and both are fixed here by taking
   the grid off rather than by patching around it.

   · IT NEVER MIRRORED. `label.required{width:130px}`,
     `.form-control-label{text-align:left}` and
     `.forgot-password{margin-left:14.38rem}` are all PHYSICAL — the same story
     rtl.css tells about the listing. Stacked labels have no side to be on, so
     the Arabic pages come out right without a single RTL override below.
   · IT WAS UNREADABLE AT THE SLAB'S WIDTH. A label at x=0 and its field at
     x=310 on a 1240px page is not a form, it is two columns of unrelated text.

   Everything below is CSS reaching into classic's own login-form.tpl and
   customer-form.tpl. Neither partial is copied into this theme, so a
   PrestaShop upgrade that adds a field gets it styled for free.
   ============================================================ */

.tw-auth{
  --tw-auth-w:520px;
  max-width:var(--tw-auth-w); margin-inline:auto;
  padding-block:clamp(8px,1.6vw,24px) clamp(28px,4vw,56px);
}
/* nine fields, not two — see the note in registration.tpl */
.tw-auth--register{ --tw-auth-w:640px; }

/* ---- the head: the account area's halo, title and lede ---- */
.tw-auth__head{ text-align:center; margin-bottom:clamp(20px,2.6vw,32px); }
.tw-auth__seal{
  display:grid; place-items:center; width:76px; height:76px; margin:0 auto 18px;
  border-radius:50%; background:var(--orange-tint); color:var(--accent);
}
.tw-auth__seal svg{ width:34px; height:34px; }
.tw-auth__title{
  margin:0 0 10px; font-family:var(--font-head); font-weight:700;
  font-size:clamp(26px,3vw,38px); line-height:1.16; color:var(--ink);
}
.tw-auth__sub{
  margin:0 auto; max-width:42ch; color:var(--muted);
  font-size:clamp(14px,1.1vw,16px); line-height:1.7;
}

/* ---- the card ----
   `#content` still carries `.page-content`, so this has to out-rank whatever
   classic hangs on that class; it does not have to out-rank `.card`, which the
   template no longer prints. */
/* `#main .page-content{margin-bottom:1.563rem}` carries an ID and wins over a
   bare class, so the gap under the card is stated here rather than left to
   classic — .tw-auth__alt sets its own margin-top and the two used to add up. */
#content.tw-auth__card{
  padding:clamp(22px,2.8vw,38px); margin:0; background:var(--white);
  border:1px solid var(--line); border-radius:var(--radius-lg);
  box-shadow:var(--shadow-sm);
}

/* ---- one field ----
   The bootstrap row is dismantled here: `.row` is flex and its children are
   percentage columns, so both have to be told to stop. */
.tw-auth .form-group.row,
.tw-auth .form-group{ display:block; margin:0 0 18px; }
.tw-auth .form-group.row [class*="col-"],
.tw-auth .form-group.row .js-input-column{
  flex:none; float:none; width:100%; max-width:none; padding-inline:0; margin:0;
}
/* the empty 3-column gutter classic leaves at the end of every row */
.tw-auth .form-group.row .col-md-3.form-control-comment:empty{ display:none; }

.tw-auth .form-control-label{
  display:block; width:auto; margin:0 0 7px; padding:0; text-align:start;
  font-family:var(--font-body); font-size:13.5px; font-weight:600; color:var(--ink);
}
/* classic marks a required field nowhere the eye can see it */
.tw-auth .form-control-label.required::after{
  content:"*"; margin-inline-start:4px; color:var(--accent); font-weight:700;
}
/* The RGPD consent and the newsletter opt-in ship an EMPTY column label — the
   sentence lives inside the checkbox's own <label> instead. Left alone it
   printed a bare orange asterisk floating on its own line above the box.
   `:empty` cannot match it (the tag is full of newlines), so the row is
   identified by what it actually contains. */
.tw-auth .form-group.row:has(.custom-checkbox) > .form-control-label{ display:none; }

.tw-auth .form-control,
.tw-auth input[type=text],
.tw-auth input[type=email],
.tw-auth input[type=password],
.tw-auth input[type=tel],
.tw-auth select{
  width:100%; height:auto; padding:13px 16px;
  background:var(--white); border:1px solid var(--line); border-radius:12px;
  font-family:var(--font-body); font-size:15px; color:var(--ink);
  transition:border-color .2s ease, box-shadow .2s ease;
}
.tw-auth .form-control::placeholder{ color:var(--muted); }
.tw-auth .form-control:focus{ border-color:var(--accent); box-shadow:0 0 0 3px var(--accent-soft); outline:0; }

/* the hint under a field, and the server's answer when it refuses one */
.tw-auth .form-control-comment{
  display:block; margin-top:7px; padding:0;
  font-size:12.5px; line-height:1.5; color:var(--muted);
}
.tw-auth .form-group.has-error .form-control,
.tw-auth .form-control.is-invalid{ border-color:#C0392B; }
.tw-auth .help-block li,
.tw-auth .form-group.has-error .form-control-comment{ color:#C0392B; list-style:none; }
.tw-auth .help-block{ margin:7px 0 0; padding:0; font-size:12.5px; }

/* ---- the password field and its « Afficher » ----
   classic's `.input-group` is display:table with a table-cell button, which
   cannot share a rounded edge with the input. Flex can. */
.tw-auth .input-group{ display:flex; width:100%; border-collapse:initial; }
.tw-auth .input-group .form-control{
  flex:1 1 auto; min-width:0;
  border-start-end-radius:0; border-end-end-radius:0; border-inline-end:0;
}
.tw-auth .input-group-btn{
  display:flex; width:auto; vertical-align:initial; font-size:inherit;
}
/* ⚠ classic paints this one `background:#7a7a7a` from
   `.input-group .input-group-btn>.btn[data-action=show-password]`, which is
   four class-level parts — measured: the button still came out grey against a
   three-part selector. The attribute is carried here for the same reason. */
.tw-auth .input-group-btn .btn,
.tw-auth .input-group .input-group-btn .btn[data-action=show-password]{
  height:auto; padding:0 16px; border:1px solid var(--line); border-inline-start:0;
  border-start-start-radius:0; border-end-start-radius:0;
  border-start-end-radius:12px; border-end-end-radius:12px;
  background:var(--cream); color:var(--muted); box-shadow:none;
  font-family:var(--font-body); font-size:12.5px; font-weight:600; text-transform:none; letter-spacing:0;
  transition:background .2s ease, color .2s ease;
}
.tw-auth .input-group .input-group-btn .btn:hover,
.tw-auth .input-group .input-group-btn .btn:focus-visible{ background:var(--accent-soft); color:var(--accent-deep); }
/* the focus ring belongs to the pair, not to the input alone, or half of the
   control lights up and the other half does not */
.tw-auth .input-group:focus-within{ border-radius:12px; box-shadow:0 0 0 3px var(--accent-soft); }
.tw-auth .input-group:focus-within .form-control,
.tw-auth .input-group:focus-within .input-group-btn .btn{ border-color:var(--accent); }
.tw-auth .input-group:focus-within .form-control{ box-shadow:none; }

/* the strength meter PrestaShop drops under the password */
.tw-auth .password-strength-feedback{ margin-top:9px; font-size:12.5px; color:var(--muted); }
.tw-auth .progress{ height:5px; margin-top:9px; border-radius:100px; background:var(--line-2); }
.tw-auth .progress-bar{ border-radius:100px; }

/* ---- radios and checkboxes ----
   Title (M./Mme), the RGPD consent and the newsletter opt-in.

   ⚠ THE CHECKBOX LABEL MUST NOT BE A FLEX CONTAINER. Its content is
   `<input><span></span>Recevoir notre newsletter<br><em>…</em>` — a bare text
   node followed by an <em>. Flex turns EACH of those into its own anonymous
   item, so the sentence and its small print end up side by side in two narrow
   columns instead of stacked. Measured on the register page; it is why this is
   a block with an absolutely-positioned box, which is classic's own model. */
.tw-auth .form-control-valign{ display:flex; flex-wrap:wrap; gap:10px 22px; padding-top:2px; }
.tw-auth .radio-inline{ display:inline-flex; align-items:center; gap:9px; margin:0; padding:0;
  font-size:14.5px; color:var(--ink); cursor:pointer; }
/* the gap above does the spacing; classic's physical margin would add to it on
   one side only, and on the wrong side in Arabic */
.tw-auth .custom-radio{ margin-right:0; margin-inline-end:0; }

.tw-auth .custom-checkbox{ position:relative; display:block; }
/* two physical rules of classic's are undone here: `.custom-checkbox>label`
   pads LEFT, and `#authentication .custom-checkbox label` (1,1,1) adds more. */
.tw-auth .custom-checkbox > label,
body#authentication .tw-auth .custom-checkbox > label{
  display:block; margin:0; padding-left:0; padding-inline-start:29px;
  font-size:14px; line-height:1.6; color:var(--ink); cursor:pointer; }
/* classic pins the drawn box to `left:0` — physical, so in Arabic it landed on
   the far side of its own sentence */
.tw-auth .custom-checkbox input[type=checkbox] + span{
  position:absolute; top:2px; left:auto; right:auto; inset-inline-start:0;
  width:18px; height:18px; margin:0; border:1px solid var(--line); border-radius:5px; }
.tw-auth .custom-checkbox em{ display:block; margin-top:4px; font-size:12.5px; color:var(--muted); font-style:normal; }

.tw-auth .custom-radio span,
.tw-auth .custom-checkbox span{ border-color:var(--line); }
/* classic fills both of these #24b9d7 at the same specificity this rule has,
   and wins on source order alone if it is ever loaded last — the :checked
   selector is spelled out to stay ahead of it either way */
.tw-auth .custom-radio input[type=radio]:checked + span,
.tw-auth .custom-checkbox input[type=checkbox]:checked + span{
  border-color:var(--accent); background:var(--accent); background-color:var(--accent); }
.tw-auth .custom-checkbox input[type=checkbox]:checked + span .checkbox-checked{ color:#fff; }

/* ---- « Mot de passe oublié ? » ----
   a real target at the end of the line, not a link floated 14.38rem from the
   left edge of a page that may not have a left edge.

   ⚠ THE ID IS LOAD-BEARING. classic centres this from
   `.page-customer-account #content .forgot-password`, which is (1,2,0) and
   beats any selector built out of classes alone — measured: `text-align`
   still computed `center` with `.tw-auth .forgot-password`. `#content` is the
   card itself, so the chain goes through `.tw-auth` to reach (1,3,0). */
.tw-auth #content.tw-auth__card .forgot-password{
  margin:-4px 0 0; padding:0; text-align:end; font-size:13.5px;
}
.tw-auth .forgot-password a{
  color:var(--muted); text-decoration:none; transition:color .2s ease;
}
.tw-auth .forgot-password a:hover,
.tw-auth .forgot-password a:focus-visible{ color:var(--accent-deep); text-decoration:underline; }

/* ---- the submit ---- */
.tw-auth .form-footer{
  display:block; margin:24px 0 0; padding:24px 0 0; text-align:center;
  border-top:1px solid var(--line-2);
}
.tw-auth .form-footer .btn,
.tw-auth .form-footer .btn-primary{
  float:none; width:100%; padding:15px 30px; border:1px solid var(--accent); border-radius:100px;
  background:var(--accent); color:#fff;
  font-family:var(--font-body); font-size:15.5px; font-weight:600; text-transform:none; letter-spacing:.01em;
  box-shadow:0 10px 22px -12px var(--accent);
  transition:background .25s var(--ease), border-color .25s var(--ease), transform .25s var(--ease), box-shadow .25s var(--ease);
}
.tw-auth .form-footer .btn:hover,
.tw-auth .form-footer .btn:focus-visible{
  background:var(--accent-deep); border-color:var(--accent-deep); color:#fff;
  transform:translateY(-2px); box-shadow:0 16px 30px -14px var(--accent);
}
.tw-auth .form-footer .btn:active{ transform:none; }

/* ---- the way to the other door ---- */
.tw-auth__alt{
  display:flex; align-items:center; justify-content:center; flex-wrap:wrap; gap:8px 16px;
  margin-top:clamp(18px,2.2vw,26px); padding:18px 22px;
  background:var(--cream); border:1px solid var(--line); border-radius:var(--radius);
}
.tw-auth__alt-q{ color:var(--muted); font-size:14.5px; }
/* the pill « Se déconnecter » is on the account dashboard — same job (the
   secondary way out of a cream row), so the same object. */
.tw-auth__alt-btn{
  display:inline-flex; align-items:center; gap:9px;
  padding:11px 22px; border:1px solid var(--line); border-radius:100px;
  background:var(--white); color:var(--accent-deep);
  font-size:14.5px; font-weight:700; text-decoration:none;
  transition:background .25s var(--ease), border-color .25s var(--ease), color .25s var(--ease);
}
.tw-auth__alt-btn .arr{ width:18px; height:18px; transition:transform .25s var(--ease); }
/* ⚠ COLOUR ALONE CANNOT BE THE HOVER HERE. `#main a:hover{color:var(--accent-deep)}`
   is (1,1,1) and this link really is inside #main, so it pins the colour to the
   very value the resting state already uses — measured: the hover changed
   nothing at all. The ground and the border carry the feedback instead, and
   they are what this component's twin on the dashboard uses anyway. */
#main .tw-auth__alt-btn:hover,
#main .tw-auth__alt-btn:focus-visible{
  background:var(--orange-tint); border-color:var(--accent); color:var(--accent-deep); text-decoration:none;
}
.tw-auth__alt-btn:hover .arr{ transform:translateX(4px); }
/* the arrow is a direction, so it turns around with the text */
.tw-auth[dir="rtl"] .tw-auth__alt-btn .arr{ transform:scaleX(-1); }
.tw-auth[dir="rtl"] .tw-auth__alt-btn:hover .arr{ transform:scaleX(-1) translateX(4px); }

@media (max-width:575.98px){
  .tw-auth__seal{ width:64px; height:64px; }
  .tw-auth__seal svg{ width:28px; height:28px; }
  .tw-auth__alt{ flex-direction:column; gap:10px; }
  /* stacked, « Afficher » beside a 15px input leaves the input barely 110px */
  .tw-auth .input-group-btn .btn{ padding:0 12px; font-size:12px; }
}

/* ============================================================
   PRODUCT PAGE (no landing) — the ~887 products landingpagecod
   does not repaint, which until now rendered as bare classic.

   The structural half of this lives in templates/catalog/product.tpl:
   the description tabs are re-emitted after .product-container instead
   of inside the right column. What is left here is the styling that
   assumes that move, plus the two things that were simply wrong on a
   themed shop — a gallery marooned beside two thousand pixels of white,
   and an empty reviews block on a shop that has never had a review.
   ============================================================ */

/* ---- 1. The gallery follows the buy box ----
   The right column on this shop is enormous (quick-order form, cooperative
   card, three policy links). The left one is a square photo and a thumbnail
   strip, so it used to sit at the top of a column of dead white. Sticky is
   only correct once there is something to stick past, hence the ≥992px gate:
   below that the two columns are stacked and the photo is simply first.

   A sticky child can only travel inside its containing block, and classic's
   .row is still Bootstrap 4's FLOAT grid (display:block — the same float grid
   that never mirrored for RTL). Under floats the left column is only as tall
   as the photo, so position:sticky computes but has nowhere to go and the
   photo scrolls away like anything else. The column has to stretch first,
   hence display:flex on the row. Measured, not assumed.

   Scoped three ways: to #product, to ≥992px (the only width where the columns
   sit side by side), and away from body.lp-chrome-hidden — the 51 products
   whose landing page replaces the site header with landingpagecod's own 56px
   bar. Those pages are the module's to lay out, and an offset measured off
   --tw-header-h would be wrong for them anyway. */
@media (min-width:992px){
  body#product:not(.lp-chrome-hidden) .product-container{
    display:flex; flex-wrap:wrap; align-items:stretch; }
  body#product:not(.lp-chrome-hidden) .product-container>.col-md-6{ float:none; }
  /* --tw-header-h, not a literal: the header is fixed and the offset has to
     track it, the way .twiza-territoires scroll-margin-top already does. */
  body#product:not(.lp-chrome-hidden) .product-container>.col-md-6:first-child>#content.page-content{
    position:sticky; top:calc(var(--tw-header-h) + 20px); }
}

/* ---- 2. Description tabs, full width ----
   .tw-product-more is the wrapper the template puts around the moved
   .tabs node. It is a direct child of #main, so it spans the container. */
/* Capped and centred rather than edge-to-edge. Readable body copy tops out at
   about 72ch; in a 1200px card that leaves a third of the white empty on the
   right, which reads as a bug rather than as a margin. The cap is set so the
   card roughly hugs that measure once its own padding is taken off — a card
   sized to its text, centred under a wider row, reads as a decision. */
.tw-product-more{ margin:clamp(32px,4vw,56px) auto 0; max-width:min(100%, 820px); }
#product .tw-product-more .tabs{
  border:1px solid var(--line); border-radius:var(--radius); background:#fff;
  padding:clamp(20px,2.4vw,34px) clamp(20px,2.8vw,40px); }
#product .tw-product-more .nav-tabs{
  display:flex; flex-wrap:wrap; gap:clamp(18px,2.4vw,34px);
  margin:0 0 clamp(18px,2vw,26px); padding:0 0 2px; list-style:none; }
#product .tw-product-more .nav-tabs .nav-item{ margin:0; }
#product .tw-product-more .nav-tabs .nav-link{
  display:block; padding:0 0 12px; font-family:var(--font-body);
  font-size:15px; font-weight:600; letter-spacing:.01em;
  border:0; border-bottom:2px solid transparent; background:transparent;
  color:var(--muted); transition:color .25s var(--ease), border-color .25s var(--ease); }
#product .tw-product-more .nav-tabs .nav-link:hover{ color:var(--ink); }
#product .tw-product-more .nav-tabs .nav-link.active{
  color:var(--accent-deep); border-bottom-color:var(--accent); }

/* Body copy: the card is full width, the paragraph is not — a 1200px line is
   as unreadable as the 55-character one this replaced. 72ch is the measure. */
#product .tw-product-more .tab-content{ font-size:15.5px; line-height:1.75; color:var(--ink); }
#product .tw-product-more .product-description{ max-width:72ch; }
#product .tw-product-more .product-description p{ margin:0 0 1em; }
#product .tw-product-more .product-description p:last-child{ margin-bottom:0; }
#product .tw-product-more .product-description h2,
#product .tw-product-more .product-description h3,
#product .tw-product-more .product-description h4{
  font-family:var(--font-head); color:var(--ink); margin:1.6em 0 .5em; }
#product .tw-product-more .product-description img{ max-width:100%; height:auto; border-radius:var(--radius-sm); }
#product .tw-product-more .product-description ul,
#product .tw-product-more .product-description ol{ padding-inline-start:1.25em; margin:0 0 1em; }

/* « Détails du produit » — classic emits <dl>/<div class="product-reference">
   rows here; give them a readable two-column rhythm instead of run-on text. */
#product .tw-product-more #product-details{ max-width:72ch; }
#product .tw-product-more #product-details .h6,
#product .tw-product-more #product-details .h5{ font-family:var(--font-head); color:var(--ink); }
#product .tw-product-more #product-details dl.data-sheet{
  display:grid; grid-template-columns:minmax(0,1fr) minmax(0,1fr); gap:0;
  margin:0; padding:0; }
#product .tw-product-more #product-details dl.data-sheet dt,
#product .tw-product-more #product-details dl.data-sheet dd{
  margin:0; padding:11px 14px; background:transparent;
  border-bottom:1px solid var(--line-2); font-size:14.5px; }
#product .tw-product-more #product-details dl.data-sheet dt{ font-weight:600; color:var(--muted); }
#product .tw-product-more #product-details dl.data-sheet dd{ color:var(--ink); }

/* ---- 3. « Vous aimerez aussi » ---- */
#product .product-accessories{ margin-top:clamp(36px,4.5vw,64px); }
#product .product-accessories>.h5,
#product .product-accessories>.h3{
  font-family:var(--font-head); font-weight:600; letter-spacing:0;
  font-size:clamp(21px,2.2vw,28px); color:var(--ink); text-transform:none;
  margin:0 0 clamp(16px,2vw,24px); }

/* Air before the footer — classic ends the page flush against it. */
#product #main{ padding-bottom:clamp(40px,5vw,72px); }

/* ---- 4. The reviews block that never has reviews ----
   qb0j_product_comment is empty, PRODUCT_COMMENTS_ALLOW_GUESTS is 0 and
   moderation is on, so every visitor got a "Commentaires (0)" counter and
   an "Aucun avis…" line and no way to add one. Both are the module's
   empty state — #product-comments-list itself is untouched, so the day a
   comment is approved it still renders. Landing pages already hid these
   (see the body.lp-chrome-hidden rule above); this extends it to the rest. */
#product .comments-nb,
#product #product-comments-list-header,
#product #empty-product-comment,
#product #product-comments-list-footer:empty{ display:none !important; }

/* ---- 5. Landing pages must not inherit the new wrapper ----
   landingpagecod hides '.tabs' by selector, which still matches after the
   move, but the wrapper around it is new and would leave a gap. */
body.lp-chrome-hidden .tw-product-more{ display:none !important; }

@media (max-width:767px){
  .tw-product-more{ margin-top:28px; }
  #product .tw-product-more .tabs{ padding:18px 16px; }
  #product .tw-product-more .nav-tabs{ gap:18px; }
  #product .tw-product-more #product-details dl.data-sheet{ grid-template-columns:1fr; }
  #product .tw-product-more #product-details dl.data-sheet dt{ padding-bottom:0; border-bottom:0; }
}
