Skip to content
WANCRAFT

H.623D & Experimental

Morphing Blob

An organic SVG blob that morphs continuously, leans toward the pointer and can merge with a gooey twin.

NewReactSVGTailwindintermediate

Overview

Morphing Blob builds a closed outline from N noise-driven radii, sampled on a circle in simplex-noise space so the loop is seamless, and joins them with a Catmull-Rom spline converted to cubic Béziers. The path is written straight to the DOM every frame — no React re-renders. A mouse pointer makes the blob lean and bulge toward it while the far side squishes. Fill it with a solid colour, a linear or radial gradient, or draw just the outline; switch on gooey to add an orbiting satellite that merges and splits through an SVG blur-and-threshold filter. Children are centred on top, ideal behind a call to action.

01Installation

Method 01 · Registry

CLI verified

Uses the shadcn CLI in a project initialised with shadcn init. Installs the file to components/ui/morphing-blob.tsx and adds its dependencies.

npx shadcn@latest add https://wancraft.my/r/morphing-blob.json

Method 02 · Copy and paste

  1. 1. No extra dependencies — React and Tailwind CSS only.
  2. 2. Copy the source from the Code tab into components/ui/morphing-blob.tsx.
  3. 3. Import it and adjust props.
Dependencies
None
Peer
react ≥ 18, tailwindcss ≥ 4
Added
13 Oct 2026
Updated
—

02Usage

The default configuration. Change properties above to generate a tailored example in the Usage tab.

example.tsx
import { MorphingBlob } from "@/components/ui/morphing-blob";

export function MorphingBlobExample() {
  return (
    <div className="relative h-96 w-full">
      <MorphingBlob>
        Start a project
      </MorphingBlob>
    </div>
  );
}

03Props

PropTypeDefaultDescription
complexitynumber8Control points around the outline (min 3). More points = more lobes.
speednumber1Morph speed multiplier; 0 holds the shape.
amplitudenumber0.18Radius variation as a fraction of the base radius (0–0.45).
fill"solid" | "linear" | "radial" | "outline""linear"Solid colour, linear or radial gradient, or outline only.
colorstring"#FF7448"Main colour (any CSS colour).
secondaryColorstring"#B6F3D1"Gradient end colour (any CSS colour).
gooeybooleanfalseAdds an orbiting satellite that merges via an SVG goo filter (filled modes).
interactivebooleantrueLean and bulge toward a mouse or pen pointer.
childrenReactNode—Content centred above the blob, e.g. a button.
...propsHTMLAttributes<HTMLDivElement>—Forwarded to the root, which fills its parent and centres its children.

04Features

  • 01Seamless noise loop: radii sampled on a circle in 3D simplex space
  • 02Catmull-Rom → cubic Bézier closed path with any number of points
  • 03Path updated directly on the DOM each frame — zero React re-renders
  • 04Pointer lean, bulge and squish with eased presence
  • 05Solid, linear, radial or outline fills; optional gooey merge filter
  • 06Deterministic first frame (seeded noise) — SSR markup matches the client
motion · continuousinput · pointerinput · hoverinput · viewport

05Accessibility

  • The SVG is aria-hidden and ignores pointer events; children (e.g. a button) keep normal semantics and focus.
  • prefers-reduced-motion renders a static shape with no morphing or pointer reaction.
  • Touch input never moves the blob; the animation pauses offscreen and in hidden tabs.