Skip to content
animorio
IT
All components

The rotary dial code field

Forms, Physics, SVGGSAPAdvancedCompressed weight: Demo 15 KBGSAP 28 KBFreeDownload the zip

The six boxes of a sign-in code and under them a 1960s telephone dial: put a finger in a hole and turn it to the chrome stop, then the wheel runs back by itself at the governor’s steady speed, filling one tick for every pulse, and only then the digit drops into its box. Digits typed on the keyboard dial themselves; with six digits the code is checked and the centre card says Verified.

The code

A folder that runs on its own: index.html, style.css, script.js and the libraries from a CDN. The React and Vue tabs hold the same demo as a ready component, which switches its animations off when it leaves the page.

<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>The rotary dial code field</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@fontsource-variable/archivo@5.3.0/wdth.css">
  <link rel="stylesheet" href="style.css">
</head>
<body>
  <main class="stage">
    <!-- the rotary dial code field: the six boxes of a sign-in code, and under them a 1960s telephone dial in sage
         enamel. A finger in a hole turns the clear wheel clockwise to the chrome stop; let go, it runs back on its own
         at the governor's steady speed, one tick filling by the stop for every pulse, and the digit drops into the
         next box. Typed digits dial themselves; six digits are checked and the centre card says Verified -->
    <section class="rd" aria-label="Verification code" data-rd>
      <!-- the boxes only show the code; the field a screen reader and the keys use is the input inside the dial -->
      <div class="rd__boxes" aria-hidden="true" data-boxes></div>

      <div class="rd__dial" data-dial>
        <!-- three layers: the still base and number card, the finger wheel (the only part redrawn as it turns), and on
             top the finger stop, the pulse ticks and the centre card -->
        <svg class="rd__art" viewBox="0 0 400 400" aria-hidden="true" data-art="base"></svg>
        <svg class="rd__art rd__art--wheel" viewBox="0 0 400 400" aria-hidden="true" data-art="wheel"></svg>
        <svg class="rd__art rd__art--top" viewBox="0 0 400 400" aria-hidden="true" data-art="top"></svg>
        <label class="sr" for="rd-code" data-label>Verification code, 6 digits</label>
        <input class="rd__input sr" id="rd-code" type="text" inputmode="numeric" autocomplete="one-time-code"
               spellcheck="false" aria-describedby="rd-hint" data-input>
      </div>
      <p class="sr" id="rd-hint">Rotary dial. Type the digits and the dial turns them for you, or put a finger in a hole
        and turn it clockwise to the metal stop. Backspace removes the last digit.</p>

      <div class="rd__actions">
        <button class="rd__quiet rd__quiet--sms" type="button" data-sms data-autoclic>
          <svg class="rd__icon" viewBox="0 0 20 20" aria-hidden="true" data-icon><path d="M4.5 3.5h11a2 2 0 0 1 2 2v6.5a2 2 0 0 1-2 2H9.2l-3.6 2.8V14H4.5a2 2 0 0 1-2-2V5.5a2 2 0 0 1 2-2z"/><path d="M6.4 7.4h7.2M6.4 10.2h4.6"/></svg>
          <span>Use code from SMS</span>
        </button>
        <button class="rd__quiet rd__quiet--clear" type="button" aria-disabled="true" data-clear>
          <svg class="rd__icon" viewBox="0 0 20 20" aria-hidden="true" data-icon><path d="M5.2 7.4a5.6 5.6 0 1 1-.8 4.8"/><path d="M4.6 3.6v4.2h4.2"/></svg>
          <span>Clear</span>
        </button>
      </div>
      <p class="sr" aria-live="polite" data-live></p>
    </section>
  </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

Change values, colours and text with the controls and watch the animation respond live. Or write in the code yourself. Then download the folder with your changes.

40 values to change

Or ask Claude Code for it

With the Animorio connector, Claude Code takes it from here, guide included, and fits it into your project. Paste this request:

Take “The rotary dial code field” from Animorio and fit it into my site

What it does

On a white background, six light grey boxes in two groups of three, and under them a telephone dial: a sage enamel base with its well, a cream number card with 1 to 9 and 0 (above them, small, the letters ABC, DEF up to OPER), a clear plastic finger wheel with a faint mint tint and ten bevelled holes, a chrome finger stop screwed to the rim at about half past four, and in the middle a cream card in a chrome ring that says DIAL. Moving the mouse over a hole shows a thin ring and the grab hand. Put a finger (or the pointer) in a hole and drag clockwise: the wheel turns with the finger, never back past its rest and never past the stop; when the hole hits the stop the wheel bounces back a hair and the stop gives a little, and a phone buzzes. Let go there and the wheel runs back by itself, always at the same speed, like a real telephone’s; by the stop one amber tick fills for every pulse (a 7 sends seven, a 0 sends ten), the wheel settles at home with a small bounce and the digit drops from above into the next box. Let go before the stop and the wheel goes back and nothing happens. With the dial focused from the keyboard (a dark green ring goes round it) typed digits dial themselves one after the other, a little faster than a hand, and Backspace lifts the last digit out of its box. Use code from SMS dials the code 481 592 by itself. With the sixth digit the figures sway while a red arc runs round the word Checking in the middle; then the boxes turn green and a tick draws itself on a green disc above VERIFIED on the card. After a few seconds the code clears itself; Clear clears it at once.

How it works

The dial in three layers

The drawing is SVG in three stacked layers: below, the base, the well and the number card, drawn once; in the middle the wheel, the only one redrawn; on top the stop, the ticks and the card. The wheel is a single path with fill-rule evenodd (the outer circle, the inner one and the ten holes), rewritten every frame from the angle; the bevel and the shadow of each hole are a group that moves without turning, so the light stays at the top left while the wheel turns.

A finger in a hole

On pointerdown the hole under the pointer is found and the pointer is captured. At every move the angle round the centre is measured with atan2 and the difference from the last one, brought between -180 and 180, is added up, so passing six o’clock makes no jump; near the centre the angle is not read. The wheel’s angle is that sum, held between 0 and the hole’s stop: (n + 1) × 30 degrees for digit n, 330 for the 0. Reaching the stop there is a knock: the wheel bounces back 1.8 degrees and the stop turns a degree round its screw.

The governor and the pulses

Let go at the stop, the wheel goes back on gsap.ticker at a constant speed (GOVERNOR degrees a second, step capped at 1/30 s), with no easing. As on a real dial it sends a pulse every 30 degrees after the first 15, and the last 45 are the pause between digits: at every pulse the next tick fills. At home a bounce of 1.3 and then 0.35 degrees, added to the angle, and the digit drops into its box with back.out. When nothing moves nothing is redrawn.

Typed digits and the automatic finger

The real field is a hidden input inside the dial, with inputmode numeric and autocomplete one-time-code: digits pressed, pasted or offered by the phone go into a queue, and an automatic finger dials them. A finger value goes with sine.inOut a little past the stop, and the wheel follows it up to the stop, so it gets there still moving and the knock is felt. The way back uses AUTO_GOVERNOR, and the next digit starts while the wheel is still settling, because the bounce is added separately.

The check and the verification

With the last digit the dial stops, a red arc runs round the card and the figures make a wave of opacity; after CHECKING seconds the boxes turn green, the card turns to VERIFIED with a tick drawn by stroke-dashoffset, and after RESET seconds the figures lift out and the field empties. An aria-live region says every step, for example “3 dialled, 4 of 6”.

Values to change

NameFileDefaultWhat it changes
LENGTHscript.js6How many digits the code has.
SAMPLEscript.js'481592'The code the Use code from SMS button dials.
GOVERNORscript.js330How fast the wheel runs home after a hand lets go, in degrees a second (a real dial does about 300).
AUTO_GOVERNORscript.js720How fast it runs home when the dial turns by itself, for typed digits and the SMS code.
FINGERscript.js1000How fast the automatic finger turns the wheel to the stop, in degrees a second.
HOLDscript.js0.06How many seconds the automatic finger stays against the stop.
CHECKINGscript.js0.8How many seconds the code takes to check.
RESETscript.js3.8How many seconds it stays verified before it clears itself.
WORDscript.js'DIAL'The word printed on the centre card (a long one is set smaller).

Try them in the Playground

When to use it

In the code step of a two-step sign-in, in confirming a phone number or in an invitation code, on a site with a period soul: a radio station, a 1960s bar or hotel, a mid-century furniture shop, a museum, a phone service. It stays a real field: the keyboard, pasting and the code offered by the phone all work, and the dial dials them by itself.

On phones

On a 390-pixel phone the dial is as wide as the screen less the margins (358 pixels), the holes stay as big as a fingertip and are turned with the finger; on the dial a finger does not scroll the page (touch-action none), elsewhere it does. Touching the dial does not open the keyboard, which would cover the dial; the hidden field has a 16-pixel typeface, so with an external keyboard or a screen reader the page does not zoom in. Where it exists, the knock at the stop buzzes the phone.

With reduced motion

The dial still turns with a finger, but does not run back: let go at the stop it fades for a moment and is already home, the ticks fill all together and the digit fades in. Typed digits and the SMS code do not turn the dial: the hole lights up and the digit appears in its box. No bounces, no entrance, and during the check the arc does not turn.

Pitfalls

  • With the clear wheel over the cream card, holes and plastic were the same colour and the holes looked like raised buttons. The plastic now has a faint mint tint and every hole a crescent of shadow at the top left, on the card: they read as holes.
  • Turning the hole groups with the wheel, the highlights of the bevels turned too and the light seemed to move. Now the wheel’s path is rewritten every frame and the hole groups only move: the light stays still at the top left.
  • atan2 jumps from 180 to -180 degrees at six o’clock: adding angles up, the wheel made a sudden turn. The difference between two readings is added, brought between -180 and 180, and near the centre the pointer does not count.
  • At the real governor’s speed (330 degrees a second) the SMS code reached Verified after 9.8 seconds, and the preview video records 6.4. The automatic dial has its own governor, faster but still constant, and the next digit starts while the wheel is still settling: Verified comes at 5 seconds, and a hand keeps the real speed.
  • The library’s preview clicks Use code from SMS every 2.8 seconds: every click started the code over halfway. Now the button rests (aria-disabled) while it dials, checks and shows the verified code.
  • With the mouse, after a click on the dial typed digits did not arrive: mousedown moved the focus to the body. Now mousedown on the dial is cancelled and the mouse’s pointerdown gives the focus to the hidden input; a finger does not, or the phone’s keyboard would cover the dial.

Libraries

GSAP 3.15.0, Archivo (font variabile) 5.3.0.

Compressed with gzip, the three demo files weigh 15 KB; the libraries: GSAP 28 KB.

Testing

Tested on 7 October 2026

  • Desktop: Done
  • Phone: Done
  • Reduced motion: Done
  • Safari on iPhone: To do

License

Use it in your own projects and in your clients’ projects. Do not resell it or redistribute it as is. GSAP stays under its own Standard license. Full license.

All components