Inline Pill Takeover

A clipped pill expands inside a sentence, pushes the words apart, and takes over the frame

Installation

$ pnpm dlx shadcn@latest add @remocn/inline-pill-takeover

Usage

The line starts with a short pill between before and after. Its first animation changes explicit background width and height values, so the shape expands outward from center without scaling its contents. The full-size insert text appears through a hard opacity switch and is cropped by overflow: hidden until the pill opens around it. When that reveal finishes, a second local pill animation increases the background width and height through independent controls without changing the text's local font size. An independent camera wrapper begins its approach at the same time, cuts instantly to 86% of its final close-up, then settles to 100%. The pill and camera therefore move toward one another, and the pill keeps growing briefly after the camera settles. All timings were measured frame-by-frame from the reference footage.

// src/Root.tsx
import { Composition } from "remotion";
import { InlinePillTakeover } from "@/components/remocn/inline-pill-takeover";
 
const InlinePillTakeoverScene = () => (
  <InlinePillTakeover
    before="powering 20%"
    insert="Start building"
    after="of the Internet."
  />
);
 
export const RemotionRoot = () => (
  <Composition
    id="InlinePillTakeover"
    component={InlinePillTakeoverScene}
    durationInFrames={45}
    fps={30}
    width={1280}
    height={720}
  />
);

With Backdrop

The component paints no background. The reference pairs warm white type and pill with an orange radial glow.

import { Composition } from "remotion";
import { InlinePillTakeover } from "@/components/remocn/inline-pill-takeover";
import { Backdrop } from "@/components/remocn/backdrop";
 
const InlinePillTakeoverScene = () => (
  <Backdrop
    fill={{
      type: "gradient",
      value:
        "radial-gradient(circle at 50% 108%, #ffd77a 0%, #ff6840 31%, #f13d21 78%)",
    }}
  >
    <InlinePillTakeover
      before="powering 20%"
      insert="Start building"
      after="of the Internet."
    />
  </Backdrop>
);
 
export const RemotionRoot = () => (
  <Composition
    id="InlinePillTakeover"
    component={InlinePillTakeoverScene}
    durationInFrames={45}
    fps={30}
    width={1280}
    height={720}
  />
);

Props

PropTypeDefaultDescription
beforerequired
stringText rendered before the expanding pill
insertrequired
stringText centered inside the pill and revealed through its clip
afterrequired
stringText rendered after the expanding pill
fontSize
number52Base font size in pixels
fontWeight
number400CSS font-weight shared by the sentence and pill
pillWidth
number260Expanded pill width in pixels; tune this when changing insert text
expandFrames
number12Frames used for the initial width-and-height reveal
pillRevealHeightScale
number0.35Starting height as a fraction of the full pill height
pillGrowAt
number12Frame on which the local width-and-height growth begins
pillGrowFrames
number24Frames used for the local width-and-height growth
pillGrowWidthScale
number1.08Final local scale applied only to the pill width
pillGrowHeightScale
number1.16Final local scale applied only to the pill height
outerExitFrames
number18Frames used to blur and remove the outer copy
takeoverAt
number12Frame on which the camera approach begins
takeoverScale
number2.15Final scale held after the takeover settles
blur
number12Maximum blur applied to the disappearing outer text in pixels
color
string"#fff3df"Outer text color
pillColor
string"#fffaf0"Pill background color
pillTextColor
string"#1c1210"Pill text color
speed
number1Playback speed multiplier
className
stringOptional className passed to the component root