Vai al contenuto
animorio
EN
Tutti i componenti

Il menu dello schedario rotante

Menu, Hover, 3DGSAP, Solo CSSImpegnativaPeso compresso: Demo 12 KBGSAP 28 KBGratisScarica lo zip

Nello stile ricco: il pulsante Menu di una stamperia a caratteri mobili apre uno schedario rotante da scrivania, con la base di noce, le gambe cromate, le manopole zigrinate e ventuno schede appese ai binari. Ogni divisorio colorato con la sua linguetta è una voce del menu: girando il tamburo le schede scavalcano i binari una dopo l’altra, ognuna con la sua molla, e la voce scelta si alza dallo schedario con una graffetta d’ottone.

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 rotary card file menu</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@fontsource-variable/mona-sans@5.3.0/wdth.css">
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@fontsource/courier-prime@5.3.0/400.css">
  <link rel="stylesheet" href="style.css">
</head>
<body>
  <main class="stage">
    <!-- the menu of a letterpress studio: the Menu button opens a rotary card file under it. The drum turns, the
         cards flip over the rails one after another, and every coloured divider with its tab is a menu item. Drag the
         cards, roll the wheel, use the arrows or point at a tab; choosing a divider lifts it out of the file. -->
    <nav class="rolo-menu" aria-label="Main" data-rolo-menu>
      <button class="rolo-btn" type="button" aria-expanded="false" aria-controls="rolo-file" data-toggle>
        <svg class="rolo-btn__icon" viewBox="0 0 44 44" aria-hidden="true">
          <path class="rolo-btn__base" d="M6 37.5 H 38 L 36 41 H 8 Z"/>
          <path class="rolo-btn__leg" d="M10 37.5 L 13 27 M34 37.5 L 31 27"/>
          <g class="rolo-btn__cards">
            <rect class="rolo-btn__card rolo-btn__card--back" data-icon-card x="14" y="11" width="16" height="16" rx="1.6"/>
            <rect class="rolo-btn__card rolo-btn__card--mid" data-icon-card x="14" y="11" width="16" height="16" rx="1.6"/>
            <rect class="rolo-btn__card rolo-btn__card--front" data-icon-card x="14" y="11" width="16" height="16" rx="1.6"/>
          </g>
          <rect class="rolo-btn__tab" x="16.5" y="8.4" width="6" height="3.2" rx="0.8"/>
          <path class="rolo-btn__rod" d="M9 27 H 35"/>
          <circle class="rolo-btn__knob" cx="8.4" cy="27" r="2.6"/>
          <circle class="rolo-btn__knob" cx="35.6" cy="27" r="2.6"/>
        </svg>
        <span class="rolo-btn__word" data-word>Menu</span>
      </button>

      <div class="rolo" id="rolo-file" inert data-rolo>
        <div class="rolo__shadow" aria-hidden="true"></div>

        <!-- the frame: walnut base, chrome legs, the hubs and the knurled knobs -->
        <div class="rolo__base" aria-hidden="true">
          <span class="rolo__base-top"></span>
          <span class="rolo__base-front"></span>
        </div>
        <span class="rolo__leg rolo__leg--l" aria-hidden="true"></span>
        <span class="rolo__leg rolo__leg--r" aria-hidden="true"></span>

        <!-- the drum: the cards are made by the script around the dividers below -->
        <div class="rolo__drum" data-drum>
          <ul class="rolo__cards" data-cards role="list">
            <li class="rolo__rail" aria-hidden="true" data-rail></li>
            <li><a class="card card--divider" href="#work" data-item style="--tone: var(--coral)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Work</span></span><span class="card__word">Work</span><span class="card__note">Posters, books, invitations</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
            <li><a class="card card--divider" href="#printing" data-item style="--tone: var(--mustard)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Printing</span></span><span class="card__word">Printing</span><span class="card__note">Letterpress and foil</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
            <li><a class="card card--divider" href="#papers" data-item style="--tone: var(--teal)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Papers</span></span><span class="card__word">Papers</span><span class="card__note">Cotton, kraft, deckle edges</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
            <li><a class="card card--divider" href="#workshops" data-item style="--tone: var(--sky)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Workshops</span></span><span class="card__word">Workshops</span><span class="card__note">Saturday classes at the press</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
            <li><a class="card card--divider" href="#journal" data-item style="--tone: var(--olive)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Journal</span></span><span class="card__word">Journal</span><span class="card__note">Notes from the press room</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
            <li><a class="card card--divider" href="#studio" data-item style="--tone: var(--plum)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Studio</span></span><span class="card__word">Studio</span><span class="card__note">Who sets the type</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
            <li><a class="card card--divider" href="#contact" data-item style="--tone: var(--rose)"><span class="card__front"><span class="card__tab"><span class="card__tab-word">Contact</span></span><span class="card__word">Contact</span><span class="card__note">Say hello, order a proof</span></span><span class="card__back"><span class="card__tab"></span></span></a></li>
          </ul>
        </div>

        <!-- the hubs on the ends of the rails (the rails sit among the cards: in front of the cards behind them,
             behind the cards in front) -->
        <span class="rolo__hub rolo__hub--l" aria-hidden="true"></span>
        <span class="rolo__hub rolo__hub--r" aria-hidden="true"></span>
        <span class="rolo__knob rolo__knob--l" aria-hidden="true" data-knob><span class="rolo__knob-mark" data-knob-mark></span></span>
        <span class="rolo__knob rolo__knob--r" aria-hidden="true" data-knob><span class="rolo__knob-mark" data-knob-mark></span></span>
        <span class="rolo__pawl" aria-hidden="true" data-pawl></span>

        <!-- the brass plate on the base: it says which divider is at the front -->
        <span class="rolo__plate">
          <span class="rolo__brand" aria-hidden="true">Kardwell</span>
          <span class="rolo__now" aria-live="polite"><span class="rolo__now-word" data-now>Work</span></span>
        </span>
      </div>
    </nav>
  </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.

42 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 menu dello schedario rotante» da Animorio e adattala al mio sito

Cosa fa

Su un fondo bianco un pulsante a pillola color inchiostro con dentro uno schedario rotante disegnato piccolo, la base di legno, le gambe e tre schede. Passandoci sopra la scheda davanti si ribalta in avanti, le altre si raddrizzano e poi tornano al loro posto; la scritta si stringe e rimbalza. Premendolo, la scritta diventa Close e sotto si apre lo schedario di Kardwell, una stamperia a caratteri mobili: la base di noce con le venature e una targhetta d’ottone, due gambe cromate, due mozzi a sfera, due manopole nere zigrinate e i binari su cui sono appese ventuno schede. Lo schedario arriva girando e le schede scavalcano i binari a cascata prima di fermarsi. Davanti c’è un divisorio colorato con la sua linguetta, il nome della voce in grande, una riga e la nota; dietro, le schede si inclinano a ventaglio e si vedono le linguette dei divisori che seguono; davanti ai binari le schede già passate sono cadute in avanti e se ne vede il retro, con il timbro Filed e le linguette colorate. Dietro ogni divisorio ci sono due schede color crema con le righe azzurre, la riga rossa e tre righe scritte a macchina. Le voci sono Work, Printing, Papers, Workshops, Journal, Studio e Contact. Si gira trascinando le schede in su o in giù, con la rotella, con le frecce o puntando una linguetta, che si alza un poco: ogni scheda cade con la sua molla e un piccolo ritardo, le zigrinature delle manopole scorrono, il segno bianco gira intorno alla manopola, il nottolino scatta a ogni scheda e la targhetta fa scorrere il nome della voce davanti. Scegliendo un divisorio, la scheda sale fuori dallo schedario, ricade con un elastico e resta un po’ più alta delle altre con una graffetta d’ottone sulla cima, e sulla targhetta passa un riflesso.

Come funziona

Un tamburo fatto di un numero

Lo schedario intero si muove da un numero solo, l’angolo del tamburo. Ogni scheda ha il suo posto sul giro, ventuno posti a 360 diviso 21 gradi l’uno; a ogni fotogramma si calcola quanto la scheda è lontana dal davanti, fra meno 180 e 180 gradi, e da lì quanto deve essere inclinata. Il tamburo segue la voce scelta con una molla che sbanda di poco; trascinando, l’angolo segue il dito e lasciando prosegue con la sua velocità e si ferma sul divisorio più vicino.

Il ventaglio e la caduta

L’inclinazione voluta viene da due tangenti iperboliche: le schede dietro si aprono piano fino a 56 gradi, quelle passate davanti ai binari cadono in fretta fino a 72. Nessuna scheda però va dritta lì: ognuna ha una molla sua, con una rigidezza un po’ diversa e poco smorzata, così ogni scheda arriva con un attimo di ritardo, scavalca la posizione e si assesta. È questo che fa la cascata quando il tamburo gira.

Schede vere in CSS 3D

Ogni scheda è una voce della lista ruotata con rotateX intorno al suo bordo basso, che sta sui binari; dentro ha due facce, il davanti e il retro girato di 180 gradi, con backface-visibility nascosta, così le schede cadute in avanti mostrano il retro. La prospettiva sta sulla lista con il punto di vista alto sopra lo schedario, e l’ordine di disegno lo decide lo script con lo z-index: dietro, la più vicina al davanti sta sopra; davanti, la più dritta copre quella più coricata, e i binari stanno in mezzo.

Le manopole, il nottolino, la targhetta

Le manopole sono cilindri visti di lato: la zigrinatura è una sfumatura che si ripete e scorre in verticale con l’angolo del tamburo, e il segno bianco fa il giro del cilindro con un seno, schiacciato dal coseno e nascosto quando passa dietro. Ogni volta che una scheda passa i binari il nottolino scatta e torna con un elastico; quando cambia il divisorio davanti la targhetta d’ottone fa uscire il nome vecchio in alto e rimbalzare quello nuovo dal basso.

Link veri e tastiera

I divisori sono i link del menu, nell’ordine giusto e raggiungibili col tasto Tab: quando uno prende il fuoco il tamburo lo porta davanti, le frecce passano al precedente e al successivo, Inizio e Fine vanno agli estremi, Esc chiude e ridà il fuoco al pulsante. La voce scelta ha aria-current, la targhetta parla in una regione aria-live, le schede scritte a macchina sono nascoste agli screen reader e lo schedario chiuso è inert.

Valori da cambiare

NomeFileDi partenzaCosa cambia
SPRINGscript.js1Quanto sono vivaci le schede quando scavalcano i binari (1 è normale).
FANscript.js56I gradi di cui si inclinano all’indietro le schede dietro.
FLOPscript.js72I gradi di cui cadono in avanti le schede davanti.
DRAGscript.js0.5I gradi di cui gira il tamburo per ogni pixel trascinato.
LIFTscript.js18Quanto sale il divisorio scelto fuori dallo schedario.
SPINscript.js1Quanto in fretta gira il tamburo verso una voce (1 è normale).

Provali nel Playground

Quando usarla

Per il menu del sito di una stamperia, di uno studio di grafica, di una cartoleria, di un archivio, di uno studio professionale o di una rubrica di contatti: le voci sono i divisori, da cinque a otto, con nomi corti come sulle linguette vere.

Sul telefono

Lo schedario è largo quanto lo schermo e alto al massimo quanto resta sotto il pulsante; le schede, i caratteri e la targhetta si misurano sulla casella con le unità dei container. Si gira trascinando le schede col dito in su o in giù, e un tocco su una linguetta porta davanti la sua voce e la sceglie.

Con il movimento ridotto

Lo schedario compare in dissolvenza già fermo sulla voce davanti; girando, le schede vanno subito al loro posto senza molle né cascata, la voce scelta resta un po’ più alta senza elastico e la graffetta compare. Niente scatto del nottolino, niente riflesso sulla targhetta.

Trappole

  • Un effetto con l’opacità o con un filtro sulle facce dentro un contesto 3D (uno pseudo-elemento con opacity variabile, poi un filter: brightness) in Chrome dipingeva certe schede tutte nere mentre giravano: l’ombra delle schede ora è un livello in più nello sfondo, una sfumatura col colore a trasparenza variabile.
  • L’opacità messa sulla voce della lista appiattisce il suo preserve-3d e il retro delle schede non si nasconde più: si vede il davanti al contrario. La dissolvenza va sulle facce, non sulla scheda.
  • Con il punto di vista alto, una scheda caduta a 50 gradi è quasi nel piano dello sguardo e si vede di taglio come una riga: le schede davanti devono cadere oltre lo sguardo (72 gradi) per mostrare il retro.
  • Al primo giro gsap.ticker.deltaRatio() non è ancora un numero: il passo di tempo veniva NaN e ogni scheda restava NaN per sempre, con la trasformazione buttata via. Il passo va controllato con Number.isFinite.
  • Le schede dietro non vanno ordinate come quelle davanti: dietro la più vicina al davanti sta sopra, davanti la più dritta copre la più coricata, perché la si guarda dall’alto.

Librerie

GSAP 3.15.0, Mona Sans (font variabile) 5.3.0, Courier Prime 5.3.0.

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

Collaudo

Provata il 23 ottobre 2026

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

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