Browser Stack
A free product showcase and browser mockup React section with a selectable, motion-driven preview stack.
Inside Atlas
One workspace, every signal in focus
Move between the product overview, delivery workflow and outcome signals without losing the shape of the system around them.
Explore the workspaceOverview
See the whole product surface at once, from live health signals to the work that needs attention next.
Customise
Code
<ShowcaseBrowserStack
title="See the complete product in motion"
frames={[
{
id: "overview",
label: "Overview",
url: "app.example.com/overview",
src: "/product-overview.png",
alt: "Product overview with live metrics",
width: 1440,
height: 900,
caption: "See the whole product surface at a glance.",
},
{
id: "workflow",
label: "Workflow",
url: "app.example.com/workflow",
src: "/product-workflow.png",
alt: "Workflow with connected delivery stages",
width: 1440,
height: 960,
caption: "Follow every decision from intake to delivery.",
},
]}
/>Browser Stack is a free product showcase component for Next.js and React, animated with Motion and styled with Tailwind. It layers two to five intrinsic-size screenshots in a selectable browser mockup React stage, then brings the chosen view forward without cloning or remounting any frame.
The selector follows the ARIA tab pattern with arrow, Home and End key support, stable controls and one active caption panel. Every screenshot keeps meaningful alt text, the tallest authored frame reserves the stage before images load, fine-pointer tilt is decorative, and reduced-motion users receive immediate state changes with no frame or caption travel.
Install
Add the @te registry to your components.json once:
{
"registries": {
"@te": "https://templateempire.io/r/{name}.json"
}
}Then install the component:
npx shadcn@latest add @te/showcase-browser-stackUsage
import { ShowcaseBrowserStack } from "@/components/showcase-browser-stack";
const frames = [
{
id: "overview",
label: "Overview",
url: "app.example.com/overview",
src: "/product-overview.png",
alt: "Product overview showing live metrics and recent work",
width: 1440,
height: 900,
caption: "See the whole product surface at a glance.",
},
{
id: "workflow",
label: "Workflow",
url: "app.example.com/workflow",
src: "/product-workflow.png",
alt: "Workflow view showing connected delivery stages",
width: 1440,
height: 960,
caption: "Follow every decision from intake to delivery.",
},
];
export function Example() {
return (
<ShowcaseBrowserStack
title="See the complete product in motion"
description="Choose a view to bring its screenshot and caption forward."
cta={{ label: "Start exploring", href: "/product" }}
frames={frames}
/>
);
}Props
| Prop | Type | Default | Description |
|---|---|---|---|
| eyebrow | string | "A closer look" | Introductory label above the section heading. |
| title | string | required | Section heading rendered as an h2. |
| description | string | undefined | Optional supporting section copy. |
| cta | { label: string; href: string } | undefined | Optional call to action rendered as a real anchor. |
| frames | { id; label; url?; src; alt; width; height; caption }[] | required | Two to five browser previews with unique stable IDs, meaningful alt text and intrinsic image dimensions. |
| activeId | string | undefined | Front frame ID in controlled mode. |
| defaultActiveId | string | first frame ID | Initial front frame ID in uncontrolled mode. |
| onActiveChange | (id: string) => void | undefined | Called after a valid frame is selected. |
| layout | "deck" | "fan" | "deck" | Stack geometry used for the settled frame transforms. |
| stackDepth | number | 20 | Per-frame z depth in CSS pixels, clamped from 8 to 40. |
| spread | number | 34 | Per-frame horizontal and vertical spread in CSS pixels, clamped from 12 to 64. |
| perspective | number | 1200 | Static stage perspective in CSS pixels, clamped from 800 to 1800. |
| maxTilt | number | 4 | Fine-pointer stage tilt in degrees, clamped from 0 to 7 and disabled on touch or reduced motion. |
| transitionDuration | number | 0.58 | Visual frame transition duration in seconds, clamped from 0.24 to 1. |
| className | string | undefined | Additional classes merged onto the section root. |
Customisation
Browser Stack exposes Tier 3 tokens for the stage, frame, browser chrome and grid line colours. Geometry and motion are controlled independently through layout, stackDepth, spread, perspective, maxTilt and transitionDuration, so the effect can be tuned without changing product copy or media:
.showcase-browser-stack {
--showcase-browser-stage: var(--surface);
--showcase-browser-frame: var(--background);
--showcase-browser-chrome: var(--surface);
--showcase-browser-grid: var(--border);
}
<ShowcaseBrowserStack
title="Explore the platform"
frames={frames}
layout="fan"
stackDepth={28}
spread={44}
perspective={1400}
maxTilt={3}
transitionDuration={0.7}
className="showcase-browser-stack"
/>Frequently asked questions
- Is Browser Stack free for commercial use?
- Yes. Browser Stack is MIT licensed, so you can use it in personal and commercial projects without attribution.
- Is Browser Stack accessible and reduced-motion safe?
- Yes. Its selectors use labelled tabs with roving focus, stable panel relationships and visible focus rings. The active screenshot retains its alt text, inactive chrome is removed from the accessibility tree, and reduced motion updates the selected frame and caption immediately without tilt or position animation.
- How do I customise the browser stack effect?
- Choose the deck or fan layout, then tune stack depth, spread, perspective, pointer tilt and transition duration through their bounded props. Use the four Tier 3 colour tokens for the stage, frame, chrome and grid, while screenshot sources, alt text and captions remain authored in the frames array.