Component
Tabs
A lilac track of medium labels; the selected tab is a white key with Shadow/S.
npx -y github:anwarlemu/inkbox-brand-cli#release add tabsManage mailboxes for your organization.
Usage
Use to switch between views of the same thing on a page (Mailboxes, Contact rules, Custom domains). Pass full to TabsList for two equal choices that fill a form's width (Login, Sign up).
Avoid
- Underlined tabs
- A purple selected tab
- Animating the white key between tabs
Exports: Tabs, TabsList, TabsTrigger, TabsContent. This component is a client component.
Dependencies: radix-ui.
Example
"use client";import { Tabs, TabsContent, TabsList, TabsTrigger } from "@/components/ui/tabs";export function Preview() { return ( <Tabs defaultValue="mailboxes" className="w-full"> <TabsList> <TabsTrigger value="mailboxes">Mailboxes</TabsTrigger> <TabsTrigger value="rules">Contact rules</TabsTrigger> <TabsTrigger value="domains">Custom domains</TabsTrigger> </TabsList> <TabsContent value="mailboxes" className="text-body text-fg-muted">Manage mailboxes for your organization.</TabsContent> <TabsContent value="rules" className="text-body text-fg-muted">Allow or block who can reach each agent.</TabsContent> <TabsContent value="domains" className="text-body text-fg-muted">Send and receive from your own domain.</TabsContent> </Tabs> );}export function Full() { return ( <Tabs defaultValue="login" className="w-full max-w-86"> <TabsList full> <TabsTrigger value="login">Login</TabsTrigger> <TabsTrigger value="signup">Sign up</TabsTrigger> </TabsList> </Tabs> );}Source
"use client";import * as React from "react";import { Tabs as TabsPrimitive } from "radix-ui";import { cn } from "@/lib/utils";// The console's tabs (Email: Mailboxes, Contact rules, Custom domains; Login and Sign up): a 42px lilac track with// 10px corners and a 2px inset, 38px tabs 8px apart with 9px of side padding and a 14px medium ink label. The selected// tab is a white key with 8px corners and Shadow/S. `full` stretches the tabs to share the track (Login, Sign up).// Switching is instant: tabs are used many times a day, and the white key moving would only slow the eye.function Tabs({ className, ...props }: React.ComponentProps<typeof TabsPrimitive.Root>) { return <TabsPrimitive.Root data-slot="tabs" className={cn("flex flex-col gap-4", className)} {...props} />;}function TabsList({ className, full = false, ...props }: React.ComponentProps<typeof TabsPrimitive.List> & { full?: boolean }) { return ( <TabsPrimitive.List data-slot="tabs-list" data-full={full ? "true" : undefined} className={cn("inline-flex h-10.5 w-fit max-w-full items-center gap-2 overflow-x-auto rounded-panel bg-subtle p-0.5 [scrollbar-width:none]", full && "flex w-full", className)} {...props} /> );}function TabsTrigger({ className, ...props }: React.ComponentProps<typeof TabsPrimitive.Trigger>) { return ( <TabsPrimitive.Trigger data-slot="tabs-trigger" className={cn( "inline-flex h-9.5 shrink-0 items-center justify-center gap-2 rounded-control px-2.25 font-sans text-body leading-tight font-medium whitespace-nowrap text-fg outline-none transition-[background-color,box-shadow,color] duration-150 ease-out hover:text-fg-brand focus-visible:outline-2 focus-visible:-outline-offset-2 focus-visible:outline-focus-ring disabled:pointer-events-none disabled:text-fg-muted data-[state=active]:bg-surface data-[state=active]:shadow-s data-[state=active]:hover:text-fg motion-reduce:transition-none in-data-[full=true]:flex-1 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-5.5", className, )} {...props} /> );}function TabsContent({ className, ...props }: React.ComponentProps<typeof TabsPrimitive.Content>) { return <TabsPrimitive.Content data-slot="tabs-content" className={cn("min-w-0 outline-none focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-focus-ring", className)} {...props} />;}export { Tabs, TabsList, TabsTrigger, TabsContent };Reference: Figma 427:2715: Email, iMessage, Webhooks and Login tabs.