Skip to content
animorio
IT
All components

The droplet menu

Menus, SVG, TransitionsGSAPMediumCompressed weight: Demo 4.9 KBGSAP 28 KBFreeDownload the zip

A round button six actions come out of like drops of a liquid: they stretch out of the button, break away and land in a circle with a bounce, and called back they run into it and melt.

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 droplet menu</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@fontsource-variable/manrope@5.3.0/index.css">
  <link rel="stylesheet" href="style.css">
</head>
<body>
  <main class="stage">
    <!-- the menu: the actions come out of the round button like drops of a liquid and go back into it.
         The drops are SVG circles under a goo filter (a blur, then a hard cut of the transparency); the icons are
         buttons laid over them -->
    <div class="radial" data-radial>
      <svg class="radial__goo" viewBox="-200 -200 400 400" aria-hidden="true">
        <defs>
          <filter id="goo" x="-50%" y="-50%" width="200%" height="200%" color-interpolation-filters="sRGB">
            <feGaussianBlur in="SourceGraphic" stdDeviation="10" result="blur" data-blur/>
            <feColorMatrix in="blur" mode="matrix" values="1 0 0 0 0  0 1 0 0 0  0 0 1 0 0  0 0 0 24 -10"/>
          </filter>
        </defs>
        <g class="radial__liquid" filter="url(#goo)">
          <circle r="40" data-core/>
          <circle r="28" data-drop/>
          <circle r="28" data-drop/>
          <circle r="28" data-drop/>
          <circle r="28" data-drop/>
          <circle r="28" data-drop/>
          <circle r="28" data-drop/>
        </g>
      </svg>

      <button class="radial__button" type="button" aria-expanded="false" aria-controls="actions" data-toggle data-autoclic>
        <span class="sr" data-name>Open the actions</span>
        <svg class="radial__plus" data-plus viewBox="0 0 24 24" aria-hidden="true"><path d="M12 4.5v15M4.5 12h15"/></svg>
      </button>

      <ul class="radial__items" id="actions" data-items inert>
        <li><button class="radial__item" type="button" aria-label="Share" data-item><svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 15V3M8 7l4-4 4 4M5 12v7h14v-7"/></svg></button></li>
        <li><button class="radial__item" type="button" aria-label="Like" data-item><svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 20s-7-4.4-7-10a4 4 0 0 1 7-2.6A4 4 0 0 1 19 10c0 5.6-7 10-7 10z"/></svg></button></li>
        <li><button class="radial__item" type="button" aria-label="Save" data-item><svg viewBox="0 0 24 24" aria-hidden="true"><path d="M6 3h12v18l-6-4.5L6 21z"/></svg></button></li>
        <li><button class="radial__item" type="button" aria-label="Edit" data-item><svg viewBox="0 0 24 24" aria-hidden="true"><path d="M15.5 4.5l4 4L8 20H4v-4zM13 7l4 4"/></svg></button></li>
        <li><button class="radial__item" type="button" aria-label="Download" data-item><svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 3v12M7 10l5 5 5-5M5 20h14"/></svg></button></li>
        <li><button class="radial__item" type="button" aria-label="Delete" data-item><svg viewBox="0 0 24 24" aria-hidden="true"><path d="M4 7h16M9 7V4h6v3M6 7l1 13h10l1-13M10 11v6M14 11v6"/></svg></button></li>
      </ul>

      <span class="radial__label" data-label aria-hidden="true"></span>
    </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

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.

11 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 droplet menu” from Animorio and fit it into my site

What it does

On a black background a round lime button with a plus. Pressing it, six actions come out of the button like drops of a liquid: each drop stretches out of the button, breaks away and lands on a circle around it with a little bounce, one after the other, while the plus turns into an X and the button squeezes and comes back. The drops carry the icons of Share, Like, Save, Edit, Download and Delete. Pointing at an action its drop grows and its name appears outside the circle, on its side; pressing it, it pulses and the menu closes. Pressing the button again the drops go back one at a time and melt into the button, which swallows them with a gulp. With the pointer on the closed button the drops peek out of its edges.

How it works

The liquid

Seven SVG circles, the button and six drops, sit in a group with a filter: feGaussianBlur blurs them and feColorMatrix cuts the transparency sharply (alpha times 24, minus 10), so two circles close to each other become one shape. GOO is the blur: higher, the longer the drops stay joined.

The drops and the buttons

Each drop has four numbers: its distance from the centre, its size, how much its icon shows and how swollen it is under the pointer. On every frame the circle’s transform is written, in drawing units (400 a side), and so is the transform of the button over it, in pixels, multiplied by the ratio between the real width and 400.

Coming out

Each drop goes out to RADIUS with elastic.out(SPRING), STAGGER seconds after the one before; its icon appears soon after. The button squeezes to 88% and comes back with an elastic, and the plus turns 135 degrees.

Going back

The drops go back with power3.in in the opposite order and the icons vanish at once; when the last one arrives, the button swells to 110% and settles: that is the gulp. On the closed button the drops move PEEK units from the centre, enough to peek out of its edge.

Keyboard and finger

The button comes before the actions in the code, so the Tab key goes from it into the actions; the arrows go round the actions, Esc closes and gives the focus back to the button, and so does an action chosen with the keyboard (not with a finger, or Safari on iPhone would draw the focus ring on it). The closed actions are inert. A tap outside closes.

Values to change

NameFileDefaultWhat it changes
RADIUSscript.js112How far from the centre the drops land, in drawing units.
SPRINGscript.js[1, 0.5]The spring of a drop landing: its strength and how quickly it settles.
STAGGERscript.js0.05The seconds between one drop and the next.
GOOscript.js10The blur of the liquid: higher, the longer the drops stay joined.
PEEKscript.js34How far the drops peek out while the pointer is on the closed button.

Try them in the Playground

When to use it

For a group of actions on an item (a photo, a message, a file) or for the main button of an app. From four to eight actions: with more the circle gets crowded.

On phones

The drawing narrows to the width of the screen and taps work like clicks. Without a pointer the drops do not peek and the names do not appear, but each action has its name for screen readers.

With reduced motion

The drops do not travel: the actions fade in and out in their places, the plus becomes an X at once and the button neither squeezes nor gulps.

Pitfalls

  • The icons are not under the filter: blurred and cut by the colour matrix they would lose their outlines. That is why they are HTML buttons over the drawing, moved by the same numbers as the circles.
  • The filter region must be widened (x, y, width and height at 200%): with the default one the blur of the far drops may get cut at the edges.
  • The colour matrix decides how sticky the liquid is: with alpha times 24 minus 10 the cut is sharp; a smaller number subtracted makes fuller, joined drops, a bigger one separates them sooner.
  • The button must come before the actions in the code: placed after, the Tab key would leave the menu from the button instead of going into the actions.

Libraries

GSAP 3.15.0, Manrope (font variabile) 5.3.0.

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

Testing

Tested on 2 October 2026

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

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