Docs·Orbit Card Stack

Orbit Card Stack

A premium interactive card stack that collapses into a tight deck, fans out on hover, and lifts the active card above the rest without changing its color or angle.

Installation

pnpm dlx shadcn@latest add @componentry/orbit-card-stack

Usage

API Reference

PropertyTypeDefault
items

Cards shown in the stack. Each item can include an `image` path.

OrbitStackItem[]—
defaultActiveIndex

Card that sits at the front when the stack is collapsed.

number2
spread

Horizontal fan distance in pixels.

number168
lift

Vertical lift for hovered cards in pixels.

number34
onActiveChange

Callback fired when the active card changes.

(item: OrbitStackItem, index: number) => void—
className

Additional CSS classes for the outer stage.

string—
cardClassName

Additional CSS classes for each card.

string—

View source

Click the icon in the preview panel to browse source for each variant.

Keep in mind

This component is inspired by various open-source projects and patterns. Please verify licenses and implementation details before using in production.

Need a custom component?

I build bespoke UI components & websites tailored to your brand.

DM me on X
Mira Vale
MV

Creative Lead

Mira Vale

Shapes visual systems with enough restraint to feel expensive and enough edge to be remembered.

Identity
Noor Kade
NK

Product Strategy

Noor Kade

Turns loose ideas into sharp product moves, crisp priorities, and launchable experiences.

Roadmap
Ari Chen
AC

Founder

Ari Chen

Sets the taste bar, protects the details, and keeps the whole team pointed at the same high signal.

Vision
Sana Holt
SH

Frontend Engineer

Sana Holt

Builds the motion, polish, and interface texture that make the product feel calm under pressure.

Motion
Ezra Moon
EM

Operations

Ezra Moon

Keeps the machine quiet, the handoffs clean, and the team moving without pointless friction.

Systems
"use client";

import { useState } from "react";
import {
  OrbitCardStack,
  type OrbitStackItem,
} from "@/components/ui/orbit-card-stack";
const team: OrbitStackItem[] = [
  {
    name: "Mira Vale",
    role: "Creative Lead",
    description: "Shapes visual systems with restraint and edge.",
    initials: "MV",
    stat: "Identity",
    accent: "#f8d66d",
    image: "/team/mira-vale.png",
  },
  {
    name: "Noor Kade",
    role: "Product Strategy",
    description: "Turns loose ideas into crisp product moves.",
    initials: "NK",
    stat: "Roadmap",
    accent: "#78dcca",
    image: "/team/noor-kade.png",
  },
  {
    name: "Ari Chen",
    role: "Founder",
    description: "Keeps the team pointed at the same signal.",
    initials: "AC",
    stat: "Vision",
    accent: "#f3f1ea",
    image: "/team/ari-chen.png",
  },
];

export default function TeamPreview() {
  const [activeMember, setActiveMember] = useState(team[2]!);

  return (
    <section className="space-y-6">
      <div>
        <p className="text-sm font-medium text-muted-foreground">
          Currently viewing
        </p>
        <h2 className="text-2xl font-semibold">{activeMember.name}</h2>
      </div>

      <div className="h-[620px] w-full">
        <OrbitCardStack
          items={team}
          defaultActiveIndex={2}
          spread={150}
          lift={40}
          onActiveChange={(item) => setActiveMember(item)}
        />
      </div>
    </section>
  );
}