@import url('fonts/noto-fonts.css');

* { box-sizing: border-box; }
html, body { margin: 0; padding: 0; }

/* Font dei tre temi, auto-ospitati (Google Fonts, file in /fonts): sostituti liberi
   metric-compatible di Arial/Courier New/Georgia, scelti da Google apposta per questo scopo, così
   il testo è identico su ogni dispositivo invece di dipendere da cosa c'è installato localmente. */
@font-face {
  font-family: 'Arimo';
  font-style: normal;
  font-weight: 400 700;
  font-display: swap;
  src: url('fonts/Arimo-Regular.woff2') format('woff2');
}
@font-face {
  font-family: 'Arimo';
  font-style: italic;
  font-weight: 400 700;
  font-display: swap;
  src: url('fonts/Arimo-Italic.woff2') format('woff2');
}
@font-face {
  font-family: 'Gelasio';
  font-style: normal;
  font-weight: 400 700;
  font-display: swap;
  src: url('fonts/Gelasio-Regular.woff2') format('woff2');
}
@font-face {
  font-family: 'Gelasio';
  font-style: italic;
  font-weight: 400 700;
  font-display: swap;
  src: url('fonts/Gelasio-Italic.woff2') format('woff2');
}
@font-face {
  font-family: 'Courier Prime';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('fonts/CourierPrime-Regular.woff2') format('woff2');
}
@font-face {
  /* Il vero taglio Bold ha tratti troppo spessi/compressi nel tema scuro (vedi nota più sotto):
     il peso 700 punta di proposito al file Regular, così il "grassetto" resta leggero, con la
     stessa spaziatura dei caratteri della Regular da cui parte. */
  font-family: 'Courier Prime';
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url('fonts/CourierPrime-Regular.woff2') format('woff2');
}
@font-face {
  font-family: 'Courier Prime';
  font-style: italic;
  font-weight: 400;
  font-display: swap;
  src: url('fonts/CourierPrime-Italic.woff2') format('woff2');
}
.cn-brand { font-family: 'Courier Prime', monospace; }
/* .cn-brand.cn-brand: stesso selettore raddoppiato solo per alzare la specificità (0,2,0) sopra
   quella di .cn-title (0,1,0) e di .cn-auth-logo span (0,1,1), così la scritta del marchio resta
   sempre in peso normale indipendentemente da quale altra classe di titolo le sta accanto. Anche
   la dimensione è fissata in rem (non em): A-/A+ cambia --cn-font-size sul documento, e un valore
   in em la seguirebbe; il marchio deve restare della stessa dimensione a qualunque zoom. */
.cn-brand.cn-brand { font-weight: 400; font-size: .95rem; }
.cn-auth-logo .cn-brand.cn-brand { font-size: 1.15rem; }

/* Coda comune ai tre temi: copertura di arabo/cinese/giapponese/coreano, indipendente dal tema
   (un solo font scelto per ciascuna scrittura, non uno stile diverso per tema — vedi Noto sopra). */

/* --cn-accent resta il colore "di richiamo" (bordi attivi, link, anello dei temi); i pulsanti
   pieni (.cn-btn) usano invece --cn-btn-bg/--cn-btn-text a sé stanti — sul tema chiaro l'accento
   teal risultava troppo simile al nero del tema scuro, e sul seppia il goldenrod era "troppo
   marrone": qui si può correggere il colore dei pulsanti senza toccare gli altri usi di --cn-accent. */
[data-theme="minimal"] {
  --cn-bg: #ffffff;
  --cn-text: #1a202c;
  --cn-font: Arimo, -apple-system, "Segoe UI", Arial, "Noto Naskh Arabic", "Noto Serif SC", "Noto Serif JP", "Noto Serif KR", sans-serif;
  --cn-accent: #166ca2;
  --cn-btn-bg: #166ca2;
  --cn-btn-text: #ffffff;
  --cn-border: rgba(22, 108, 162, 0.3);
  --cn-icon-bg: rgba(22, 108, 162, 0.1);
  --cn-icon-border: #166ca2;
  --cn-muted: rgba(26, 32, 44, 0.6);
}
/* Il peso 700 di Courier Prime punta al file Regular (vedi @font-face più sopra): senza altro
   sarebbe identico alla Regular, non "leggermente in grassetto". Un filo di contorno via
   text-stroke aggiunge un po' di peso ai tratti — meno del vero Bold — senza cambiare font né
   larghezza dei caratteri (a differenza di font-weight, non rompe l'allineamento monospaziato). */
[data-theme="dark"] :is(b, strong, h1, h2, h3, h4, h5, h6) { -webkit-text-stroke: .9px currentColor; }
[data-theme="dark"] {
  --cn-bg: #0a0e1a;
  --cn-text: #e7fbff;
  --cn-font: "Courier Prime", "Courier New", Courier, "Noto Naskh Arabic", "Noto Serif SC", "Noto Serif JP", "Noto Serif KR", monospace;
  --cn-accent: #00e5ff;
  --cn-btn-bg: #00e5ff;
  --cn-btn-text: #041014;
  --cn-border: rgba(0, 229, 255, 0.25);
  --cn-icon-bg: rgba(0, 229, 255, 0.12);
  --cn-icon-border: #00e5ff;
  --cn-muted: rgba(231, 251, 255, 0.6);
}
[data-theme="papyrus"] {
  --cn-bg: #f3ede1;
  --cn-text: #2b2015;
  --cn-font: Gelasio, Georgia, "Times New Roman", "Noto Naskh Arabic", "Noto Serif SC", "Noto Serif JP", "Noto Serif KR", serif;
  --cn-accent: #b8860b;
  --cn-btn-bg: #d9a635;
  --cn-btn-text: #2b2015;
  --cn-border: rgba(184, 134, 11, 0.3);
  --cn-icon-bg: rgba(184, 134, 11, 0.12);
  --cn-icon-border: #b8860b;
  --cn-muted: rgba(43, 32, 21, 0.6);
}

body {
  background: var(--cn-bg);
  color: var(--cn-text);
  font-family: var(--cn-font);
  font-size: var(--cn-font-size, 1rem);
  transition: background .2s ease, color .2s ease;
  min-height: 100vh;
}
/* Ogni testo che non fissa una propria dimensione eredita quella di body, quindi A-/A+ (che
   cambiano --cn-font-size) ingrandiscono anche pulsanti/etichette, non solo il testo del romanzo.
   Le dimensioni sotto sono apposta in "em" (relative al genitore), non "rem" (fisse sulla radice),
   per scalare insieme; misure di layout (padding, gap, larghezze) restano invece in rem, così
   cambia il testo ma non le proporzioni dell'impaginazione. */
/* Pagine statiche (elenco romanzi, privacy, chi siamo): il footer resta ancorato in fondo
   alla finestra anche quando il contenuto è breve, invece di seguire subito il contenuto. */
body.cn-page-body { display: flex; flex-direction: column; }
body.cn-page-body .cn-page { flex: 1 0 auto; }
body.cn-page-body .cn-footer { margin-top: auto; }

a { color: var(--cn-accent); }

/* Senza questa regola il placeholder di input/textarea usa il colore di default del browser
   (pensato per sfondi chiari): nel tema scuro risultava un grigio scuro poco leggibile sullo
   sfondo quasi nero. --cn-muted è già il "testo secondario" di ciascun tema, qui applicato anche
   ai placeholder con opacity:1 per non sommare un'ulteriore trasparenza a quella già nel colore. */
::placeholder { color: var(--cn-muted); opacity: 1; }

/* ---------- toolbar (a comparsa) ---------- */
.cn-toolbar {
  position: sticky;
  top: 0;
  z-index: 25;
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  gap: .5rem;
  padding: .75rem 1rem;
  border-bottom: 1px solid var(--cn-border);
  background: var(--cn-bg);
  transition: transform .2s ease, opacity .2s ease;
}
.cn-toolbar.is-hidden { transform: translateY(-100%); opacity: 0; pointer-events: none; }
.cn-toolbar > .cn-toolbar-group:first-child { justify-self: start; }
.cn-toolbar > .cn-toolbar-group:nth-child(2) { justify-self: center; }
.cn-toolbar > .cn-toolbar-group:last-child { justify-self: end; }

.cn-toolbar-reveal {
  position: fixed; top: .75rem; right: 1rem; z-index: 22;
  width: 2.2rem; height: 2.2rem; border-radius: 50%;
  /* Sfondo PIENO (--cn-bg, non --cn-icon-bg): questo pulsante fluttua sopra il testo del romanzo
     mentre la barra è nascosta (vedi initBarraLettore), --cn-icon-bg è troppo trasparente (alpha
     bassa) per restare leggibile sopra al testo che scorre sotto — stesso criterio già usato per
     le altre icone a comparsa sopra un contenuto, es. .cn-libreria-elimina. */
  border: 1px solid var(--cn-icon-border); background: var(--cn-bg); color: inherit;
  display: flex; align-items: center; justify-content: center; cursor: pointer;
  opacity: 0; pointer-events: none; transition: opacity .2s ease;
}
.cn-toolbar-reveal.is-visible { opacity: 1; pointer-events: auto; }
.cn-toolbar-group { display: flex; align-items: center; gap: .35rem; }
.cn-logo-link { display: flex; align-items: center; gap: .5rem; text-decoration: none; color: inherit; }
.cn-title { font-weight: 600; font-size: .95em; opacity: .85; }
/* Telefono in orizzontale: il titolo lungo andrebbe a capo e ingrandirebbe la barra, quindi non si mostra. */
@media (pointer: coarse) and (max-height: 500px) { .cn-title { display: none; } }
/* Indicatore "usati/tetto" dei crediti IA (prova gratuita o Premium, vedi renderCreditoBadge() in
   app.js): un badge piccolo e discreto accanto al titolo del romanzo, non un elemento che debba
   attirare l'attenzione. */
.cn-credito-badge {
  font-size: .75em; opacity: .6; white-space: nowrap;
  border: 1px solid var(--cn-icon-border); border-radius: 1em; padding: .1rem .55rem;
}
.cn-logo { width: 1.9rem; height: 1.9rem; object-fit: contain; background: transparent; }
/* Sfondo trasparente su tema chiaro/seppia (colore naturale dell'icona); sul tema scuro l'icona
   (glifo scuro su alpha) viene invertita in bianco, sempre a sfondo trasparente. */
[data-theme="dark"] .cn-logo { filter: invert(1); }

.cn-icon-btn {
  width: 2.2rem; height: 2.2rem; border-radius: 50%;
  border: 1px solid var(--cn-icon-border);
  background: var(--cn-icon-bg);
  color: inherit; font-size: 1em;
  display: flex; align-items: center; justify-content: center;
  cursor: pointer;
}
.cn-icon-btn:hover { filter: brightness(0.95); }
.cn-icon-btn.is-active { box-shadow: 0 0 0 2px var(--cn-accent); }
/* A-/A+ cambiano --cn-font-size: se scalassero anche loro (ereditando da body) diventerebbero
   sempre più grandi/piccoli a ogni click. Restano fissi in rem, ancorati alla radice. */
#font-minus, #font-plus { font-size: 1rem; }
/* #font-plus-mobile e #btn-drawer-toggle-mobile esistono solo per la riga a comparsa su telefono
   (vedi il blocco @media più sotto): su schermi larghi i pulsanti "veri" (A+/Faro) bastano già da
   soli, quindi questi restano sempre nascosti finché quel blocco non li riporta in vita. */
#font-plus-mobile, #btn-drawer-toggle-mobile { display: none; }

.cn-icon { display: inline-flex; position: relative; width: 1.1rem; height: 1.1rem; }
.cn-icon svg, .cn-icon img { width: 100%; height: 100%; display: block; }
/* Le icone sono PNG nere fisse (vedi icon() in icons.js): sul tema scuro, dove il testo è chiaro
   su sfondo scuro, un'icona nera sarebbe pressoché invisibile — stessa inversione già usata per
   .cn-logo qui sopra, stesso motivo. */
[data-theme="dark"] .cn-icon img { filter: invert(1); }
.cn-btn .cn-icon { width: 1rem; height: 1rem; margin-right: .35rem; vertical-align: -2px; }
.cn-btn .cn-icon.cn-icona-leggi { vertical-align: -3px; }
.cn-icon-btn .cn-icon { width: 1.05rem; height: 1.05rem; }

/* Icona "vista del testo" in reader/leggi.html (Originale/Tradotto/Affiancati): al click mostra le
   tre icone rotonde originali — niente riquadro/sfondo proprio dietro di loro, solo attorno alle
   singole icone. .cn-icon-btn usa di norma uno sfondo translucido (--cn-icon-bg): va bene dentro
   la barra, che ha già il suo sfondo pieno sotto (stesso ragionamento del blocco commentato più
   sopra per il gruppo A-/A+ su telefono) — queste però galleggiano sopra il testo della pagina
   (position:absolute), quindi qui serve uno sfondo pieno per restare leggibili invece di lasciar
   trasparire il testo sotto. */
.cn-vista-testo-wrap { position: relative; display: inline-flex; }
.cn-vista-testo-menu {
  position: absolute; top: 100%; left: 50%; transform: translateX(-50%); margin-top: .4rem;
  display: flex; gap: .35rem; z-index: 30;
}
.cn-vista-testo-menu[hidden] { display: none; }
.cn-vista-testo-menu .cn-icon-btn { background: var(--cn-bg); box-shadow: 0 2px 8px rgba(0, 0, 0, .15); }

.cn-theme-btn { width: 1.8rem; height: 1.8rem; border-radius: 50%; cursor: pointer; padding: 0; border: 2px solid var(--cn-icon-border); }
.cn-theme-btn.is-active { box-shadow: 0 0 0 2px var(--cn-accent); }
.cn-theme-btn[data-theme-choice="minimal"] { background: #ffffff; }
.cn-theme-btn[data-theme-choice="dark"] { background: #0a0e1a; }
.cn-theme-btn[data-theme-choice="papyrus"] { background: #f3ede1; }
.cn-theme-selector { display: flex; align-items: center; gap: .35rem; }

/* ---------- reading column ---------- */
.cn-content {
  max-width: 42rem;
  margin: 0 auto;
  line-height: 1.7;
  padding: 2rem 1.5rem 6rem;
}
@media (max-width: 40rem) { .cn-content { padding: 1.5rem 1rem 5rem; } }

/* ---------- schermi stretti (telefoni): barra più compatta ---------- */
@media (max-width: 40rem) {
  /* Marchio/titolo del romanzo accanto al logo: tolto per fare spazio alle icone, il logo da
     solo basta a identificare la pagina. */
  .cn-title { display: none; }
  /* Con il badge dei crediti visibile il logo si toglie: il badge è più utile dello spazio che occupa. */
  .cn-logo-link:has(~ #credito-badge:not([hidden])) { display: none; }
  /* Nella barra in alto (non nel selettore dentro Impostazioni > Personalizza tema, che è un
     contesto diverso, sempre con spazio a sufficienza) resta visibile solo il pallino del tema
     attivo, finché il selettore non viene espanso (vedi initTheme in app.js) o non lo è già il
     gruppo A-/A+ che lo contiene (vedi sotto): libera lo spazio che serviva a leggere-ad-alta-voce
     e impostazioni, spinti fuori schermo su telefoni stretti. */
  .cn-toolbar .cn-theme-selector:not(.is-espanso) .cn-theme-btn:not(.is-active) { display: none; }
  #toolbar-group-font.is-espanso .cn-theme-selector .cn-theme-btn { display: inline-block; }

  /* Editor su telefono (vedi scrivi.js): troppi pulsanti in barra durante la scrittura
     (impostazioni, faro, scrittura a più mani, A-/A+, temi, vista lettura). Restano sempre
     visibili solo A+, leggi-ad-alta-voce e Faro; A+ e Faro sono anche l'innesco che apre sotto,
     al tocco, il resto del proprio gruppo (stesso schema del pallino del tema qui sopra: primo
     tocco apre, non agisce). Entrambi gli inneschi sempre visibili (A+ e Faro, cioè #font-plus e
     #btn-drawer-toggle) fanno SOLO questo su telefono, mai l'azione vera (vedi
     initToolbarMobileGroups in scrivi.js): l'azione vera è nei loro gemelli dentro la riga a
     comparsa, #font-plus-mobile e #btn-drawer-toggle-mobile (nascosti di default fuori da questo
     blocco, vedi sopra), riportati in vita qui sotto solo quando il gruppo è espanso. */
  #toolbar-group-font:not(.is-espanso) #font-minus,
  #toolbar-group-font:not(.is-espanso) .cn-theme-selector { display: none; }
  #toolbar-group-menu:not(.is-espanso) #btn-view-toggle,
  #toolbar-group-menu:not(.is-espanso) #btn-collab,
  #toolbar-group-menu:not(.is-espanso) #btn-debug,
  #toolbar-group-menu:not(.is-espanso) #btn-settings { display: none; }
  /* Da espansi, il resto del gruppo compare in una riga assolutamente posizionata sotto l'innesco
     (position:absolute, non flex-wrap): così non partecipa più al flusso del gruppo e non ne
     allarga la riga, quindi né l'altezza della barra né la posizione degli altri pulsanti/gruppi
     si spostano, si vedono solo i nuovi pulsanti comparire sotto. */
  #toolbar-group-font, #toolbar-group-menu { position: relative; }
  #toolbar-group-font.is-espanso #font-minus,
  #toolbar-group-font.is-espanso .cn-theme-selector {
    position: absolute;
    top: calc(100% + .5rem);
  }
  #toolbar-group-font.is-espanso #font-plus-mobile {
    display: flex;
    position: absolute;
    top: calc(100% + .5rem);
  }
  /* Esattamente sotto A+ (primo pulsante visibile del gruppo, quindi bordo sinistro del gruppo
     stesso): A- allineato a sinistra, subito a destra il vero A+ (#font-plus-mobile, accanto ad
     A- come richiesto), poi i temi. */
  #toolbar-group-font.is-espanso #font-minus { left: 0; }
  #toolbar-group-font.is-espanso #font-plus-mobile { left: 2.55rem; }
  #toolbar-group-font.is-espanso .cn-theme-selector { left: 5.1rem; }
  #toolbar-group-menu.is-espanso #btn-view-toggle,
  #toolbar-group-menu.is-espanso #btn-collab,
  #toolbar-group-menu.is-espanso #btn-debug,
  #toolbar-group-menu.is-espanso #btn-settings {
    position: absolute;
    top: calc(100% + .5rem);
  }
  #toolbar-group-menu.is-espanso #btn-drawer-toggle-mobile {
    display: flex;
    position: absolute;
    top: calc(100% + .5rem);
  }
  /* Il gruppo, da chiuso, è largo solo quanto l'innesco Faro (#btn-drawer-toggle) ed è ancorato al
     bordo destro della barra: le extra si allineano allo stesso bordo destro, non a sinistra,
     altrimenti sconfinerebbero fuori schermo. #btn-debug (solo admin) resta più a sinistra di
     tutte così, quando nascosto (utenti non admin), non lascia un buco fra le altre tre. Esattamente
     sotto l'innesco Faro compare il suo gemello vero #btn-drawer-toggle-mobile (right:0, come A+
     nell'altro gruppo), le altre spinte più a sinistra di conseguenza. */
  #toolbar-group-menu.is-espanso #btn-drawer-toggle-mobile { right: 0; }
  #toolbar-group-menu.is-espanso #btn-settings { right: 2.55rem; }
  #toolbar-group-menu.is-espanso #btn-collab { right: 5.1rem; }
  #toolbar-group-menu.is-espanso #btn-view-toggle { right: 7.65rem; }
  #toolbar-group-menu.is-espanso #btn-debug { right: 10.2rem; }
  /* .cn-icon-btn usa di norma uno sfondo translucido (--cn-icon-bg): va bene dentro la barra,
     che ha già il suo sfondo pieno sotto. Questi però galleggiano sopra il contenuto della
     pagina (position:absolute), quindi serve uno sfondo pieno per restare leggibili. */
  #toolbar-group-font.is-espanso #font-minus,
  #toolbar-group-font.is-espanso #font-plus-mobile,
  #toolbar-group-menu.is-espanso #btn-view-toggle,
  #toolbar-group-menu.is-espanso #btn-collab,
  #toolbar-group-menu.is-espanso #btn-debug,
  #toolbar-group-menu.is-espanso #btn-settings,
  #toolbar-group-menu.is-espanso #btn-drawer-toggle-mobile {
    background: var(--cn-bg);
    box-shadow: 0 2px 8px rgba(0, 0, 0, .15);
  }
  /* La larghezza personalizzata del paragrafo di scrittura (trascinabile su desktop, vedi
     initParagraphResize) non ha senso su uno schermo già stretto: usa sempre tutto lo spazio
     disponibile, a prescindere da un valore salvato in una sessione desktop precedente. */
  .cn-format-wrap-paragrafo { max-width: 100% !important; }
  /* Indietro/Avanti/Concludi il capitolo/Concludi il romanzo in fila: su schermi stretti nowrap
     li stringe abbastanza da spezzare "Concludi il capitolo/romanzo" su tre righe e da far
     debordare la riga oltre il bordo destro. Vanno bene su due righe. */
  .cn-draft-controls { flex-wrap: wrap; }
}

.cn-paragraph { margin-top: 0; margin-bottom: 1.25rem; white-space: pre-wrap; }
/* Numero di paragrafo nel romanzo: nascosto di norma (rumore per chi scrive/legge), mostrato solo
   mentre la scheda "Controlla" del drawer è aperta, per capire a quale paragrafo si riferisce un
   avviso (vedi renderCoerenzaHtml/renderStory in scrivi.js). */
.cn-numero-paragrafo { display: none; }
body.cn-mostra-numeri-paragrafo .cn-numero-paragrafo {
  display: block;
  font-family: monospace;
  font-size: .75rem;
  opacity: .55;
  margin-bottom: .25rem;
}
.cn-paragraph.is-draft[contenteditable="true"], textarea.is-draft {
  outline: 2px dashed var(--cn-accent);
  border-radius: .4rem;
  padding: .75rem;
  cursor: text;
}
textarea.is-draft {
  width: 100%; font: inherit; resize: vertical; border: none; background: transparent; color: var(--cn-text);
}
.cn-draft-controls { display: flex; gap: .5rem; margin: .75rem 0 2rem; }
.cn-draft-stile-riga { display: flex; justify-content: flex-end; margin-top: .35rem; }
.cn-draft-stile-nome {
  background: none; border: none; font: inherit; font-size: .75em; opacity: .6;
  cursor: pointer; padding: .15rem .3rem; color: inherit;
}
.cn-draft-stile-nome:hover { opacity: .9; text-decoration: underline; }
.cn-draft-stile-riga select {
  font-size: .75em; padding: .15rem .3rem; border-radius: .3rem;
  border: 1px solid var(--cn-border); background: var(--cn-bg); color: var(--cn-text);
}
/* "Indietro" e il bottone di conferma condividono questa riga quando possibile (allineata a
   destra), tornando su due righe solo se lo spazio non basta — flex-wrap fa tutto da solo, senza
   bisogno di media query dedicate. */
.cn-indietro-sotto { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: .5rem; margin-top: 1rem; }
/* margin-bottom oltre al margin-top: senza, il pulsante "Rigenera" (alternative del turno,
   scrivi.js) restava incollato senza spazio al campo "O spiegami cosa vorresti..." subito sotto —
   .cn-field ha margine solo in basso su di sé, nessuno in cima. */
.cn-concludi-romanzo { display: flex; justify-content: flex-end; margin: 1.5rem 0; }
.cn-concluso-azioni { display: flex; gap: .5rem; margin-top: .75rem; align-items: center; }

.cn-actions { display: flex; flex-direction: column; gap: .5rem; margin: 1.5rem 0; }
/* Stessa dimensione delle opzioni sottostanti (.cn-action-btn): a differenza di .cn-punto-meta,
   qui è un titolo di sezione, non una nota secondaria, quindi niente rimpicciolimento/opacità. */
.cn-scegli-titolo { font-size: .95em; margin: 0; font-style: italic; }
.cn-action-btn {
  text-align: left; padding: .75rem 1rem; border-radius: .5rem;
  border: 1px solid var(--cn-border); background: var(--cn-icon-bg);
  color: inherit; font: inherit; font-size: .95em; cursor: pointer;
}
.cn-action-btn:hover { border-color: var(--cn-accent); }
/* renderStileScelta (scrivi.js/demo.js): descrizione di uno stile preconfigurato, dentro al suo
   stesso pulsante — a differenza di .cn-punto-meta niente opacità ridotta (stesso colore del
   titolo sopra, eredita .cn-action-btn { color: inherit }), solo un filo più grande di una nota
   secondaria perché qui è il contenuto vero e proprio, non un'annotazione. */
.cn-stile-preset-desc { font-size: .85em; margin-top: .15rem; }
/* espandiStiliPersonali (scrivi.js): un div normale non fa stretchare i <button> a piena larghezza
   come .cn-actions (flex column, cross-axis stretch di default) — senza questa regola i pulsanti
   degli stili personali restavano larghi solo quanto il loro testo, molto più stretti degli altri
   pulsanti stile sopra di loro. */
.cn-stile-personali-lista { display: flex; flex-direction: column; gap: .5rem; }
.cn-action-free { display: flex; gap: .5rem; }
/* Invia (spiega) e Inserisci (continua) dopo le alternative proposte dall'IA: stessa larghezza,
   non quella intrinseca del testo del pulsante, così il paio risulta visivamente allineato. */
#btn-spiega-invia, #btn-continua-invia { flex: 0 0 7rem; width: 7rem; text-align: center; }
.cn-action-free input, .cn-action-free textarea {
  flex: 1; padding: .65rem .8rem; border-radius: .5rem;
  border: 1px solid var(--cn-border); background: transparent; color: inherit; font: inherit;
}

.cn-btn {
  padding: .55rem 1.1rem; border-radius: .5rem; border: 1px solid var(--cn-btn-bg);
  background: var(--cn-btn-bg); color: var(--cn-btn-text); font: inherit; font-size: .9em; font-weight: 600; cursor: pointer;
  text-decoration: none; display: inline-block;
}
/* .cn-btn imposta display e batterebbe l'attributo hidden: senza questa riga un pulsante "nascosto" resta visibile. */
.cn-btn[hidden] { display: none; }
.cn-btn:hover { filter: brightness(1.05); }
.cn-btn.secondary { background: transparent; color: inherit; border-color: var(--cn-border); font-weight: 400; }
.cn-btn:disabled { opacity: .5; cursor: not-allowed; }
.cn-btn.cn-btn-piccolo { padding: .3rem .6rem; font-size: .78em; white-space: nowrap; }
/* Pulsantino in linea con una riga di testo (Impostazioni: "Passa a Premium" accanto al piano): stessa grandezza del testo. */
.cn-btn.cn-btn-inline { display: inline-block; width: auto; margin: 0 0 0 .5rem; padding: 0 .5em; font-size: inherit; line-height: inherit; white-space: nowrap; vertical-align: baseline; opacity: 1; }
.cn-drawer-header h2 { min-width: 0; overflow-wrap: anywhere; }

.cn-page-indicator { text-align: center; font-size: .8em; opacity: .5; padding-bottom: 2rem; }

/* ---------- drawer (Faro / Punti aperti / Schede / Analisi) ---------- */
.cn-drawer {
  position: fixed; top: 3.75rem; right: 0; width: min(var(--cn-drawer-width, 23.6rem), 100vw); height: calc(100vh - 3.75rem);
  background: var(--cn-bg); color: var(--cn-text); border-left: 1px solid var(--cn-border);
  box-shadow: -6px 0 24px rgba(0, 0, 0, .18);
  transform: translateX(100%);
  transition: transform .25s ease;
  z-index: 20; overflow-y: auto; padding: 1.5rem;
}
.cn-drawer.is-open { transform: translateX(0); }
/* Admin in sola lettura (vedi render() in scrivi.js, .cn-sola-lettura su body): disabilita in
   blocco ogni form del cassetto invece di dover intervenire pannello per pannello — i pulsanti di
   navigazione/tab restano invece cliccabili (fuori da .cn-drawer-panel), solo il CONTENUTO dei
   pannelli diventa inerte. */
.cn-sola-lettura .cn-drawer-panel input,
.cn-sola-lettura .cn-drawer-panel textarea,
.cn-sola-lettura .cn-drawer-panel select,
.cn-sola-lettura .cn-drawer-panel button {
  pointer-events: none; opacity: .55;
}
/* La transizione è su transform, non su width: il ridimensionamento trascinato (che cambia solo
   --cn-drawer-width, vedi wireDrawerResizeHandle in app.js) segue il mouse 1:1 senza ritardo,
   indipendentemente da questa regola. */
/* Maniglia sul bordo sinistro del drawer Faro per ridimensionarlo trascinando col mouse (vedi
   initDrawerResize() in scrivi.js): larga 8px ma centrata sul bordo (-4px) così l'area cliccabile
   sporge un po' su entrambi i lati, più facile da agganciare col cursore. */
.cn-drawer-resize-handle {
  position: absolute; left: -4px; top: 0; width: 8px; height: 100%; cursor: ew-resize; z-index: 5;
}

.cn-drawer-header { display: flex; justify-content: space-between; align-items: center; margin-bottom: 1rem; }
/* "Impostazioni" e "Dietro le quinte": stessa dimensione di un titolo di capitolo (.cn-capitolo-titolo). */
.cn-drawer-header h2, .cn-drawer-header strong { font-size: 1.3em; margin: 0; }
/* Pulsante "x" delle Impostazioni: stessa altezza esatta del pulsante "Esci"/"Accedi" affiancato
   (box-sizing:border-box globale rende height/width la misura vera del pulsante), non la misura
   rotonda standard di .cn-icon-btn (2.2rem), più alta. */
#settings-drawer .cn-drawer-header .cn-btn-piccolo,
#settings-drawer .cn-drawer-header .cn-drawer-close { height: 1.9rem; }
#settings-drawer .cn-drawer-header .cn-drawer-close { width: 1.9rem; }
.cn-drawer-tabs { display: flex; gap: .35rem; flex-wrap: wrap; margin-bottom: 1rem; }
.cn-tab { padding: .35rem .7rem; border-radius: 999px; border: 2px solid var(--cn-border); background: transparent; color: inherit; font: inherit; font-size: .8em; cursor: pointer; }
.cn-tab.is-active { background: transparent; color: var(--cn-accent); border-color: var(--cn-accent); }
.cn-drawer-panel { display: none; }
.cn-drawer-panel.is-active { display: block; }

/* Badge "Tradotto" (vedi badgeTradotto() in app.js): stesso linguaggio visivo pillola di .cn-tab,
   ma non cliccabile — solo un'etichetta. */
.cn-badge-tradotto { display: inline-flex; align-items: center; gap: .3em; padding: .2rem .6rem; border-radius: 999px; border: 1px solid var(--cn-icon-border); background: var(--cn-icon-bg); font-size: .8em; }
.cn-badge-tradotto .cn-icon { width: .9em; height: .9em; }

.cn-drawer-section { margin-top: 1.5rem; }
.cn-drawer-section h3, .cn-drawer-collapse-header h3 { font-size: .78em; text-transform: uppercase; opacity: .55; letter-spacing: .06em; margin: 0 0 .6rem; }
.cn-drawer-section > .cn-btn { margin-bottom: .6rem; }

/* Sezioni "a comparsa" del drawer Impostazioni (tema personalizzato, pagamenti, cambio dati
   account): contratte di default, mostrano solo il titolo finché non si clicca per espanderle —
   evita che la barra risulti troppo lunga con tutto sempre visibile. */
.cn-drawer-collapse { margin-top: 1.5rem; }
.cn-drawer-collapse-header {
  display: flex; align-items: center; justify-content: space-between; gap: .5rem; width: 100%;
  background: transparent; border: none; padding: 0; margin: 0 0 .6rem; cursor: pointer;
  color: inherit; font: inherit; text-align: left;
}
.cn-drawer-collapse-header h3 { flex: 1; }
.cn-drawer-collapse-header svg { width: 1em; height: 1em; opacity: .55; flex-shrink: 0; transition: transform .2s ease; }
.cn-drawer-collapse.is-espanso .cn-drawer-collapse-header svg { transform: rotate(180deg); }
.cn-drawer-collapse-body { display: none; }
.cn-drawer-collapse.is-espanso .cn-drawer-collapse-body { display: block; }
/* Pannello admin > Provider IA: i titoli dei blocchi (Modello principale, Modello secondario,
   Controllo testo e copertina, IA Admin) sono a comparsa come le altre sezioni del drawer, ma in
   evidenza (scuri, non piccoli/discreti) perché sono la navigazione principale di questa scheda,
   non un dettaglio secondario. */
#admin-content .cn-drawer-collapse-header h3 { font-size: .95em; text-transform: none; letter-spacing: normal; opacity: 1; color: var(--cn-text); font-weight: 700; }
.cn-field { margin-bottom: .8rem; }
/* 1em, non 1.05em: né l'etichetta né il testo dei campi del drawer (Faro, Impostazioni, ...) devono
   avere una dimensione diversa dal testo del romanzo — entrambi ereditano da --cn-font-size senza
   alcuna moltiplicazione, esattamente come .cn-paragraph. */
.cn-field label { display: block; font-size: 1em; opacity: .8; margin-bottom: .35rem; }
.cn-field textarea, .cn-field input:not([type="radio"]):not([type="checkbox"]), .cn-field select {
  width: 100%; padding: .55rem; border-radius: .4rem; border: 1px solid var(--cn-border);
  background: transparent; color: inherit; font: inherit; font-size: 1em;
}
.cn-field textarea { resize: vertical; min-height: 4rem; }
.cn-file-picker { display: flex; align-items: center; gap: .7rem; flex-wrap: wrap; }

/* Chrome/Safari colorano di giallo/blu i campi che riconoscono come credenziali di login
   (tipicamente username e password, non email o conferma password) appena l'autofill li tocca,
   sovrascrivendo lo sfondo trasparente del template sopra. Il box-shadow enorme "riempie" il
   campo con lo sfondo del tema invece del giallo nativo, senza toccare bordo/testo. */
.cn-field input:-webkit-autofill,
.cn-field input:-webkit-autofill:hover,
.cn-field input:-webkit-autofill:focus {
  -webkit-text-fill-color: var(--cn-text);
  box-shadow: 0 0 0 1000px var(--cn-bg) inset;
  transition: background-color 5000s ease-in-out 0s;
}

/* Radio/checkbox dentro .cn-field ereditavano width:100%/padding/border dalla regola sopra,
   destinata a testarea/input di testo/select: li deformava in riquadri enormi, disallineati dal
   testo dell'etichetta. Qui vengono resettati alla loro dimensione naturale e allineati in riga. */
.cn-field input[type="radio"], .cn-field input[type="checkbox"] {
  width: auto; flex-shrink: 0; margin: 0;
}
.cn-field label:has(> input[type="radio"]) {
  display: inline-flex; align-items: center; gap: .45em; margin: 0 1.2rem .35rem 0;
}
/* Checkbox associato a un testo lungo (es. dichiarazione di responsabilità in pubblicazione): allineato
   in alto sulla prima riga invece che al centro di tutto il blocco di testo andato a capo. */
.cn-field label:has(> input[type="checkbox"]) {
  display: flex; align-items: flex-start; gap: .45em; margin: 0 0 .35rem 0;
}
.cn-field label:has(> input[type="checkbox"]) input { margin-top: .2em; }

/* Textarea dei Punti aperti: NON dentro un .cn-field (è un elemento libero in .cn-punto), quindi
   senza questa regola resta con lo sfondo bianco di default del browser invece di quello del tema. */
.punto-descrizione {
  width: 100%; padding: .55rem; border-radius: .4rem; border: 1px solid var(--cn-border);
  background: transparent; color: inherit; font: inherit; font-size: 1em; resize: vertical;
}

/* Nome dei personaggi principali (Faro) e nome nelle Schede (personaggio/oggetto/luogo): risalta
   rispetto agli altri campi nella stessa card. Specificità .cn-field input.xxx (0,3,0) necessaria
   per battere ".cn-field input" (0,2,0), la cui "font: inherit" shorthand azzererebbe altrimenti
   il font-weight impostato qui. */
.cn-field input.fp-nome, .cn-field input.frp-nome, .cn-field input.scheda-nome { font-weight: 700; }

/* I <select> nativi non ereditano colori dal tema come input/textarea: senza queste regole
   restano con lo sfondo bianco di default del browser anche nei temi scuro/papiro. */
select {
  background: var(--cn-bg); color: var(--cn-text); font: inherit;
  border: 1px solid var(--cn-border); border-radius: .4rem; padding: .4rem .5rem;
}
select option { background: var(--cn-bg); color: var(--cn-text); }

.cn-punto, .cn-scheda-card, .cn-avviso, .cn-correzione {
  padding: .6rem .7rem; border-radius: .4rem; border: 1px solid var(--cn-border);
  margin-bottom: .5rem; font-size: .85em;
}
.cn-punto.is-risolto { opacity: .5; text-decoration: line-through; }
.cn-scheda-card-cliccabile { cursor: pointer; }
.cn-scheda-card-cliccabile:hover { border-color: var(--cn-accent); }
/* Stile attivo sulla creazione corrente (vedi renderStiliPanel): sfondo tenue invece del solo
   bordo, per essere riconoscibile a colpo d'occhio tra più voci della libreria. */
.cn-scheda-card.is-attivo {
  border-color: var(--cn-accent);
  background: color-mix(in srgb, var(--cn-accent) 12%, transparent);
}
.cn-punto-meta, .cn-scheda-meta { font-size: .75em; opacity: .6; margin-top: .2rem; }
/* renderStileScelta (scrivi.js/demo.js): la nota "puoi comunque cambiare stile più avanti" resta
   un'annotazione secondaria (stessa opacità ridotta di .cn-punto-meta) ma un filo più leggibile
   delle altre note della stessa classe, essendo sopra a un intero elenco di pulsanti e non accanto
   a un singolo elemento. */
.cn-stile-nota-modificabile { font-size: .85em; }
.cn-avviso.gravita-alta { border-color: #e05252; }
.cn-avviso-actions { display: flex; gap: .4rem; margin-top: .4rem; }
.cn-avviso-actions button { font-size: .75em; padding: .25rem .6rem; }

.cn-proposta { border: 1px solid var(--cn-accent); border-radius: .5rem; padding: .75rem; margin-bottom: 1rem; font-size: .85em; }
.cn-proposta-actions { display: flex; gap: .5rem; margin-top: .6rem; }

/* ---------- conversazione (chat) view ---------- */
.cn-turn { margin-bottom: 1.75rem; }
.cn-turn[contenteditable="true"] { cursor: text; border-radius: .4rem; }
.cn-turn[contenteditable="true"]:focus { outline: 2px dashed var(--cn-accent); padding: .5rem; }
.cn-modifica-inline { margin: .75rem 0 1.75rem; }

/* ---------- capitoli ---------- */
.cn-capitolo-titolo { text-align: center; font-weight: 700; font-size: 1.3em; margin: 2.5rem 0 1.25rem; }
.cn-capitolo-marker {
  display: flex; align-items: center; justify-content: center; gap: .5rem;
  font-weight: 700; font-size: 1.15em; margin: 2.5rem 0 1rem; text-align: center;
}
.cn-capitolo-marker .cn-icon-btn { opacity: .5; }
.cn-capitolo-marker .cn-icon-btn:hover { opacity: 1; }
.cn-capitolo-nome[contenteditable="true"] { cursor: text; border-radius: .3rem; padding: .1rem .3rem; }
.cn-capitolo-nome[contenteditable="true"]:hover { outline: 1px dashed var(--cn-border); }
.cn-capitolo-nome[contenteditable="true"]:focus { outline: 2px dashed var(--cn-accent); }
.cn-aggiungi-capitolo {
  display: none; align-items: center; gap: .3rem; margin: 1.5rem auto 1rem;
  font-size: .78em; padding: .3rem .7rem; opacity: .45;
}
.cn-aggiungi-capitolo:hover { opacity: 1; }
/* Il pulsante compare solo sopra e sotto il paragrafo che si sta modificando (bordo tratteggiato,
   vedi .cn-turn[contenteditable="true"]:focus sopra), non su ogni paragrafo del romanzo: sopra è il
   pulsante del blocco stesso, sotto è quello del blocco successivo (vedi wrapping .cn-paragrafo-
   blocco in renderStory, scrivi.js). Il marker di un capitolo già esistente resta sempre visibile,
   non è toccato da questa regola. */
.cn-paragrafo-blocco:has(.cn-turn:focus) .cn-aggiungi-capitolo,
.cn-paragrafo-blocco:has(.cn-turn:focus) + .cn-paragrafo-blocco .cn-aggiungi-capitolo {
  display: flex;
}

/* ---------- misc ---------- */
.cn-empty { opacity: .55; font-size: .9em; }

/* Barra di avanzamento minimale (es. importazione manoscritto, un blocco alla volta): niente di
   più di un contorno sottile e un riempimento pieno, coerente con lo stile essenziale del resto
   dei controlli dell'app. */
.cn-progress-bar {
  width: 100%; height: .5rem; border: 1px solid var(--cn-border); border-radius: .3rem;
  overflow: hidden; margin: .75rem 0 .35rem;
}
.cn-progress-bar-fill { height: 100%; background: var(--cn-accent); transition: width .3s ease; }
/* Finché non si conosce ancora il numero totale di blocchi (validazione file, o subito dopo aver
   premuto "Riprova"), una barra ferma allo 0% è indistinguibile da una pagina bloccata: questa
   variante scorre avanti e indietro per mostrare che qualcosa sta comunque succedendo. */
.cn-progress-bar-fill.is-indeterminate {
  width: 40% !important; animation: cn-progress-indeterminate 1.1s ease-in-out infinite;
}
@keyframes cn-progress-indeterminate {
  0% { margin-left: 0%; }
  50% { margin-left: 60%; }
  100% { margin-left: 0%; }
}
/* Anello che gira usato da attesaIaHtml() (app.js) dopo il messaggio d'attesa di ogni chiamata IA:
   stesso colore del testo (currentColor, niente accento colorato), coerente con un sito
   minimalista — niente puntini (molti messaggi d'attesa finiscono già con "…" nel testo), niente
   icona disegnata, niente barra di avanzamento (tutte scartate). */
.cn-ia-spinner {
  display: inline-block; width: .8em; height: .8em; margin-left: .4em; vertical-align: -.1em;
  border: 2px solid currentColor; border-top-color: transparent; border-radius: 50%;
  opacity: .6; animation: cn-ia-girare .8s linear infinite;
}
@keyframes cn-ia-girare { to { transform: rotate(360deg); } }
.cn-toast-container { position: fixed; bottom: 1rem; left: 50%; transform: translateX(-50%); z-index: 50; display: flex; flex-direction: column; gap: .5rem; align-items: center; }
.cn-toast { padding: .6rem 1.1rem; border-radius: .4rem; background: var(--cn-text); color: var(--cn-bg); font-size: .85em; box-shadow: 0 4px 14px rgba(0,0,0,.2); }
.cn-toast.error { background: #e05252; color: #fff; }
.cn-avviso-sito { position: fixed; top: 0; left: 0; right: 0; z-index: 70; display: flex; align-items: center; justify-content: center; gap: .8rem; padding: .55rem 1rem; background: #e05252; color: #fff; font-size: .9em; line-height: 1.4; text-align: center; box-shadow: 0 2px 10px rgba(0,0,0,.25); }
.cn-avviso-sito-chiudi { background: none; border: 0; color: inherit; font-size: 1.4em; line-height: 1; cursor: pointer; padding: 0 .3rem; }

.cn-modal-backdrop { position: fixed; inset: 0; background: rgba(0,0,0,.4); display: flex; align-items: center; justify-content: center; z-index: 40; }
.cn-modal { background: var(--cn-bg); color: var(--cn-text); border-radius: .6rem; padding: 1.5rem; width: min(30rem, 92vw); max-height: 85vh; overflow-y: auto; }
.cn-modal h2 { margin-top: 0; }
.cn-modal-intro { font-size: .9em; opacity: .8; }
.cn-modal-header { display: flex; align-items: center; justify-content: space-between; gap: .75rem; }
.cn-modal-header h2 { margin: 0; font-size: 1.05em; }
.cn-modal-header .cn-icon-btn { flex-shrink: 0; width: 1.9rem; height: 1.9rem; }
.cn-modal-actions { display: flex; justify-content: flex-end; gap: .5rem; margin-top: 1.25rem; }
.cn-modal-largo { width: min(46rem, 92vw); }

/* Mappa dei rami (Registra nuova demo, vedi scrivi.js apriMappaRami) */
.cn-mappa-rami { margin-top: 1rem; }
.cn-mappa-nodo-testo { font-size: .9em; }
.cn-mappa-opzioni { list-style: none; margin: .4rem 0 .8rem; padding-left: 1.1rem; border-left: 2px solid var(--cn-border, currentColor); display: flex; flex-direction: column; gap: .6rem; }
.cn-mappa-opzione { font-size: .9em; }
.cn-mappa-opzione-azione { font-style: italic; opacity: .85; margin-bottom: .25rem; }
.cn-mappa-opzione.is-completata .cn-mappa-opzione-azione { color: #2f9e64; }
.cn-mappa-opzione.is-bozza .cn-mappa-opzione-azione { color: #c8850f; }
.cn-mappa-nodo-nota { font-size: .85em; opacity: .7; margin: .25rem 0 0; }
.cn-mappa-badge { display: inline-block; font-size: .75em; font-weight: 600; padding: .1rem .4rem; border-radius: .3rem; background: var(--cn-icon-bg); margin-left: .35rem; }
.cn-mappa-badge-finale { color: #2f9e64; }
.cn-mappa-badge-qui { color: var(--cn-accent); }
.cn-mappa-vai { font-size: .85em; padding: .3rem .6rem; }

.cn-auth-logo { display: flex; align-items: center; gap: .6rem; justify-content: center; margin-bottom: 1.25rem; }
.cn-auth-logo img { width: 2.4rem; height: 2.4rem; object-fit: contain; }
[data-theme="dark"] .cn-auth-logo img { filter: invert(1); }
.cn-auth-logo span { font-weight: 700; font-size: 1.15em; }

/* ---------- index.html (project list) ---------- */
.cn-page { max-width: 42rem; width: 100%; margin: 0 auto; padding: 2rem 1.5rem 4rem; }
/* Ritmo verticale dei titoli di sezione e dei paragrafi: più spazio sopra i titoli (li stacca dal
   paragrafo precedente), meno spazio sotto (li avvicina al testo che introducono), leggermente
   meno spazio fra un paragrafo e l'altro. Margine solo in basso sui paragrafi così il distacco
   dipende sempre dall'elemento sopra, senza ambiguità di collasso dei margini. */
.cn-page h2 { margin-top: 30px; margin-bottom: .5em; font-size: 1.15em; }
.cn-page p { margin-top: 0; margin-bottom: .8em; }
.cn-page-header { display: flex; justify-content: space-between; align-items: center; margin-bottom: 1.5rem; gap: .75rem; flex-wrap: wrap; }
.cn-page-header-actions { position: relative; display: flex; align-items: center; gap: .6rem; flex-wrap: wrap; }
.cn-project-card { display: flex; align-items: center; justify-content: space-between; gap: .75rem; padding: 1rem; border: 1px solid var(--cn-border); border-radius: .6rem; margin-bottom: .75rem; cursor: pointer; }
.cn-project-card-top { display: flex; align-items: center; gap: .75rem; min-width: 0; flex: 1; }
.cn-project-cover-thumb { width: 2.4rem; height: 3.6rem; object-fit: cover; border-radius: .25rem; flex-shrink: 0; background: var(--cn-border); }
.cn-project-card:hover { border-color: var(--cn-accent); }
.cn-project-card-main { min-width: 0; }
.cn-project-card .cn-project-titolo { font-weight: 600; margin-bottom: .25rem; }
.cn-project-card .cn-project-meta { font-size: .8em; opacity: .6; }
.cn-project-card-actions { display: flex; gap: .35rem; flex-shrink: 0; }
.cn-project-card-actions .cn-icon-btn { width: 1.9rem; height: 1.9rem; }
/* Sul cellulare una card a due colonne (testo a sinistra, icone a destra) stringe troppo il
   testo: sotto i 40rem diventa una sola colonna, con le icone su una riga a sé sotto tutto il
   testo invece che schiacciate di fianco. */
@media (max-width: 40rem) {
  .cn-project-card { flex-direction: column; align-items: stretch; }
  .cn-project-card-actions { justify-content: flex-end; }
}

/* ---------- scrittura a più mani (pagina spettatore + pannello editor) ---------- */
.cn-empty-state { max-width: 30rem; margin: 3rem auto; text-align: center; }
.cn-empty-state h1 { font-size: 1.2em; margin-bottom: .6em; }
.cn-empty-state p { opacity: .75; margin-bottom: 1.25em; }
.cn-collab-badge { font-size: .8em; opacity: .65; white-space: nowrap; display: inline-flex; align-items: center; gap: .4em; }
.cn-collab-live-dot { display: inline-block; width: .5em; height: .5em; border-radius: 50%; background: #e0303f; flex-shrink: 0; }
.cn-collab-storia .cn-paragraph { cursor: default; }
.cn-collab-storia .cn-capitolo-marker { text-align: center; opacity: .6; font-size: .85em; margin: 1.5em 0 .75em; }

/* Badge di voto lato autore: piccolo bottone a sé accanto (mai al posto di) ogni bottone/campo
   reale — vedi collabVotoHtml in scrivi.js. */
.cn-collab-voto-btn {
  display: inline-flex; align-items: center; gap: .3rem;
  height: 1.9rem; padding: 0 .55rem; border-radius: 999px;
  border: 1px solid var(--cn-icon-border); background: var(--cn-icon-bg); color: inherit;
  font-size: .8em; cursor: pointer; vertical-align: middle;
}
.cn-collab-voto-btn:hover { filter: brightness(0.95); }
.cn-collab-voto-btn.is-active { box-shadow: 0 0 0 2px var(--cn-accent); }
.cn-collab-voto-btn .cn-icon { width: .9rem; height: .9rem; margin: 0; }
.cn-collab-voto-conteggio { min-width: 1em; text-align: center; }
/* .cn-actions (le alternative fra cui scegliere) è una colonna flex: senza questo wrapper riga per
   riga, il badge di voto affiancato a ciascuna opzione (collabVotoHtml) finiva come figlio
   diretto della colonna, quindi su una propria riga a piena larghezza sotto l'opzione — un'ovale
   di testo seguita da una barra lunga col conteggio, invece dei due affiancati. */
.cn-collab-opzione-riga { display: flex; align-items: stretch; gap: .5rem; }
.cn-collab-opzione-riga .cn-action-btn { flex: 1; }
.cn-collab-opzione-riga .cn-collab-voto-btn { flex-shrink: 0; align-self: center; }
.cn-collab-banner { background: var(--cn-icon-bg); border: 1px solid var(--cn-accent); border-radius: .5rem; padding: .6rem .9rem; margin-bottom: 1rem; font-size: .9em; }

/* Opzioni lato spettatore (collab.js): stesso look di .cn-action-btn, col pallino di voto fuori
   dal rettangolo dell'opzione (dentro .cn-collab-opzione-riga, condivisa con le alternative lato
   autore in scrivi.js) invece che incollato dentro il bottone — stessa impostazione visiva da
   entrambi i lati, un solo ovale "esterno" col conteggio invece di uno annidato nell'altro. */
.cn-collab-opzioni { display: flex; flex-direction: column; gap: .5rem; margin: .75rem 0; }
/* Il click di voto è sull'intera .cn-collab-opzione-riga (vedi renderPuntoDecisione in
   collab.js), non solo sul bottone di testo al suo interno: senza cursor:pointer qui il pallino
   del conteggio, essendo fuori dal bottone, sembrava non cliccabile. */
.cn-collab-opzioni .cn-collab-opzione-riga { cursor: pointer; }
.cn-collab-spett-opt { text-align: left; }
.cn-collab-opzione-riga.is-active .cn-collab-spett-opt { border-color: var(--cn-accent); box-shadow: 0 0 0 1px var(--cn-accent); }
/* Stesso ovale (icona spunta + numero, sfondo arrotondato) usato per il voto indicativo
   dell'autore (.cn-collab-voto-btn): qui non è un bottone a sé — il voto scatta cliccando
   l'intera opzione — quindi niente cursor/hover propri, solo l'aspetto. */
.cn-collab-voto-pill {
  display: inline-flex; align-items: center; gap: .3rem;
  height: 1.9rem; padding: 0 .55rem; border-radius: 999px;
  border: 1px solid var(--cn-icon-border); background: var(--cn-icon-bg); color: inherit;
  font-size: .8em; flex-shrink: 0; align-self: center;
}
.cn-collab-voto-pill .cn-icon { width: .9rem; height: .9rem; margin: 0; }
.cn-collab-opzione-riga.is-active .cn-collab-voto-pill { box-shadow: 0 0 0 2px var(--cn-accent); }

/* ---------- chat flottante della scrittura a più mani ---------- */
/* Posizione di default: affiancata a destra della colonna di testo (.cn-content, 42rem centrata
   nel viewport), non più nell'angolo in basso a destra — lì restava fuori dal campo visivo di chi
   sta scrivendo nel paragrafo, sopra al quale la si voleva invece sempre visibile senza dover
   cliccare "Chat" per accorgersi che c'era già. */
.cn-collab-chat {
  position: fixed; left: calc(50% + 22.5rem); top: 4.75rem; z-index: 40;
  width: 20rem; height: 16rem; min-width: 220px; min-height: 180px;
  max-width: calc(100vw - 1.5rem); max-height: calc(100vh - 1.5rem);
  display: flex; flex-direction: column;
  background: var(--cn-bg); border: 1px solid var(--cn-border); border-radius: .6rem;
  box-shadow: 0 4px 18px rgba(0,0,0,.18);
}
/* Senza questa riga il display:flex qui sopra vince comunque sull'attributo hidden (stessa
   regola già serve a .cn-footer-menu/.cn-header-menu): impostare el.hidden = true sul bottone di
   chiusura non nascondeva la finestra, restava visibile. */
.cn-collab-chat[hidden] { display: none; }
/* Sotto questa larghezza non c'è spazio per affiancare la chat alla colonna di testo (42rem di
   contenuto + margini) senza farla uscire dal viewport: torna nell'angolo in basso a destra,
   come overlay flottante. */
@media (max-width: 88rem) {
  .cn-collab-chat { left: auto; top: auto; right: 1.5rem; bottom: 1.5rem; }
}
/* Su schermi stretti una geometria salvata da una sessione desktop (localStorage, vedi
   apriWidgetChatCollab in app.js) potrebbe uscire dal viewport: qui si forza una posizione/misura
   sicura, ignorando lo style inline impostato dal trascinamento. */
@media (max-width: 480px) {
  .cn-collab-chat { left: auto !important; top: auto !important; right: .75rem !important; bottom: .75rem !important; width: calc(100vw - 1.5rem) !important; height: 60vh !important; }
}
.cn-collab-chat-header {
  display: flex; align-items: center; justify-content: space-between;
  padding: .5rem .75rem; border-bottom: 1px solid var(--cn-border);
  font-weight: 600; font-size: .85em; cursor: move; user-select: none;
}
.cn-collab-chat-header .cn-icon-btn { width: 1.6rem; height: 1.6rem; }
/* Titolo "Chat" + badge online raggruppati a sinistra: lo spazio fra i due resta fisso (gap)
   invece di essere spinto dallo justify-content:space-between dell'header, che altrimenti
   distribuirebbe i tre elementi (titolo, badge, chiudi) a distanza uguale l'uno dall'altro. */
.cn-collab-chat-header-info { display: flex; align-items: center; gap: .6rem; font-weight: 400; }
.cn-collab-chat-header-info > span:first-child { font-weight: 600; }
/* Link e chiudi raggruppati stretti a destra: senza questo lo justify-content:space-between
   dell'header li spargerebbe a distanza uguale invece di tenerli accostati. */
.cn-collab-chat-header-azioni { display: flex; align-items: center; gap: .2rem; }
.cn-collab-chat-messaggi { flex: 1; overflow-y: auto; padding: .5rem .75rem; font-size: .85em; }
.cn-collab-chat-msg { margin-bottom: .4em; line-height: 1.4; }
.cn-collab-chat-nome { font-weight: 600; margin-right: .35em; }
.cn-collab-chat-invio { display: flex; gap: .4rem; padding: .5rem .75rem; border-top: 1px solid var(--cn-border); }
.cn-collab-chat-invio input {
  flex: 1; font-size: .85em; padding: .4rem .6rem; border-radius: .4rem;
  border: 1px solid var(--cn-border); background: transparent; color: inherit; font-family: inherit;
}
.cn-collab-chat-invio .cn-icon-btn { width: 1.9rem; height: 1.9rem; flex-shrink: 0; }
.cn-collab-chat-resize {
  position: absolute; right: 0; bottom: 0; width: 1rem; height: 1rem; cursor: nwse-resize;
  background: linear-gradient(135deg, transparent 50%, var(--cn-border) 50%);
  border-bottom-right-radius: .6rem;
}

/* ---------- galleria copertine (modale Esporta/Pubblica) ---------- */
.cn-cover-gallery { display: flex; flex-wrap: wrap; gap: .75rem; margin-top: .75rem; }
.cn-cover-thumb { display: flex; align-items: flex-start; gap: .4rem; }
.cn-cover-thumb img { width: 6.5rem; aspect-ratio: 2/3; object-fit: cover; border-radius: .3rem; border: 2px solid var(--cn-border); display: block; cursor: zoom-in; }
.cn-cover-delete { width: 1.6rem; height: 1.6rem; border: none; background: transparent; }

/* ---------- Homepage: due CTA verso Writer/Reader ---------- */
.cn-home-cta { display: flex; gap: 1.25rem; flex-wrap: wrap; margin: 2rem 0; }
.cn-home-cta .cn-btn { display: block; flex: 1; min-width: 14rem; padding: 1.25rem 1.5rem; text-align: left; text-decoration: none; }
.cn-home-cta-logo { display: block; width: 2.4rem; height: 2.4rem; margin-bottom: .6rem; object-fit: contain; }
/* I due pulsanti in alto hanno lo stesso trattamento di quelli duplicati più in basso, in "Due porte,
   un solo account" (.cn-home-cta-btn-solido, sotto): sfondo pieno del colore del tema, che al
   passaggio del mouse diventa trasparente. Come nell'app. Il logo (nero su trasparente, con zone
   interne bianche) resta normale di default e nel tema scuro si inverte solo al passaggio del mouse,
   quando lo sfondo pieno sparisce. */
.cn-btn.cn-home-cta-btn { background: var(--cn-btn-bg); color: var(--cn-btn-text); border-width: 2px; border-color: var(--cn-btn-bg); font-weight: 400; }
.cn-home-cta-btn:hover { background: transparent; color: inherit; }
[data-theme="dark"] .cn-home-cta-btn:hover .cn-home-cta-logo { filter: invert(1); }

/* Pulsanti duplicati nella sezione "Due porte, un solo account" più in basso: stesso aspetto di
   quelli in alto (pieni di default, trasparenti al passaggio del mouse). Nel tema minimal l'icona
   resta sempre normale, mai invertita. */
.cn-btn.cn-home-cta-btn-solido { border-width: 2px; border-color: var(--cn-btn-bg); }
.cn-home-cta-btn-solido:hover { background: transparent; color: inherit; }
[data-theme="dark"] .cn-home-cta-btn-solido:hover .cn-home-cta-logo { filter: invert(1); }
.cn-home-editabile { outline: 1px dashed var(--cn-accent); outline-offset: .25rem; border-radius: .2rem; cursor: text; }
.cn-rte-toolbar { display: flex; gap: .4rem; margin-bottom: .8rem; flex-wrap: wrap; }
.cn-rte-toolbar button[data-rte="bold"] { font-weight: 700; }
.cn-rte-toolbar button[data-rte="italic"] { font-style: italic; }
/* La barra della homepage resta fissa in cima allo schermo per tutta la modifica, invece di
   seguire il campo a fuoco: quel comportamento (versione precedente) a volte finiva sotto al
   paragrafo o restava visibile anche dopo aver chiuso la modifica. Da fissa, mostrarla/nasconderla
   è solo display:flex/none in attivaModificaHome — niente più riposizionamenti nel DOM che
   potevano lasciarla in uno stato sbagliato. hp-modifica-attiva su body aggiunge lo spazio in
   cima al contenuto perché la barra fissa non lo copra. */
#hp-rte-toolbar.cn-rte-toolbar {
  position: fixed; top: 0; left: 50%; transform: translateX(-50%); z-index: 45;
  width: max-content; max-width: min(42rem, 96vw); margin-bottom: 0;
  background: var(--cn-bg); border: 1px solid var(--cn-border); border-top: none;
  border-radius: 0 0 .6rem .6rem; box-shadow: 0 6px 16px rgba(0, 0, 0, .15);
  padding: .5rem .75rem; overflow-x: auto;
}
body.cn-hp-modifica-attiva .cn-page { padding-top: 3.75rem; }
.cn-rte-box { border: 1px solid var(--cn-accent); border-radius: .5rem; padding: 1rem 1.25rem; margin: 1rem 0; background: color-mix(in srgb, var(--cn-accent) 8%, transparent); }
.cn-rte-html-source, .cn-rte-html-source-pagina { width: 100%; min-height: 8rem; font-family: monospace; font-size: .85em; }
/* Pulsante a larghezza automatica inseribile nei riquadri della homepage: <a class="cn-btn"> è di
   base un elemento inline, quindi si allarga o restringe da solo in base al testo che contiene
   (anche quando l'autore lo modifica), senza bisogno di calcolarne la larghezza via JS. */
.cn-rte-pulsante { margin: 0 .2rem; }
/* Spazio extra fra un paragrafo e l'altro, inseribile al cursore. */
.cn-rte-spazio { height: 1.4em; }
/* Immagini caricate nei riquadri della homepage: senza un limite non potrebbero mai superare lo
   schermo su schermi stretti. La manopola di ridimensionamento (sotto) può comunque ingrandirle
   fino a quel limite, mai oltre. */
.cn-hp-blocco-testo img, .cn-hp-colonna img, .cn-rte-box img { max-width: 100%; height: auto; }
.cn-rte-img-selezionata { outline: 2px solid var(--cn-accent); outline-offset: 1px; }
.cn-rte-img-manopola {
  position: fixed; width: 14px; height: 14px;
  background: var(--cn-accent); border: 2px solid var(--cn-bg); border-radius: 50%;
  cursor: nwse-resize; z-index: 60;
}
/* Icone PNG (faro/orme/strada/penna/altoparlante/nuvola/download/cuore) davanti ai titoli in
   grassetto dei riquadri della homepage. cn-icon resta per eventuali icone SVG residue. */
.cn-hp-blocco-testo strong .cn-icon, .cn-hp-blocco-testo b .cn-icon,
.cn-hp-blocco-testo strong .cn-icon-img, .cn-hp-blocco-testo b .cn-icon-img,
.cn-hp-blocco-testo h2 .cn-icon, .cn-hp-blocco-testo h2 .cn-icon-img {
  width: 1.65em; height: 1.65em; vertical-align: -.35em; margin-right: .4rem; object-fit: contain; display: inline-block;
}
/* Alcune sagome (es. il cuore di "Come supportare il progetto") riempiono quasi tutto il loro
   riquadro, quindi a parità di larghezza dichiarata sembrano più grandi delle altre icone: vanno
   rimpicciolite apposta con questo modificatore. */
.cn-hp-blocco-testo strong .cn-icon.cn-icon-piccola, .cn-hp-blocco-testo b .cn-icon.cn-icon-piccola,
.cn-hp-blocco-testo strong .cn-icon-img.cn-icon-piccola, .cn-hp-blocco-testo b .cn-icon-img.cn-icon-piccola,
.cn-hp-blocco-testo h2 .cn-icon.cn-icon-piccola, .cn-hp-blocco-testo h2 .cn-icon-img.cn-icon-piccola {
  width: 1.25em; height: 1.25em;
}
/* Tutte le icone PNG della homepage sono sagome nere su sfondo trasparente: nel tema scuro,
   sullo sfondo quasi nero della pagina, sparirebbero senza invertirle in bianco. */
[data-theme="dark"] .cn-hp-blocco-testo .cn-icon-img { filter: invert(1); }
/* Più spazio fra il titoletto in grassetto (es. "Installazione locale — completamente gratis") e
   il paragrafo sotto: il <br> che li separa nell'HTML salvato normalmente dà solo l'interlinea
   di una riga vuota, poco distinguibile dal resto. display:block + margin-top su un <br> è una
   tecnica CSS valida e supportata per allargare apposta quel singolo a-capo. */
.cn-hp-blocco-testo strong + br, .cn-hp-colonna strong + br,
.cn-hp-blocco-testo b + br, .cn-hp-colonna b + br,
#hp-intro strong + br, #hp-intro b + br {
  display: block; content: ""; margin-top: 1.15rem;
}
/* Più respiro fra i punti di un elenco puntato dentro i riquadri della homepage (es. i due punti
   in "Versione cloud — cosa aggiunge"): di base sono attaccati uno all'altro. */
.cn-hp-blocco-testo li, .cn-hp-colonna li { margin-bottom: .6rem; }
.cn-hp-blocco-testo li:last-child, .cn-hp-colonna li:last-child { margin-bottom: 0; }
/* Il pulsante "Crea un account" (in alto sotto i riquadri Writer/Reader, e in fondo alla pagina)
   è un link: senza questa regola avrebbe la sottolineatura di default di un <a>. */
a[data-azione="apri-registrazione"] { text-decoration: none; }
a[data-azione="apri-registrazione"]:hover { background: transparent; color: inherit; border-width: 2px; margin: -1px; }
/* Icone social per condividere la homepage (Facebook, X, WhatsApp, LinkedIn): stesso trattamento
   in bianco e nero dei loghi PNG usati altrove nella homepage, con leggero effetto hover. */
.cn-hp-social-riga { display: flex; gap: .85rem; margin: .75rem 0; align-items: center; }
.cn-hp-social-link { display: inline-flex; line-height: 0; opacity: .8; }
.cn-hp-social-link:hover { opacity: 1; }
.cn-hp-social-link .cn-icon-img { width: 1.7em; height: 1.7em; object-fit: contain; }

/* ---------- blocchi extra homepage: riquadri a colonna intera o a due colonne, inseribili con un
   "+" fra un blocco e l'altro (solo in modalità modifica) ---------- */
.cn-hp-plus-riga { display: none; gap: .4rem; margin: .6rem 0; }
#hp-blocchi-extra.is-editing .cn-hp-plus-riga { display: flex; }
.cn-hp-plus { width: 1.7rem; height: 1.7rem; border-radius: 50%; border: 1px dashed var(--cn-accent); background: transparent; color: var(--cn-accent); cursor: pointer; display: flex; align-items: center; justify-content: center; padding: 0; }
.cn-hp-plus .cn-icon { width: .9rem; height: .9rem; }
.cn-hp-blocco-full, .cn-hp-blocco-due-colonne { position: relative; margin: .5rem 0; }
.cn-hp-blocco-due-colonne { display: flex; gap: 1rem; }
/* .cn-hp-colonna stessa si allarga già alla pari (flex:1 dentro un flex-parent stretch di
   default), ma il pulsante VISIBILE al suo interno (il bordo/sfondo che si vede) è display:block
   e resta alto quanto il proprio contenuto: con descrizioni Writer/Reader di lunghezza diversa
   (righe diverse) restava visibilmente più basso uno dei due nonostante il contenitore invisibile
   fosse già alla pari. display:flex sul contenitore + flex:1 sul pulsante lo fa combaciare. */
.cn-hp-blocco-due-colonne > .cn-hp-colonna { flex: 1; min-width: 0; display: flex; }
.cn-hp-colonna > .cn-home-cta-btn-solido { flex: 1; }
.cn-hp-blocco-rimuovi { display: none; width: 1.6rem; height: 1.6rem; z-index: 2; }
.cn-hp-blocco-rimuovi .cn-icon { width: .75rem; height: .75rem; }
/* Riquadri extra in modifica: su/giù/rimuovi raggruppati in alto a destra, per riordinare i
   blocchi senza dover ricreare o incollare contenuto. I "+" di inserimento fra i blocchi non si
   spostano: si scambiano solo i due blocchi, vedi spostaBlocco() in index.html. */
.cn-hp-blocco-controlli { display: none; position: absolute; top: -.6rem; right: -.6rem; z-index: 2; gap: .3rem; }
#hp-blocchi-extra.is-editing .cn-hp-blocco-controlli { display: flex; }
#hp-blocchi-extra.is-editing .cn-hp-blocco-controlli .cn-hp-blocco-rimuovi { display: flex; }
.cn-hp-blocco-su .cn-icon svg, .cn-hp-blocco-su .cn-icon img { transform: rotate(180deg); }

/* Paragrafi fissi cancellabili (intro, testo ecosistema, spiegazione): stesso pulsante cestino dei
   riquadri extra, ma da solo (senza su/giù: l'ordine di questi paragrafi è fisso) e visibile in
   base alla modalità modifica generale della pagina, non a #hp-blocchi-extra.is-editing. */
.cn-hp-campo-wrap { position: relative; }
.cn-hp-campo-wrap > .cn-hp-blocco-rimuovi { position: absolute; top: -.6rem; right: -.6rem; }
body.cn-hp-modifica-attiva .cn-hp-campo-wrap > .cn-hp-blocco-rimuovi { display: flex; }

/* ---------- Reader: filtri, griglia libri, pagina di dettaglio/lettura ---------- */
.cn-reader-filtri { margin-bottom: 1.5rem; font-size: .9em; }
.cn-reader-filtri-riga { display: flex; gap: 1rem; flex-wrap: wrap; }
.cn-reader-filtri-riga .cn-field { flex: 1; min-width: 9rem; }

.cn-book-grid { display: flex; flex-wrap: wrap; gap: 1.25rem; }
.cn-book-card { width: 10rem; cursor: pointer; }
.cn-book-card:hover .cn-book-titolo { color: var(--cn-accent); }
.cn-book-cover img, .cn-book-cover-vuota {
  width: 100%; aspect-ratio: 2/3; object-fit: cover; border-radius: .4rem;
  border: 1px solid var(--cn-border); display: block; background: var(--cn-icon-bg);
}
/* Pulsante "ritira pubblicazione" sulla propria pagina autore (vedi renderLibri in autore.js):
   nascosto finché non si passa sopra la copertina, come i pulsanti di eliminazione già usati
   altrove sulle card libro. */
.cn-book-card-azione {
  display: none; position: absolute; top: .3rem; right: .3rem; width: 1.7rem; height: 1.7rem;
  background: var(--cn-bg); z-index: 2;
}
.cn-book-cover:hover .cn-book-card-azione { display: flex; }
.cn-book-titolo { font-weight: 600; margin-top: .5rem; font-size: .92em; }
.cn-book-autore { font-size: .8em; opacity: .65; }
/* Badge "traduzione automatica disponibile" in Vetrina (vedi bookCardHtml in reader/index.js): una
   piccola icona tonda accanto al numero di paragrafi — l'immagine della copertina resta libera
   da sovrapposizioni. Ripetuto anche nella legenda in cima alla Vetrina. */
.cn-book-badge-traduzione {
  display: inline-flex; align-items: center; justify-content: center; flex-shrink: 0;
  width: 1.35rem; height: 1.35rem; border-radius: 50%;
  border: 1px solid var(--cn-border); background: var(--cn-icon-bg);
}
.cn-book-badge-traduzione .cn-icon { width: .8rem; height: .8rem; }
/* Legenda in cima alla Vetrina: cosa indicano i due simboli delle card. */
.cn-reader-legenda {
  display: flex; flex-wrap: wrap; gap: .4rem 1.5rem; margin-bottom: 1.25rem;
  font-size: .8em; opacity: .8;
}
.cn-reader-legenda-voce { display: inline-flex; align-items: center; gap: .4rem; }
.cn-reader-legenda .cn-icon { width: 1em; height: 1em; }
.cn-book-valutazione { display: flex; align-items: center; gap: .3rem; margin-top: .3rem; }
.cn-book-valutazione .cn-stelle .cn-icon { width: .85rem; height: .85rem; }
.cn-book-meta { display: flex; justify-content: space-between; align-items: center; font-size: .8em; margin-top: .3rem; opacity: .8; }
.cn-book-meta .cn-icon { width: 1em; height: 1em; }
/* align-items:center su .cn-book-meta centra lo <span> del numero di paragrafi rispetto al prezzo,
   ma non l'icona rispetto al numero DENTRO quello span: senza questa regola icona e testo restano
   allineati sulla baseline di default, leggermente sfalsati invece che centrati fra loro. */
.cn-book-paragrafi { display: inline-flex; align-items: center; gap: .3rem; }
.cn-book-meta-sx { display: inline-flex; align-items: center; gap: .5rem; }
.cn-book-prezzo { font-weight: 600; }
/* Titoli di sezione in "La mia libreria": romanzi acquistati/gratuiti, poi i file caricati dall'utente. */
.cn-libreria-sezione { font-size: 1em; margin: 1.5rem 0 .75rem; opacity: .85; }

/* ---------- Reader: tre schede in alto (Vetrina / Pubblicati / Libreria) ---------- */
.cn-reader-tab-nav { display: flex; gap: .6rem; flex-wrap: wrap; margin-bottom: 1.5rem; }
.cn-reader-tab {
  display: flex; align-items: center; gap: .5rem; padding: .55rem 1rem; border-radius: .5rem;
  border: 1px solid var(--cn-border); background: transparent; color: inherit; font: inherit;
  font-size: .9em; cursor: pointer;
}
.cn-reader-tab.is-active { background: var(--cn-btn-bg); color: var(--cn-btn-text); border-color: var(--cn-btn-bg); }
.cn-reader-tab-icona { width: 1.85em; height: 1.85em; object-fit: contain; }
.cn-reader-tab-icona-grande { width: 2.15em; height: 2.15em; }
.cn-reader-tab-icona-traduci { width: 1.65em; height: 1.65em; }
[data-theme="dark"] .cn-reader-tab .cn-reader-tab-icona { filter: invert(1); }
[data-theme="dark"] .cn-reader-tab.is-active .cn-reader-tab-icona { filter: none; }

/* ---------- La mia libreria: upload locale + copertina rimovibile sul riquadro ---------- */
.cn-libreria-azioni { display: flex; flex-direction: column; align-items: flex-start; gap: .5rem; margin-bottom: 1.5rem; }
/* Il vertical-align basato sulla baseline del testo (usato per le altre .cn-icon) non è
   affidabile qui perché #lib-carica-icona è un <span> vuoto riempito via JS con icon('carica'),
   quindi un secondo livello di <span class="cn-icon"> annidato attorno all'svg: qualunque
   offset in px va storto appena cambiano font-size/line-height del tema. Si centra invece
   #lib-carica-btn stesso con flexbox, che allinea icona e testo in base alla loro altezza reale
   invece che alla baseline sintetizzata. */
#lib-carica-btn { display: inline-flex; align-items: center; }
.cn-libreria-azioni .cn-icon { width: 1rem; height: 1rem; margin-right: .35rem; }
.cn-book-cover { position: relative; }
.cn-libreria-elimina {
  display: none; position: absolute; top: .3rem; right: .3rem; width: 1.7rem; height: 1.7rem;
  background: var(--cn-bg); z-index: 2;
}
.cn-libreria-modifica {
  display: none; position: absolute; top: .3rem; left: .3rem; width: 1.7rem; height: 1.7rem;
  background: var(--cn-bg); z-index: 2;
}
.cn-book-cover:hover .cn-libreria-elimina, .cn-book-cover:hover .cn-libreria-modifica { display: flex; }
/* Su touch (nessun hover) i pulsanti sulla copertina sarebbero irraggiungibili: sempre visibili. */
@media (hover: none) {
  .cn-libreria-elimina, .cn-libreria-modifica { display: flex; }
}
.cn-libreria-copertina-anteprima { width: 9rem; margin: 0 auto 1rem; }
.cn-libreria-copertina-anteprima img, .cn-libreria-copertina-anteprima .cn-book-cover-vuota {
  width: 100%; aspect-ratio: 2/3; object-fit: cover; border-radius: .4rem; border: 1px solid var(--cn-border);
  display: block; background: var(--cn-icon-bg);
}

.cn-libro-intestazione { display: flex; gap: 1.5rem; flex-wrap: wrap; margin-bottom: 1.5rem; }
.cn-libro-copertina { width: 11rem; aspect-ratio: 2/3; object-fit: cover; border-radius: .5rem; border: 1px solid var(--cn-border); flex-shrink: 0; }
.cn-libro-info { flex: 1; min-width: 14rem; }
.cn-libro-prezzo { font-weight: 700; font-size: 1.1em; margin: .5rem 0; }
.cn-libro-autore { font-size: 1.05em; margin: 0 0 .5rem; }
.cn-libro-azioni { display: flex; gap: .5rem; flex-wrap: wrap; }
.cn-libro-sinossi { font-style: italic; opacity: .85; margin: 1.5rem 0; padding: 1rem; border-left: 3px solid var(--cn-border); }
.cn-libro-testo { margin-top: 2rem; }
.cn-libro-testo .cn-paragraph { margin-bottom: 1.1em; }

/* ---------- Recensioni (stelline + testo, scheda del romanzo) ---------- */
.cn-recensioni { margin-top: 2.5rem; border-top: 1px solid var(--cn-border); padding-top: 1.5rem; }
.cn-recensioni-intestazione { display: flex; align-items: center; gap: .6rem; flex-wrap: wrap; margin-bottom: 1rem; }
.cn-recensioni-media { font-weight: 700; }
/* Stessa icona 'star' di icons.js ovunque (media, singola recensione, selettore del form): PNG,
   non più SVG, quindi il riempimento non può più essere un fill via currentColor — icon() per
   'star' scrive due <img> sovrapposte (vuota/piena, vedi icons.js), qui si mostra solo quella
   giusta in base alla classe .is-piena sul contenitore .cn-icon. */
.cn-icon-piena { position: absolute; inset: 0; opacity: 0; }
.cn-icon.is-piena .cn-icon-vuota { opacity: 0; }
.cn-icon.is-piena .cn-icon-piena { opacity: 1; }
.cn-recensioni-intestazione .cn-icon { color: var(--cn-accent); width: 1.2rem; height: 1.2rem; }
.cn-stelle { display: inline-flex; gap: .1rem; color: var(--cn-accent); }
.cn-stelle .cn-icon { width: 1.05rem; height: 1.05rem; }
/* Selettore interattivo nel form: stelle più grandi e cliccabili, con hover che anticipa il voto
   fino alla stella sorvolata (vedi wireStelleInput in reader/libro.js). */
.cn-stelle-input { display: inline-flex; gap: .15rem; }
.cn-stelle-input button { background: none; border: none; padding: .15rem; margin: 0; cursor: pointer; color: var(--cn-accent); line-height: 0; }
.cn-stelle-input .cn-icon { width: 1.6rem; height: 1.6rem; }
.cn-recensione-form { margin-bottom: 1.5rem; padding: 1rem; border: 1px solid var(--cn-border); border-radius: .5rem; }
.cn-recensione-form textarea {
  width: 100%; min-height: 5rem; margin: .7rem 0; padding: .55rem; border-radius: .4rem;
  border: 1px solid var(--cn-border); background: transparent; color: inherit; font: inherit; resize: vertical;
}
.cn-recensione-card { padding: 1rem 0; border-top: 1px solid var(--cn-border); }
.cn-recensione-card:first-child { border-top: none; padding-top: 0; }
.cn-recensione-autore { display: flex; align-items: center; gap: .5rem; margin-bottom: .3rem; }
.cn-recensione-avatar { width: 1.8rem; height: 1.8rem; border-radius: 50%; object-fit: cover; flex-shrink: 0; }
.cn-recensione-avatar-vuoto { width: 1.8rem; height: 1.8rem; border-radius: 50%; background: var(--cn-icon-bg); flex-shrink: 0; }
.cn-recensione-testo { margin: .4rem 0 0; white-space: pre-wrap; }

/* ---------- Lettore (reader/leggi.html): titolo/autore in barra + colonna ridimensionabile ---------- */
.cn-leggi-titolo { display: flex; flex-direction: column; gap: 0; line-height: 1.2; }
.cn-leggi-titolo .cn-title { font-size: .95em; }
.cn-leggi-titolo .cn-punto-meta { margin: 0; }

/* Larghezza della colonna di lettura, separata da --cn-paragraph-width di Writer: qui non c'è un
   drawer laterale di cui tener conto, il massimo è solo la larghezza della finestra. */
.cn-leggi-viewport { position: relative; max-width: var(--cn-reader-width, 42rem); }
/* Testo non selezionabile/copiabile SOLO per le copie tradotte automaticamente dalla funzione
   Traduci lato Reader (vedi 'tradotto' in reader/api/libro.php): a tutela del testo dell'autore
   per una traduzione non rivista da nessuno, non una vera protezione anti-copia (chi vuole
   aggirarla può comunque farlo dagli strumenti sviluppatore). Classe generica (non legata a
   .cn-leggi-viewport): leggi.js la mette sull'intero viewport in vista "Tradotto"
   (impostaVistaTesto) o sulla sola colonna destra in "Affiancati" (vedi .cn-leggi-affiancati-
   colonna sotto e il markup in leggi.html) — mai sui romanzi ORIGINALI (anche un'edizione in
   un'altra lingua pubblicata deliberatamente dall'autore, non una copia personale di un lettore),
   che restano selezionabili apposta per la traduzione automatica nativa del dispositivo. Non si
   applica comunque a "La mia libreria" (leggi-locale.js/.cn-leggi-locale-area), file propri
   dell'utente caricati da un file che possiede già. */
.is-traduzione-ia { user-select: none; -webkit-user-select: none; }
.is-traduzione-ia input, .is-traduzione-ia textarea { user-select: text; -webkit-user-select: text; }

/* Vista "Affiancati" (vedi impostaVistaTesto/renderAffiancati in leggi.js): due colonne, una sopra
   l'altra ("metà schermo" ciascuna, non fianco a fianco — più leggibile su schermi stretti), ognuna
   con scorrimento proprio sincronizzato per paragrafo con l'altra. L'altezza è impostata inline da
   JS (stessa .altezzaPaginaPx() già usata da scatti, per tenere conto della barra in alto),
   non fissabile qui in CSS perché dipende dall'altezza reale della finestra e della barra. */
.cn-leggi-affiancati { display: flex; flex-direction: column; }
.cn-leggi-affiancati-colonna {
  flex: 1 1 0; min-height: 0; overflow-y: auto; background: var(--cn-bg);
  padding: 1.25rem 1.5rem; line-height: 1.7; max-width: var(--cn-reader-width, 42rem);
  margin: 0 auto; width: 100%; box-sizing: border-box;
}
@media (max-width: 40rem) { .cn-leggi-affiancati-colonna { padding: 1rem; } }
/* Separatore fra le due colonne: una linea tratteggiata, stesso stile del bordo che compare
   intorno a un paragrafo mentre lo si modifica in Writer (vedi .cn-turn[contenteditable]:focus),
   non più uno sfondo colorato — con un po' di margine sopra e sotto invece di stare incollata a
   entrambi i testi. flex: 0 0 auto perché è l'unico elemento di altezza fissa tra le due colonne
   che si dividono il resto dello spazio (flex: 1 1 0 sopra). */
.cn-leggi-affiancati-separatore { flex: 0 0 auto; margin: .75rem 0; border-top: 2px dashed var(--cn-accent); }
/* Separatore fra capitoli di un epub caricato in "La mia libreria" (vedi leggi-locale.js): niente
   titoli di capitolo propri (l'OPF non li fornisce in modo affidabile, vedi libreria.js), solo un
   confine visibile fra un capitolo e il successivo. */
.cn-leggi-locale-capitolo { margin-bottom: 2rem; padding-bottom: 2rem; border-bottom: 1px solid var(--cn-border); }
.cn-leggi-locale-capitolo:last-child { border-bottom: none; }
.cn-leggi-locale-capitolo img { max-width: 100%; height: auto; display: block; margin: 1rem auto; }

/* ---------- "La mia libreria": lettura, modalità continuo/scatti (leggi-locale.js) ---------- */
/* Stesso contenitore per entrambe le modalità (niente contenuto duplicato): in "continuo" è un
   normale flusso verticale (la pagina scorre col resto del sito); in "scatti" diventa colonne CSS
   larghe quanto il riquadro (column-width impostato inline da JS in ricalcolaPagine()) spostate con
   translateX SENZA transizione — un vero cambio pagina animato (rotazione 3D, scorrimento
   laterale...) è stato provato e scartato: a schermo risultava innaturale, un salto netto "a
   scatti" (da cui il nome) è più onesto di un'animazione che non convince. */
.cn-leggi-locale-area {
  max-width: 42rem;
  margin: 0 auto;
  padding: 1.5rem 1.5rem 4rem;
}
.cn-leggi-locale-area.is-scatti {
  height: calc(100vh - 4.5rem);
  min-height: 20rem;
  overflow: hidden;
  cursor: pointer;
}
.cn-leggi-locale-corpo { line-height: 1.7; }
.cn-leggi-locale-area.is-scatti .cn-leggi-locale-corpo { height: 100%; column-fill: auto; }
@media (max-width: 40rem) {
  .cn-leggi-locale-area { padding: 1.25rem 1rem 3rem; }
}

/* Segnalibro: un simbolo ancorato al paragrafo dove è stato messo — figlio del blocco stesso
   (aggiornaSimboloSegnalibro in leggi.js, con più segnalibri per romanzo; in leggi-locale.js, con
   uno solo per libro), quindi scorre insieme al testo invece di restare fermo sullo schermo. Sta
   appeso al bordo destro del paragrafo; il blocco che lo ospita riceve .cn-segnalibro-ospite
   (position:relative) solo finché il segnalibro c'è. Condiviso da entrambe le pagine. */
.cn-segnalibro-ospite { position: relative; }
.cn-segnalibro-ancorato {
  position: absolute;
  top: -.1rem;
  right: -.5rem;
  z-index: 2;
  width: 1.4rem;
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, .3));
  pointer-events: none;
  user-select: none;
  -webkit-user-select: none;
}
.cn-segnalibro-ancorato .cn-icon img { width: 100%; height: auto; display: block; }
#btn-segnalibro.is-active { opacity: 1; background: var(--cn-icon-bg); }
.cn-leggi-resize-handle {
  display: none; position: absolute; top: 0; bottom: 0; width: 14px; cursor: ew-resize; z-index: 6;
}
.cn-leggi-resize-handle.left { left: -14px; border-right: 2px dashed var(--cn-accent); }
.cn-leggi-resize-handle.right { right: -14px; border-left: 2px dashed var(--cn-accent); }
.cn-leggi-viewport.is-resizable .cn-leggi-resize-handle { display: block; }

/* Riga non ultima di un turno spezzato per l'impaginazione (vedi blocchiPerImpaginazione in
   leggi.js): niente spazio sotto, resta "attaccata" alla riga successiva come nel modo continuo,
   invece di sembrare un paragrafo vuoto. */
.cn-paragraph.cn-paragraph-stretto { margin-bottom: 0; }

/* ---------- modo "a scatti": una facciata alla volta ---------- */
.cn-leggi-libro { position: relative; overflow: hidden; min-height: 60vh; }
.cn-leggi-pagina-statica { position: relative; z-index: 1; }

/* Il paragrafo (colonna di lettura, --cn-reader-width) diviso in 3 colonne virtuali: il terzo di
   sinistra e quello di destra, ALLARGATI fino a inglobare anche il margine esterno fino al bordo
   dello SCHERMO, cambiano pagina; il terzo centrale (mai coperto da queste zone: ci passa sotto il
   click normale del lettore) fa comparire/nascondere la barra in alto, gestito da initBarraLettore
   sul #viewport stesso. Un tocco/click su una zona cambia pagina. Distanza dal bordo
   SCHERMO al confine interno della zona: metà schermo meno UN SESTO della colonna (= margine
   esterno intero + il primo/ultimo terzo della colonna). Sugli schermi dove la colonna riempie
   tutta la larghezza (mobile, margine 0) la formula degrada da sola a "un terzo dello schermo",
   niente pavimento minimo dedicato da mantenere a parte. Attive solo in scatti — in continuo
   restano inerti (pointer-events:none), e temporaneamente inerti anche quando le maniglie di
   ridimensionamento sono attive (vedi cn-reader-resize-mode più sotto), per non coprirle. */
.cn-leggi-zona-nav {
  position: fixed; top: 0; bottom: 0; z-index: 8; cursor: pointer; pointer-events: none;
  width: max(2rem, calc(50vw - (var(--cn-reader-width, 42rem) / 6)));
}
.cn-leggi-zona-nav.sinistra { left: 0; }
.cn-leggi-zona-nav.destra { right: 0; }
body.cn-zone-nav-attive .cn-leggi-zona-nav { pointer-events: auto; }
body.cn-reader-resize-mode .cn-leggi-zona-nav { pointer-events: none; }

/* Numero di pagina sempre nello stesso punto dello SCHERMO, non del documento: di base
   .cn-page-indicator scorre in fondo al contenuto (giusto per Writer, dove segna la fine del
   flusso), qui invece va ancorato al viewport perché resti fermo cambiando facciata o modo. */
.cn-leggi-indicatore-fisso {
  position: fixed; left: 50%; bottom: .75rem; transform: translateX(-50%);
  padding-bottom: 0; z-index: 6; pointer-events: none;
}

/* ---------- indice del Lettore: capitoli / segnalibri / ricerca (riusa .cn-drawer di Writer) ---------- */
.cn-indice-voce {
  display: block; width: 100%; text-align: left; background: none; border: none; font: inherit;
  color: inherit; padding: .5rem .3rem; border-radius: .3rem; cursor: pointer; font-size: .9em;
}
.cn-indice-voce:hover { background: var(--cn-icon-bg); }
.cn-indice-anteprima { opacity: .6; font-style: italic; }
.cn-indice-riga { display: flex; align-items: center; gap: .3rem; }
.cn-indice-riga .cn-indice-voce { flex: 1; }
.cn-indice-elimina { width: 1.8rem; height: 1.8rem; flex-shrink: 0; }
.cn-indice-elimina .cn-icon { width: .8rem; height: .8rem; }
.cn-indice-voce-cerca mark { background: color-mix(in srgb, var(--cn-accent) 35%, transparent); color: inherit; border-radius: .15rem; }
.cn-cerca-panel { font-size: .9em; }
#cerca-input {
  width: 100%; padding: .55rem; border-radius: .4rem; border: 1px solid var(--cn-border);
  background: transparent; color: inherit; font: inherit;
}

/* ---------- copertina ingrandibile (reader/libro.js) ---------- */
.cn-libro-copertina { cursor: zoom-in; }
.cn-lightbox-backdrop {
  position: fixed; inset: 0; background: rgba(0, 0, 0, .85); z-index: 60;
  display: flex; align-items: center; justify-content: center; cursor: zoom-out; padding: 2rem;
}
.cn-lightbox-backdrop img { max-width: 100%; max-height: 100%; object-fit: contain; border-radius: .4rem; box-shadow: 0 8px 40px rgba(0, 0, 0, .5); }

.cn-autore-intestazione { display: flex; align-items: center; gap: 1.25rem; margin-bottom: 1.5rem; }
.cn-autore-avatar-wrap { position: relative; width: 5rem; height: 5rem; flex-shrink: 0; }
.cn-autore-avatar, .cn-autore-avatar-vuoto {
  width: 5rem; height: 5rem; border-radius: 50%; object-fit: cover;
  border: 1px solid var(--cn-border); background: var(--cn-icon-bg); display: block;
}
.cn-autore-avatar-modifica { position: absolute; right: -.3rem; bottom: -.3rem; width: 1.8rem; height: 1.8rem; }
.cn-autore-bio textarea {
  width: 100%; padding: .55rem; border-radius: .4rem; border: 1px solid var(--cn-border);
  background: transparent; color: inherit; font: inherit; font-size: 1em; resize: vertical; min-height: 4rem;
}
.cn-autore-bio-testo { white-space: pre-wrap; opacity: .85; }

.cn-footer { display: flex; align-items: center; justify-content: center; text-align: center; padding: 2rem 1.5rem 3rem; font-size: .8em; }
.cn-footer-inline { position: relative; display: inline-flex; }
.cn-footer-trigger {
  display: inline-flex; align-items: center; gap: .4rem; background: none; border: none; cursor: pointer;
  color: var(--cn-accent); font: inherit; font-size: 1em; padding: .3rem .5rem; opacity: .85;
}
.cn-footer-trigger:hover, .cn-footer-trigger[aria-expanded="true"] { opacity: 1; }
.cn-footer-favicon {
  width: 1.5em; height: 1.5em; display: inline-block; flex-shrink: 0;
  background-color: var(--cn-accent);
  -webkit-mask-image: url('logoCiaoNovel.png'); mask-image: url('logoCiaoNovel.png');
  -webkit-mask-size: contain; mask-size: contain;
  -webkit-mask-repeat: no-repeat; mask-repeat: no-repeat;
  -webkit-mask-position: center; mask-position: center;
}
.cn-footer-menu {
  position: absolute; bottom: 100%; left: 50%; transform: translateX(-50%); margin-bottom: .3rem;
  background: var(--cn-bg); color: var(--cn-text); border: 1px solid var(--cn-border); border-radius: .5rem;
  padding: .4rem 0; display: flex; flex-direction: column; min-width: 12rem; box-shadow: 0 4px 16px rgba(0,0,0,.18); z-index: 30;
}
.cn-footer-menu[hidden] { display: none; }
.cn-footer-menu a { padding: .5rem 1rem; color: inherit; text-decoration: none; white-space: nowrap; text-align: left; }
.cn-footer-menu a:hover { background: var(--cn-border); text-decoration: underline; }

.cn-header-menu-wrap { display: inline-flex; position: relative; }
.cn-header-menu {
  /* Ancorato a .cn-header-menu-wrap (il solo pulsante "+"), non a .cn-page-header-actions: parte
     da sotto il "+" che lo apre. Con right:0 sul contenitore intero era allineato al bordo destro
     del pulsante "Nuovo romanzo", che sul cellulare può stare molto più a destra del "+" — la
     larghezza minima del riquadro lo spingeva così fuori dallo schermo a sinistra. */
  position: absolute; top: 100%; left: 0; margin-top: .3rem;
  background: var(--cn-bg); color: var(--cn-text); border: 1px solid var(--cn-border); border-radius: .5rem;
  padding: .4rem 0; display: flex; flex-direction: column; min-width: 12rem; box-shadow: 0 4px 16px rgba(0,0,0,.18); z-index: 30;
}
.cn-header-menu[hidden] { display: none; }
.cn-header-menu button { background: none; border: none; font: inherit; font-size: 1em; padding: .5rem 1rem; color: inherit; text-align: left; cursor: pointer; white-space: nowrap; }
.cn-header-menu button:hover { background: var(--cn-border); }

/* ---------- onboarding conversazionale (nuovo romanzo) ---------- */
.cn-question { display: flex; align-items: flex-start; gap: .6rem; margin-bottom: 1rem; }
.cn-question p { margin: 0; flex: 1; }
.cn-question .cn-icon-btn { flex-shrink: 0; width: 1.9rem; height: 1.9rem; }
.cn-onboarding-answer { margin-bottom: 2rem; }
/* renderStileScelta (scrivi.js/demo.js): unico punto dove un <label> nudo compare come prima riga
   di .cn-onboarding-answer invece del solito .cn-question — senza questa regola il browser non gli
   dà nessun margine e il testo tocca la textarea sotto. */
.cn-onboarding-answer > label { display: block; margin-bottom: .5rem; }

/* ---------- cerchietti annulla/ripeti (sinistra) e B/I (destra) sui campi di prosa (bozza IA,
   "continua tu la storia", paragrafi già scritti in vista conversazione quando cliccati per la
   modifica — vedi onParagraphClickedPerModifica) ---------- */
.cn-format-wrap { position: relative; }
.cn-format-wrap textarea { width: 100%; }
.cn-format-wrap .cn-paragraph.is-draft[contenteditable="true"],
.cn-format-wrap .cn-turn[contenteditable="true"] { padding-bottom: 2.2rem; }
/* Riga unica con i due gruppi agli estremi opposti (annulla/ripeti a sinistra, B/I a destra), in
   sovrimpressione in basso al riquadro di default. */
.cn-format-row {
  position: absolute; left: .4rem; right: .4rem; bottom: .4rem;
  display: flex; justify-content: space-between; gap: .3rem; z-index: 4;
}
.cn-undo-redo-btns, .cn-format-btns { display: flex; gap: .3rem; }
/* Una <textarea> ha l'angolo nativo del browser per il ridimensionamento in basso a destra: la
   riga in sovrimpressione lo coprirebbe (un contenteditable non ha quell'angolo, quindi lì la
   sovrimpressione resta corretta). Solo per le textarea, la riga esce dal riquadro e si mette
   subito sotto, leggermente rientrata dai bordi invece di restarci incollata. */
.cn-format-wrap:has(textarea) .cn-format-row {
  position: static; margin: .3rem .6rem 0 .6rem;
}
/* Eccezione dentro .cn-action-free ("continua tu la storia" + pulsante Inserisci accanto): lì
   .cn-format-wrap è uno dei due figli di una riga flex, e il pulsante (l'altro figlio) si allunga
   di default per pareggiarne l'altezza. Se la riga qui sotto contasse nell'altezza di
   .cn-format-wrap (come subito sopra), il pulsante si allungherebbe fino a includerla invece di
   fermarsi al bordo della sola textarea. Tornare ad assoluta ma SOTTO il riquadro (non sopra come
   il default globale, che coprirebbe l'angolo di resize) toglie la riga dal flusso:
   .cn-format-wrap torna alto quanto la sola textarea, e con lui il pulsante Inserisci. */
.cn-action-free .cn-format-wrap:has(textarea) .cn-format-row {
  position: absolute; top: 100%; bottom: auto; left: .6rem; right: .6rem; margin: .3rem 0 0;
}
/* Il pulsante accanto (es. "Inserisci") si stira per uguagliare l'altezza NATURALE del riquadro
   (quella che avrebbe la sola textarea, senza contare la riga sotto — vedi sopra), ma è il div
   .cn-format-wrap a stirarsi, non la textarea al suo interno: senza height:100% la textarea
   restava alla propria altezza intrinseca, un po' più bassa del pulsante. */
.cn-action-free .cn-format-wrap:has(textarea) textarea { height: 100%; }
/* La riga B/I in sovrimpressione (sopra) esce dal flusso: senza questo margine il pulsante
   "Concludi il romanzo" subito sotto la ignora e ci si sovrappone (vedi .cn-field-continua in
   scrivi.js). */
.cn-field-continua + .cn-concludi-romanzo {
  margin-top: 2.5rem;
}
.cn-format-btn {
  width: 1.5rem; height: 1.5rem; border-radius: 50%; border: 1px solid var(--cn-icon-border);
  background: var(--cn-icon-bg); color: inherit; font-size: .68rem; font-weight: 700;
  display: flex; align-items: center; justify-content: center; line-height: 1; padding: 0; cursor: pointer;
}
.cn-format-btn[data-format="italic"] { font-style: italic; }
.cn-format-btn[data-history] .cn-icon { width: .85rem; height: .85rem; }

/* ---------- larghezza regolabile del riquadro tratteggiato in scrittura (bozza IA o paragrafo
   cliccato per la modifica in vista conversazione): passando il mouse sul bordo tratteggiato
   compare il cursore "doppia freccia", trascinando si allarga/restringe restando centrato (vedi
   initParagraphResize in scrivi.js). Solo sui riquadri di prosa vera, non su .cn-format-wrap
   generico (che include anche la textarea di "continua tu la storia", non regolabile). */
.cn-format-wrap-paragrafo {
  max-width: var(--cn-paragraph-width, 100%); margin-left: auto; margin-right: auto;
}
/* Le maniglie di ridimensionamento sopra reagiscono solo a mousedown/mousemove/mouseup (vedi
   initParagraphResize in scrivi.js), quindi su un dispositivo touch non sono mai utilizzabili:
   --cn-paragraph-width può comunque restare valorizzata in localStorage da una sessione col mouse
   precedente (stesso dispositivo in modalità desktop, o un trackpad/stilo) e quel valore in rem è
   fisso, non ricalcolato alla rotazione — capitava che il riquadro tratteggiato restasse stretto
   quanto in verticale anche ruotando lo schermo in orizzontale, mentre i paragrafi già scritti (che
   non usano questa variabile) si allargavano regolarmente. Su touch la larghezza personalizzata non
   ha senso: si ignora sempre, restando piena come gli altri paragrafi. */
@media (pointer: coarse) {
  .cn-format-wrap-paragrafo { max-width: 100%; }
}
.cn-paragraph-resize-handle {
  position: absolute; top: 0; bottom: 0; width: 10px; cursor: ew-resize; z-index: 3;
}
.cn-paragraph-resize-handle.left { left: -5px; }
.cn-paragraph-resize-handle.right { right: -5px; }

/* ---------- pannello Debug (solo admin, vedi btn-debug/renderDebugBox in scrivi.js): mostra fra
   un paragrafo e l'altro esattamente il prompt inviato all'IA (e la risposta grezza, solo se
   diversa da quella pubblicata) — sfondo nero "da codice", volutamente fuori stile dal resto
   dell'interfaccia perché sia inequivocabile che è un pannello tecnico, non contenuto del romanzo. */
.cn-debug-box {
  background: #111; color: #d8d8d8; border-radius: .5rem; padding: 1rem;
  margin: 1rem 0; font-family: "SFMono-Regular", Consolas, "Liberation Mono", Menlo, monospace;
  font-size: .8em; line-height: 1.5;
}
.cn-debug-box-titolo {
  color: #8a8a8a; text-transform: uppercase; letter-spacing: .05em; font-size: .85em;
  margin: 1rem 0 .35rem;
}
.cn-debug-box-titolo:first-child { margin-top: 0; }
.cn-debug-box pre {
  white-space: pre-wrap; word-break: break-word; margin: 0; max-height: 16rem; overflow-y: auto;
}

/* ---------- coppia selettore colore + campo hex (Impostazioni > Personalizza colori tema) ---------- */
.cn-color-field { display: flex; gap: .5rem; align-items: center; }
.cn-color-field input[type="color"] {
  flex: 0 0 2.6rem; width: 2.6rem; height: 2.6rem; padding: .2rem; border-radius: .4rem;
  border: 1px solid var(--cn-border); background: transparent; cursor: pointer;
}
.cn-color-field input[type="text"] { flex: 1; }

/* ---------- grafico a barre o a linee (statistiche account e admin, vedi graficoHtml in app.js) ---------- */
.cn-graf { direction: ltr; font-size: .75em; margin-bottom: 1rem; }
.cn-graf-testa { display: flex; flex-wrap: wrap; justify-content: space-between; align-items: flex-start; gap: .4rem 1rem; margin-bottom: .6rem; }
.cn-graf-legenda { display: flex; flex-wrap: wrap; gap: .3rem 1rem; }
.cn-graf-legenda span { display: inline-flex; align-items: center; gap: .35rem; }
.cn-graf-legenda i { display: inline-block; width: .7rem; height: .7rem; border-radius: .15rem; }
.cn-graf-legenda small { opacity: .6; font-size: 1em; }
.cn-graf-tipo { display: inline-flex; border: 1px solid var(--cn-border); border-radius: .4rem; overflow: hidden; }
.cn-graf-tipo button { border: 0; background: transparent; color: inherit; font: inherit; padding: .15rem .6rem; cursor: pointer; }
.cn-graf-tipo button.is-active { background: var(--cn-icon-bg); font-weight: 600; }
.cn-graf svg text { font-family: inherit; }
.cn-graf [data-grafico-vista] rect[fill="transparent"]:hover { fill: var(--cn-icon-bg); }

/* ---------- Corso di scrittura creativa (corso.html, corso.js) ---------- */
.cn-corso-intro { margin: 0 0 1.5rem; line-height: 1.6; }
.cn-corso-intro p { margin: 0 0 .8rem; opacity: .85; }
.cn-corso-sezione { font-size: 1.05em; margin: 2rem 0 .8rem; }
.cn-corso-corso { border: 1px solid var(--cn-border); border-radius: .6rem; padding: 1rem 1.1rem; margin-bottom: 1rem; }
.cn-corso-corso.is-bloccato { opacity: .6; }
.cn-corso-corso-testa { display: flex; align-items: center; justify-content: space-between; gap: .6rem; flex-wrap: wrap; }
.cn-corso-corso h2 { margin: 0; font-size: 1.1em; }
.cn-corso-desc { margin: .3rem 0 .8rem; opacity: .75; font-size: .9em; }
.cn-corso-programma-titolo { margin: .8rem 0 .3rem; font-size: .85em; font-weight: 600; }
.cn-corso-programma { margin: 0; padding-left: 1.2rem; font-size: .9em; opacity: .8; }
.cn-corso-lezioni { list-style: none; margin: 0; padding: 0; }
.cn-corso-lezione-voce {
  display: flex; align-items: center; gap: .75rem; width: 100%; padding: .6rem .3rem; background: none; border: none;
  border-top: 1px solid var(--cn-border); font: inherit; color: inherit; text-align: left; cursor: pointer;
}
.cn-corso-lezione-voce:hover:not([disabled]) { background: var(--cn-icon-bg); }
.cn-corso-lezione-voce[disabled] { opacity: .5; cursor: default; }
.cn-corso-lezione-num {
  flex: 0 0 auto; width: 1.6rem; height: 1.6rem; border-radius: 50%; border: 1px solid var(--cn-icon-border);
  display: flex; align-items: center; justify-content: center; font-size: .8em;
}
.cn-corso-lezione-titolo { flex: 1; min-width: 0; }
.cn-corso-stato { flex: 0 0 auto; font-size: .75em; padding: .15rem .55rem; border-radius: 1rem; border: 1px solid var(--cn-border); opacity: .85; white-space: nowrap; }
.cn-corso-stato.is-completata { border-color: var(--cn-accent); color: var(--cn-accent); opacity: 1; }
.cn-corso-stato.is-in_corso { border-style: dashed; border-color: var(--cn-accent); opacity: 1; }

.cn-corso-lezione-h1 { font-size: 1.4em; margin: .4rem 0 1.2rem; }
.cn-corso-spiegazione p { margin: 0 0 .9rem; }
.cn-corso-esempi { display: grid; gap: .8rem; margin: 1.2rem 0; }
@media (min-width: 720px) { .cn-corso-esempi { grid-template-columns: 1fr 1fr; } }
.cn-corso-esempio { border: 1px solid var(--cn-border); border-left-width: 4px; border-radius: .5rem; padding: .7rem .9rem; }
.cn-corso-esempio.is-riuscito { border-left-color: var(--cn-accent); }
.cn-corso-esempio.is-debole { border-left-color: var(--cn-muted); }
.cn-corso-esempio p { margin: 0 0 .4rem; }
.cn-corso-esempio-etichetta { font-size: .75em; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; opacity: .7; }
.cn-corso-esempio-testo { font-style: italic; }
.cn-corso-esempio .cn-punto-meta { font-size: .95em; opacity: .8; line-height: 1.5; }
.cn-corso-consegna { margin: 1.6rem 0 1rem; padding: .9rem 1.1rem; border-radius: .6rem; background: var(--cn-icon-bg); }
.cn-corso-consegna h3 { margin: 0 0 .4rem; font-size: 1em; }
.cn-corso-consegna p { margin: 0 0 .3rem; }

/* La casella di scrittura: bordo tratteggiato, come "qui scrivi tu". */
.cn-corso-casella {
  display: block; width: 100%; min-height: 12rem; box-sizing: border-box; padding: .9rem 1rem;
  border: 2px dashed var(--cn-accent); border-radius: .6rem; background: transparent; color: inherit;
  font: inherit; line-height: 1.6; resize: vertical;
}
.cn-corso-casella:focus { outline: none; border-style: solid; }
.cn-corso-casella:disabled { opacity: .6; }
.cn-corso-sotto-casella { display: flex; align-items: center; justify-content: space-between; gap: .75rem; margin-top: .6rem; }
.cn-corso-tentativo-etichetta { margin: 1.4rem 0 .5rem; font-size: .85em; font-weight: 600; opacity: .8; }
.cn-corso-scrittura .cn-corso-tentativo-etichetta { margin-top: 2.6rem; }
#corso-invia:disabled { opacity: 1; }
.cn-corso-brano { white-space: pre-wrap; padding: .8rem 1rem; border-radius: .6rem; border: 1px dashed var(--cn-border); margin-bottom: .8rem; }
.cn-corso-feedback { border: 1px solid var(--cn-border); border-left: 4px solid var(--cn-accent); border-radius: .5rem; padding: .3rem 1rem; }
.cn-corso-fb-blocco { padding: .5rem 0; }
.cn-corso-fb-blocco + .cn-corso-fb-blocco { border-top: 1px solid var(--cn-border); }
.cn-corso-fb-blocco h4 { margin: 0 0 .25rem; font-size: .85em; text-transform: uppercase; letter-spacing: .04em; color: var(--cn-text); }
.cn-corso-fb-blocco p { margin: 0; }
.cn-corso-fb-blocco blockquote { margin: 0 0 .4rem; padding-left: .8rem; border-left: 3px solid var(--cn-border); font-style: italic; }
.cn-corso-chiusura { margin-top: 1.8rem; padding: 1rem 1.1rem; border-radius: .6rem; border: 1px solid var(--cn-accent); }
.cn-corso-chiusura h3 { margin: 0 0 .5rem; font-size: 1.05em; }
.cn-corso-chiusura p { margin: 0 0 .6rem; }
.cn-corso-azioni { display: flex; gap: .6rem; flex-wrap: wrap; margin-top: .8rem; }
.cn-corso-storico { margin-top: 2rem; }
.cn-corso-storico summary { cursor: pointer; font-weight: 600; }
.cn-corso-giro { margin-top: 1rem; padding-top: .4rem; border-top: 1px solid var(--cn-border); }
.cn-corso-giro h4 { margin: .5rem 0 0; font-size: .95em; }

/* ---------- Analisi del manoscritto (struttura e stile), vedi analisi.js ---------- */
.cn-analisi-scelta { margin-top: 1.25rem; padding-top: 1rem; border-top: 1px solid var(--cn-border); }
.cn-analisi-scelta h3 { margin: 0 0 .25rem; font-size: 1.05em; }
.cn-analisi-check { display: flex; gap: .6rem; align-items: flex-start; margin: .75rem 0; cursor: pointer; font-size: .92em; line-height: 1.45; }
.cn-analisi-check input { margin-top: .3rem; flex-shrink: 0; }
.cn-analisi-check-inline { margin: .5rem 0; }
.cn-analisi-costo { margin: .75rem 0 .25rem; font-size: .95em; }
.cn-analisi-avviso { color: #b3261e; font-size: .9em; }
.cn-analisi-pannello { display: flex; flex-direction: column; gap: 1.5rem; }
.cn-analisi-sezione h3 { margin: 0 0 .5rem; font-size: 1.05em; }
.cn-analisi-sezione h4 { margin: 1rem 0 .4rem; font-size: .95em; }
.cn-analisi-punto { border: 1px solid var(--cn-border); border-left-width: 4px; border-radius: .4rem; padding: .6rem .75rem; margin: .6rem 0; }
.cn-analisi-punto p { margin: .35rem 0; font-size: .92em; }
.cn-analisi-punto-testa { display: flex; align-items: center; justify-content: space-between; gap: .5rem; }
.cn-analisi-badge { font-size: .75em; padding: .1rem .5rem; border-radius: 1rem; border: 1px solid var(--cn-border); white-space: nowrap; }
.cn-analisi-regge { border-left-color: #2e7d32; }
.cn-analisi-debole { border-left-color: #e8a317; }
.cn-analisi-manca { border-left-color: #c62828; }
.cn-analisi-non_ancora { border-left-color: var(--cn-border); opacity: .8; }
.cn-analisi-link { background: none; border: none; padding: 0; font: inherit; font-size: .85em; color: var(--cn-accent); cursor: pointer; text-decoration: underline; text-align: left; }
.cn-analisi-pattern { display: flex; flex-wrap: wrap; align-items: baseline; gap: .5rem; margin: .3rem 0; }
.cn-analisi-pattern.is-silenziato { opacity: .6; }
.cn-analisi-sugg { opacity: .9; }

/* Sottolineature di stile nel testo: un tratto diverso per ciascuna categoria, così il peso
   dell'osservazione si vede prima ancora di leggere la scheda. */
.cn-seg { text-decoration-line: underline; text-decoration-thickness: 2px; text-underline-offset: .18em; cursor: help; }
.cn-seg-errore { text-decoration-style: wavy; text-decoration-color: #d93025; }
.cn-seg-certa { text-decoration-style: solid; text-decoration-color: #e8a317; }
.cn-seg-soggettiva { text-decoration-style: dotted; text-decoration-color: #4a86e8; }
.cn-seg-card { position: fixed; z-index: 60; width: min(22rem, calc(100vw - 16px)); background: var(--cn-bg); color: var(--cn-text); border: 1px solid var(--cn-border); border-radius: .5rem; padding: .75rem .85rem; box-shadow: 0 6px 24px rgba(0,0,0,.22); font-size: .9rem; line-height: 1.45; }
.cn-seg-card p { margin: .4rem 0; }
.cn-seg-card-testa { display: flex; align-items: center; gap: .5rem; flex-wrap: wrap; }
.cn-seg-tag { font-size: .72em; font-weight: 600; padding: .1rem .5rem; border-radius: 1rem; color: #fff; }
.cn-seg-tag-errore { background: #d93025; }
.cn-seg-tag-certa { background: #b97d00; }
.cn-seg-tag-soggettiva { background: #3b6fc7; }
.cn-seg-proposta { margin: .5rem 0; padding: .45rem .6rem; border-left: 3px solid var(--cn-accent); background: rgba(127,127,127,.09); border-radius: .25rem; }
.cn-seg-proposta strong { display: block; font-size: .8em; opacity: .7; margin-bottom: .15rem; }
.cn-seg-azioni { display: flex; flex-wrap: wrap; gap: .4rem; margin-top: .6rem; }
.cn-seg-azioni .cn-btn { padding: .3rem .7rem; font-size: .85em; }

/* Chat con l'insegnante, tra il primo feedback e il secondo tentativo */
.cn-corso-chat { margin-top: 1rem; border: 1px solid var(--cn-border); border-radius: .6rem; padding: .6rem 1rem .8rem; }
.cn-corso-chat summary { cursor: pointer; font-weight: 600; }
.cn-corso-chat-lista { display: flex; flex-direction: column; gap: .6rem; margin: .8rem 0 .6rem; }
.cn-corso-bolla { max-width: 92%; padding: .55rem .8rem; border-radius: .7rem; border: 1px solid var(--cn-border); }
.cn-corso-bolla p { margin: .15rem 0 0; white-space: pre-wrap; line-height: 1.5; }
.cn-corso-bolla-chi { font-size: .72em; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; opacity: .65; }
.cn-corso-bolla.is-utente { align-self: flex-end; background: var(--cn-icon-bg); }
.cn-corso-bolla.is-insegnante { align-self: flex-start; }
.cn-corso-chat-form textarea {
  display: block; width: 100%; box-sizing: border-box; padding: .6rem .8rem; border: 1px solid var(--cn-border); border-radius: .5rem;
  background: transparent; color: inherit; font: inherit; line-height: 1.5; resize: vertical;
}
.cn-corso-chat-form textarea:focus { outline: none; border-color: var(--cn-accent); }

/* Testo originale mostrato sopra la proposta di modifica di un punto della struttura (analisi.js). */
.cn-analisi-originale { max-height: 14rem; overflow-y: auto; margin: .6rem 0 1rem; padding: .6rem .9rem; border: 1px dashed var(--cn-border); border-radius: .5rem; font-size: .9em; line-height: 1.5; }
.cn-analisi-originale h4 { margin: 0 0 .4rem; font-size: .8em; text-transform: uppercase; letter-spacing: .04em; opacity: .7; }
.cn-analisi-originale p { margin: 0 0 .6rem; white-space: pre-wrap; }

/* Pagina "Il tuo account": titoli delle sezioni più scuri del testo e un poco più grandi; mesi gratuiti in evidenza. */
.cn-account .cn-drawer-section h3 { font-size: .95em; opacity: 1; color: var(--cn-text); font-weight: 700; }
.cn-referral-mesi { margin: 1.5rem 0 .4rem; font-size: 1em; opacity: .8; }
