{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "sidebar-02",
  "title": "Sidebar 02",
  "type": "registry:block",
  "files": [
    {
      "path": "packages/registry-react/blocks/sidebar-02/Sidebar02.tsx",
      "content": "'use client'\n\nimport { BookOpen, Bot, Frame, LifeBuoy, Map, PieChart, Send, Settings2, SquareTerminal } from 'lucide-react'\nimport { Sidebar, SidebarContent, SidebarFooter, SidebarHeader, SidebarRail } from '@/components/ui/sidebar'\nimport { NavMain } from './NavMain'\nimport { NavProjects } from './NavProjects'\nimport { NavSecondary } from './NavSecondary'\nimport { NavUser } from './NavUser'\nimport { TeamSwitcher } from './TeamSwitcher'\n\nconst data = {\n  user: {\n    name: 'shadcn',\n    email: 'm@example.com',\n  },\n  navMain: [\n    {\n      title: 'Playground',\n      url: '#',\n      icon: SquareTerminal,\n      isActive: true,\n      items: [\n        { title: 'History', url: '#' },\n        { title: 'Starred', url: '#' },\n        { title: 'Settings', url: '#' },\n      ],\n    },\n    {\n      title: 'Models',\n      url: '#',\n      icon: Bot,\n      items: [\n        { title: 'Genesis', url: '#' },\n        { title: 'Explorer', url: '#' },\n        { title: 'Quantum', url: '#' },\n      ],\n    },\n    {\n      title: 'Documentation',\n      url: '#',\n      icon: BookOpen,\n      items: [\n        { title: 'Introduction', url: '#' },\n        { title: 'Get Started', url: '#' },\n        { title: 'Tutorials', url: '#' },\n        { title: 'Changelog', url: '#' },\n      ],\n    },\n    {\n      title: 'Settings',\n      url: '#',\n      icon: Settings2,\n      items: [\n        { title: 'General', url: '#' },\n        { title: 'Team', url: '#' },\n        { title: 'Billing', url: '#' },\n        { title: 'Limits', url: '#' },\n      ],\n    },\n  ],\n  navSecondary: [\n    { title: 'Support', url: '#', icon: LifeBuoy },\n    { title: 'Feedback', url: '#', icon: Send },\n  ],\n  projects: [\n    { name: 'Design Engineering', url: '#', icon: Frame },\n    { name: 'Sales & Marketing', url: '#', icon: PieChart },\n    { name: 'Travel', url: '#', icon: Map },\n  ],\n}\n\nexport function Sidebar02() {\n  return (\n    <Sidebar collapsible=\"icon\">\n      <SidebarHeader>\n        <TeamSwitcher />\n      </SidebarHeader>\n      <SidebarContent>\n        <NavMain items={data.navMain} />\n        <NavProjects projects={data.projects} />\n        <NavSecondary items={data.navSecondary} className=\"mt-auto\" />\n      </SidebarContent>\n      <SidebarFooter>\n        <NavUser user={data.user} />\n      </SidebarFooter>\n      <SidebarRail />\n    </Sidebar>\n  )\n}\n",
      "type": "registry:block",
      "target": "~/components/blocks/sidebar-02/Sidebar02.tsx"
    },
    {
      "path": "packages/registry-react/blocks/sidebar-02/TeamSwitcher.tsx",
      "content": "'use client'\n\n// Edit teams + activeTeam below to match your tenant model. The dropdown\n// is the full team switcher pattern -- avatar tile, label, kbd shortcut,\n// and a \"Add team\" footer row. Wire setActive() to your tenant API.\n\nimport * as React from 'react'\nimport { AudioWaveform, Check, ChevronsUpDown, Command, Plus, type LucideIcon } from 'lucide-react'\nimport {\n  DropdownMenu,\n  DropdownMenuContent,\n  DropdownMenuItem,\n  DropdownMenuLabel,\n  DropdownMenuSeparator,\n  DropdownMenuShortcut,\n  DropdownMenuTrigger,\n} from '@/components/ui/dropdown-menu'\nimport { SidebarMenu, SidebarMenuButton, SidebarMenuItem, useSidebar } from '@/components/ui/sidebar'\n\n// 4-quadrant uipkge logo. Inline component so it can sit next to Lucide\n// icons in the teams array without an extra file.\nconst UipkgeMark = ({ className }: { className?: string }) => (\n  <svg viewBox=\"0 0 24 24\" className={className} fill=\"currentColor\" aria-hidden=\"true\">\n    <rect x=\"2\" y=\"2\" width=\"9\" height=\"9\" rx=\"1.5\" />\n    <rect x=\"13\" y=\"2\" width=\"9\" height=\"9\" rx=\"1.5\" opacity=\"0.55\" />\n    <rect x=\"2\" y=\"13\" width=\"9\" height=\"9\" rx=\"1.5\" opacity=\"0.55\" />\n    <rect x=\"13\" y=\"13\" width=\"9\" height=\"9\" rx=\"1.5\" />\n  </svg>\n)\n\ntype Team = {\n  name: string\n  logo: LucideIcon | ((props: { className?: string }) => React.ReactElement)\n  plan: string\n}\n\nconst teams: Team[] = [\n  { name: 'uipkge', logo: UipkgeMark, plan: 'UI registry' },\n  { name: 'uipkge HRMS', logo: AudioWaveform, plan: 'Vertical' },\n  { name: 'uipkge Hospital', logo: Command, plan: 'Vertical' },\n]\n\nexport function TeamSwitcher() {\n  const { isMobile } = useSidebar()\n  const [activeTeam, setActiveTeam] = React.useState<Team>(teams[0]!)\n  const ActiveLogo = activeTeam.logo\n\n  return (\n    <SidebarMenu>\n      <SidebarMenuItem>\n        <DropdownMenu>\n          <DropdownMenuTrigger asChild>\n            <SidebarMenuButton\n              size=\"lg\"\n              className=\"data-[state=open]:bg-sidebar-accent data-[state=open]:text-sidebar-accent-foreground group-data-[collapsible=icon]:!justify-center\"\n            >\n              <div className=\"bg-sidebar-primary text-sidebar-primary-foreground flex aspect-square size-8 shrink-0 items-center justify-center rounded-lg group-data-[collapsible=icon]:size-6\">\n                <ActiveLogo className=\"size-4 group-data-[collapsible=icon]:size-3.5\" />\n              </div>\n              <div className=\"grid flex-1 text-left text-sm leading-tight group-data-[collapsible=icon]:hidden\">\n                <span className=\"font-display truncate font-bold\">{activeTeam.name}</span>\n                <span className=\"text-muted-foreground truncate text-xs\">{activeTeam.plan}</span>\n              </div>\n              <ChevronsUpDown className=\"ml-auto size-4 group-data-[collapsible=icon]:hidden\" />\n            </SidebarMenuButton>\n          </DropdownMenuTrigger>\n          <DropdownMenuContent\n            className=\"w-(--radix-dropdown-menu-trigger-width) min-w-56 rounded-lg\"\n            side={isMobile ? 'bottom' : 'right'}\n            align=\"start\"\n            sideOffset={4}\n          >\n            <DropdownMenuLabel className=\"text-muted-foreground text-xs\">Teams</DropdownMenuLabel>\n            {teams.map((team, i) => {\n              const Logo = team.logo\n              return (\n                <DropdownMenuItem key={team.name} className=\"gap-2 p-2\" onSelect={() => setActiveTeam(team)}>\n                  <div className=\"flex size-6 items-center justify-center rounded-sm border\">\n                    <Logo className=\"size-3.5 shrink-0\" />\n                  </div>\n                  {team.name}\n                  {activeTeam === team ? (\n                    <Check className=\"ml-auto size-4\" />\n                  ) : (\n                    <DropdownMenuShortcut>⌘{i + 1}</DropdownMenuShortcut>\n                  )}\n                </DropdownMenuItem>\n              )\n            })}\n            <DropdownMenuSeparator />\n            <DropdownMenuItem className=\"gap-2 p-2\">\n              <div className=\"bg-background flex size-6 items-center justify-center rounded-md border\">\n                <Plus className=\"size-4\" />\n              </div>\n              <div className=\"text-muted-foreground font-medium\">Add team</div>\n            </DropdownMenuItem>\n          </DropdownMenuContent>\n        </DropdownMenu>\n      </SidebarMenuItem>\n    </SidebarMenu>\n  )\n}\n",
      "type": "registry:block",
      "target": "~/components/blocks/sidebar-02/TeamSwitcher.tsx"
    },
    {
      "path": "packages/registry-react/blocks/sidebar-02/NavMain.tsx",
      "content": "'use client'\n\nimport { ChevronRight, type LucideIcon } from 'lucide-react'\nimport { Collapsible, CollapsibleContent, CollapsibleTrigger } from '@/components/ui/collapsible'\nimport {\n  SidebarGroup,\n  SidebarGroupLabel,\n  SidebarMenu,\n  SidebarMenuAction,\n  SidebarMenuButton,\n  SidebarMenuItem,\n  SidebarMenuSub,\n  SidebarMenuSubButton,\n  SidebarMenuSubItem,\n} from '@/components/ui/sidebar'\n\nexport interface NavMainProps {\n  items: {\n    title: string\n    url: string\n    icon: LucideIcon\n    isActive?: boolean\n    items?: {\n      title: string\n      url: string\n      isActive?: boolean\n    }[]\n  }[]\n}\n\nexport function NavMain({ items }: NavMainProps) {\n  return (\n    <SidebarGroup>\n      <SidebarGroupLabel>Platform</SidebarGroupLabel>\n      <SidebarMenu>\n        {items.map((item) => (\n          <Collapsible key={item.title} asChild defaultOpen={item.isActive}>\n            <SidebarMenuItem>\n              <SidebarMenuButton asChild tooltip={item.title} isActive={item.isActive}>\n                <a href={item.url}>\n                  <item.icon />\n                  <span>{item.title}</span>\n                </a>\n              </SidebarMenuButton>\n              {item.items?.length ? (\n                <>\n                  <CollapsibleTrigger asChild>\n                    <SidebarMenuAction className=\"data-[state=open]:rotate-90\">\n                      <ChevronRight />\n                      <span className=\"sr-only\">Toggle</span>\n                    </SidebarMenuAction>\n                  </CollapsibleTrigger>\n                  <CollapsibleContent>\n                    <SidebarMenuSub>\n                      {item.items.map((subItem) => (\n                        <SidebarMenuSubItem key={subItem.title}>\n                          <SidebarMenuSubButton asChild isActive={subItem.isActive}>\n                            <a href={subItem.url}>\n                              <span>{subItem.title}</span>\n                            </a>\n                          </SidebarMenuSubButton>\n                        </SidebarMenuSubItem>\n                      ))}\n                    </SidebarMenuSub>\n                  </CollapsibleContent>\n                </>\n              ) : null}\n            </SidebarMenuItem>\n          </Collapsible>\n        ))}\n      </SidebarMenu>\n    </SidebarGroup>\n  )\n}\n",
      "type": "registry:block",
      "target": "~/components/blocks/sidebar-02/NavMain.tsx"
    },
    {
      "path": "packages/registry-react/blocks/sidebar-02/NavProjects.tsx",
      "content": "'use client'\n\nimport { Folder, Forward, MoreHorizontal, Trash2, type LucideIcon } from 'lucide-react'\nimport {\n  DropdownMenu,\n  DropdownMenuContent,\n  DropdownMenuItem,\n  DropdownMenuSeparator,\n  DropdownMenuTrigger,\n} from '@/components/ui/dropdown-menu'\nimport {\n  SidebarGroup,\n  SidebarGroupLabel,\n  SidebarMenu,\n  SidebarMenuAction,\n  SidebarMenuButton,\n  SidebarMenuItem,\n  useSidebar,\n} from '@/components/ui/sidebar'\n\nexport interface NavProjectsProps {\n  projects: {\n    name: string\n    url: string\n    icon: LucideIcon\n  }[]\n}\n\nexport function NavProjects({ projects }: NavProjectsProps) {\n  const { isMobile } = useSidebar()\n\n  return (\n    // Upstream shadcn-ui hides this entire group on icon-mode collapse\n    // with `group-data-[collapsible=icon]:hidden`. We keep it visible so\n    // the project icons stay reachable in the narrow column; the\n    // SidebarGroupLabel below and the `<span>` children of each\n    // SidebarMenuButton already self-hide on collapse, leaving an\n    // icon-only column that lines up with NavMain.\n    <SidebarGroup>\n      <SidebarGroupLabel>Projects</SidebarGroupLabel>\n      <SidebarMenu>\n        {projects.map((item) => (\n          <SidebarMenuItem key={item.name}>\n            <SidebarMenuButton asChild>\n              <a href={item.url}>\n                <item.icon />\n                <span>{item.name}</span>\n              </a>\n            </SidebarMenuButton>\n            <DropdownMenu>\n              <DropdownMenuTrigger asChild>\n                <SidebarMenuAction showOnHover>\n                  <MoreHorizontal />\n                  <span className=\"sr-only\">More</span>\n                </SidebarMenuAction>\n              </DropdownMenuTrigger>\n              <DropdownMenuContent\n                className=\"w-48 rounded-lg\"\n                side={isMobile ? 'bottom' : 'right'}\n                align={isMobile ? 'end' : 'start'}\n              >\n                <DropdownMenuItem>\n                  <Folder className=\"text-muted-foreground\" />\n                  <span>View Project</span>\n                </DropdownMenuItem>\n                <DropdownMenuItem>\n                  <Forward className=\"text-muted-foreground\" />\n                  <span>Share Project</span>\n                </DropdownMenuItem>\n                <DropdownMenuSeparator />\n                <DropdownMenuItem>\n                  <Trash2 className=\"text-muted-foreground\" />\n                  <span>Delete Project</span>\n                </DropdownMenuItem>\n              </DropdownMenuContent>\n            </DropdownMenu>\n          </SidebarMenuItem>\n        ))}\n        <SidebarMenuItem>\n          <SidebarMenuButton>\n            <MoreHorizontal />\n            <span>More</span>\n          </SidebarMenuButton>\n        </SidebarMenuItem>\n      </SidebarMenu>\n    </SidebarGroup>\n  )\n}\n",
      "type": "registry:block",
      "target": "~/components/blocks/sidebar-02/NavProjects.tsx"
    },
    {
      "path": "packages/registry-react/blocks/sidebar-02/NavSecondary.tsx",
      "content": "'use client'\n\nimport * as React from 'react'\nimport { type LucideIcon } from 'lucide-react'\nimport {\n  SidebarGroup,\n  SidebarGroupContent,\n  SidebarMenu,\n  SidebarMenuButton,\n  SidebarMenuItem,\n} from '@/components/ui/sidebar'\n\nexport interface NavSecondaryProps extends React.ComponentProps<typeof SidebarGroup> {\n  items: {\n    title: string\n    url: string\n    icon: LucideIcon\n    isActive?: boolean\n  }[]\n}\n\nexport function NavSecondary({ items, ...props }: NavSecondaryProps) {\n  return (\n    <SidebarGroup {...props}>\n      <SidebarGroupContent>\n        <SidebarMenu>\n          {items.map((item) => (\n            <SidebarMenuItem key={item.title}>\n              <SidebarMenuButton asChild size=\"sm\" isActive={item.isActive}>\n                <a href={item.url}>\n                  <item.icon />\n                  <span>{item.title}</span>\n                </a>\n              </SidebarMenuButton>\n            </SidebarMenuItem>\n          ))}\n        </SidebarMenu>\n      </SidebarGroupContent>\n    </SidebarGroup>\n  )\n}\n",
      "type": "registry:block",
      "target": "~/components/blocks/sidebar-02/NavSecondary.tsx"
    },
    {
      "path": "packages/registry-react/blocks/sidebar-02/NavUser.tsx",
      "content": "'use client'\n\nimport * as React from 'react'\nimport {\n  BadgeCheck,\n  Bell,\n  ChevronsUpDown,\n  CreditCard,\n  LogOut,\n  Monitor,\n  Moon,\n  Palette,\n  Sparkles,\n  Sun,\n} from 'lucide-react'\nimport { useTheme } from '@/lib/use-theme'\nimport { Avatar, AvatarFallback } from '@/components/ui/avatar'\nimport {\n  DropdownMenu,\n  DropdownMenuContent,\n  DropdownMenuGroup,\n  DropdownMenuItem,\n  DropdownMenuLabel,\n  DropdownMenuRadioGroup,\n  DropdownMenuRadioItem,\n  DropdownMenuSeparator,\n  DropdownMenuSub,\n  DropdownMenuSubContent,\n  DropdownMenuSubTrigger,\n  DropdownMenuTrigger,\n} from '@/components/ui/dropdown-menu'\nimport { SidebarMenu, SidebarMenuButton, SidebarMenuItem, useSidebar } from '@/components/ui/sidebar'\n\nexport interface NavUserProps {\n  user: {\n    name: string\n    email: string\n  }\n}\n\nexport function NavUser({ user }: NavUserProps) {\n  const { isMobile } = useSidebar()\n  const { theme, setTheme } = useTheme()\n\n  const initials = React.useMemo(() => {\n    const parts = user.name.trim().split(/\\s+/).slice(0, 2)\n    return parts.map((p) => p[0]?.toUpperCase()).join('') || 'U'\n  }, [user.name])\n\n  return (\n    <SidebarMenu>\n      <SidebarMenuItem>\n        <DropdownMenu>\n          <DropdownMenuTrigger asChild>\n            <SidebarMenuButton\n              size=\"lg\"\n              className=\"data-[state=open]:bg-sidebar-accent data-[state=open]:text-sidebar-accent-foreground group-data-[collapsible=icon]:!justify-center\"\n            >\n              <Avatar className=\"h-8 w-8 shrink-0 rounded-lg group-data-[collapsible=icon]:size-6\">\n                <AvatarFallback className=\"rounded-lg text-xs group-data-[collapsible=icon]:text-[10px]\">\n                  {initials}\n                </AvatarFallback>\n              </Avatar>\n              <div className=\"grid flex-1 text-left text-sm leading-tight group-data-[collapsible=icon]:hidden\">\n                <span className=\"truncate font-medium\">{user.name}</span>\n                <span className=\"truncate text-xs\">{user.email}</span>\n              </div>\n              <ChevronsUpDown className=\"ml-auto size-4 group-data-[collapsible=icon]:hidden\" />\n            </SidebarMenuButton>\n          </DropdownMenuTrigger>\n          <DropdownMenuContent\n            className=\"w-(--radix-dropdown-menu-trigger-width) min-w-56 rounded-lg\"\n            side={isMobile ? 'bottom' : 'right'}\n            align=\"end\"\n            sideOffset={4}\n          >\n            <DropdownMenuLabel className=\"p-0 font-normal\">\n              <div className=\"flex items-center gap-2 px-1 py-1.5 text-left text-sm\">\n                <Avatar className=\"h-8 w-8 rounded-lg\">\n                  <AvatarFallback className=\"rounded-lg text-xs\">{initials}</AvatarFallback>\n                </Avatar>\n                <div className=\"grid flex-1 text-left text-sm leading-tight\">\n                  <span className=\"truncate font-semibold\">{user.name}</span>\n                  <span className=\"truncate text-xs\">{user.email}</span>\n                </div>\n              </div>\n            </DropdownMenuLabel>\n            <DropdownMenuSeparator />\n            <DropdownMenuGroup>\n              <DropdownMenuItem>\n                <Sparkles />\n                Upgrade to Pro\n              </DropdownMenuItem>\n            </DropdownMenuGroup>\n            <DropdownMenuSeparator />\n            <DropdownMenuGroup>\n              <DropdownMenuItem>\n                <BadgeCheck />\n                Account\n              </DropdownMenuItem>\n              <DropdownMenuItem>\n                <CreditCard />\n                Billing\n              </DropdownMenuItem>\n              <DropdownMenuItem>\n                <Bell />\n                Notifications\n              </DropdownMenuItem>\n            </DropdownMenuGroup>\n            <DropdownMenuSeparator />\n            <DropdownMenuSub>\n              <DropdownMenuSubTrigger>\n                <Palette />\n                Theme\n                <span className=\"text-muted-foreground ml-auto text-xs capitalize\">{theme}</span>\n              </DropdownMenuSubTrigger>\n              <DropdownMenuSubContent className=\"min-w-36\">\n                <DropdownMenuRadioGroup value={theme} onValueChange={(v) => setTheme(v)}>\n                  <DropdownMenuRadioItem value=\"light\">\n                    <Sun /> Light\n                  </DropdownMenuRadioItem>\n                  <DropdownMenuRadioItem value=\"dark\">\n                    <Moon /> Dark\n                  </DropdownMenuRadioItem>\n                  <DropdownMenuRadioItem value=\"system\">\n                    <Monitor /> System\n                  </DropdownMenuRadioItem>\n                </DropdownMenuRadioGroup>\n              </DropdownMenuSubContent>\n            </DropdownMenuSub>\n            <DropdownMenuSeparator />\n            <DropdownMenuItem>\n              <LogOut />\n              Log out\n            </DropdownMenuItem>\n          </DropdownMenuContent>\n        </DropdownMenu>\n      </SidebarMenuItem>\n    </SidebarMenu>\n  )\n}\n",
      "type": "registry:block",
      "target": "~/components/blocks/sidebar-02/NavUser.tsx"
    },
    {
      "path": "packages/registry-react/blocks/sidebar-02/page.tsx",
      "content": "// Demo page wired by `npx shadcn@latest add https://uipkge.dev/r/react/sidebar-02.json`.\n// Visit /sidebar-02-demo after install to see the block without\n// editing your own pages. Free to edit or delete me.\nimport { Sidebar02 } from '@/components/blocks/sidebar-02/Sidebar02'\nimport { SidebarInset, SidebarProvider, SidebarTrigger } from '@/components/ui/sidebar'\n\nexport default function Page() {\n  return (\n    <SidebarProvider>\n      <Sidebar02 />\n      <SidebarInset>\n        <header className=\"border-border flex h-14 shrink-0 items-center gap-3 border-b px-4\">\n          <SidebarTrigger className=\"size-7\" />\n          <h1 className=\"text-sm font-semibold\">sidebar-02 demo</h1>\n        </header>\n        <div className=\"flex-1 p-6\">\n          <div className=\"grid auto-rows-min gap-4 md:grid-cols-3\">\n            <div className=\"bg-muted/50 aspect-video rounded-xl\" />\n            <div className=\"bg-muted/50 aspect-video rounded-xl\" />\n            <div className=\"bg-muted/50 aspect-video rounded-xl\" />\n          </div>\n          <div className=\"bg-muted/50 mt-4 min-h-[60vh] rounded-xl\" />\n        </div>\n      </SidebarInset>\n    </SidebarProvider>\n  )\n}",
      "type": "registry:block",
      "target": "~/app/sidebar-02-demo/page.tsx"
    }
  ],
  "dependencies": [
    "lucide-react"
  ],
  "devDependencies": [],
  "registryDependencies": [
    "https://uipkge.dev/r/react/sidebar.json",
    "https://uipkge.dev/r/react/avatar.json",
    "https://uipkge.dev/r/react/collapsible.json",
    "https://uipkge.dev/r/react/dropdown-menu.json",
    "https://uipkge.dev/r/react/use-theme.json"
  ],
  "description": "Full-featured app sidebar -- collapsible=\"icon\" rail with TeamSwitcher header, primary nav, projects section, secondary nav, and user dropdown footer. Each section ships as a sibling file in the same folder so consumers can edit one piece at a time.",
  "categories": [
    "sidebar",
    "layout"
  ]
}