Dashboard frame
Fold the sidebar with the header’s button; on the rail, entries name themselves in a tooltip, Billing shows its pages beside its icon, and the organization and account menus show their pictures alone. The other apps open in a new tab. Below lg the menu button opens the drawer.
Skip to content
Contacts
Contacts
Everyone your agents talked to.
import { ChatsIcon, GearSixIcon, HourglassIcon, MagnifyingGlassIcon, MegaphoneIcon, ReceiptIcon, RobotIcon, SquaresFourIcon, UserCircleIcon, UsersIcon, UsersThreeIcon } from '@phosphor-icons/react';
import { useState } from 'react';
import { AccountMenu, AppShell, Button, ColorSchemeSubmenu, LanguageSubmenu, MenuItem, MenuSeparator, OrganizationMenu, PageContainer, PageDescription, PageHeader, PageTitle, productIcon } from '@arbol-ai/ui';
import type { ColorScheme, NavigationGroup } from '@arbol-ai/ui';
const NAVIGATION: NavigationGroup[] = [
{
items: [
{ label: 'Overview', href: '#/app-shell', icon: SquaresFourIcon },
{ label: 'Conversations', href: '#/app-shell/conversations', icon: ChatsIcon },
{ label: 'Contacts', href: '#/app-shell/contacts', icon: UsersIcon },
{ label: 'Agents', href: '#/app-shell/agents', icon: RobotIcon },
{ label: 'Campaigns', href: '#/app-shell/campaigns', icon: MegaphoneIcon },
{ label: 'Waiting list', href: '#/app-shell/waitlist', icon: HourglassIcon, badge: 3 },
],
},
{
label: 'Administration',
items: [
{ label: 'Team', href: '#/app-shell/team', icon: UsersThreeIcon },
{
label: 'Billing',
href: '#/app-shell/billing',
icon: ReceiptIcon,
pages: [
{ label: 'Summary', href: '#/app-shell/billing' },
{ label: 'Invoices', href: '#/app-shell/billing/invoices' },
],
},
],
},
{
label: 'Applications',
items: [
{ label: 'Agenda', href: 'https://agenda.example.com', icon: productIcon('agenda'), target: '_blank' },
{ label: 'Ámbar', href: 'https://ambar.example.com', icon: productIcon('ambar'), target: '_blank' },
],
},
];
const LANGUAGES = [
{ label: 'English', value: 'en' },
{ label: 'Español', value: 'es' },
] as const;
const DashboardFrame = () => {
const [isCollapsed, setIsCollapsed] = useState(false);
const [colorScheme, setColorScheme] = useState<ColorScheme>('system');
const [language, setLanguage] = useState<'en' | 'es'>('en');
return (
<AppShell
accountMenu={
<AccountMenu email="ana.ruiz@example.com" name="Ana Ruiz" onSignOut={() => undefined}>
<MenuItem href="#/app-shell/profile" icon={<UserCircleIcon />}>
Profile
</MenuItem>
<MenuSeparator />
<ColorSchemeSubmenu onChange={setColorScheme} value={colorScheme} />
<LanguageSubmenu onChange={setLanguage} options={LANGUAGES} value={language} />
</AccountMenu>
}
className="rounded-card h-[520px] overflow-hidden border"
currentPath="#/app-shell/contacts"
header={<span className="truncate text-sm">Contacts</span>}
headerActions={
<Button aria-label="Search" size="icon" variant="ghost">
<MagnifyingGlassIcon aria-hidden />
</Button>
}
isCollapsed={isCollapsed}
navigation={NAVIGATION}
onCollapsedChange={setIsCollapsed}
organizationSwitcher={
<OrganizationMenu name="Clínica Norte" onSwitch={() => undefined}>
<MenuItem href="#/app-shell/settings" icon={<GearSixIcon />}>
Settings
</MenuItem>
</OrganizationMenu>
}
secondaryNavigation={[{ label: 'Settings', href: '#/app-shell/settings', icon: GearSixIcon }]}
>
<PageContainer>
<PageHeader>
<div>
<PageTitle>Contacts</PageTitle>
<PageDescription>Everyone your agents talked to.</PageDescription>
</div>
</PageHeader>
</PageContainer>
</AppShell>
);
};
<DashboardFrame />Source
The examples above are src/components/app-shell/app-shell.examples.tsx, which the library’s tests render too.