Liquid Transition

v1.0.1
FreeTransitions

A full-screen scroll- and swipe-driven page transition: a liquid S-curve wave curtain sweeps across the screen, swaps the content behind the cover, then peels away to reveal the next screen. Directional per step, boundary-locked (no looping), wheel and touch driven. Dependency-free.

Liquid Transition

Installation

Step 1. Initialize ProjectOne-time setup

Run once in your project root to configure paths and dependencies:

npx vectorvesper init
Step 2. Add ComponentInstalls source & assets

Downloads and registers the component in your project:

npx vectorvesper add liquid-transition
Requires Tailwind CSS to be configured in your project.

Usage

Import

import { LiquidTransition } from "@/components/vv/liquid-transition";

Usage

<LiquidTransition />
This component respects prefers-reduced-motion and provides a graceful fallback.
Tailwind CSS must be configured in your project for styles to apply correctly.

Props

Full-screen pages you move between with a curtain that pours across the viewport rather than cutting. Scroll or swipe to advance; the direction the curtain travels changes each time. Everything is driven by one array of screens.

<LiquidTransition />

The whole pager. It takes over the viewport, so give it a route or a section of its own.

PropTypeDefaultDescription
pages*PageData[]The screens to page through, in order. This is the component's only prop — everything else is set per screen.

<PageData />

type

One screen.

PropTypeDefaultDescription
tag*stringSmall label above the headline, usually a number or section name.
title*stringThe headline. Newlines in the string are honoured, so you can control the line breaks.
subtitle*stringSupporting line under the headline. Pass an empty string to leave it out.
bgColor*stringBackground of the screen.
textColor*stringColour of the type on it.
transitionColorstringColour of the curtain as it sweeps in over this screen. Set it per screen to change the sweep without changing the page itself.

Examples

A four-screen pager
import LiquidTransition, { PageData } from "@/components/vv/liquid-transition/LiquidTransition";

const pages: PageData[] = [
  {
    tag: "01 / STUDIO",
    title: "Ship interfaces\npeople remember",
    subtitle: "",
    bgColor: "#E5E3DC",
    textColor: "#1C1C1E",
    transitionColor: "#0e0e11",
  },
  {
    tag: "02 / WORK",
    title: "Start ahead,\nfinish beyond",
    subtitle: "Selected projects, 2021–2026.",
    bgColor: "#DFE5E0",
    textColor: "#1A231C",
    transitionColor: "#0e0e11",
  },
];

<LiquidTransition pages={pages} />
A sweep that matches each screen
const pages = sections.map((s) => ({
  ...s,
  transitionColor: s.accent,
}));

<LiquidTransition pages={pages} />
The curtain runs on every page change with no reduced-motion guard, and it covers the whole viewport. This is the component to think hardest about if your audience includes people sensitive to large-area motion.
Client component. It listens for wheel and touch input and animates the curtain per frame, so it has to run in the browser.
It fills the viewport and captures scroll while mounted. Give it its own route rather than placing it inside a longer scrolling page.

Source

/**
 * Liquid Transition — Vector Vesper
 * https://vectorvesper.dev/components
 *
 * Copyright (c) 2026 Vector Vesper
 * Released under the MIT License. This notice must be retained in copies and
 * substantial portions of the file. https://vectorvesper.dev/license
 */
export { default as LiquidTransition } from "./LiquidTransition";
export type { LiquidTransitionProps, PageData } from "./LiquidTransition";
View on GitHubReport an issue