tree
kibo-ui-registry/treeFreeComponent
A composable tree component with animated expand/collapse and customizable nodes.
Live preview
live · rendered by the registry
Rendered by Kibo UI Registry on their own page — this is the component running, not a screenshot of it.Install it
npx shadcn@latest add https://www.kibo-ui.com/r/tree.jsonSource
1"use client";23import { ChevronRight, File, Folder, FolderOpen } from "lucide-react";4import { AnimatePresence, motion } from "motion/react";5import {6 type ComponentProps,7 createContext,8 type HTMLAttributes,9 type ReactNode,10 useCallback,11 useContext,12 useId,13 useState,14} from "react";15import { cn } from "@/lib/utils";1617type TreeContextType = {18 expandedIds: Set<string>;19 selectedIds: string[];20 toggleExpanded: (nodeId: string) => void;21 handleSelection: (nodeId: string, ctrlKey: boolean) => void;22 showLines?: boolean;23 showIcons?: boolean;24 selectable?: boolean;25 multiSelect?: boolean;26 indent?: number;27 animateExpand?: boolean;28};2930const TreeContext = createContext<TreeContextType | undefined>(undefined);3132const useTree = () => {33 const context = useContext(TreeContext);34 if (!context) {35 throw new Error("Tree components must be used within a TreeProvider");36 }37 return context;38};3940type TreeNodeContextType = {41 nodeId: string;42 level: number;43 isLast: boolean;44 parentPath: boolean[];45};4647const TreeNodeContext = createContext<TreeNodeContextType | undefined>(48 undefined49);5051const useTreeNode = () => {52 const context = useContext(TreeNodeContext);53 if (!context) {54 throw new Error("TreeNode components must be used within a TreeNode");55 }56 return context;57};5859export type TreeProviderProps = {60 children: ReactNode;61 defaultExpandedIds?: string[];62 showLines?: boolean;63 showIcons?: boolean;64 selectable?: boolean;65 multiSelect?: boolean;66 selectedIds?: string[];67 onSelectionChange?: (selectedIds: string[]) => void;68 indent?: number;69 animateExpand?: boolean;70 className?: string;71};7273export const TreeProvider = ({74 children,75 defaultExpandedIds = [],76 showLines = true,77 showIcons = true,78 selectable = true,79 multiSelect = false,80 selectedIds,81 onSelectionChange,82 indent = 20,83 animateExpand = true,84 className,85}: TreeProviderProps) => {86 const [expandedIds, setExpandedIds] = useState<Set<string>>(87 new Set(defaultExpandedIds)88 );89 const [internalSelectedIds, setInternalSelectedIds] = useState<string[]>(90 selectedIds ?? []91 );9293 const isControlled =94 selectedIds !== undefined && onSelectionChange !== undefined;95 const currentSelectedIds = isControlled ? selectedIds : internalSelectedIds;9697 const toggleExpanded = useCallback((nodeId: string) => {98 setExpandedIds((prev) => {99 const newSet = new Set(prev);100 if (newSet.has(nodeId)) {101 newSet.delete(nodeId);102// … truncated
What it pulls in
npm packages
Files it writes
More from Kibo UI Registry
All 41 items| Component | Registry | Kind | Access | Installs | Command |
|---|---|---|---|---|---|
| announcementannouncement | Kibo UI Registry | Components | Free | no deps | |
| avatar-stackavatar-stack | Kibo UI Registry | Components | Free | no deps | |
| bannerbanner | Kibo UI Registry | Components | Free | 2 deps | |
| calendarcalendar | Kibo UI Registry | Components | Free | 3 deps | |
| choiceboxchoicebox | Kibo UI Registry | Components | Free | 2 deps | |
| code-blockcode-block | Kibo UI Registry | Components | Free | 5 deps · 2 files | |
| color-pickercolor-picker | Kibo UI Registry | Components | Free | 3 deps | |
| comboboxcombobox | Kibo UI Registry | Components | Free | 2 deps |
