Vai al contenuto
animorio
EN
Tutti i componenti

Il pulsante a carta elettronica

Pulsanti, TransizioniCanvasImpegnativaPeso compresso: Demo 6,9 KBGSAP 28 KBGratisScarica lo zip

Il pulsante Sync library di un lettore di libri è un pezzo di schermo a inchiostro elettronico nella sua cornice: premuto fa il refresh vero degli e-reader, lampo nero, negativo, bianco e la nuova immagine che si compone a bande di righe. Mentre sincronizza le frecce circolari girano a scatti, pochi fotogrammi al secondo in bianco e nero puro, e ognuno lascia l'ombra del precedente; finito, solo le parole si aggiornano col loro piccolo lampo.

Il codice

Una cartella che funziona da sola: index.html, style.css, script.js e le librerie da CDN. Nelle schede React e Vue la stessa demo è già un componente, che spegne le sue animazioni quando esce dalla pagina.

<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>The e-ink button</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@fontsource-variable/literata@5.3.0/opsz.css">
  <link rel="stylesheet" href="style.css">
</head>
<body>
  <main class="stage">
    <!-- the e-ink button: a book reader's Sync library button drawn as a piece of electronic paper in its bezel. The
         screen is a low resolution canvas with real e-ink refreshes: flashes, a spinner in black and white at a few
         frames a second leaving ghosts behind it, and a partial refresh of the words when it is done -->
    <div class="eink" data-eink>
      <button class="eink__btn" type="button" aria-label="Sync library. Last synced 2 days ago" data-btn data-autoclic>
        <span class="eink__bezel" aria-hidden="true"></span>
        <span class="eink__screen" aria-hidden="true">
          <canvas class="eink__canvas" width="312" height="92" data-canvas></canvas>
          <span class="eink__glass"></span>
        </span>
      </button>
      <p class="sr" aria-live="polite" data-live></p>
    </div>
  </main>

  <script src="https://cdn.jsdelivr.net/npm/gsap@3.15.0/dist/gsap.min.js"></script>
  <script src="script.js"></script>
</body>
</html>

Playground

Cambia valori, colori e testi con le manopole e guarda l’animazione rispondere dal vivo. Oppure scrivi tu nel codice. Poi scarica la cartella con le tue modifiche.

20 valori da cambiare

Oppure chiedila a Claude Code

Col connettore di Animorio, Claude Code la prende da qui con tutta la sua guida e la adatta al tuo progetto. Incolla questa richiesta:

Prendi «Il pulsante a carta elettronica» da Animorio e adattala al mio sito

Cosa fa

Su un fondo bianco una cornice di grafite con dentro un pezzo di schermo a inchiostro elettronico, grigio caldo e opaco: a sinistra un'icona di due frecce in cerchio, un filetto grigio retinato, e a destra Sync library e, più piccolo e grigio, Last synced 2 days ago, in un carattere da libro. Da vicino si vedono i pixel e la retinatura dei grigi. Aprendo la pagina lo schermo si sveglia come un lettore: un lampo nero, l'immagine in negativo, bianco, poi l'immagine. Col mouse sopra la cornice si alza un poco (l'inchiostro non si illumina); premendo scende. Cliccando, tutto lo schermo diventa nero, poi mostra in negativo la schermata nuova, diventa bianco e la schermata nuova si stende dall'alto in basso a bande di righe, con la banda in scrittura ancora grigia: Syncing library, Checking 214 books. Le frecce girano a scatti, cinque fotogrammi al secondo, disegnate solo in bianco e nero con la retinatura, e ogni fotogramma lascia un'ombra grigia di quello prima. A metà la riga sotto diventa Downloading new books. Finito, le frecce si fermano dove erano partite, solo la zona delle parole lampeggia nera e bianca e compare Synced · 3 new books, Library up to date, con una spunta nelle frecce, mentre intorno restano le ombre del giro. Dopo qualche secondo le parole tornano Sync library, Last synced just now con lo stesso piccolo refresh, e nelle frecce resta un'ombra leggerissima della spunta.

Come funziona

Uno schermo a bassa risoluzione

Lo schermo è un canvas di 312 per 92 pixel, uno per pixel CSS, ingrandito con image-rendering: pixelated: sugli schermi a doppia densità ogni pixel dell'inchiostro è un quadratino di quattro, e i pixel si vedono da vicino come su un lettore vero. Ogni schermata si disegna in un canvas nascosto: le frecce sono tracciati SVG passati a Path2D e ruotati, le parole sono testo vero in Literata, rasterizzato con fillText.

La retinatura

Il grigio di ogni pixel passa per una retinatura ordinata con la matrice di Bayer 4 per 4: per gli aggiornamenti normali porta a 16 livelli (la matrice sceglie fra i due livelli vicini), per quelli veloci a bianco e nero puro, come la modalità rapida dei lettori. Così il filetto, la riga grigia sotto e i bordi delle lettere mostrano il motivo regolare della retinatura.

Un buffer d'inchiostro e il ghosting

Quello che si vede non è l'immagine, ma un buffer di numeri da 0 (nero) a 1 (bianco): lo stato dell'inchiostro. Un refresh pieno lo porta esattamente alla nuova immagine; un aggiornamento senza lampo lo sposta verso la nuova immagine ma ne lascia una parte della vecchia (GHOST): è il ghosting, e si accumula fotogramma dopo fotogramma. Il colore di ogni pixel è un misto fra il colore della carta e quello dell'inchiostro del CSS, con un poco di grana fissa.

Scatti contati sul ticker

Ogni cambiamento dello schermo è un passo di una coda: il ticker di GSAP (requestAnimationFrame) somma il tempo, con il passo limitato a 1/30 di secondo, e quando è passato il tempo del passo cambia l'inchiostro una volta sola. Il refresh pieno è nero, negativo, bianco e sette bande di righe; lo spinner è un fotogramma ogni 1/SPIN_FPS di secondo, ruotato di SPIN_STEP gradi, aggiornato solo nel rettangolo dell'icona. Il canvas si ridisegna solo quando l'inchiostro è cambiato.

Il refresh parziale

A fine sincronizzazione solo il rettangolo delle parole fa un lampo nero e bianco e mostra la scritta nuova pulita; la spunta nelle frecce entra con lo stesso passo, sopra le ombre del giro, che restano. Il numero dei fotogrammi dello spinner è un multiplo di mezzo giro, così le frecce si fermano esattamente dove erano partite.

Valori da cambiare

NomeFileDi partenzaCosa cambia
SYNCscript.js2.6I secondi che dura la sincronizzazione finta.
SPIN_FPSscript.js5I fotogrammi al secondo dello spinner: l'inchiostro elettronico è lento.
SPIN_STEPscript.js30Di quanti gradi girano le frecce a ogni fotogramma.
GHOSTscript.js0.26Quanta parte dell'immagine vecchia lascia un aggiornamento veloce in bianco e nero.
FLASHscript.js0.11I secondi di ogni passo del refresh pieno (nero, negativo, bianco).
HOLDscript.js4I secondi in cui resta Synced prima che il pulsante torni a riposo.
NEW_BOOKSscript.js3Quanti libri nuovi trova la sincronizzazione.
TEXTSscript.js{ rest: ['Sync library', 'Last synced 2 days ago'], … }Le parole sullo schermo nei vari momenti: il titolo e la riga sotto.

Provali nel Playground

Quando usarla

Per un'app di lettura, un archivio di note, un sito di editoria o qualunque prodotto che vuole il carattere calmo della carta: sincronizzare, scaricare, aggiornare. L'inchiostro elettronico è volutamente lento: va su un'azione che dura qualche secondo, non su un pulsante da premere di continuo.

Sul telefono

La cornice è larga 340 pixel e sta in uno schermo da 390; sotto i 380 pixel si rimpicciolisce appena. Sugli schermi a doppia densità i pixel dell'inchiostro sono quadratini di quattro, come su un lettore. Il tocco fa scendere la cornice come il clic.

Con il movimento ridotto

Niente lampi e niente frecce che girano: le parole cambiano al loro posto con un aggiornamento senza lampo, Syncing library, Downloading new books, Synced · 3 new books con la spunta, e poi tornano a riposo; la cornice non si alza sotto il mouse.

Trappole

  • Il ritorno a riposo con un aggiornamento senza lampo su tutto lo schermo lasciava l'ombra di Synced · 3 new books sotto Sync library: due scritte sovrapposte. Le parole hanno sempre il loro refresh parziale pulito; il ghosting resta solo nell'icona.
  • Synced · 3 new books in corpo 21 usciva dal bordo destro dello schermo: il titolo è a 19,5 pixel e comincia un poco più a sinistra.
  • Rasterizzare il testo prima che il carattere fosse caricato lasciava lo schermo col carattere di ripiego: si disegna subito la schermata col ripiego, poi, quando Literata è pronto, il risveglio con il lampo la ridisegna.
  • Se il numero dei fotogrammi dello spinner non è un multiplo di mezzo giro le frecce si fermano storte: il numero si arrotonda a mezzi giri interi (le frecce sono simmetriche).
  • I tempi dei passi si contano sommando il tempo del ticker, non i fotogrammi: col banco della libreria che rallenta l'orologio, o su uno schermo a 120 Hz, lo spinner resta a SPIN_FPS fotogrammi al secondo.

Librerie

GSAP 3.15.0, Literata (font variabile) 5.3.0.

Compressi con gzip, i tre file della demo pesano 6,9 KB; le librerie: GSAP 28 KB.

Collaudo

Provata il 5 ottobre 2026

  • Computer: Fatto
  • Telefono: Fatto
  • Movimento ridotto: Fatto
  • Safari su iPhone: Fatto

Licenza d’uso

Puoi usarla nei tuoi progetti e in quelli dei tuoi clienti. Non puoi rivenderla né ridistribuirla così com’è. GSAP resta sotto la sua licenza Standard. Licenza completa.

Tutti i componenti