/* ════════════════════════════════════════════════════════════════════════
   prodotto-vb.css — RESTYLE PRODOTTO · VARIANTE B · SEZIONE 1: .cfg-card
   ------------------------------------------------------------------------
   Look "variante-b" applicato alle card di selezione del configuratore e
   all'intestazione step numerata. SOLO override estetici: nessuna modifica
   al markup PHP, ai ganci JS (.sel / aria-pressed restano quelli usati da
   js/configuratore.js:261-262), ai data-* o agli id.

   Caricato DOPO css/pages.css (vince per ordine sorgente, a parità di
   specificità). Isolato e rimovibile: basta togliere il <link>.

   TOKEN: la variante-b usa gli STESSI valori dei token reali già definiti
   in css/style.css :root (--bg-card #0D0D1A, CMYK --cyan/--magenta/--yellow,
   font --f-display/--f-ui/--f-mono, raggi --r-sm/--r-md). Non ridefiniti qui
   per evitare duplicazioni: si referenziano direttamente le var() del sito.

   ACCENTO: cyan fisso (var(--cyan)). --cat-accent è scoping delle pagine
   CATEGORIA (.vb-cat, categoria-stampa.css), non del configuratore prodotto.

   COLOR-CODING PRESERVATO: le card --magenta/--yellow/--blue mantengono il
   loro stato selezionato colorato (semantica: fronte/retro, finiture). Le
   varianti di layout --delivery/--qty mantengono griglia e disposizione.
   ════════════════════════════════════════════════════════════════════════ */

/* ─── Griglia card ─────────────────────────────────────────────────────────
   Da colonne fisse 120px a colonne fluide minmax: le card riempiono la riga
   (look variante-b). Esclude le griglie a layout proprio (qty/delivery/grafica). */
.cfg-cards:not(.cfg-cards--qty):not(.cfg-cards--delivery):not(.cfg-cards--grafica) {
  grid-template-columns: repeat(auto-fill, minmax(140px, 1fr));
  gap: 0.65rem;
}
.cfg-cards--wide:not(.cfg-cards--qty):not(.cfg-cards--delivery):not(.cfg-cards--grafica) {
  grid-template-columns: repeat(auto-fill, minmax(168px, 1fr));
}

/* ─── Cornice card ─────────────────────────────────────────────────────────
   Props universali e sicure (bg/bordo/raggio/transizione). */
.cfg-card {
  background: var(--bg-card);
  border: 1px solid var(--border-2);
  border-radius: var(--r-md);
  color: var(--text);
  transition: border-color 0.14s, background 0.14s, transform 0.12s, box-shadow 0.14s;
}
/* Props di disposizione: allineamento a sinistra in stile variante-b.
   Escluse le varianti row/compact che hanno layout proprio. */
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) {
  align-items: stretch;
  justify-content: flex-start;
  text-align: left;
  gap: 0.3rem;
  padding: 0.95rem 0.8rem 0.85rem;
  min-height: 0;
}

/* hover: sollevamento + bordo chiaro neutro. Escluse le color-variant così
   conservano il loro hover colorato (magenta/yellow/blue). */
.cfg-card:hover { transform: translateY(-2px); }
.cfg-card:not(.cfg-card--magenta):not(.cfg-card--yellow):not(.cfg-card--blue):hover {
  border-color: rgba(255, 255, 255, 0.28);
  background: var(--bg-card);
}

/* selezionato (plain): bordo + glow accento cyan, stile variante-b (inset).
   Stilati ENTRAMBI i ganci (.sel e aria-pressed) anche se il JS li tiene
   allineati. Escluse le color-variant: mantengono il loro sel colorato. */
.cfg-card.sel:not(.cfg-card--magenta):not(.cfg-card--yellow):not(.cfg-card--blue),
.cfg-card[aria-pressed="true"]:not(.cfg-card--magenta):not(.cfg-card--yellow):not(.cfg-card--blue) {
  border-color: var(--cyan);
  background: rgba(0, 212, 255, 0.08);
  box-shadow: inset 0 0 0 1px rgba(0, 212, 255, 0.5);
}

/* ─── Spunta (check) ───────────────────────────────────────────────────────
   Quadratino in alto a destra, visibile solo quando selezionata (eredita
   opacity:0 → 1 da pages.css). Cambia solo forma: da cerchio a quadrato. */
.cfg-card__check {
  top: 0.6rem; right: 0.6rem;
  width: 18px; height: 18px;
  border-radius: 4px;
  border: 1px solid var(--border-2);
  transform: scale(0.7);
}
.cfg-card.sel .cfg-card__check { transform: scale(1); }
/* sel: riempimento accento + spunta scura (plain; color-variant invariate). */
.cfg-card.sel:not(.cfg-card--magenta):not(.cfg-card--yellow):not(.cfg-card--blue) .cfg-card__check {
  background: var(--cyan);
  border-color: var(--cyan);
  color: #07070F;
}
.cfg-card__check svg { width: 12px; height: 12px; }

/* ─── ICONA NUDA + INGRANDITA (verbatim mockup, righe 167-169) ─────────────
   Il mockup NON ha box dietro l'icona: ".cfg-card__icon{color:var(--text-2);
   margin-bottom:.35rem}" + ".cfg-card.sel .cfg-card__icon{color:cyan}" +
   "svg{34px}". pages.css invece le mette un RIQUADRO (1268: 58px, raggio 12px,
   background rgba .04, display:flex centrato) e tinte di sfondo in hover/sel
   (1284-1305): è il box chiaro che si intravede.

   Qui lo ANNULLO del tutto e lascio SOLO color + margin, come il mockup:
     · niente width/height/min-width/padding/border/border-radius del box;
     · display:block (no flex-centering) → l'svg sta a SINISTRA come nel mockup;
     · background:none !important → copre default + hover + sel + color-variant
       in un colpo (le regole pages NON sono !important, quindi !important vince
       a prescindere dalla specificità).

   SCOPE: solo card a colonna. Escludo --delivery e --qty (layout a RIGA con
   box-icona proprio, 1353-1359), come già in Sez.1: lì il riquadro è voluto.

   DIMENSIONE svg → 48px (non 34): le nostre sprite (viewBox 64, disegno in
   porzione ridotta del canvas) a 34px apparivano piccole; 48px le rende grandi
   come nel mockup ed è un compromesso ragionevole anche per le legacy (viewBox
   24, che riempiono il canvas). Gli accenti CMYK fissi nei path delle sprite
   (rect fill cyan/magenta) restano: voluto. */
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card__icon {
  display: block;
  width: auto;
  height: auto;
  min-width: 0;
  padding: 0;
  border: 0;
  border-radius: 0;
  background: none !important;
  color: var(--text-2);
  margin-bottom: 0.5rem;
}
/* SVG a 76px = stessa resa del catalogo icone (.it .ic{width:76px;height:76px}).
   L'ingrandimento lo fa il box CSS, NON lo sprite: lo scale(1.25) sui formati è
   stato rimosso da icone.svg, quindi tutte le icone hanno lo STESSO stroke 2.4
   → tratto e dimensione uniformi tra i gruppi. I formati mantengono la scala ISO
   interna naturale (A6<A5<A4<A3). Vale per sprite (viewBox 64) e legacy (viewBox
   24): entrambe vettoriali, nitide. margin-inline:auto centra l'svg nel box. */
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card__icon svg {
  display: block;
  width: 76px;
  height: 76px;
  margin-inline: auto;
}
/* accento icona quando selezionata (plain; color-variant tengono il loro colore). */
.cfg-card.sel:not(.cfg-card--magenta):not(.cfg-card--yellow):not(.cfg-card--blue) .cfg-card__icon {
  color: var(--cyan);
}

/* ─── Tipografia label / sub ───────────────────────────────────────────────*/
.cfg-card__label {
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: 0.92rem;
  line-height: 1.15;
}
.cfg-card__sub {
  font-family: var(--f-mono);
  font-size: 0.62rem;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--text-3);
  line-height: 1.3;
}

/* ─── Badge "Popolare" ──────────────────────────────────────────────────────
   Da centrato a ancorato a sinistra (look variante-b). */
.cfg-card__badge {
  left: 0.7rem;
  transform: none;
  top: -8px;
  background: var(--yellow);
  color: #07070F;
  font-family: var(--f-mono);
  font-size: 0.54rem;
  font-weight: 700;
  letter-spacing: 0.1em;
  padding: 0.16rem 0.45rem;
}

/* ─── Intestazione step numerata ───────────────────────────────────────────
   .cfg-block-head / -num / -title in stile "scheda di lavorazione". */
.cfg-block-head {
  gap: 0.7rem;
  margin-bottom: 0.95rem;
}
.cfg-block-num {
  width: 30px; height: 30px;
  min-width: 30px;
  border-radius: var(--r-sm);
  border: 1px solid var(--border-2);
  background: rgba(0, 212, 255, 0.06);
  font-family: var(--f-mono);
  font-weight: 700;
  font-size: 0.7rem;
  color: var(--cyan);
}
/* alcune block-num contengono un'icona SVG invece del numero (qty/upload/soggetti) */
.cfg-block-num svg { width: 18px; height: 18px; }
.cfg-block-title {
  font-family: var(--f-display);
  font-weight: 700;
  font-size: 1.5rem;
  letter-spacing: 0.01em;
  text-transform: uppercase;
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 2 — TABELLA TIRATURA / VELOCITÀ (look variante-b)
   ------------------------------------------------------------------------
   ADATTAMENTO ALLA REALTÀ (≠ mockup): la tabella reale è cell-based ed è già
   molto più evoluta del mockup. Ganci INTATTI, solo stilati:
     · #ptv2-body popolato da js/configuratore.js (celle [data-qty][data-consegna])
     · selezione = td.ptv2-sel (NON tr.sel: il JS non usa righe selezionate)
     · corsie colore = classi reali .ptv2-td-std/-fast/-urg (NON td:nth-child)
     · header date dal delivery-engine in #ptv2-hd-std/-fast/-urg (= .ptv2-speed-sub)
   pages.css impone la palette Standard=BLU (#4a90e2). La variante-b la vuole
   CYAN: qui ri-coloro SOLO la corsia Standard blu→cyan (fast=magenta e
   urg=giallo già combaciano col mockup). pages.css usa !important diffuso →
   gli override usano !important con specificità pari alle regole vincenti.
   NOTA mobile: il markup reale NON ha la versione .pt-mobile/.ptm; la tabella
   resta responsive con scroll orizzontale (overflow-x del wrapper, già in
   pages.css) — NON introdotta alcuna versione mobile a blocchi.
   ════════════════════════════════════════════════════════════════════════ */

/* ─── Nota consegna → box info cyan (mockup 178) ───────────────────────────
   pages.css la rende un riquadro grigio neutro; la variante-b la vuole cyan. */
.ptv2-delivery-note {
  background: rgba(0, 212, 255, 0.05);
  border: 1px solid rgba(0, 212, 255, 0.18);
  color: #9be7ff;
  font-family: var(--f-body);
}
.ptv2-delivery-note svg { color: var(--cyan); }

/* ─── Cornice tabella (mockup 180) ─────────────────────────────────────────
   Additivo: la base pages.css imposta solo overflow-x (nessun bordo). */
.price-table-wrap {
  border: 1px solid var(--border-2);
  border-radius: var(--r-md);
  background: rgba(7, 7, 15, 0.5);
}

/* ─── Corsia STANDARD: blu (#4a90e2) → cyan ────────────────────────────────
   Override 1:1 delle regole effettive di pages.css (stessa specificità +
   !important). fast/urg restano magenta/giallo (già conformi al mockup). */

/* bordo verticale corsia */
.ptv2-th-std,
.ptv2-td-std { border-left: 3px solid var(--cyan) !important; }

/* sfumatura corsia nel corpo — zebra (specificità 0,3,0, vince su .ptv2-td-std) */
.ptv2-row:nth-child(odd)  .ptv2-td-std { background: rgba(0, 212, 255, 0.05) !important; }
.ptv2-row:nth-child(even) .ptv2-td-std { background: rgba(0, 212, 255, 0.03) !important; }
/* fallback corsia (se la zebra non si applica) */
.ptv2-td-std { background: rgba(0, 212, 255, 0.045) !important; }

/* hover cella */
.ptv2-td-std:hover { background: rgba(0, 212, 255, 0.11) !important; }

/* colonna attiva (intera corsia illuminata) */
.ptv2-active-std .ptv2-td-std { background: rgba(0, 212, 255, 0.07) !important; }

/* cella selezionata — glow cyan della colonna */
.ptv2-td-std.ptv2-sel {
  background: rgba(0, 212, 255, 0.16) !important;
  box-shadow: inset 0 0 0 2px var(--cyan), inset 0 0 18px rgba(0, 212, 255, 0.18) !important;
}
/* selezione sotto hover-riga (specificità 0,4,0) */
.ptv2-row:hover .ptv2-td-std.ptv2-sel { background: rgba(0, 212, 255, 0.18) !important; }

/* header: nome colonna + data (delivery-engine) → cyan */
.ptv2-th-std .ptv2-speed-name { color: var(--cyan) !important; }
.ptv2-th-std .ptv2-speed-sub  { color: var(--cyan) !important; }

/* prezzo nella cella selezionata → cyan (specificità 0,3,0) */
.ptv2-td-std.ptv2-sel .ptv2-price { color: var(--cyan) !important; }

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 3 — TABELLA TIRATURA/VELOCITÀ · VERBATIM MOCKUP (DESKTOP + TABLET)
   ------------------------------------------------------------------------
   Porta la tabella reale al look del mockup variante-b
   (_design-proposta/variante-b/prodotto-mockup.html: CSS 176-195, 550-556).
   SOLO override estetici sui ganci esistenti — nessun markup, nessun JS.

   SCOPE ≥768px = "TEMPO 1" desktop/tablet. Sotto i 768px (mobile = "TEMPO 2",
   futura versione .ptm) la tabella resta INVARIATA: stile pages.css + scroll
   orizzontale del .price-table-wrap (overflow-x già in pages.css). Qui NON si
   introduce alcun markup .ptm: il mobile è fuori scope di questo intervento.

   pages.css applica !important diffuso (sez. ~3270-3407 e ~3630-3690): gli
   override qui sotto usano !important MIRATO solo dove una regola !important
   di pages.css vincerebbe altrimenti. L'id #ptv2-body alza la specificità
   (1,x,0) per zebra/hover/selezione senza ricorrere a !important.
   ════════════════════════════════════════════════════════════════════════ */
@media (min-width: 768px) {

  /* ─── G · Base: mono .84rem bianco (mockup 181) ──────────────────────────*/
  .price-table {
    font-family: var(--f-mono);
    font-size: 0.84rem;
    color: #fff;
  }

  /* ─── E · Testatina: tinta corsia tenue + separatore (mockup 182-186) ────
     pages.css azzera lo sfondo header a #0d0d1a !important e toglie il bordo:
     qui si ripristina la tinta cyan/magenta/giallo .06 e la linea del mockup. */
  .ptv2-head-row th {
    padding: 0.7rem 0.9rem !important;
    border-bottom: 1px solid var(--border-2) !important;
    vertical-align: top;
  }
  .ptv2-th-qty  { color: #c8c8c8 !important; }
  .ptv2-th-std  { background: rgba(0, 212, 255, 0.06) !important; }
  .ptv2-th-fast { background: rgba(255, 45, 120, 0.06) !important; }
  .ptv2-th-urg  { background: rgba(255, 214, 0, 0.06) !important; }

  /* ─── A · Gerarchia header: NOME grande, data sotto, gloss, pill ─────────
     Inverte lo stato di partenza (data 1.15rem/800 dominante) mantenendo la
     gerarchia nome > data > gloss. Dimensioni ALZATE in v7 per leggibilità
     (prima erano troppo piccole): nome .9rem, data .82rem, gloss .64rem
     (la pill è in SEZIONE 6). La data ("MAR 7 LUG", scritta dal JS nello
     stesso span .ptv2-speed-sub) e lo <small.ptv2-gl> restano nei loro
     elementi: NESSUNA modifica al JS. Lo spazio recuperato togliendo l'a capo
     della gloss (sotto) è usato per gap più ariosi. */
  .ptv2-speed-name {
    font-size: 0.9rem !important;
    letter-spacing: 0.05em;
    margin-bottom: 0;
  }
  .ptv2-speed-sub {
    font-size: 0.82rem !important;
    font-weight: 500 !important;
    letter-spacing: 0.02em !important;
    text-transform: none !important;   /* mantiene "gg lav."/.ptv2-gl minuscoli */
    margin-top: 0.3rem;
    opacity: 0.85;
  }
  /* "gg lavorativi (non festivi)" su UNA sola riga: il JS la scrive con un <br>
     (configuratore.js ~1094: innerHTML '…gg lavorativi<br>(non festivi)…').
     Lo neutralizzo via CSS — br{display:none} — e forzo nowrap così le due
     parti restano sulla stessa riga. Nessuna modifica al JS. */
  .ptv2-gl {
    font-size: 0.64rem;
    opacity: 0.75;
    margin-top: 0.15rem;
    white-space: nowrap;
  }
  .ptv2-gl br { display: none; }

  /* ─── B · Pill +0%/+20%/+50% → vedi SEZIONE 6 ────────────────────────────
     La pill di Standard NON è più un ::after qui: dalla v5 le tre pill sono
     <em class="ptv2-pct"> reali, figlie dirette del <th>, impilate in basso
     (testatina verbatim mockup). Stile e posizionamento nella SEZIONE 6. */

  /* ─── G · Celle: padding compatto mockup (th .7/.9 sopra, td .65/.9) ──────
     pages.css forza .9rem 1rem !important su entrambe → serve !important. */
  .ptv2-td-price,
  .ptv2-td-qty { padding: 0.65rem 0.9rem !important; }

  /* ─── G · Quantità: mono bianca/bold (mockup .pt-qty) ────────────────────*/
  .ptv2-td-qty {
    font-family: var(--f-mono);
    font-weight: 700;
    color: #fff !important;
  }

  /* ─── C · "TIR. NN" sotto la quantità via counter CSS (mockup .pt-tier) ───
     Numerazione progressiva delle righe, zero-padded, senza toccare il markup
     (il JS scrive solo "<strong>NNN pz</strong>" nella cella). */
  #ptv2-body { counter-reset: tir; }
  .ptv2-row  { counter-increment: tir; }
  .ptv2-td-qty::after {
    content: "TIR. " counter(tir, decimal-leading-zero);
    display: block;
    margin-top: 0.1rem;
    font-family: var(--f-mono);
    font-size: 0.58rem;
    font-weight: 400;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    color: var(--text-3);
  }

  /* ─── G · Prezzi: mono .84rem bianco (mockup: celle €, non display 1.1rem)
     pages.css impone display/900/1.1rem !important → override !important. Il
     prezzo della cella SELEZIONATA resta colorato (regole .ptv2-sel, 0,3,0). */
  .ptv2-price {
    font-family: var(--f-mono) !important;
    font-size: 0.84rem !important;
    font-weight: 500 !important;
    color: #fff !important;
    letter-spacing: 0 !important;
  }

  /* ─── E · Zebra corpo verbatim (mockup 190-191) ──────────────────────────
     #ptv2-body alza la specificità (1,2,0) sopra le pages.css
     .ptv2-row:nth-child() (0,2,0) — niente !important. Le tinte di colonna
     (.ptv2-td-*, !important) restano sopra; lo zebra traspare dalla colonna
     Quantità (cella trasparente). */
  #ptv2-body .ptv2-row:nth-child(odd)  { background: rgba(255, 255, 255, 0.025); }
  #ptv2-body .ptv2-row:nth-child(even) { background: rgba(0, 0, 0, 0.18); }

  /* hover riga → tinta cyan tenue (mockup 192) */
  #ptv2-body .ptv2-row:hover { background: rgba(0, 212, 255, 0.06); }

  /* ─── D · Selezione: barra-riga cyan + tinta di riga (mockup 193, 554) ────
     Il JS marca la CELLA (td.ptv2-sel), non la riga: :has() porta la tinta
     sulla <tr> che contiene la cella selezionata. La regola sta DOPO zebra e
     hover (stessa specificità 1,2,0) → vince anche durante l'hover di riga.
     La BARRA (mockup: box-shadow inset su <tr>) è applicata alla cella
     Quantità: con border-collapse:collapse il box-shadow su <tr> non viene
     renderizzato, sul td (bordo sinistro della riga) è robusto e identico.
     L'evidenziazione della CELLA selezionata (glow di colonna) resta gestita
     dalle .ptv2-td-*.ptv2-sel esistenti — invariata, color-coding preservato. */
  #ptv2-body .ptv2-row:has(.ptv2-sel) { background: rgba(0, 212, 255, 0.14); }
  #ptv2-body .ptv2-row:has(.ptv2-sel) .ptv2-td-qty {
    box-shadow: inset 3px 0 0 var(--cyan);
  }
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 4 — RIFINITURE TABELLA (≥768px) · identità verbatim col mockup
   ------------------------------------------------------------------------
   Allinea i dettagli residui al mockup (_design-proposta/variante-b/
   prodotto-mockup.html, righe 176-195 e 550-556). SOLO CSS, scope desktop/
   tablet: sotto i 768px nulla cambia (mobile = Tempo 2, tabella in scroll).
   La DATA reale nell'header (delivery-engine, es. "MAR 7 LUG") NON è toccata:
   resta nel suo span .ptv2-speed-sub, nessuna modifica al JS/markup.
   ════════════════════════════════════════════════════════════════════════ */
@media (min-width: 768px) {

  /* ─── 1 · Via le barre verticali colorate spesse ─────────────────────────
     Il mockup separa le colonne SOLO con la tinta di sfondo: nessun bordo
     verticale. Le barre cyan/magenta/giallo full-height del reale sono il
     border-left:3px di pages.css (3279-3286) + SEZIONE 2 (Standard). Le azzero
     — header inclusa — e tolgo anche il filo destro della colonna Quantità
     (mockup: zero separatori verticali). L'identità di colonna resta affidata
     alla tinta header .06 e alla corsia di sfondo nel corpo, come nel mockup. */
  .ptv2-th-std,  .ptv2-td-std,
  .ptv2-th-fast, .ptv2-td-fast,
  .ptv2-th-urg,  .ptv2-td-urg { border-left: 0 !important; }
  .ptv2-td-qty,
  .ptv2-th-qty { border-right: 0 !important; }

  /* ─── 2 · Separatori orizzontali netti come il mockup (righe 194-195) ─────
     border-bottom 1px var(--border) a livello di CELLA: con border-collapse:
     collapse il bordo di cella vince su quello di riga di pages.css (tr,
     rgba .05) e rende il filo nitido. Ultima riga senza bordo. */
  .ptv2-row td { border-bottom: 1px solid var(--border); }
  .ptv2-row:last-child td { border-bottom: 0; }

  /* ─── 3 · Header e celle allineati a SINISTRA (mockup: th + tbody td left)
     pages.css centra header (.ptv2-th-speed) e prezzi (.ptv2-td-price); il
     mockup è interamente left. Nome/data/pill ereditano l'allineamento del th,
     così l'intera colonna (testatina + prezzi) è a filo sinistro. */
  .ptv2-th-speed { text-align: left !important; }
  .ptv2-td-price { text-align: left !important; }

  /* ─── 4 · Padding/altezza righe: GIÀ verbatim dalla SEZIONE 3 ─────────────
     th .7rem .9rem, td .65rem .9rem (mockup 182 e 194): nessuna ulteriore
     modifica — la diversa percezione di spaziatura era data dalle barre
     verticali e dalla centratura, ora corretti ai punti 1 e 3. */
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 5 — CONDIZIONI DI DIMENSIONAMENTO COLONNE = MOCKUP (≥768px)
   ------------------------------------------------------------------------
   Obiettivo: far AUTO-dimensionare le colonne come nel mockup
   (~176|195|195|220px) replicandone le CONDIZIONI, senza imporre width.

   DIVERGENZE pages.css individuate (tutte ≥768px; le regole mobile <768
   restano intatte — Tempo 2):
     · 2205  .price-table border-collapse: collapse  → mockup: SEPARATE
     · 2970  .pricetable-v2 table-layout: FIXED       → mockup: auto
              ↑ CAUSA PRIMARIA: con 'fixed' le colonne ignorano il contenuto
                e si distribuiscono in modo uniforme/da width esplicite.
     · 2985  .ptv2-th-qty   width: 110px              → mockup: nessuna width
     · 2990  .ptv2-th-speed min-width: 130px          → mockup: nessuna min-width
     · 2974  th padding .875rem 1rem                  → mockup .7/.9 (già fix Sez.3)
     · 3279-3286 border-left:3px colorati (occupano larghezza) → già rimossi Sez.4
   ════════════════════════════════════════════════════════════════════════ */
@media (min-width: 768px) {

  /* 1 · Modello tabella del mockup: SEPARATE + border-spacing 0, width 100%,
     table-layout AUTO (mai fixed) → le larghezze nascono dal contenuto.
     (I separatori orizzontali della Sez.4 sono a livello di cella: restano
     nitidi anche in separate; la barra-selezione e lo zebra non cambiano.) */
  .price-table {
    border-collapse: separate;
    border-spacing: 0;
    width: 100%;
  }
  .pricetable-v2 { table-layout: auto; }

  /* 3 · Via le larghezze esplicite → colonne in AUTO, nessuna forzatura.
     Annulla width:110px (Quantità) e min-width:130px (colonne velocità). */
  .ptv2-th-qty   { width: auto; }
  .ptv2-th-speed { min-width: 0; }

  /* 6 · nowrap su intestazioni e celle (mockup 182, 194): impedisce il
     ritorno a capo che falserebbe la larghezza misurata della colonna.
     La data (.ptv2-speed-sub) e lo <small.ptv2-gl> conservano il wrap proprio
     (regole esistenti), così la data reale del delivery-engine resta intatta. */
  .ptv2-head-row th,
  .ptv2-row td { white-space: nowrap; }
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 6 — TESTATINA: pill % IN BASSO su riga propria (verbatim mockup)
   ------------------------------------------------------------------------
   Disposizione testatina impilata come il mockup:
     1. NOME (.ptv2-speed-name)        — in alto, grande
     2. DATA reale (.ptv2-speed-sub)   — sotto (scritta dal JS, NON toccata)
     3. "gg lavorativi…" (.ptv2-gl)    — piccola (dentro la data)
     4. PILL % (.ptv2-pct)             — in basso, su riga propria

   PERCHÉ NON CSS-ONLY PURO (order): 'order' riordina solo i figli DIRETTI del
   contenitore flex. La pill +20%/+50% era una NIPOTE (dentro .ptv2-speed-name)
   e quella +0% un ::after del nome → irraggiungibili da order sul <th>.
   MICRO-MODIFICA MARKUP (stampa-config.php, autorizzata): la <em.ptv2-pct> è
   stata estratta da .ptv2-speed-name e resa FIGLIA DIRETTA del <th>, dopo la
   data (per Standard aggiunta una <em.ptv2-pct>+0% reale al posto del ::after).
   Così, in flusso blocco normale (th = table-cell, figli impilati), la pill
   finisce IN BASSO DA SOLA: niente display:flex/order sul <th> (che
   altererebbe il dimensionamento table-cell della Sez.5). Classi e contenuto
   preservati; id ptv2-hd-*, data-*, .ptv2-sel e JS invariati.

   EFFETTO COLLATERALE POSITIVO: tolta la pill inline, la larghezza colonna ora
   è guidata dal solo nome ("Prioritaria") come nel mockup → le colonne
   velocità si avvicinano a 195/220 senza l'allargamento da "Veloce +20%".
   ════════════════════════════════════════════════════════════════════════ */
@media (min-width: 768px) {

  /* Pill su riga propria sotto la data, stile mockup (riga 188): contorno
     currentColor, raggio pill, piccola, sfondo trasparente. Override dello
     stile "riempito"/inline di pages.css (3333-3349) e del margin-left (3339). */
  .ptv2-pct {
    display: inline-block;
    margin: 0.35rem 0 0 0 !important;    /* gap dalla gloss; annulla margin-left inline */
    padding: 0.08rem 0.42rem !important;
    font-size: 0.62rem !important;
    font-weight: 700;
    line-height: 1.4;
    letter-spacing: 0.02em;
    border: 1px solid currentColor !important;
    border-radius: var(--r-pill);
    background: transparent !important;
    vertical-align: baseline;
    opacity: 0.9;
  }
  /* colore pill = colore corsia (currentColor governa bordo + testo) */
  .ptv2-th-std  .ptv2-pct { color: var(--cyan)    !important; }
  .ptv2-th-fast .ptv2-pct { color: var(--magenta) !important; }
  .ptv2-th-urg  .ptv2-pct { color: var(--yellow)  !important; }
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 7 — CARD: nuovo layout (icona grande sx + testo compatto) · GLOBALE
   ------------------------------------------------------------------------
   Layout card validato su formato/lato, ora ESTESO a TUTTE le .cfg-card a
   colonna della pagina prodotto (rimosso l'isolamento per-step #step-*) per
   uniformare l'intera pagina. Parte dal layout variante-b (icona alto-sx,
   testo sotto-sx) + distanze "mockup Corrado":
     1) icona più GRANDE e NUDA (60px, vs 76 di Sez.1 / 34 del mockup), a SINISTRA;
     2) icona più VICINA al bordo sup-sinistro (padding sup/sx ridotto);
     3) righe testo RAVVICINATE + titolo un filo più grande (1rem) per prominenza.
   Resto INVARIATO: check quadrato alto-destra, badge, bordo + inset-glow cyan in
   .sel; color-coding --magenta/--yellow/--blue/--verifica-paid preservato (qui
   si toccano solo dimensioni/distanze, mai i colori di stato).

   SCOPE = stesse esclusioni della Sez.1: tutte le card a COLONNA, escluse
   --delivery e --qty (layout a RIGA con box-icona proprio). Selettori a pari
   specificità della Sez.1 → vincono per ordine sorgente (SEZIONE 7 dopo Sez.1).
   Nessuna modifica a markup/JS: solo override estetici sui ganci .cfg-card__*.

   CARD "GRAFICA"/"VERIFICA" (card larghe, .cfg-cards--grafica 2 col): label +
   sub + prezzo stanno nel wrapper .cfg-card-text → gli do lo stesso ritmo
   verticale e tengo il prezzo (.cfg-card__price-sup, +€) distinto poco sotto.

   SCALA ISO FORMATI PRESERVATA: box svg FISSO (60px) → le sprite ic-formato-*
   disegnano il foglio in proporzione nello stesso viewBox 64 → A6<A5<A4<A3<SRA3
   resta visibile. Nessuna normalizzazione per-formato.
   ════════════════════════════════════════════════════════════════════════ */

/* 1-2-3 · icona grande, nuda, a sinistra e vicina al bordo sup-sx; testo compatto */
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) {
  padding: 0.62rem 0.72rem 0.8rem 0.62rem;
  gap: 0.14rem;
}
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card__icon {
  margin-bottom: 0.18rem;
}
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card__icon svg {
  width: 60px; height: 60px;    /* più grande del 34 mockup, nuda */
  margin-inline: 0;             /* a sinistra, non centrata */
}
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card__label {
  font-size: 1rem;
  line-height: 1.12;
}

/* card grafica/verifica: stesso ritmo verticale dentro il wrapper testo */
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card-text {
  display: flex;
  flex-direction: column;
  gap: 0.14rem;
}
.cfg-card:not(.cfg-card--delivery):not(.cfg-card--qty) .cfg-card__price-sup {
  margin-top: 0.28rem;          /* prezzo distinto, poco sotto la descrizione */
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 8 — PROD-INTRO · HEADER CONFIGURATORE · GALLERY CHROME (verbatim)
   ------------------------------------------------------------------------
   Porta la pagina prodotto al look "scheda di lavorazione / press ticket" del
   mockup variante-b (_design-proposta/variante-b/prodotto-mockup.html, blocco
   <style> righe 40, 89-157). SOLO override estetici: pages.css è caricato prima,
   quindi queste regole vincono a pari specificità. GANCI INTATTI — #gallery-main
   / #gallery-img / .prod-thumb[data-src/-alt/-target] / .sel / .gallery-placeholder
   / data-product-* / itemprop NON sono toccati.

   MICRO-MARKUP aggiunto in stampa-config.php (autorizzato): wrapper .gallery-stage
   attorno a #gallery-main + righelli/quote/bleed; <span.cfg-spec-no> in ogni head;
   numeri step zero-padded (str_pad). Le quote .dim-x/.dim-y sono rese server-side
   dal formato selezionato e sincronizzate live da uno script passivo in coda pagina.
   ════════════════════════════════════════════════════════════════════════ */

/* ─── 1 · Sfondo quadrettato (griglia 46px) SCOPATO alla pagina prodotto ───
   mockup riga 40 (lì su body). Qui solo su .product-page → copre l'intera
   pagina prodotto senza toccare body/pages.css globale. */
.product-page {
  background-color: var(--bg);
  background-image:
    linear-gradient(rgba(255, 255, 255, 0.018) 1px, transparent 1px),
    linear-gradient(90deg, rgba(255, 255, 255, 0.018) 1px, transparent 1px);
  background-size: 46px 46px;
}

/* ─── 2 · Intro: spaziatura + griglia 1fr/1fr (mockup 89, 93) ──────────────*/
.prod-intro { padding: 1.6rem 0 2.4rem; }
.prod-intro-grid {
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: clamp(24px, 4vw, 56px);
}

/* ─── 3 · Breadcrumb mono "press ticket" (mockup 90) ──────────────────────*/
.breadcrumb {
  font-family: var(--f-mono);
  font-size: 0.68rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  gap: 0.5rem;
  margin-bottom: 1.6rem;
}

/* ─── 4 · GALLERY CHROME: stage + righelli + quote + bleed + crop-mark ─────
   mockup 96-114. .gallery-stage avvolge #gallery-main (markup); righelli e
   quote sono assoluti dentro lo stage (che ha il padding per ospitarli). */
.prod-gallery-main {
  aspect-ratio: 1 / 1;                 /* mockup 105 (era 4/3 in pages.css) */
  border-color: var(--border-2);
}
.gallery-stage { position: relative; padding: 30px 30px 16px 30px; }
.ruler-x {
  position: absolute; top: 8px; left: 30px; right: 30px; height: 16px;
  border-bottom: 1px solid var(--border-2);
  background-image: repeating-linear-gradient(90deg, var(--border-2) 0 1px, transparent 1px 100%);
  background-size: 11px 7px; background-position: bottom; background-repeat: repeat-x;
}
.ruler-y {
  position: absolute; left: 8px; top: 30px; bottom: 16px; width: 16px;
  border-right: 1px solid var(--border-2);
  background-image: repeating-linear-gradient(0deg, var(--border-2) 0 1px, transparent 1px 100%);
  background-size: 7px 11px; background-position: right; background-repeat: repeat-y;
}
.dim-x {
  position: absolute; top: -6px; left: 50%; transform: translateX(-50%);
  font-family: var(--f-mono); font-size: 0.6rem; color: var(--cyan);
  letter-spacing: 0.1em; background: var(--bg); padding: 0 0.4rem;
}
.dim-y {
  position: absolute; left: -8px; top: 50%;
  transform: translate(-50%, -50%) rotate(-90deg); transform-origin: center;
  font-family: var(--f-mono); font-size: 0.6rem; color: var(--magenta);
  letter-spacing: 0.1em; background: var(--bg); padding: 0 0.4rem; white-space: nowrap;
}
.bleed-tag {
  position: absolute; right: 34px; top: 34px;
  font-family: var(--f-mono); font-size: 0.54rem; letter-spacing: 0.08em;
  text-transform: uppercase; color: var(--text-2);
  border: 1px dashed var(--border-2); border-radius: 3px; padding: 0.12rem 0.4rem; z-index: 4;
}
/* crop-mark agli angoli dell'anteprima (mockup 107-109) */
.prod-gallery-main::before,
.prod-gallery-main::after {
  content: ""; position: absolute; width: 18px; height: 18px; z-index: 3; opacity: 0.6;
}
.prod-gallery-main::before { top: 9px; left: 9px; border-top: 1.5px solid var(--text-2); border-left: 1.5px solid var(--text-2); }
.prod-gallery-main::after  { bottom: 9px; right: 9px; border-bottom: 1.5px solid var(--text-2); border-right: 1.5px solid var(--text-2); }

/* ─── 5 · PRODUCT INFO verbatim (mockup 130-142) ──────────────────────────
   Da flex-gap (pages.css) a flusso a blocco con i margini del mockup. */
.prod-info { display: block; }
.prod-badge {
  gap: 0.4rem;
  font-family: var(--f-mono);
  font-size: 0.62rem;
  letter-spacing: 0.18em;
  border: 1px solid rgba(0, 212, 255, 0.35);
  background: rgba(0, 212, 255, 0.08);
  border-radius: var(--r-pill);
  padding: 0.3rem 0.7rem;
  margin-bottom: 1rem;
}
.prod-badge::before {
  content: ""; width: 7px; height: 7px; border-radius: 50%;
  background: var(--cyan); display: inline-block; flex-shrink: 0;
}
.prod-title {
  font-weight: 800;
  font-size: clamp(2.4rem, 5.5vw, 3.8rem);
  line-height: 0.92;
  letter-spacing: -0.01em;
  margin: 0;
}
.prod-title-sub {
  font-family: var(--f-ui);
  color: var(--text-2);
  font-size: 0.96rem;
  margin: 0.5rem 0 0;
}
.prod-reviews { margin: 1rem 0 1.2rem; }
.prod-stars { letter-spacing: 0.12em; font-size: 1rem; }
.prod-desc {
  font-size: 0.98rem;
  line-height: 1.6;
  color: var(--text-2);
  background: none;
  border: 0;
  border-radius: 0;
  padding: 0;
  margin: 0 0 1.4rem;
}
.prod-highlights { gap: 0.6rem; margin: 0; }
.prod-hl-item { font-size: 0.9rem; color: #dcdcec; }
.prod-hl-item svg { width: 18px; height: 18px; }

/* ─── 6 · Etichetta intro configuratore (mockup 147): box → border-left ────*/
.cfg-intro-label {
  font-family: var(--f-mono);
  font-size: 0.68rem;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--text-2);
  border: 0;
  border-left: 3px solid var(--cyan);
  border-radius: 0;
  background: none;
  padding: 0.3rem 0 0.3rem 0.7rem;
  margin-bottom: 1.6rem;
  display: block;
}
.cfg-intro-label::before { content: none; display: none; }

/* ─── 7 · Step SENZA box-cornice (mockup: .prod-body pulito, .cfg-block solo
   margine). pages.css mette bg-card+bordo+padding ad OGNI .cfg-block: lo annullo
   per gli step, ECCETTO .prod-upload-block (resta una card). ───────────────*/
.cfg-block:not(.prod-upload-block) {
  background: none;
  border: 0;
  border-radius: 0;
  padding: 0;
  margin-bottom: 1.8rem;
}

/* ─── 8 · Scritte SPEC laterali (mockup 157): mono, spinte a destra ────────*/
.cfg-spec-no {
  margin-left: auto;
  font-family: var(--f-mono);
  font-size: 0.6rem;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--text-3);
}
/* soggetti: la toggle-btn è già a destra (margin-left:auto); la spec resta a
   filo titolo per non litigare con due auto-margin. */
#step-soggetti .cfg-spec-no { margin-left: 0; }

/* ─── 9 · Info button (mockup 155-156): cerchio 20px, bordo border-2,
   trasparente, hover cyan. pages.css (riga 5978) lo fa 22px con bordo/sfondo
   cyan: riallineo al mockup. L'svg "i" interno resta (gancio tooltip). ─────*/
.cfg-info-btn {
  width: 20px; height: 20px;
  margin-left: 0.1rem;
  border-radius: 50%;
  border: 1px solid var(--border-2);
  background: transparent;
  color: var(--text-3);
  opacity: 1;
}
.cfg-info-btn:hover,
.cfg-info-btn:focus-visible,
.cfg-info-btn.is-open {
  color: var(--cyan);
  border-color: var(--cyan);
  background: transparent;
}
.cfg-info-btn svg { width: 13px; height: 13px; }

/* ─── 10 · Body grid: config + summary 372px (mockup 145-146) ──────────────*/
.prod-body { padding: 2.4rem 0; }
.prod-body-grid {
  grid-template-columns: minmax(0, 1fr) 372px;
  gap: clamp(20px, 2.6vw, 40px);
}

/* ─── 11 · Wrapper .cfg SENZA cornice (mockup: nessun box attorno agli step)
   .cfg (css/style.css:1938) ha bg-card + bordo + radius + overflow:hidden →
   è il riquadro attorno all'INTERO configuratore (gli step in loop). Nel mockup
   non esiste un wrapper equivalente: gli step stanno su fondo pulito (solo il
   quadrettato di .product-page). Azzero box + overflow (così i badge .sel a
   top:-8px della prima riga non vengono clippati). .cfg non ha padding → la
   spaziatura resta data da .cfg-block (margin-bottom 1.8rem): nulla da toccare.
   Le .cfg-card mantengono il loro bg/bordo proprio (non toccate). ───────────*/
.cfg {
  background: transparent;
  border: 0;
  border-radius: 0;
  overflow: visible;
}

/* ─── Mobile: spec-no upload a capo (mockup 757-758), e nessun box-cornice da
   compensare (gli step sono già senza riquadro). ──────────────────────────*/
@media (max-width: 767px) {
  .prod-upload-block .cfg-spec-no { margin-left: 0; flex: 0 0 100%; }
}

/* ─── 12 · ZONA CARICAMENTO FILE — restyle estetico verbatim variante-b ───────
   Firma della sezione: dropzone "prepara il file" con crop-mark (tratteggio
   diagonale 45° = taglio + squadrette angolari di registro). Solo ASPETTO.
   pages.css (2537+) resta la base FUNZIONALE: stati .has-file/.uploading/
   .dragover, .upload-input, .upload-body e i nodi runtime .uprev-* /.
   .upload-progress-* NON si toccano. Gli override del resting-state sono scoped
   a .prod-upload-block (specificità ≥ pages.css) e limitati a :not(.has-file)
   così quando un file è caricato resta la veste "file presente" di pages.css. */

/* card contenitore (resta una card) */
.prod-upload-block {
  border: 1px solid var(--border-2);
  border-radius: var(--r-lg);
  background: var(--bg-card);
  padding: 1.5rem;
}

/* dropzone: hatch diagonale + bordo dashed */
.prod-upload-block .upload-zone:not(.has-file) {
  position: relative;
  border: 1.5px dashed var(--border-2);
  border-radius: var(--r-md);
  background:
    repeating-linear-gradient(45deg, rgba(255,255,255,.012) 0 12px, transparent 12px 24px),
    var(--bg-input);
  padding: 2.4rem 1.5rem;
  text-align: center;
  cursor: pointer;
  transition: border-color .15s, background .15s;
}
.prod-upload-block .upload-zone:not(.has-file):hover {
  border-color: var(--cyan);
  background: rgba(0,212,255,.04);
}

/* CROP-MARK: squadrette angolari (registro di taglio) — solo a riposo */
.prod-upload-block .upload-zone:not(.has-file)::before,
.prod-upload-block .upload-zone:not(.has-file)::after {
  content: "";
  position: absolute;
  width: 16px; height: 16px;
  opacity: .5;
}
.prod-upload-block .upload-zone:not(.has-file)::before {
  top: 10px; left: 10px;
  border-top: 1.5px solid var(--text-2);
  border-left: 1.5px solid var(--text-2);
}
.prod-upload-block .upload-zone:not(.has-file)::after {
  bottom: 10px; right: 10px;
  border-bottom: 1.5px solid var(--text-2);
  border-right: 1.5px solid var(--text-2);
}

/* annullo il gap di .upload-body (pages.css) per ottenere il ritmo del mockup,
   affidato ai margini espliciti di icona/hint qui sotto */
.prod-upload-block .upload-body { gap: 0; }

/* icona: cerchio cyan. Nel markup reale .upload-icon È lo <svg> (nessun wrapper):
   applico il cerchio direttamente all'svg (background+border+radius+padding).
   box-sizing:border-box → 54px = diametro esterno, icona resa ~28px all'interno.
   VIA SCELTA: CSS-only, nessun micro-markup. */
.prod-upload-block .upload-icon {
  box-sizing: border-box;
  width: 54px; height: 54px;
  margin: 0 auto .7rem;
  padding: 12px;
  border-radius: 50%;
  background: rgba(0,212,255,.08);
  border: 1px solid rgba(0,212,255,.3);
  color: var(--cyan);
}

/* testo dropzone */
.prod-upload-block .upload-primary {
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: 1rem;
  color: #fff;
}
.prod-upload-block .upload-link { color: var(--cyan); text-decoration: underline; }
.prod-upload-block .upload-hint {
  font-family: var(--f-mono);
  font-size: .66rem;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--text-3);
  margin-top: .5rem;
}

/* nota sicurezza */
.prod-upload-block .upload-note {
  display: flex;
  gap: .5rem;
  align-items: flex-start;
  margin-top: 1rem;
  font-size: .8rem;
  color: var(--text-2);
}
.prod-upload-block .upload-note svg {
  width: 16px; height: 16px;
  flex-shrink: 0;
  margin-top: 1px;
  color: var(--text-3);
}
.prod-upload-block .upload-note a { color: var(--cyan); }

/* nome lavorazione (selettori adattati ai nomi reali: -label/-input/-hint) */
.prod-upload-block .upload-nome-wrap { margin: 1rem 0; }
.prod-upload-block .upload-nome-label {
  display: flex;
  align-items: center;
  gap: .45rem;
  font-family: var(--f-mono);
  font-size: .66rem;
  letter-spacing: .1em;
  text-transform: uppercase;
  color: var(--text-2);
  margin-bottom: .5rem;
}
.prod-upload-block .upload-nome-label svg { width: 15px; height: 15px; color: var(--cyan); }
.prod-upload-block .upload-nome-input {
  width: 100%;
  background: var(--bg-input);
  border: 1px solid var(--border-2);
  border-radius: var(--r-sm);
  padding: .7rem .85rem;
  color: #fff;
  font-family: var(--f-body);
  font-size: .92rem;
}
.prod-upload-block .upload-nome-hint { font-size: .74rem; color: var(--text-3); margin-top: .4rem; }

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 2 · STICKY SUMMARY (riepilogo "Il Tuo Preventivo")
   ------------------------------------------------------------------------
   Porting VERBATIM del look variante-b del riepilogo ordine dal mockup
   _design-proposta/variante-b/prodotto-mockup.html (regole CSS 224-258).
   SOLO override estetici: nessun markup nuovo, nessun gancio JS toccato.

   Adattamenti di selettore (il markup REALE diverge dal mockup):
     mockup .ss-row .k            → reale .ss-row-key
     mockup .ss-row .v            → reale .ss-row-val
     mockup .iva-toggle-btn[aria-pressed="true"] → reale .iva-toggle-btn.sel
        (lo stato attivo è la classe .sel scritta da js/configuratore.js)
     mockup .summary-tot-final .k / .v → reale span:first-child / :last-child

   pages.css stila già il summary in DUE blocchi (base ~2251 + override
   magenta con !important ~3697). Per vincere uso il prefisso .prod-summary-col
   (specificità ≥ pages.css, e prodotto-vb è caricato DOPO pages.css) e
   !important SOLO dove pages.css lo impone.

   PRESERVATI INTATTI di proposito (NON ridisegnati qui):
     · .summary-delivery-box → semaforo FUNZIONALE giallo/cyan/magenta
       (Standard/Fast/Urgent) pilotato da classi JS .delivery-fast/-urgent:
       il mockup mostra solo lo stato cyan statico, appiattirlo perderebbe
       informazione reale → lasciato a pages.css.
     · #price-breakdown / .price-row → dettaglio prezzo iniettato da
       configuratore.js (già a tema, assente nel mockup).
     · #ss-price in promo → resta magenta via guardia body[data-promo-active]
       (la logica promo di shop-core.js scrive il colore inline su #ss-price).
   ════════════════════════════════════════════════════════════════════════ */

/* Card: bordo/raggio mockup */
.prod-summary-col .summary-card {
  border: 1px solid var(--border-2);
  border-radius: var(--r-lg);
}

/* Header glassmorphism + barra gradient CMYK (cyan→magenta→yellow) */
.prod-summary-col .summary-glass-header {
  padding: 1.1rem 1.25rem;
  background: linear-gradient(135deg, rgba(0,212,255,.14), rgba(255,45,120,.1));
  border-bottom: 1px solid var(--border-2);
  position: relative;
}
.prod-summary-col .summary-glass-header::after {
  content: "";
  position: absolute;
  left: 0; right: 0; bottom: 0;
  height: 3px;
  background: linear-gradient(90deg, var(--cyan), var(--magenta), var(--yellow));
}
.prod-summary-col .summary-glass-label {
  font-family: var(--f-mono);
  font-size: .62rem;
  font-weight: 400;
  letter-spacing: .2em;
  text-transform: uppercase;
  color: var(--text-2);
}
.prod-summary-col .summary-glass-title {
  font-family: var(--f-display);
  font-weight: 800;
  font-size: 1.7rem;
  letter-spacing: normal;
  text-transform: uppercase;
  line-height: 1;
  margin-top: .2rem;
  color: var(--text);
  text-shadow: none;
}

/* Nome prodotto: sottotitolo (non più micro-label uppercase) */
.prod-summary-col .summary-product-name {
  padding: 1.1rem 1.25rem 0;
  margin-bottom: .7rem;
  background: none;
  border: 0;
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: .92rem;
  letter-spacing: normal;
  text-transform: none;
  color: var(--text-2);
}

/* Prezzo grande (#price-head) + unitario, linea tratteggiata sotto */
.prod-summary-col .summary-price-head {
  padding: 0 1.25rem .7rem;
  border-bottom: 1px dashed var(--border-2);
}
.prod-summary-col .summary-price-val {
  font-family: var(--f-ui);
  font-weight: 700;
  font-size: 2rem;
  color: #fff !important;            /* batte pages.css 3769 (magenta !important) */
  letter-spacing: -.02em !important;
  text-shadow: none !important;
}
.prod-summary-col .summary-price-unit {
  font-family: var(--f-mono);
  font-size: .66rem;
  text-transform: uppercase;
  color: var(--text-3);
}

/* Risparmio (#price-saving): testo mono giallo, niente pillola.
   Il display (none/inline-flex) resta gestito da configuratore.js. */
.prod-summary-col .summary-saving {
  margin: .4rem 1.25rem 0;
  padding: 0;
  background: none;
  border: 0;
  border-radius: 0;
  width: auto;
  font-family: var(--f-mono);
  font-size: .68rem;
  font-weight: 400;
  color: var(--yellow);
}

/* Righe spec: key mono uppercase, val chiara allineata a destra */
.prod-summary-col .summary-card .summary-rows {
  padding: 0 1.25rem;
  margin: .7rem 0;
  border-bottom: 0;
}
.prod-summary-col .summary-card .ss-row {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 1rem;
  padding: .36rem 0;
  font-size: .82rem;
  border-bottom: 1px solid var(--border);
}
.prod-summary-col .summary-card .ss-row:last-child { border-bottom: 0; }
.prod-summary-col .summary-card .ss-row-key {
  font-family: var(--f-mono);
  font-size: .62rem;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--text-3);
}
.prod-summary-col .summary-card .ss-row-val {
  color: #e6e6f0;
  text-align: right;
  font-weight: 500;
}
.prod-summary-col .summary-card .ss-row-val--cyan { color: var(--cyan); }

/* Toggle IVA a pillola (stato attivo = .sel scritta dal JS) */
.prod-summary-col .iva-toggle-wrap {
  display: flex;
  gap: .3rem;
  margin: .6rem 1.25rem;
  padding: .2rem;
  background: var(--bg-input);
  border: 1px solid var(--border-2) !important;  /* batte border-bottom-color magenta !important (pages 3784) */
  border-radius: var(--r-pill);
}
.prod-summary-col .iva-toggle-btn {
  flex: 1;
  border: 0;
  background: transparent;
  padding: .4rem;
  border-radius: var(--r-pill);
  font-family: var(--f-mono);
  font-size: .62rem;
  font-weight: 400;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--text-2);
  cursor: pointer;
}
.prod-summary-col .iva-toggle-btn.sel {
  background: var(--cyan);
  border-color: transparent;
  color: #07070F;
  font-weight: 700;
}

/* Totali: bordo tratteggiato in alto, valori mono */
.prod-summary-col .summary-totals {
  padding: .7rem 1.25rem;
  gap: .35rem;
  border-top: 1px dashed var(--border-2);
  border-bottom: 0;
}
.prod-summary-col .summary-tot-row {
  font-size: .84rem;
  color: var(--text-2);
}
.prod-summary-col .summary-tot-row span:last-child {
  font-family: var(--f-mono);
  font-weight: 400;
  color: #e6e6f0;
}
.prod-summary-col .summary-tot-final {
  margin-top: .2rem;
  padding-top: .5rem;
  border-top: 1px solid var(--border-2) !important;  /* batte border-top-color magenta !important (pages 3786) */
  align-items: baseline;
}
.prod-summary-col .summary-tot-final span:first-child {
  font-family: var(--f-display);
  font-weight: 700;
  font-size: 1.2rem;
  text-transform: uppercase;
  color: #fff;
}
.prod-summary-col .summary-tot-final span:last-child {
  font-family: var(--f-ui) !important;
  font-weight: 700;
  font-size: 1.5rem !important;
  color: var(--cyan) !important;       /* batte pages.css 3775 (magenta !important) */
  letter-spacing: normal !important;
  text-shadow: none !important;
}
/* Promo attiva: #ss-price torna magenta (shop-core.js scrive il colore inline;
   la guardia evita che il cyan !important sovrascriva la formattazione promo). */
body[data-promo-active] .prod-summary-col .summary-tot-final span:last-child {
  color: var(--magenta) !important;
}

/* CTA "Aggiungi al Carrello": cyan mockup (batte override magenta pages 3790).
   width/margin di inset restano da pages.css. */
.prod-summary-col .btn-add-cart {
  border-radius: var(--r-md);
  padding: .95rem;
  font-size: 1rem;
  font-weight: 700;
  letter-spacing: .01em;
  text-transform: none;
  background: var(--cyan) !important;
  color: #07070F !important;
  box-shadow: none !important;
}
.prod-summary-col .btn-add-cart:hover {
  background: var(--cyan) !important;
  filter: brightness(1.08);
  box-shadow: none !important;
  transform: translateY(-1px) !important;
}

/* Trust note: testo piccolo centrato, icona tenue */
.prod-summary-col .summary-trust-note {
  margin-top: .8rem;
  font-size: .74rem;
  color: var(--text-3);
}
.prod-summary-col .summary-trust-note svg { color: var(--text-2); }

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE: .cfg-quote-box — Box preventivo personalizzato (variante-b)
   ------------------------------------------------------------------------
   Allineato VERBATIM al mockup variante-b (stile + struttura). Il markup
   reale è BEM (stampa-config.php ~541): i selettori del mockup (h3/p/a)
   sono mappati sui nomi reali — h3→__title, p→__desc, a→__btn — e
   flex-shrink:0 va sul flex-child reale (.cfg-quote-box__action, wrapper
   del link). Valori identici al mockup. Mailto preservato (nessun gancio
   toccato).
   ════════════════════════════════════════════════════════════════════════ */
.cfg-quote-box{display:flex;justify-content:space-between;align-items:center;gap:1rem;flex-wrap:wrap;border:1px solid rgba(255,45,120,.3);background:linear-gradient(120deg,rgba(255,45,120,.06),rgba(255,214,0,.04));border-radius:var(--r-md);padding:1.1rem 1.2rem}
.cfg-quote-box__title{font-family:var(--f-display);font-weight:700;font-size:1.3rem;text-transform:uppercase;margin:0 0 .2rem}
.cfg-quote-box__desc{font-size:.84rem;color:var(--text-2);margin:0;max-width:46ch}
.cfg-quote-box__action{flex-shrink:0}
.cfg-quote-box__btn{display:inline-flex;align-items:center;gap:.4rem;background:var(--magenta);color:#fff;font-family:var(--f-ui);font-weight:700;font-size:.82rem;text-transform:none;border-radius:var(--r-sm);padding:.6rem 1rem}
.cfg-quote-box__btn svg{flex-shrink:0;width:16px;height:16px}
@media(max-width:768px){.cfg-quote-box{flex-direction:column;align-items:flex-start}}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE FINALE · prod-final (Guida File + Come Ordinare + SEO) — variante-b
   ------------------------------------------------------------------------
   Porting VERBATIM (solo ASPETTO) del look variante-b dal mockup
   _design-proposta/variante-b/prodotto-mockup.html (CSS 284-310). Le classi
   coincidono al 100% col markup reale → zero micro-markup.

   pages.css stila già la sezione in DUE punti (.prod-final/.pfc-* ~3413,
   .prod-seo-text ~2746). Per vincere uso il prefisso .prod-final (specificità
   ≥ pages.css, e prodotto-vb è caricato DOPO): gli override colorati
   (.pfc-icon-wrap, .pfc-step-n, .pfc-tpl-badge) sono scoped a 3 livelli per
   battere le regole .pfc-guida/.pfc-howto di pages.css.

   COLOR MAPPING del mockup (DIVERSO da pages.css):
     · icona guida = CYAN · icona howto = MAGENTA  (pages: guida magenta/howto giallo)
     · step-n = quadrato MAGENTA  (pages: cerchio giallo)

   PRESERVATI (solo stile, nessun gancio toccato): .pfc-tpl--pdf/--ai restano
   i selettori letti da vector-generator.js + auth-guard.js; href/download nel
   markup intatti; testo SEO reale e link tel:/mailto: invariati. ───────────*/

/* Sezione: su fondo pagina (niente pannello bg-card/border-top di pages.css) */
.prod-final {
  padding: 1rem 0 2.6rem;
  border-top: 0;
  background: transparent;
}
.prod-final-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 1.4rem;
  margin-bottom: 0;
}

/* Card */
.prod-final .pfc-card {
  border: 1px solid var(--border);
  border-radius: var(--r-md);
  background: var(--bg-card);
  padding: 1.4rem 1.3rem;
  gap: 0;                       /* annullo il gap flex di pages.css: ritmo via margini */
}

/* Header card + icona */
.prod-final .pfc-head {
  display: flex;
  align-items: center;
  gap: .7rem;
  margin-bottom: .9rem;
}
.prod-final .pfc-icon-wrap {
  width: 42px; height: 42px; min-width: 42px;
  border-radius: var(--r-sm);
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(0,212,255,.1);
  border: 1px solid rgba(0,212,255,.3);
  color: var(--cyan);
}
.prod-final .pfc-icon-wrap svg { width: 22px; height: 22px; }
/* color mapping mockup: guida cyan (base) · howto magenta */
.prod-final .pfc-guida .pfc-icon-wrap {
  background: rgba(0,212,255,.1);
  border-color: rgba(0,212,255,.3);
  color: var(--cyan);
}
.prod-final .pfc-howto .pfc-icon-wrap {
  background: rgba(255,45,120,.1);
  border-color: rgba(255,45,120,.3);
  color: var(--magenta);
}

.prod-final .pfc-title {
  font-family: var(--f-display);
  font-weight: 700;
  font-size: 1.3rem;
  text-transform: uppercase;
  letter-spacing: normal;
  margin: 0;
  line-height: 1.05;
  color: var(--text);
}
.prod-final .pfc-desc {
  font-size: .86rem;
  color: var(--text-2);
  line-height: 1.6;
  margin: 0 0 1rem;
}

/* Template scaricabili (badge solidi mono) — classi --pdf/--ai INTATTE (ganci JS) */
.prod-final .pfc-templates {
  display: flex;
  gap: .6rem;
  flex-wrap: wrap;
  margin-bottom: .8rem;
  align-items: flex-start;
}
.prod-final .pfc-tpl {
  display: inline-flex;
  flex: 0 0 auto;               /* override del 50/50 stretch di pages.css (media 768) */
  align-items: center;
  gap: .5rem;
  border: 1px solid var(--border-2);
  border-radius: var(--r-sm);
  padding: .5rem .8rem;
  background: none;
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: .82rem;
  color: var(--text-2);
  text-decoration: none;
  transition: border-color var(--dur-fast);
}
.prod-final .pfc-tpl:hover { background: none; border-color: var(--cyan); color: var(--text-2); }
.prod-final .pfc-tpl-badge {
  display: inline-block;
  width: auto; height: auto;
  font-family: var(--f-mono);
  font-size: .56rem;
  font-weight: 700;
  letter-spacing: normal;
  color: #fff;
  padding: .18rem .4rem;
  border: 0;
  border-radius: 3px;
}
.prod-final .pfc-tpl--pdf .pfc-tpl-badge { background: #e53e3e; color: #fff; }
.prod-final .pfc-tpl--ai  .pfc-tpl-badge { background: #ed8936; color: #fff; }

/* Hint: mono uppercase nudo (niente box di pages.css) */
.prod-final .pfc-hint {
  font-family: var(--f-mono);
  font-size: .66rem;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--text-3);
  margin: 0;
  padding: 0;
  background: none;
  border: 0;
}

/* Come Ordinare: steps con badge quadrato magenta, senza divisori */
.prod-final .pfc-steps {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: .9rem;
}
.prod-final .pfc-step {
  display: flex;
  gap: .8rem;
  align-items: flex-start;
  padding: 0;
  border-bottom: 0;
}
.prod-final .pfc-step-n {
  width: 28px; height: 28px; min-width: 28px;
  flex-shrink: 0;
  border: 1px solid var(--border-2);
  border-radius: var(--r-sm);
  background: none;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: var(--f-mono);
  font-weight: 700;
  font-size: .8rem;
  color: var(--magenta);
  margin-top: 0;
}
.prod-final .pfc-step-body { gap: .15rem; }
.prod-final .pfc-step-body strong {
  display: block;
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: .92rem;
  color: #fff;
}
.prod-final .pfc-step-body span {
  font-size: .82rem;
  color: var(--text-2);
  line-height: 1.5;
}

/* SEO + FAQ: griglia 2 colonne. Il separatore (border-top) è sul WRAPPER così
   resta a tutta larghezza sopra entrambe le colonne (testo + FAQ). */
.prod-final .prod-seo-grid {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 370px;
  gap: 2.6rem;
  margin-top: 1.6rem;
  padding-top: 2rem;
  border-top: 1px solid var(--border);
}

/* SEO: niente box né separatore proprio (spostato sul wrapper); titolo display uppercase */
.prod-final .prod-seo-text {
  margin-top: 0;
  padding: 0;
  background: none;
  border: 0;
  border-radius: 0;
  font-size: .92rem;
  line-height: 1.7;
  color: var(--text-2);
}
.prod-final .prod-seo-text h2 {
  font-family: var(--f-display);
  font-weight: 700;
  font-size: clamp(1.5rem, 3.4vw, 2.1rem);
  text-transform: uppercase;
  color: var(--text);
  margin: 0 0 1rem;
}
.prod-final .prod-seo-text p {
  color: var(--text-2);
  font-size: .92rem;
  margin: 0 0 .9rem;
  max-width: 78ch;
}
.prod-final .prod-seo-text p:last-child { margin-bottom: 0; }
.prod-final .prod-seo-text a { color: var(--cyan); text-decoration: none; }
.prod-final .prod-seo-text a:hover { text-decoration: underline; }

/* ─── FAQ: accordion <details> nativi (zero JS), stile variante-b ──────────── */
.prod-final .prod-faq { align-self: start; }

/* Etichetta: mono uppercase + barra cyan (coerente con .cfg-intro-label) */
.prod-final .prod-faq-label {
  display: block;
  font-family: var(--f-mono);
  font-size: 0.68rem;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--text-2);
  border-left: 3px solid var(--cyan);
  padding: 0.3rem 0 0.3rem 0.7rem;
  margin: 0 0 1.1rem;
}

/* Ogni FAQ = card border-2, hover/open cyan, radius r-sm */
.prod-final .prod-faq-item {
  background: var(--bg-card);
  border: 1px solid var(--border-2);
  border-radius: var(--r-sm);
  margin-bottom: 0.6rem;
  transition: border-color .18s;
}
.prod-final .prod-faq-item:last-child { margin-bottom: 0; }
.prod-final .prod-faq-item:hover,
.prod-final .prod-faq-item[open] { border-color: var(--cyan); }

.prod-final .prod-faq-item summary {
  display: flex;
  align-items: center;
  gap: 0.7rem;
  list-style: none;
  cursor: pointer;
  padding: 0.85rem 0.95rem;
  font-family: var(--f-ui);
  font-size: 0.86rem;
  font-weight: 600;
  line-height: 1.35;
  color: var(--text);
  transition: color .18s;
}
.prod-final .prod-faq-item summary::-webkit-details-marker { display: none; }
.prod-final .prod-faq-item summary:hover,
.prod-final .prod-faq-item[open] summary { color: var(--cyan); }
.prod-final .prod-faq-item summary:focus-visible {
  outline: 2px solid var(--cyan);
  outline-offset: -2px;
  border-radius: var(--r-sm);
}

/* Marker +/× : il "+" ruota di 45° in stato [open] */
.prod-final .prod-faq-item summary::after {
  content: '+';
  margin-left: auto;
  flex-shrink: 0;
  font-family: var(--f-mono);
  font-size: 1.15rem;
  font-weight: 400;
  line-height: 1;
  color: var(--cyan);
  transition: transform .22s ease;
}
.prod-final .prod-faq-item[open] summary::after { transform: rotate(45deg); }

/* Risposta: hairline divider inset, testo --text-2 */
.prod-final .prod-faq-answer {
  margin: 0 0.95rem;
  padding: 0.8rem 0 0.9rem;
  border-top: 1px solid var(--border);
  font-family: var(--f-ui);
  font-size: 0.82rem;
  line-height: 1.6;
  color: var(--text-2);
}

/* Responsive — soglia allineata al mockup (prodotto-mockup.html 606/826):
   guida + come-ordinare restano APPAIATE (2 col) su tutto l'iPad (768-1023) e
   collassano a 1 col solo ≤767. La regola tablet riafferma 1fr 1fr per battere
   pages.css (.prod-final-grid → 1fr a ≤768, specificità 0,1,0) a 768px esatti.
   .prod-seo-grid (testo+FAQ, non presente nel mockup) segue la stessa policy:
   resta 2 col su iPad (base minmax(0,1fr) 370px) e collassa solo ≤767. */
@media (min-width: 768px) and (max-width: 1023px) {
  .prod-final .prod-final-grid { grid-template-columns: 1fr 1fr; gap: 1.3rem; }
}
@media (max-width: 767px) {
  .prod-final .prod-final-grid { grid-template-columns: 1fr; }
  .prod-final .prod-seo-grid  { grid-template-columns: 1fr; gap: 2rem; }
}

@media (prefers-reduced-motion: reduce) {
  .prod-final .prod-faq-item summary::after { transition: none; }
}

/* ════════════════════════════════════════════════════════════════════════
   GRUPPO A · RESPONSIVE CSS-PURO — allineamento verbatim al mockup variante-b
   (_design-proposta/variante-b/prodotto-mockup.html). Solo CARD + UPLOAD.
   Il collasso layout intro/body e la barra CTA/bottom-sheet mobile sono
   GRUPPO B (non toccati qui: senza la barra CTA, anticipare il collasso a
   1023 lascerebbe la summary nel flusso su iPad → peggiore). Desktop ≥1024
   INVARIATO. ════════════════════════════════════════════════════════════ */

/* ── CARD configuratore: colonne fisse ai breakpoint del mockup (579/591) ──
   Il reale di base usa auto-fill minmax(140/168px) a specificità (0,4,0)
   (righe 28-33): ripeto la stessa catena :not() per PAREGGIARE la specificità
   — i media query, più in basso nel file, vincono al cambio breakpoint, senza
   !important. Le griglie a layout proprio (qty/delivery/grafica) restano
   escluse, esattamente come nel mockup. */
@media (max-width: 1023px) {
  .cfg-cards:not(.cfg-cards--qty):not(.cfg-cards--delivery):not(.cfg-cards--grafica),
  .cfg-cards--wide:not(.cfg-cards--qty):not(.cfg-cards--delivery):not(.cfg-cards--grafica) {
    grid-template-columns: repeat(3, 1fr);
  }
}
@media (max-width: 767px) {
  .cfg-cards:not(.cfg-cards--qty):not(.cfg-cards--delivery):not(.cfg-cards--grafica),
  .cfg-cards--wide:not(.cfg-cards--qty):not(.cfg-cards--delivery):not(.cfg-cards--grafica) {
    grid-template-columns: repeat(2, 1fr);
  }
}

/* ── UPLOAD mobile: wrapping anti-sforo verbatim mockup (756-766) ──────────
   Dropzone più compatta + testo/email lunga che vanno a capo invece di
   sforare il box. Il padding resting del reale è
   .prod-upload-block .upload-zone:not(.has-file) (0,3,0, riga 851): ripeto la
   stessa specificità per vincere su mobile.
   .upload-note (BUG FIX): su mobile deve essere UN paragrafo unico, non una
   flex-row. Con display:flex i figli (svg + testo NUDO + <a> email) diventano
   flex-item affiancati → il testo si spezza in colonne. Qui si passa a
   display:block con svg in float:left: il testo torna flusso inline continuo che
   scorre attorno all'icona, e l'email (white-space:nowrap) resta INTERA su una
   riga o va a capo tutta insieme, mai a metà. Specificità
   .prod-upload-block .upload-note (0,2,0) per battere la regola desktop di
   riga 924 (stessa specificità → vince l'ordine sorgente, questa è dopo) e
   resta confinata al mobile dal @media. Desktop (≥768) INVARIATO. */
@media (max-width: 767px) {
  /* pages.css (2883) azzera il box su mobile con .prod-upload-block{padding:0
     !important}: header "Dai un nome", input e nota finivano appiccicati ai
     bordi della card. Ripristino un respiro interno ~1rem. Serve specificità
     ≥ (0,2,0) + !important per battere il !important di pages.css. */
  .prod-body .prod-upload-block { padding: 1.1rem 1rem !important; }
  .prod-upload-block .cfg-block-head { gap: 0.5rem; }
  .prod-upload-block .upload-zone:not(.has-file) { padding: 1.9rem 1rem; }
  .upload-primary,
  .upload-hint,
  .upload-hint-small { overflow-wrap: anywhere; word-break: break-word; }
  .upload-hint { letter-spacing: 0.03em; }
  /* nota = paragrafo con ICONA "appesa" nel gutter sinistro. Niente flex
     (l'<a> email è figlio diretto → diventerebbe un flex-item a sé, spezzando
     il testo in colonne) e niente float (rientrava solo la 1ª riga, non la 2ª/3ª).
     Qui: svg in position:absolute nel gutter, testo con padding-left costante →
     TUTTE le righe partono dalla stessa colonna. Nessun rientro irregolare. */
  .prod-upload-block .upload-note {
    display: block;
    position: relative;
    padding-left: 1.6rem;   /* gutter icona (16px) + respiro */
    font-size: .78rem;
    line-height: 1.55;
  }
  .prod-upload-block .upload-note svg {
    position: absolute;
    left: 0;
    top: .18rem;
    float: none;
    margin: 0;
  }
  /* email: intera su una riga (o a capo tutta insieme), mai spezzata a metà */
  .prod-upload-block .upload-note a { white-space: nowrap; }
}

/* ── INTRO/GALLERY mobile: collasso a 1 colonna (gallery sopra, info sotto) ──
   FIX: il restyle ha ridefinito .prod-intro-grid (riga 636,
   minmax(0,1fr) minmax(0,1fr), specificità 0,1,0) caricato DOPO pages.css →
   scavalcava il collasso mobile di pages.css (.prod-intro-grid → 1fr a ≤768),
   lasciando 2 colonne anche su smartphone (bug a 402px: 169px+169px).
   Ripeto lo stesso selettore (0,1,0) qui, a fine file → vince a ≤1023. Valori
   verbatim mockup (prodotto-mockup.html 574). La gallery è già static a ≤768
   via pages.css (.prod-gallery{position:static!important}, riga 2789): qui
   basta sciogliere la griglia, gallery e info diventano full-width (1fr).
   SCOPE ≤1023 (GRUPPO B attivo): con la barra CTA fissa la summary laterale è
   nascosta anche su iPad, quindi intro/body collassano a 1 colonna già da ≤1023
   come nel mockup (prodotto-mockup.html 565-578). Desktop ≥1024 invariato. */
@media (max-width: 1023px) {
  .prod-intro-grid { grid-template-columns: 1fr; gap: 1.4rem; }
}

/* ── BODY mobile: collasso a 1 colonna (configuratore → upload → summary) ────
   Il collasso del prod-body vive in pages.css (≤768:
   .prod-body-grid{display:contents!important} + .prod-body .container flex
   column + order 1/2/3). Il restyle ridefinisce .prod-body-grid (riga 807,
   grid-template-columns minmax(0,1fr) 372px) ma NON il display → non scavalca
   quel meccanismo: in locale il body collassa già. Replico qui lo STESSO
   meccanismo (scope ≤767) così il collasso è GARANTITO anche se la pages.css
   servita è una copia vecchia/cache (deploy parziale) — e viaggia con questo
   file, che è quello bump-ato.
   display:contents scioglie la GRIGLIA (la regola 372px del restyle, stessa
   specificità 0,1,0, diventa moot perché il box-griglia sparisce): cfg-col +
   summary-col diventano figli diretti del .container flex, dove upload-block è
   già figlio → cfg-col + upload-block si impilano full-width. La summary col
   è invece NASCOSTA a ≤1023 (GRUPPO B attivo, vedi sotto): il suo posto lo
   prende la barra CTA fissa + bottom-sheet.
   Dove pages.css usa !important (≤768) vince pages.css, con esito identico.
   Ganci summary intatti (#sticky-summary/#ss-* / #price-*): tocco solo
   contenitore/colonna, nessun nodo interno. Desktop ≥1024 invariato.
   GRUPPO B: a ≤1023 la summary laterale è NASCOSTA (display:none) — il
   preventivo vive nella barra CTA fissa + bottom-sheet; il body collassa
   configuratore → upload a 1 colonna. I nodi #ss-* / #price-* restano nel DOM
   (display:none non li rimuove): configuratore.js li aggiorna e la barra/sheet
   li copiano via js/prodotto-mobile-cta.js. */
@media (max-width: 1023px) {
  .prod-body .container { display: flex; flex-direction: column; gap: 2.5rem; }
  .prod-body-grid { display: contents; }
  .prod-cfg-col { order: 1; min-width: 0; }
  .prod-upload-block { order: 2; }
  /* !important: pages.css (@media ≤1024, riga ~2888) forza position/width/top/
     transform/float di .prod-summary-col con !important per il vecchio collasso
     "summary in fondo". Senza !important il display:none vince per cascata, ma
     lo rendo a prova di cache/override allineandomi al pattern !important che
     pages.css usa su QUESTO stesso elemento. I nodi #ss-* / #price-* restano nel
     DOM (display:none non li rimuove) → la barra CTA li copia. */
  .prod-summary-col { display: none !important; }   /* → barra CTA mobile/tablet (GRUPPO B) */
}

/* ════════════════════════════════════════════════════════════════════════
   GRUPPO B · BARRA CTA FISSA + BOTTOM-SHEET RIEPILOGO  (mobile/tablet ≤1023)
   Verbatim variante-b (prodotto-mockup.html 682-702, 768-780, 850-854).
   Nascosti di default; visibili SOLO ≤1023; forzati via !important ≥1024.
   ════════════════════════════════════════════════════════════════════════ */
.pd-mobile-cta, .pd-sheet, .pd-sheet-ov { display: none; }
/* L'overlay esiste solo a sheet aperto: il JS toggla l'attributo [hidden]
   (ov.hidden = true/false). Dentro @media ≤1023 .pd-sheet-ov ha display:block,
   che però scavalca lo stile UA [hidden]{display:none} → da chiuso l'overlay
   resterebbe a z-149 sopra la pagina e intercetterebbe i click sulle card.
   Questa regola (specificità 0,2,0 + !important) garantisce che con [hidden]
   l'overlay sparisca davvero; ricompare solo quando il JS rimuove [hidden]. */
.pd-sheet-ov[hidden] { display: none !important; }

/* Body-lock a sheet aperto: il JS aggiunge .pd-sheet-open al <body> quando
   apre lo sheet e la rimuove alla chiusura (X/overlay/Escape/toggle passano
   tutti da openSheet/closeSheet). overflow:hidden blocca lo scroll di pagina;
   rimuovendo la classe la cascata ripristina l'overflow precedente (nessuno
   stato da salvare a mano). Solo classe → nessun rischio a sheet chiuso. */
body.pd-sheet-open { overflow: hidden; }

@media (max-width: 1023px) {
  /* Reserve per la barra CTA fissa. La barra è position:fixed → non rispetta il
     flusso: scrollando in fondo, l'ULTIMA riga del footer (© / P.IVA, dentro
     .footer-bottom-wrap) restava dietro la barra. Il padding NON va sul body né
     sul main: sul body cade SOTTO il footer (vuoto scuro); sul main resta sopra
     il footer e non protegge il footer stesso (il footer è l'ultimo elemento in
     flusso). Va quindi sull'ultima fascia del footer: ne estendo il
     padding-bottom (fascia #040408) così la riga © sale sopra la barra e lo
     spazio extra è dello stesso colore → nessun seam, nessun vuoto.
     88px = 72px barra + 16px respiro; + safe-area perché la barra la include a
     sua volta. Scoped a .product-page ~ .footer: il footer è condiviso, la barra
     CTA esiste solo sulle pagine prodotto mobile. */
  .product-page ~ .footer .footer-bottom-wrap {
    padding-bottom: calc(88px + env(safe-area-inset-bottom));
  }

  .pd-mobile-cta {
    display: flex;
    position: fixed; left: 0; right: 0; bottom: 0; z-index: 150;
    align-items: center; gap: .8rem;
    padding: .72rem .9rem;
    padding-bottom: calc(.72rem + env(safe-area-inset-bottom));
    background: rgba(10,10,20,.96);
    -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px);
    border-top: 1px solid var(--border-2);
  }
  /* Colonna totale: etichetta discreta sopra, valore grande sotto, con stacco
     netto (gap). min-width:0 → non spinge fuori chevron/bottone. */
  .pd-cta-info { display: flex; flex-direction: column; gap: 4px; line-height: 1; min-width: 0; padding-right: .1rem; }
  /* Etichetta: secondaria ma leggibile — un filo più grande e più chiara
     (text-2 anziché text-3), resta mono/uppercase/tracked. */
  .pd-cta-label { font-family: var(--f-mono); font-size: .62rem; letter-spacing: .12em; text-transform: uppercase; color: var(--text-2); line-height: 1.2; }
  /* Prezzo = la cifra che conta: giallo promo (--yellow), più grande, così
     salta all'occhio senza sovrastare il bottone (blocco cyan pieno).
     tabular-nums: le cifre non ballano mentre il JS aggiorna il totale;
     nowrap: resta su una riga, non rompe il layout della barra. */
  .pd-cta-price {
    font-family: var(--f-ui); font-weight: 800; font-size: 1.5rem; line-height: 1;
    color: var(--yellow); white-space: nowrap; font-variant-numeric: tabular-nums;
  }
  .pd-cta-toggle {
    width: 40px; height: 44px; flex: 0 0 auto;
    background: none; border: 1px solid var(--border-2); border-radius: 8px;
    color: var(--text-2); cursor: pointer;
    display: flex; align-items: center; justify-content: center;
  }
  .pd-cta-toggle svg { width: 18px; height: 18px; transition: transform .2s; }
  .pd-sheet.open ~ .pd-mobile-cta .pd-cta-toggle svg { transform: rotate(180deg); }
  .pd-cta-add {
    flex: 1; min-height: 48px;
    background: var(--cyan); color: #04111a; border: 0; border-radius: 10px;
    font-family: var(--f-ui); font-weight: 800; font-size: .9rem; letter-spacing: .02em;
    cursor: pointer; display: flex; align-items: center; justify-content: center; gap: .4rem;
  }

  /* ── overlay + sheet ── */
  .pd-sheet-ov { display: block; position: fixed; inset: 0; background: rgba(0,0,0,.5); z-index: 149; }
  .pd-sheet {
    display: block;
    position: fixed; left: 0; right: 0; bottom: 0; z-index: 151;
    background: #0d0d1a; border-top: 2px solid var(--cyan); border-radius: 16px 16px 0 0;
    transform: translateY(100%); transition: transform .3s var(--ease-out, ease);
    max-height: 72vh; overflow: hidden;
  }
  .pd-sheet.open { transform: translateY(0); }

  .pd-sheet h4 { font-family: var(--f-display); font-weight: 700; font-size: 1.3rem; text-transform: uppercase; margin: 0; }
  .ps-head {
    display: flex; align-items: flex-start; justify-content: space-between; gap: .6rem;
    padding: 1rem 1.1rem .7rem; border-bottom: 1px solid var(--border);
    position: sticky; top: 0; background: #0d0d1a; z-index: 2;
  }
  .ps-sub { font-family: var(--f-ui); font-size: .82rem; color: var(--text-2); margin-top: .2rem; }
  .ps-close {
    flex: 0 0 auto; width: 38px; height: 38px;
    border: 1px solid var(--border-2); border-radius: 9px; background: none;
    color: var(--text-2); cursor: pointer; display: flex; align-items: center; justify-content: center;
  }
  .ps-close svg { width: 18px; height: 18px; }
  .ps-scroll {
    padding: .4rem 1.1rem calc(1.4rem + env(safe-area-inset-bottom));
    overflow-y: auto; -webkit-overflow-scrolling: touch;
    overscroll-behavior: contain;   /* niente scroll-chaining: lo scroll a fine sheet non trascina il body */
    max-height: calc(72vh - 66px);
  }
  .ps-group-label {
    font-family: var(--f-mono); font-size: .58rem; letter-spacing: .16em; text-transform: uppercase;
    color: var(--text-3); margin: .95rem 0 .25rem;
  }
  .ps-group-label:first-child { margin-top: .4rem; }
  .pd-sheet .ps-row {
    display: flex; justify-content: space-between; gap: .8rem;
    padding: .4rem 0; font-size: .84rem; border-bottom: 1px solid var(--border);
  }
  .pd-sheet .ps-row .k {
    font-family: var(--f-mono); font-size: .62rem; letter-spacing: .06em; text-transform: uppercase; color: var(--text-3);
  }
  .pd-sheet .ps-row .v {
    color: #e6e6f0; text-align: right;
    display: inline-flex; align-items: baseline; gap: .45rem; flex-wrap: wrap; justify-content: flex-end;
  }
  .pd-sheet .ps-price { font-family: var(--f-mono); font-weight: 700; font-size: .8rem; white-space: nowrap; color: #fff; font-style: normal; }
  .pd-sheet .ps-price--add { color: var(--yellow); }
  .pd-sheet .ps-price--inc { color: var(--text-3); font-weight: 500; }

  .ps-delivery {
    display: flex; align-items: center; gap: .55rem; margin: .7rem 0 .2rem; padding: .6rem .7rem;
    border-radius: 8px; background: rgba(0,212,255,.06); border: 1px solid rgba(0,212,255,.22);
    font-size: .82rem; color: #9be7ff;
  }
  .ps-delivery svg { width: 18px; height: 18px; flex-shrink: 0; color: var(--cyan); }
  .ps-delivery b { color: #fff; }

  /* toggle IVA dentro lo sheet (fuori da .prod-summary-col → stile proprio,
     verbatim mockup 242-244; selezione su .sel perché configuratore.js aggancia
     nativamente questi .iva-toggle-btn via initIvaToggle()). !important sul bordo per battere la
     regola magenta globale di pages.css (.iva-toggle-wrap border-bottom !important). */
  .pd-sheet .iva-toggle-wrap {
    display: flex; gap: .3rem; margin: .6rem 0 .2rem; padding: .2rem;
    background: var(--bg-input); border: 1px solid var(--border-2) !important; border-radius: var(--r-pill);
  }
  .pd-sheet .iva-toggle-btn {
    flex: 1; border: 0; background: transparent; padding: .4rem; border-radius: var(--r-pill);
    font-family: var(--f-mono); font-size: .62rem; font-weight: 400; letter-spacing: .08em; text-transform: uppercase;
    color: var(--text-2); cursor: pointer;
  }
  .pd-sheet .iva-toggle-btn.sel { background: var(--cyan); border-color: transparent; color: #07070F; font-weight: 700; }

  .pd-sheet .ps-tot {
    display: flex; justify-content: space-between; align-items: baseline;
    padding-top: .7rem; margin-top: .5rem; border-top: 1px dashed var(--border-2);
  }
  .pd-sheet .ps-tot .k { font-family: var(--f-display); font-weight: 700; font-size: 1.2rem; text-transform: uppercase; color: #fff; }
  .pd-sheet .ps-tot .v { font-family: var(--f-ui); font-weight: 700; font-size: 1.5rem; color: var(--cyan); }
}

@media (min-width: 1024px) {
  .pd-mobile-cta, .pd-sheet, .pd-sheet-ov { display: none !important; }
}

@media (prefers-reduced-motion: reduce) {
  .pd-sheet { transition: none; }
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 9 — LISTINO MOBILE .ptm (≤767px) · VERBATIM MOCKUP variante-b
   ------------------------------------------------------------------------
   Sotto i 767px la tabella tiratura/velocità (.price-table-wrap) è nascosta e
   sostituita dallo stepper + 3 velocità + scaglioni a richiesta (.ptm).
   Stile 1:1 dal mockup (_design-proposta/variante-b/prodotto-mockup.html:
   CSS 782-817 struttura + 856-866 tinte corsia). Markup nel template
   stampa-config.php; comportamento in js/prodotto-mobile-listino.js.
   Token (--cyan/--magenta/--yellow, --f-*, --border*, --bg-*) dal :root globale.
   ════════════════════════════════════════════════════════════════════════ */

/* ── Struttura (mockup 782-817) ── */
.ptm{display:none;flex-direction:column;gap:.8rem}
/* .ptm vive DENTRO la card .prod-qty-section (bordo). Senza padding, "TIRATURA"
   e gli stepper toccavano i bordi L/R/basso della card → respiro ~1rem su mobile
   (top 0: la .ptv2-delivery-note sopra ha già margin-bottom). */
@media(max-width:767px){.ptm{display:flex;padding:0 1rem 1rem}}
.ptm-pick{display:flex;flex-wrap:wrap;align-items:center;gap:.5rem .7rem}
.ptm-pick-lbl{font-family:var(--f-mono);font-size:.62rem;letter-spacing:.14em;text-transform:uppercase;color:var(--text-2)}
.ptm-stepper{display:flex;align-items:stretch;border:1px solid var(--border-2);border-radius:10px;overflow:hidden;background:var(--bg-input);flex:1;min-width:180px}
.ptm-step{width:44px;flex:0 0 auto;background:rgba(255,255,255,.03);border:0;color:#fff;font-size:1.35rem;line-height:1;cursor:pointer}
.ptm-step:hover{background:rgba(0,212,255,.12);color:var(--cyan)}
.ptm-select{flex:1;min-width:0;background:transparent;border:0;border-left:1px solid var(--border-2);border-right:1px solid var(--border-2);color:#fff;font-family:var(--f-ui);font-weight:700;font-size:.95rem;padding:.65rem .6rem;text-align:center;text-align-last:center;cursor:pointer;-webkit-appearance:none;appearance:none}
.ptm-select option{background:#0d0d1a;color:#fff}
.ptm-pick-hint{flex:1 0 100%;font-family:var(--f-mono);font-size:.6rem;letter-spacing:.06em;color:var(--text-3)}
.ptm-current{border:1px solid var(--cyan);border-radius:12px;overflow:hidden;background:rgba(0,212,255,.05);box-shadow:0 0 0 1px rgba(0,212,255,.25)}
.ptm-cur-top{display:flex;align-items:baseline;gap:.5rem;padding:.7rem .9rem;border-bottom:1px solid rgba(0,212,255,.22);background:rgba(0,212,255,.08)}
.ptm-cur-q{font-family:var(--f-display);font-weight:800;font-size:1.7rem;line-height:1;color:#fff}
.ptm-cur-u{font-family:var(--f-mono);font-size:.62rem;letter-spacing:.08em;text-transform:uppercase;color:var(--text-2)}
.ptm-cur-tag{margin-left:auto;font-family:var(--f-mono);font-size:.54rem;letter-spacing:.1em;text-transform:uppercase;color:#04111a;background:var(--cyan);padding:.22rem .5rem;border-radius:999px}
.ptm-speeds{display:grid;grid-template-columns:repeat(3,1fr);gap:.5rem;padding:.7rem}
.ptm-speed{display:flex;flex-direction:column;gap:.15rem;align-items:flex-start;text-align:left;padding:.6rem .5rem;border:1px solid var(--border-2);border-radius:9px;background:var(--bg-card);color:var(--text);cursor:pointer;transition:border-color .14s,background .14s}
.ptm-sp-name{font-family:var(--f-ui);font-weight:700;font-size:.76rem}
.ptm-sp-days{font-family:var(--f-mono);font-size:.52rem;letter-spacing:.04em;text-transform:uppercase;color:var(--text-3)}
.ptm-sp-price{font-family:var(--f-mono);font-size:.9rem;color:#fff;margin-top:.15rem}
.ptm-speed--std.is-on{border-color:var(--cyan);background:rgba(0,212,255,.12)}
.ptm-speed--fast.is-on{border-color:var(--magenta);background:rgba(255,45,120,.12)}
.ptm-speed--urg.is-on{border-color:var(--yellow);background:rgba(255,214,0,.12)}
.ptm-more{display:flex;align-items:center;justify-content:center;gap:.45rem;width:100%;padding:.7rem;background:none;border:1px dashed var(--border-2);border-radius:10px;color:var(--text-2);font-family:var(--f-ui);font-weight:600;font-size:.82rem;cursor:pointer}
.ptm-more:hover{border-color:var(--cyan);color:#fff}
.ptm-more svg{width:16px;height:16px;transition:transform .2s}
.ptm-more.is-open svg{transform:rotate(180deg)}
.ptm-all{border:1px solid var(--border-2);border-radius:10px;overflow:hidden;background:rgba(7,7,15,.5)}
.ptm-all-row{display:grid;grid-template-columns:1.05fr 1fr 1fr 1fr;gap:.4rem;width:100%;align-items:center;padding:.55rem .7rem;background:none;border:0;border-bottom:1px solid var(--border);color:var(--text-2);font-family:var(--f-mono);font-size:.74rem;text-align:right;cursor:pointer}
.ptm-all-row span:first-child{text-align:left}
.ptm-all-row .q{color:#fff;font-weight:700}
.ptm-all-row:last-child{border-bottom:0}
.ptm-all-head{color:var(--text-3);font-size:.56rem;letter-spacing:.06em;text-transform:uppercase;background:rgba(255,255,255,.03);cursor:default}
.ptm-all-row.is-sel{background:rgba(0,212,255,.1);box-shadow:inset 3px 0 0 var(--cyan)}
.ptm-all-row:not(.ptm-all-head):hover{background:rgba(0,212,255,.06)}

/* ── Tinte corsia tenui, come il desktop: STANDARD=cyan · VELOCE=magenta ·
      PRIORITARIA=giallo (mockup 856-866, solo il fondo colore) ── */
.ptm-speed--std{background:rgba(0,212,255,.06)}
.ptm-speed--fast{background:rgba(255,45,120,.06)}
.ptm-speed--urg{background:rgba(255,214,0,.05)}
.ptm-all-row:not(.ptm-all-head) span:nth-child(2),
.ptm-all-row:not(.ptm-all-head) span:nth-child(3),
.ptm-all-row:not(.ptm-all-head) span:nth-child(4){align-self:stretch;display:flex;align-items:center;justify-content:flex-end;padding:.18rem .4rem;border-radius:4px}
.ptm-all-row:not(.ptm-all-head) span:nth-child(2){background:rgba(0,212,255,.05)}
.ptm-all-row:not(.ptm-all-head) span:nth-child(3){background:rgba(255,45,120,.05)}
.ptm-all-row:not(.ptm-all-head) span:nth-child(4){background:rgba(255,214,0,.045)}

/* ── Sotto i 767px la tabella desktop lascia il posto alla .ptm ── */
@media(max-width:767px){.price-table-wrap{display:none}}

/* ═══ 13 · MULTI-SOGGETTO — restyle estetico verbatim variante-b ═══════════════
   Sezione #step-soggetti ("07 · Soggetti e Copie" nel mockup). SOLO ASPETTO.
   La struttura RICCA reale resta INTATTA: pannello + lista .ms-item (nome +
   rimuovi + stepper copie) + riga totale + upload/preview per soggetto. Il markup
   è generato da mscInit (stampa-config.php) e dal MultiUploadManager
   (shop-core.js): non si tocca. Qui si porta la veste del mockup sui selettori
   REALI. Metafora coerente col resto della scheda: "piano di taglio" tratteggiato
   (come la dropzone) su cui si dispongono i soggetti.
   Specificità: scope su #step-soggetti / #id → batte pages.css (.ms-*, 5507+) e
   lo <style> inline del template (.ms-toggle-btn, ~106) senza !important.
   Gli stati runtime restano ai rispettivi JS e NON vengono forzati da qui:
   colore inline di #msc-distributed (verde/magenta), display del pannello,
   .ms-btn:disabled, e i colori-stato degli upload per soggetto (.ivac-ms-row
   has-file/uploading/error, iniettati da shop-core). ────────────────────────── */

/* toggle "Gestisci più soggetti/file" — pill accento cyan (mockup 201-203) */
#ms-toggle-btn {
  margin-left: auto;
  display: inline-flex;
  align-items: center;
  gap: .4rem;
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: .78rem;
  color: var(--text-2);
  background: transparent;
  border: 1px solid var(--border-2);
  border-radius: var(--r-pill);
  padding: .4rem .8rem;
  cursor: pointer;
  transition: color .16s, border-color .16s, background .16s;
}
#ms-toggle-btn svg { width: 15px; height: 15px; }
#ms-toggle-btn:hover:not(:disabled),
#ms-toggle-btn.attivo {
  color: #fff;
  border-color: var(--cyan);
  background: rgba(0, 212, 255, .06);
}
#ms-toggle-btn:disabled { opacity: .4; cursor: not-allowed; }

/* pannello soggetti — "piano di taglio" tratteggiato (mockup 204) */
#step-soggetti .ms-panel {
  border: 1px dashed var(--border-2);
  border-radius: var(--r-md);
  background: var(--bg-card);
  padding: 1rem;
}

/* lista soggetti */
#step-soggetti .ms-list {
  display: flex;
  flex-direction: column;
  gap: .6rem;
  margin: 0;
}

/* riga soggetto = card: [nome (+rimuovi) | stepper copie] (mockup 205-207) */
#step-soggetti .ms-item {
  display: flex;
  align-items: center;
  gap: .8rem;
  margin: 0;
  padding: .6rem .7rem;
  border: 1px solid var(--border);
  border-radius: var(--r-sm);
  background: var(--bg-input);
  transition: border-color .18s;
}
#step-soggetti .ms-item:hover { border-color: rgba(0, 212, 255, .25); }

/* testata riga: nome soggetto a piena larghezza + eventuale tasto rimuovi */
#step-soggetti .ms-item-head {
  flex: 1;
  min-width: 0;
  display: flex;
  align-items: center;
  gap: .5rem;
  margin: 0;
}
#step-soggetti .ms-nome-input {
  flex: 1;
  min-width: 0;
  background: transparent;
  border: 0;
  border-radius: 0;
  padding: .2rem 0;
  color: #fff;
  font-family: var(--f-body);
  font-size: .88rem;
  box-shadow: none;
}
#step-soggetti .ms-nome-input:focus { outline: none; box-shadow: none; }
#step-soggetti .ms-nome-input::placeholder { color: var(--text-3); }

/* tasto rimuovi soggetto — icona quieta, accento "taglio" magenta al hover */
#step-soggetti .ms-btn-remove {
  flex-shrink: 0;
  width: 26px;
  height: 26px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  border: 1px solid var(--border-2);
  border-radius: var(--r-sm);
  background: transparent;
  color: var(--text-3);
  cursor: pointer;
  transition: color .15s, border-color .15s, background .15s;
}
#step-soggetti .ms-btn-remove:hover {
  color: var(--magenta);
  border-color: rgba(255, 45, 120, .5);
  background: rgba(255, 45, 120, .08);
}

/* stepper copie — segmentato mono, coerente con .ptm-stepper (mockup 208-211) */
#step-soggetti .ms-copie-ctrl {
  flex-shrink: 0;
  display: inline-flex;
  align-items: center;
  gap: .5rem;
}
#step-soggetti .ms-copie-ctrl .ms-btn {
  width: 28px;
  height: 28px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  border: 1px solid var(--border-2);
  border-radius: var(--r-sm);
  background: transparent;
  color: #fff;
  font-size: 1.05rem;
  line-height: 1;
  cursor: pointer;
  transition: color .14s, border-color .14s, background .14s;
}
#step-soggetti .ms-copie-ctrl .ms-btn:hover:not(:disabled) {
  color: var(--cyan);
  border-color: var(--cyan);
  background: rgba(0, 212, 255, .1);
}
#step-soggetti .ms-copie-ctrl .ms-btn:disabled { opacity: .35; cursor: not-allowed; }
#step-soggetti .ms-copie-val {
  min-width: 36px;
  text-align: center;
  font-family: var(--f-mono);
  font-size: .86rem;
  font-weight: 700;
  color: #fff;
}
#step-soggetti .ms-copie-label {
  font-family: var(--f-mono);
  font-size: .58rem;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--text-3);
}

/* riga totale — "ledger" mono uppercase (mockup 212-213) */
#step-soggetti .ms-total-row {
  display: flex;
  align-items: center;
  gap: .4rem;
  margin: .85rem .2rem 0;
  font-family: var(--f-mono);
  font-size: .72rem;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--text-2);
}
#step-soggetti .ms-total-row strong {
  font-family: var(--f-mono);
  font-size: .8rem;
  font-weight: 700;
  color: var(--cyan);
}

/* aggiungi soggetto — dashed full-width, hover cyan (mockup 214-215) */
#msc-add-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: .5rem;
  width: 100%;
  margin-top: .7rem;
  padding: .6rem;
  border: 1px dashed var(--border-2);
  border-radius: var(--r-sm);
  background: transparent;
  color: var(--text-2);
  font-family: var(--f-ui);
  font-weight: 600;
  font-size: .82rem;
  cursor: pointer;
  transition: color .16s, border-color .16s, background .16s;
}
#msc-add-btn:hover {
  color: #fff;
  border-color: var(--cyan);
  background: rgba(0, 212, 255, .06);
}
#msc-add-btn svg { width: 16px; height: 16px; }

/* ── Mobile: riga soggetto impilata, stepper allineato a sinistra (mockup
   748-754). Input a 16px sotto 1024px = anti-zoom iOS Safari (CLAUDE.md §1). ── */
@media (max-width: 1024px) {
  #step-soggetti .ms-nome-input { font-size: 16px; }
}
@media (max-width: 767px) {
  /* BUG FIX header: la sigla laterale .cfg-spec-no è decorativa e su mobile
     (titolo Barlow 1.5rem white-space:nowrap + toggle) si accavallava / sforava.
     La nascondo sotto i 767px (tutti gli step, non solo soggetti). */
  .cfg-spec-no { display: none; }
  /* header soggetti: consenti il wrap così #ms-toggle-btn (flex:1 0 100%) va a
     capo su riga propria a piena larghezza invece di essere tagliato a destra. */
  #step-soggetti .cfg-block-head { flex-wrap: wrap; }

  #step-soggetti .ms-item { flex-direction: column; align-items: stretch; gap: .6rem; }
  #step-soggetti .ms-copie-ctrl { justify-content: flex-start; gap: .7rem; }
  #step-soggetti .ms-copie-val { min-width: 52px; }
  #ms-toggle-btn { margin-left: 0; flex: 1 0 100%; width: 100%; justify-content: center; margin-top: .6rem; }
}

/* ════════════════════════════════════════════════════════════════════════
   SEZIONE 2 · RECENSIONI (Step 3) — riepilogo d'impatto + card
   ------------------------------------------------------------------------
   "Pannello di controllo qualità" della stampa: media grande in Barlow
   (cyan, l'eroe), stelle a riempimento parziale e barre di distribuzione
   tipo ink-meter (gradiente cyan→magenta). Card recensioni sobrie, con
   pill "Acquisto verificato" cyan. Token da style.css :root. Rimovibile.
   ════════════════════════════════════════════════════════════════════════ */

/* ── Componente stelle a riempimento parziale (percentuale reale) ───────── */
.stars { display: inline-block; line-height: 1; font-size: 1.2rem; }
.stars .stars__track { position: relative; display: inline-block; white-space: nowrap; color: rgba(255,255,255,.16); letter-spacing: .08em; }
.stars .stars__fill { position: absolute; top: 0; left: 0; width: 0; overflow: hidden; white-space: nowrap; color: var(--yellow); letter-spacing: .08em; text-shadow: 0 0 8px rgba(255,214,0,.32); }
.stars--lg { font-size: 1.7rem; }
.stars--lg .stars__fill { text-shadow: 0 0 14px rgba(255,214,0,.4); }  /* glow più marcato sul rating eroe */

/* ── Rating sintetico sotto il titolo prodotto ──────────────────────────── */
.prod-reviews--live { display: inline-flex; align-items: center; gap: .5rem; text-decoration: none; }
.prod-reviews-score { font-family: var(--f-ui); font-weight: 700; color: var(--text); }
.prod-reviews-count { font-family: var(--f-mono); font-size: .78rem; color: var(--text-2); transition: color .18s; }
.prod-reviews--live:hover .prod-reviews-count { color: var(--cyan); }
.prod-reviews--empty { display: inline-flex; align-items: center; gap: .4rem; font-family: var(--f-ui); font-size: .85rem; color: var(--text-2); text-decoration: none; transition: color .18s; }
.prod-reviews--empty svg { width: 15px; height: 15px; color: var(--yellow); }
.prod-reviews--empty:hover { color: var(--cyan); }

/* ── Sezione ────────────────────────────────────────────────────────────── */
.prod-reviews-sec { padding: clamp(2.5rem, 6vw, 4.5rem) 0; border-top: 1px solid var(--border); }
.revx-head { margin-bottom: clamp(1.5rem, 4vw, 2.4rem); }
.revx-eyebrow { display: inline-block; font-family: var(--f-mono); font-size: .68rem; letter-spacing: .16em; text-transform: uppercase; color: var(--cyan); border-left: 3px solid var(--cyan); padding-left: .7rem; }
.revx-title { font-family: var(--f-display); font-weight: 800; font-size: clamp(2rem, 5vw, 3.2rem); line-height: .95; text-transform: uppercase; letter-spacing: -.01em; margin: .55rem 0 0; }

/* ── Riepilogo d'impatto ────────────────────────────────────────────────── */
.revx-summary {
  display: grid; grid-template-columns: minmax(0,auto) 1fr;
  gap: clamp(1.5rem, 5vw, 3.5rem); align-items: center;
  background: linear-gradient(160deg, var(--bg-card), var(--bg));
  border: 1px solid var(--border-2); border-radius: var(--r-lg);
  padding: clamp(1.5rem, 4vw, 2.5rem);
  margin-bottom: clamp(1.4rem, 4vw, 2.2rem);
}
.revx-score { text-align: center; }
.revx-score-num { font-family: var(--f-display); font-weight: 900; font-size: clamp(4rem, 13vw, 6.5rem); line-height: .8; color: var(--cyan); text-shadow: 0 0 34px rgba(0,212,255,.32); }
.revx-score-num sup { font-size: .3em; font-weight: 700; color: var(--text-3); vertical-align: super; }
.revx-score .stars { margin: .55rem 0 .4rem; }
.revx-score-count { font-family: var(--f-mono); font-size: .74rem; letter-spacing: .04em; color: var(--text-2); }

.revx-dist { display: flex; flex-direction: column; gap: .5rem; min-width: 0; }
.revx-dist-row { display: grid; grid-template-columns: 2.4rem 1fr 2rem; align-items: center; gap: .7rem; }
.revx-dist-k { font-family: var(--f-mono); font-size: .74rem; color: var(--text-2); white-space: nowrap; }
.revx-dist-k b { color: var(--yellow); font-weight: 700; }
.revx-dist-track { height: 8px; border-radius: 99px; background: rgba(255,255,255,.06); overflow: hidden; }
.revx-dist-fill { display: block; height: 100%; border-radius: 99px; background: linear-gradient(90deg, var(--cyan), var(--magenta)); box-shadow: 0 0 12px rgba(0,212,255,.28); }
.revx-dist-n { font-family: var(--f-mono); font-size: .72rem; color: var(--text-3); text-align: right; }

/* ── Griglia card ───────────────────────────────────────────────────────── */
.revx-grid { display: grid; grid-template-columns: repeat(2, 1fr); gap: clamp(.9rem, 2.5vw, 1.4rem); }
.revx-card { display: flex; flex-direction: column; gap: .55rem; background: var(--bg-card); border: 1px solid var(--border); border-radius: var(--r-md); padding: clamp(1.1rem, 3vw, 1.5rem); transition: border-color .2s, transform .2s; }
.revx-card:hover { border-color: rgba(0,212,255,.35); transform: translateY(-2px); }
.revx-card.is-hidden { display: none; }
.revx-card-top { display: flex; align-items: center; justify-content: space-between; gap: .75rem; }
.revx-card .stars { font-size: 1.08rem; }
.revx-card-date { font-family: var(--f-mono); font-size: .68rem; color: var(--text-3); white-space: nowrap; }
.revx-card-title { font-family: var(--f-ui); font-weight: 700; font-size: 1.02rem; line-height: 1.3; color: var(--text); margin: 0; }
.revx-card-body { font-size: .92rem; line-height: 1.6; color: var(--text-2); margin: 0; }
.revx-card-foot { display: flex; align-items: center; gap: .6rem; flex-wrap: wrap; margin-top: .15rem; }
.revx-author { font-family: var(--f-mono); font-size: .78rem; letter-spacing: .02em; color: var(--text); }
.revx-verified { display: inline-flex; align-items: center; gap: .3rem; font-family: var(--f-ui); font-size: .68rem; font-weight: 700; color: var(--cyan); background: rgba(0,212,255,.1); border: 1px solid rgba(0,212,255,.32); border-radius: 99px; padding: .18rem .55rem; }
.revx-verified svg { width: 12px; height: 12px; }

/* ── Mostra tutte ───────────────────────────────────────────────────────── */
.revx-more-wrap { text-align: center; margin-top: clamp(1.2rem, 3vw, 1.8rem); }
.revx-more { font-family: var(--f-ui); font-weight: 700; font-size: .85rem; color: var(--cyan); background: transparent; border: 1.5px solid var(--border-2); border-radius: var(--r-sm); padding: .7rem 1.6rem; cursor: pointer; transition: border-color .2s, background .2s; }
.revx-more:hover { border-color: var(--cyan); background: rgba(0,212,255,.06); }

/* ── Stato vuoto ────────────────────────────────────────────────────────── */
.revx-empty { text-align: center; padding: clamp(2rem, 6vw, 3.5rem); background: var(--bg-card); border: 1px dashed var(--border-2); border-radius: var(--r-lg); }
.revx-empty-ico { display: block; width: 52px; height: 52px; margin: 0 auto 1rem; color: var(--cyan); opacity: .85; }
.revx-empty-title { font-family: var(--f-ui); font-weight: 700; font-size: 1.15rem; color: var(--text); margin: 0 0 .4rem; }
.revx-empty-sub { max-width: 42ch; margin: 0 auto; font-size: .95rem; color: var(--text-2); }

/* ── Responsive ─────────────────────────────────────────────────────────── */
@media (max-width: 720px) {
  .revx-grid { grid-template-columns: 1fr; }
}
@media (max-width: 560px) {
  .revx-summary { grid-template-columns: 1fr; gap: 1.4rem; text-align: center; }
  .revx-dist { max-width: 320px; margin: 0 auto; width: 100%; }
}
@media (prefers-reduced-motion: reduce) {
  .revx-card { transition: none; }
  .revx-card:hover { transform: none; }
}
