Two Doors Tabs

Two ways in

Pickthedoorthatfeelslighter.Youcanalwaysusetheother.

A curved city beach along a bay

For what is heavy and has been for a while

Therapy at Altair looks back as well as forward. It is led by registered psychotherapists and moves at whatever pace lets the hard things be said.

  • 60 or 75 minute sessions
  • Weekly to begin with
  • In the room or on video
Start with therapy
About this block

Two Doors TabsPRO

A tabbed comparison under a centred serif heading that settles in word by word: pill tabs switch between approaches, each blurring in a drifting portrait photograph beside a serif title, a description, a ruled fact list and a sliding-marker pill.

Feature278: Two Doors Tabs

Two doors behind one pill tab bar: choosing a tab blurs in a portrait photograph that drifts inside its frame, beside a serif title, a paragraph, a ruled list of facts and that door's own action.

Upgrade to Pro

Pro blocks install through the shadcn CLI with your license key and ship their full source. Docs and live previews stay open to everyone, so you can read every block's details first.

Upgrade Now

Installation

Swap YOUR_EMAIL and YOUR_KEY for the email and license key on your account. Find your license key on your account page.

Radix flavor

bash
npx shadcn add "https://ui.beste.co/r/feature278?email=YOUR_EMAIL&license_key=YOUR_KEY"

Base UI flavor

bash
npx shadcn add "https://ui.beste.co/r-base/feature278?email=YOUR_EMAIL&license_key=YOUR_KEY"

This installs the block to components/beste/block/feature278.tsx, the shadcn tabs primitive it is built on, and the button22 sliding-marker pill and the text1 word stagger it uses.

Quick start

The installed file exports feature278Demo alongside the block: the exact props behind the preview above. Spread it to get a working two-door feature in one line.

tsx
import { Feature278, feature278Demo } from "@/components/beste/block/feature278";

export default function Page() {
  return <Feature278 {...feature278Demo} />;
}

Then replace the demo with your own props. Written out, a trimmed setup looks like this:

tsx
import { Feature278 } from "@/components/beste/block/feature278";

export default function Page() {
  return (
    <Feature278
      eyebrow="Two ways in"
      heading="Pick the door that feels lighter. You can always use the other."
      items={[
        {
          tabLabel: "Therapy",
          title: "For what is heavy and has been for a while",
          description: "Therapy looks back as well as forward, and moves at whatever pace lets the hard things be said.",
          facts: ["60 or 75 minute sessions", "Weekly to begin with", "In the room or on video"],
          button: { label: "Start with therapy", href: "/therapy", tone: "dark" },
          image: { src: "/photos/pines.jpg", alt: "Pine trees standing in soft morning fog" },
        },
      ]}
    />
  );
}

Props

PropTypeDefaultDescription
eyebrowstring–Small-caps line above the heading
headingstring–Section heading, rendered as an h2 through Text1
itemsApproach[][]The doors; the first is selected on mount
classNamestring–Extra classes for the outer <section>
ts
type Approach = {
  tabLabel: string;
  title: string;
  description: string;
  facts: string[];
  button: ActionButton;
  image: { src: string; alt: string };
};

type ActionButton = {
  label: string;
  href: string;
  tone?: "primary" | "light" | "dark" | "outline";
};

Behavior notes

  • tabLabel doubles as the tab's value, so two approaches must not share a label; give them distinct names and the tabs track correctly.
  • defaultValue is read from the first item, so the section opens on a real door rather than with nothing selected.
  • Each panel animates on animate rather than whileInView, because a tab panel is mounted when its tab is chosen and would otherwise never have a moment to arrive; the copy is given a 0.1s head start behind the image so the two do not land together.
  • The tab rail is restyled into a pill track, with the active trigger inverting to the ink surface and its shadow removed, which is the set's language rather than the shadcn default.
  • Keyboard support comes from the shadcn Tabs: arrow keys move between doors and the panel follows.
  • Each approach carries its own button, so the two doors can point at entirely different flows.
  • The facts list is ruled top and bottom with divide-y between, so a short list of three reads as a small table rather than as bullets.
  • The photograph drifts -10% to 10% against a 1.2 scale and clears from blur(24px) on decode, with a complete check on mount for cached files.

More Feature blocks

View all Feature
PRO

feature298

Ask At Any Size Tabs

PRO

feature288

Honest Comparison

PRO

feature276

Sticky Chapters

Get Pro access