@arbidocs/blocks 0.4.8 → 0.4.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (67) hide show
  1. package/dist/agents/index.cjs +159 -159
  2. package/dist/agents/index.js +2 -2
  3. package/dist/chat/AssistantToaster.d.ts +8 -0
  4. package/dist/chat/index.cjs +68 -62
  5. package/dist/chat/index.d.ts +1 -0
  6. package/dist/chat/index.js +3 -1
  7. package/dist/{chunk-MGUHR3JI.cjs → chunk-22T6KHGB.cjs} +10 -2
  8. package/dist/chunk-22T6KHGB.cjs.map +1 -0
  9. package/dist/chunk-5LUI4G5R.js +34 -0
  10. package/dist/chunk-5LUI4G5R.js.map +1 -0
  11. package/dist/{chunk-SY7UURF7.cjs → chunk-67HGXV4I.cjs} +3 -3
  12. package/dist/{chunk-SY7UURF7.cjs.map → chunk-67HGXV4I.cjs.map} +1 -1
  13. package/dist/{chunk-YP264PVL.js → chunk-CVFBSUXL.js} +3 -3
  14. package/dist/{chunk-YP264PVL.js.map → chunk-CVFBSUXL.js.map} +1 -1
  15. package/dist/{chunk-LRUCMZK6.cjs → chunk-D6XY3C4O.cjs} +4 -15
  16. package/dist/chunk-D6XY3C4O.cjs.map +1 -0
  17. package/dist/chunk-FX3K6LNZ.cjs +47 -0
  18. package/dist/chunk-FX3K6LNZ.cjs.map +1 -0
  19. package/dist/{chunk-QXEJXIP4.js → chunk-H7OD4CHN.js} +5 -16
  20. package/dist/chunk-H7OD4CHN.js.map +1 -0
  21. package/dist/{chunk-7OCFHEE6.js → chunk-IMA6I73C.js} +10 -3
  22. package/dist/chunk-IMA6I73C.js.map +1 -0
  23. package/dist/{chunk-QMDLPO3M.cjs → chunk-LXC5PTTI.cjs} +2 -2
  24. package/dist/{chunk-QMDLPO3M.cjs.map → chunk-LXC5PTTI.cjs.map} +1 -1
  25. package/dist/{chunk-G2E3O3HI.js → chunk-OJSWQM4G.js} +158 -5
  26. package/dist/chunk-OJSWQM4G.js.map +1 -0
  27. package/dist/{chunk-JG4TFS3Z.cjs → chunk-RGHQFJOL.cjs} +160 -2
  28. package/dist/chunk-RGHQFJOL.cjs.map +1 -0
  29. package/dist/chunk-SLSBJRWW.js +41 -0
  30. package/dist/chunk-SLSBJRWW.js.map +1 -0
  31. package/dist/chunk-TO4FAMQP.cjs +37 -0
  32. package/dist/chunk-TO4FAMQP.cjs.map +1 -0
  33. package/dist/{chunk-EY2RJW27.js → chunk-ZJ6RIPFS.js} +2 -2
  34. package/dist/{chunk-EY2RJW27.js.map → chunk-ZJ6RIPFS.js.map} +1 -1
  35. package/dist/collaboration/contacts/ContactCard.d.ts +43 -0
  36. package/dist/collaboration/contacts/index.d.ts +2 -0
  37. package/dist/collaboration/contacts/vcard.d.ts +26 -0
  38. package/dist/collaboration/index.cjs +56 -36
  39. package/dist/collaboration/index.js +1 -1
  40. package/dist/facts/index.cjs +4 -3
  41. package/dist/facts/index.cjs.map +1 -1
  42. package/dist/facts/index.js +2 -1
  43. package/dist/facts/index.js.map +1 -1
  44. package/dist/files/index.cjs +7 -6
  45. package/dist/files/index.cjs.map +1 -1
  46. package/dist/files/index.js +3 -2
  47. package/dist/files/index.js.map +1 -1
  48. package/dist/index.cjs +353 -299
  49. package/dist/index.cjs.map +1 -1
  50. package/dist/index.js +7 -5
  51. package/dist/index.js.map +1 -1
  52. package/dist/lib/use-media-query.d.ts +32 -0
  53. package/dist/shell/Toaster.d.ts +28 -0
  54. package/dist/shell/index.cjs +72 -42
  55. package/dist/shell/index.d.ts +2 -0
  56. package/dist/shell/index.js +3 -1
  57. package/dist/workspaces/index.cjs +10 -3
  58. package/dist/workspaces/index.cjs.map +1 -1
  59. package/dist/workspaces/index.js +11 -4
  60. package/dist/workspaces/index.js.map +1 -1
  61. package/package.json +3 -3
  62. package/dist/chunk-7OCFHEE6.js.map +0 -1
  63. package/dist/chunk-G2E3O3HI.js.map +0 -1
  64. package/dist/chunk-JG4TFS3Z.cjs.map +0 -1
  65. package/dist/chunk-LRUCMZK6.cjs.map +0 -1
  66. package/dist/chunk-MGUHR3JI.cjs.map +0 -1
  67. package/dist/chunk-QXEJXIP4.js.map +0 -1
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/lib/useListKeyNav.ts","../src/chat/SlashMenu.tsx","../src/chat/PinnedDocChip.tsx","../src/chat/ConversationLayout.tsx","../src/chat/BranchControls.tsx","../src/chat/ModelPicker.tsx","../src/chat/ConversationParts.tsx","../src/chat/ThreadMap.tsx","../src/lib/useLongPaste.ts","../src/chat/PendingAnswerBar.tsx","../src/chat/ConversationSearchView.tsx","../src/chat/ContextPanel.tsx","../src/lib/useDismissibleCard.ts","../src/chat/LabelPinRow.tsx"],"names":["useState","useId","useEffect","useCallback","jsx","BookOpen","SquareSlash","memo","SlashMenu","useRef","jsxs","cn","testIdOr","prefixedTestId","Globe","Pin","X","Tooltip","TooltipTrigger","Network","TooltipContent","ArrowLeft","ArrowRight","Zap","Glasses","Crown","Sparkles","forwardRef","ModelPickerTrigger","Button","ChevronsUpDown","BlocksTooltipProvider","Popover","PopoverTrigger","PopoverContent","Check","Settings","Plus","Bot","Download","DOMPurify","useMemo","MessageCircleQuestion","Clock","Play","Pause","Fragment","User","Loader2","Search","MessageSquare","PassageCard","ContextPanelContent","HoverCardContent","CheckCircle","ContextSearchInput","Input","ContextActionButton","Badge","Tabs","TabsList","TabsTrigger","TabsContent","TagIcon"],"mappings":"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","file":"chunk-MGUHR3JI.cjs","sourcesContent":["import { useCallback, useEffect, useId, useState, type KeyboardEvent } from 'react'\n\n/** Id of the option at `index` in the listbox `listboxId`. Rows and the combobox agree on it. */\nexport function listOptionId(listboxId: string, index: number): string {\n return `${listboxId}-option-${index}`\n}\n\nexport interface UseListKeyNavOptions<T> {\n /** Whether the list is currently shown. Keys fall through when false. */\n open: boolean\n items: ReadonlyArray<T>\n /** Enter / Tab on the highlighted row. */\n onPick: (item: T) => void\n /** Escape. */\n onDismiss?: () => void\n /** Changing this resets the highlight to the first row (e.g. the filter query). */\n resetKey?: unknown\n}\n\n/** ARIA attributes that make the text field the combobox that owns the list. */\nexport interface ListComboboxProps {\n role: 'combobox'\n 'aria-autocomplete': 'list'\n 'aria-haspopup': 'listbox'\n 'aria-expanded': true\n 'aria-controls': string\n 'aria-activedescendant': string\n}\n\nexport interface UseListKeyNav {\n /** Pass to the list (`listboxId`) so the field's `aria-controls` points at it. */\n listboxId: string\n /**\n * Spread onto the text field (`<input>` or `<textarea>`). Empty while the list is closed, so a\n * prompt that is usually just a text box is not announced as a collapsed combobox; it becomes\n * the combobox (expanded, with its active option) the moment the list opens.\n */\n comboboxProps: ListComboboxProps | Record<string, never>\n selectedIndex: number\n setSelectedIndex: (index: number) => void\n /** Call first in the textarea `onKeyDown`. Returns true when the key was consumed. */\n handleKeyDown: (event: KeyboardEvent<HTMLElement>) => boolean\n}\n\n/**\n * Headless keyboard navigation for an autocomplete list that sits over a text field:\n * ArrowUp/ArrowDown wrap, Enter/Tab pick, Escape dismisses. Only consumes keys while open.\n */\nexport function useListKeyNav<T>({\n open,\n items,\n onPick,\n onDismiss,\n resetKey,\n}: UseListKeyNavOptions<T>): UseListKeyNav {\n const [selectedIndex, setSelectedIndex] = useState(0)\n const listboxId = useId()\n const isExpanded = open && items.length > 0\n\n useEffect(() => {\n setSelectedIndex(0)\n }, [resetKey, items.length])\n\n const handleKeyDown = useCallback(\n (event: KeyboardEvent<HTMLElement>): boolean => {\n if (!open || items.length === 0) return false\n switch (event.key) {\n case 'ArrowDown':\n event.preventDefault()\n setSelectedIndex((i) => (i + 1) % items.length)\n return true\n case 'ArrowUp':\n event.preventDefault()\n setSelectedIndex((i) => (i - 1 + items.length) % items.length)\n return true\n case 'Enter':\n case 'Tab': {\n event.preventDefault()\n const pick = items[selectedIndex] ?? items[0]\n if (pick !== undefined) onPick(pick)\n return true\n }\n case 'Escape':\n event.preventDefault()\n onDismiss?.()\n return true\n default:\n return false\n }\n },\n [open, items, selectedIndex, onPick, onDismiss]\n )\n\n const comboboxProps: UseListKeyNav['comboboxProps'] = isExpanded\n ? {\n role: 'combobox',\n 'aria-autocomplete': 'list',\n 'aria-haspopup': 'listbox',\n 'aria-expanded': true,\n 'aria-controls': listboxId,\n 'aria-activedescendant': listOptionId(listboxId, selectedIndex),\n }\n : {}\n\n return { listboxId, comboboxProps, selectedIndex, setSelectedIndex, handleKeyDown }\n}\n","import { memo, useEffect, useId, useRef } from 'react'\nimport { BookOpen, Globe, SquareSlash } from 'lucide-react'\nimport { cn } from '@arbidocs/react/ui'\nimport { listOptionId } from '../lib/useListKeyNav'\nimport { prefixedTestId, testIdOr } from './test-id'\n\n/** Which list an entry came from: drives the menu's section grouping. */\nexport type SlashItemKind = 'command' | 'skill'\n\nexport interface SlashMenuItem {\n /** Slug used to invoke the entry (`/<slug>`). */\n name: string\n description?: string\n /** `command` = shipped built-in; `skill` = user-authored. */\n kind: SlashItemKind\n /** Args hint, e.g. `<prompt>`. */\n argHint?: string\n /** Marketplace visibility: drives the \"Global\" affordance. Skills only. */\n visibility?: 'mine' | 'global'\n}\n\n/** Every fixed string of the slash menu. Pass a partial `labels` to translate or reword. */\nexport interface SlashMenuLabels {\n hint: string\n commands: string\n skills: string\n global: string\n globalTitle: string\n /** Accessible name of the list. */\n list: string\n /** Polite count announced as the menu opens or the filter narrows it. */\n resultCount: (count: number) => string\n /** Footer action that opens the skills browser. */\n browse: string\n}\n\nexport const DEFAULT_SLASH_MENU_LABELS: SlashMenuLabels = {\n hint: 'Enter or Tab to insert, Esc to dismiss',\n commands: 'Commands',\n skills: 'Skills',\n global: 'Global',\n globalTitle: 'Shared skill from the marketplace',\n list: 'Commands and skills',\n resultCount: (count) => `${count} ${count === 1 ? 'command' : 'commands'} available`,\n browse: 'Browse skills',\n}\n\nexport interface SlashMenuProps {\n open: boolean\n /** The chat composer sits at the bottom (menu above); a top-of-page ask pill opens below. */\n placement?: 'above' | 'below'\n /** Highlighted row, 0-based over the flat list. */\n selectedIndex: number\n setSelectedIndex: (i: number) => void\n /**\n * Id of the listbox. Take it (and `comboboxProps`) from `useListKeyNav` so the text field's\n * `aria-controls` / `aria-activedescendant` point at this menu.\n */\n listboxId?: string\n /** Filtered list, already ordered commands-then-skills. */\n items: SlashMenuItem[]\n /** Adds a \"Browse skills\" footer that calls this (the host opens its skills browser). */\n onBrowse?: () => void\n onSelect: (item: SlashMenuItem) => void\n className?: string\n labels?: Partial<SlashMenuLabels>\n /** Test id of the menu (default `slash-menu`). */\n testId?: string\n /** Row prefixes (`<prefix>-<kind|name>`); defaults `slash-section` / `slash-item`. */\n testIds?: Partial<Record<'section' | 'item' | 'browse', string>>\n}\n\nfunction SectionIcon({ kind }: { kind: SlashItemKind }) {\n return kind === 'skill' ? (\n <BookOpen className=\"h-3 w-3\" aria-hidden=\"true\" />\n ) : (\n <SquareSlash className=\"h-3 w-3\" aria-hidden=\"true\" />\n )\n}\n\n/**\n * Slash-command autocomplete that floats over a text field. Presentational: the host owns the\n * filter, the highlighted index (see `useListKeyNav`) and what selecting an item does.\n */\nexport const SlashMenu = memo(function SlashMenu({\n open,\n placement = 'above',\n selectedIndex,\n setSelectedIndex,\n listboxId: listboxIdProp,\n items,\n onBrowse,\n onSelect,\n className,\n labels,\n testId,\n testIds,\n}: SlashMenuProps) {\n const l = { ...DEFAULT_SLASH_MENU_LABELS, ...labels }\n const ownId = useId()\n const listboxId = listboxIdProp ?? ownId\n // Keep the keyboard-highlighted row visible. Rows are split across per-section lists, so the\n // flat `data-slash-index` is the stable handle.\n const scrollRef = useRef<HTMLDivElement>(null)\n useEffect(() => {\n if (!open) return\n const el = scrollRef.current?.querySelector<HTMLElement>(\n `[data-slash-index=\"${selectedIndex}\"]`\n )\n // jsdom has no scrollIntoView.\n el?.scrollIntoView?.({ block: 'nearest' })\n }, [open, selectedIndex])\n\n if (!open || items.length === 0) return null\n\n let offset = 0\n const SECTIONS: ReadonlyArray<{ kind: SlashItemKind; label: string }> = [\n { kind: 'command', label: l.commands },\n { kind: 'skill', label: l.skills },\n ]\n const sections = SECTIONS.map(({ kind, label }) => {\n const rows = items.filter((i) => i.kind === kind)\n const section = { kind, label, rows, offset }\n offset += rows.length\n return section\n }).filter((s) => s.rows.length > 0)\n\n return (\n <div\n data-slot=\"slash-menu\"\n className={cn(\n 'absolute left-0 right-0 z-30 max-h-64 overflow-hidden rounded-md border border-border bg-popover text-popover-foreground shadow-lg',\n placement === 'above' ? 'bottom-full mb-2' : 'top-full mt-2',\n className\n )}\n // mousedown would blur the textarea (closing the menu before the click lands).\n onMouseDown={(e) => e.preventDefault()}\n data-testid={testIdOr(testId, { testId: 'slash-menu' })}\n >\n <div className=\"border-b border-border/50 px-3 py-1.5 text-xs text-muted-foreground\">\n {l.hint}\n </div>\n <div className=\"sr-only\" role=\"status\" aria-live=\"polite\" aria-atomic=\"true\">\n {l.resultCount(items.length)}\n </div>\n <div\n ref={scrollRef}\n id={listboxId}\n role=\"listbox\"\n aria-label={l.list}\n className=\"scrollbar-subtle max-h-56 overflow-y-auto py-1\"\n >\n {sections.map((section) => (\n <div\n key={section.kind}\n role=\"group\"\n aria-labelledby={`${listboxId}-section-${section.kind}`}\n >\n <div\n id={`${listboxId}-section-${section.kind}`}\n className=\"flex items-center gap-1.5 px-3 pb-1 pt-1.5 text-xs font-medium text-muted-foreground\"\n data-testid={prefixedTestId(testIds?.section, section.kind, {\n testId: `slash-section-${section.kind}`,\n })}\n >\n <SectionIcon kind={section.kind} />\n <span>{section.label}</span>\n </div>\n {section.rows.map((item, idx) => {\n const flatIndex = section.offset + idx\n const isActive = flatIndex === selectedIndex\n return (\n <div\n key={item.name}\n id={listOptionId(listboxId, flatIndex)}\n role=\"option\"\n aria-selected={isActive}\n data-slash-index={flatIndex}\n className={cn(\n 'flex cursor-pointer items-baseline gap-2 px-3 py-1.5 text-sm pointer-coarse:min-h-11 pointer-coarse:items-center',\n isActive ? 'bg-accent text-accent-foreground' : 'hover:bg-accent/50'\n )}\n onMouseEnter={() => setSelectedIndex(flatIndex)}\n onClick={() => onSelect(item)}\n data-testid={prefixedTestId(testIds?.item, item.name, {\n testId: `slash-item-${item.name}`,\n })}\n >\n <span className=\"shrink-0 font-mono text-foreground\">/{item.name}</span>\n {item.argHint && (\n <span className=\"shrink-0 font-mono text-xs text-muted-foreground\">\n {item.argHint}\n </span>\n )}\n {item.description && (\n <span className=\"truncate text-xs text-muted-foreground\">\n {item.description}\n </span>\n )}\n {item.visibility === 'global' && (\n <span\n className=\"ml-auto inline-flex shrink-0 items-center gap-1 text-xs text-muted-foreground\"\n title={l.globalTitle}\n >\n <Globe className=\"h-3 w-3\" />\n {l.global}\n </span>\n )}\n </div>\n )\n })}\n </div>\n ))}\n </div>\n {onBrowse && (\n <button\n type=\"button\"\n onClick={onBrowse}\n className=\"flex w-full items-center gap-1.5 border-t border-border/50 px-3 py-1.5 text-left text-xs text-muted-foreground hover:bg-accent/50 pointer-coarse:min-h-11\"\n data-testid={testIdOr(testIds?.browse, { testId: 'slash-browse-skills' })}\n >\n <BookOpen className=\"h-3 w-3\" aria-hidden=\"true\" />\n {l.browse}\n </button>\n )}\n </div>\n )\n})\n","import { Pin, X } from 'lucide-react'\nimport { cn } from '@arbidocs/react/ui'\n\n/** Every fixed string of the chip. Pass a partial `labels` to translate or reword. */\nexport interface PinnedDocChipLabels {\n unpin: string\n /** Accessible name; `title` is the pinned document's name. */\n unpinDocument: (title: string) => string\n}\n\nexport const DEFAULT_PINNED_DOC_CHIP_LABELS: PinnedDocChipLabels = {\n unpin: 'Unpin',\n unpinDocument: (title) => `Unpin ${title}`,\n}\n\nexport interface PinnedDocChipProps {\n title: string\n onUnpin: () => void\n className?: string\n labels?: Partial<PinnedDocChipLabels>\n testId?: string\n}\n\n/**\n * The pinned-document chip that lives inside a composer's attach button: shows which document\n * holds the full-context pin and unpins it in ONE tap (the X is always visible, so touch and\n * keyboard reach it). It is a span with button semantics because it sits inside the attach\n * `<button>`, where nested buttons are invalid; `stopPropagation` keeps the tap from also\n * triggering the parent.\n */\nexport function PinnedDocChip({\n title,\n onUnpin,\n className,\n labels,\n testId = 'unpin-document-button',\n}: PinnedDocChipProps) {\n const l = { ...DEFAULT_PINNED_DOC_CHIP_LABELS, ...labels }\n return (\n <span\n role=\"button\"\n tabIndex={0}\n data-slot=\"pinned-doc-chip\"\n onClick={(e) => {\n e.stopPropagation()\n onUnpin()\n }}\n onKeyDown={(e) => {\n if (e.key === 'Enter' || e.key === ' ') {\n e.stopPropagation()\n onUnpin()\n }\n }}\n title={l.unpin}\n aria-label={l.unpinDocument(title)}\n className={cn(\n '-mx-0.5 flex min-w-0 items-center gap-1 rounded-sm px-1 text-foreground hover:bg-accent focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring',\n className\n )}\n data-testid={testId}\n >\n <Pin className=\"h-3 w-3 shrink-0 fill-primary\" />\n <X className=\"order-last h-3 w-3 shrink-0 text-muted-foreground\" />\n <span className=\"truncate text-sm\">{title}</span>\n </span>\n )\n}\n","import type { HTMLAttributes, ReactNode } from 'react'\nimport { cn } from '@arbidocs/react/ui'\n\n/** Every fixed string of the conversation layout. Pass a partial `labels` to reword. */\nexport interface ConversationLayoutLabels {\n loadingMessages: string\n}\n\nexport const DEFAULT_CONVERSATION_LAYOUT_LABELS: ConversationLayoutLabels = {\n loadingMessages: 'Loading messages...',\n}\n\n/**\n * Page frame of a conversation. The chat scroll surface belongs to the HOST (the outer\n * `[data-scroll-container]`), so this column must GROW with its content, not stay\n * viewport-capped: the sticky header and the sticky composer dock need a containing block that\n * spans the whole thread, otherwise `position: sticky` is clamped to one screen and both unpin.\n *\n * Do NOT put `overflow: clip/hidden`, `transform`, `filter`, `will-change` or `contain` on\n * {@link ConversationBody}: `overflow: clip` collapses the scrollHeight so the thread cannot\n * scroll, and a transform creates a containing block that breaks the dock's `bottom: 0`.\n */\nexport function ConversationRoot({\n className,\n children,\n testId = 'conversation',\n ...rest\n}: HTMLAttributes<HTMLDivElement> & { testId?: string }) {\n return (\n <div\n data-slot=\"conversation\"\n className={cn('flex min-h-full shrink-0 flex-col', className)}\n data-testid={testId}\n {...rest}\n >\n {children}\n </div>\n )\n}\n\n/** Sticky strip at the top (tabs and their actions). */\nexport function ConversationHeader({\n className,\n children,\n ...rest\n}: HTMLAttributes<HTMLDivElement>) {\n return (\n <div\n data-slot=\"conversation-header\"\n className={cn('sticky top-0 z-10 bg-background', className)}\n {...rest}\n >\n {children}\n </div>\n )\n}\n\n/** Grows (never shrinks) to the thread's full height so the sticky dock spans the scroll range. */\nexport function ConversationBody({ className, children, ...rest }: HTMLAttributes<HTMLDivElement>) {\n return (\n <div\n data-slot=\"conversation-body\"\n className={cn('flex flex-[1_0_auto] flex-col', className)}\n {...rest}\n >\n {children}\n </div>\n )\n}\n\n/** The thread (or its empty / loading state). `relative` so absolutely-filled states fit. */\nexport function ConversationMain({ className, children, ...rest }: HTMLAttributes<HTMLElement>) {\n return (\n <main\n data-slot=\"conversation-main\"\n className={cn('relative flex flex-[1_0_auto] flex-col', className)}\n {...rest}\n >\n {children}\n </main>\n )\n}\n\n/** Centered status while the thread loads. */\nexport function ConversationLoading({\n children,\n labels,\n className,\n testId = 'loading-messages',\n}: {\n /** Text; wins over `labels.loadingMessages`. */\n children?: ReactNode\n labels?: Partial<ConversationLayoutLabels>\n className?: string\n testId?: string\n}) {\n const l = { ...DEFAULT_CONVERSATION_LAYOUT_LABELS, ...labels }\n return (\n <div className={cn('flex h-64 items-center justify-center', className)} data-testid={testId}>\n <p className=\"text-muted-foreground\">{children ?? l.loadingMessages}</p>\n </div>\n )\n}\n\nexport const Conversation = {\n Root: ConversationRoot,\n Header: ConversationHeader,\n Body: ConversationBody,\n Main: ConversationMain,\n Loading: ConversationLoading,\n}\n","import { ArrowLeft, ArrowRight, Network } from 'lucide-react'\nimport { cn, Tooltip, TooltipContent, TooltipTrigger } from '@arbidocs/react/ui'\nimport { testIdOr } from './test-id'\n\n/** Every fixed string of the branch controls. Pass a partial `labels` to translate or reword. */\nexport interface BranchControlsLabels {\n /** \"Branch 2 of 3\" (1-based `current`). */\n branchOf: (current: number, total: number) => string\n previewHint: string\n previousBranch: string\n nextBranch: string\n}\n\nexport const DEFAULT_BRANCH_CONTROLS_LABELS: BranchControlsLabels = {\n branchOf: (current, total) => `Branch ${current} of ${total}`,\n previewHint: 'Click for side-by-side view',\n previousBranch: 'Previous branch',\n nextBranch: 'Next branch',\n}\n\nexport interface BranchControlsProps {\n /** 0-based index of the active branch. */\n index: number\n /** Number of branches at this fork; nothing renders when there is only one. */\n count: number\n onSwitch: (targetIndex: number) => void\n /** Makes the label a button that opens the side-by-side view. */\n onPreview?: () => void\n /** Tooltip of the preview button; wins over `labels.previewHint`. */\n previewHint?: string\n className?: string\n labels?: Partial<BranchControlsLabels>\n /** Per-part test ids; defaults are the current ids. */\n testIds?: Partial<{\n root: string\n preview: string\n icon: string\n indicator: string\n previous: string\n next: string\n }>\n}\n\nconst ARROW =\n 'rounded p-1 hover:bg-muted focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring disabled:cursor-not-allowed disabled:opacity-50 pointer-coarse:p-3'\n\n/** \"Branch 2 of 3\" with previous/next arrows at a fork in the conversation. */\nexport function BranchControls({\n index,\n count,\n onSwitch,\n onPreview,\n previewHint,\n className,\n labels,\n testIds,\n}: BranchControlsProps) {\n if (count <= 1) return null\n const l = { ...DEFAULT_BRANCH_CONTROLS_LABELS, ...labels }\n const label = l.branchOf(index + 1, count)\n const rootTestId = testIdOr(testIds?.root, { testId: 'branch-controls' })\n const previewTestId = testIdOr(testIds?.preview, { testId: 'threads-preview-button' })\n const iconTestId = testIdOr(testIds?.icon, { testId: 'branch-icon' })\n const indicatorTestId = testIdOr(testIds?.indicator, { testId: 'branch-indicator' })\n const previousTestId = testIdOr(testIds?.previous, { testId: 'previous-branch-button' })\n const nextTestId = testIdOr(testIds?.next, { testId: 'next-branch-button' })\n\n return (\n <div\n data-slot=\"branch-controls\"\n className={cn('branch-controls flex items-center gap-1', className)}\n data-testid={rootTestId}\n >\n {onPreview ? (\n <Tooltip>\n <TooltipTrigger asChild>\n <button\n type=\"button\"\n onClick={onPreview}\n className=\"flex items-center gap-1 rounded-md bg-muted px-2 py-1 transition-colors hover:bg-accent focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring pointer-coarse:min-h-11\"\n data-testid={previewTestId}\n >\n <Network size={12} className=\"text-primary\" data-testid={iconTestId} />\n <span\n className=\"text-sm font-medium text-muted-foreground\"\n data-testid={indicatorTestId}\n >\n {label}\n </span>\n </button>\n </TooltipTrigger>\n <TooltipContent>\n <p>{previewHint ?? l.previewHint}</p>\n </TooltipContent>\n </Tooltip>\n ) : (\n <span\n className=\"flex items-center gap-1 px-2 py-1 text-sm font-medium text-muted-foreground\"\n data-testid={indicatorTestId}\n >\n <Network size={12} className=\"text-primary\" data-testid={iconTestId} />\n {label}\n </span>\n )}\n\n <div className=\"flex items-center gap-1\">\n <button\n type=\"button\"\n onClick={() => onSwitch(index - 1)}\n disabled={index <= 0}\n className={ARROW}\n title={l.previousBranch}\n aria-label={l.previousBranch}\n data-testid={previousTestId}\n >\n <ArrowLeft size={12} />\n </button>\n <button\n type=\"button\"\n onClick={() => onSwitch(index + 1)}\n disabled={index >= count - 1}\n className={ARROW}\n title={l.nextBranch}\n aria-label={l.nextBranch}\n data-testid={nextTestId}\n >\n <ArrowRight size={12} />\n </button>\n </div>\n </div>\n )\n}\n","import { forwardRef } from 'react'\nimport type { ComponentType, ReactNode } from 'react'\nimport { Check, ChevronsUpDown, Crown, Glasses, Settings, Sparkles, Zap } from 'lucide-react'\nimport {\n Button,\n Popover,\n PopoverContent,\n PopoverTrigger,\n Tooltip,\n TooltipContent,\n TooltipTrigger,\n cn,\n} from '@arbidocs/react/ui'\nimport { BlocksTooltipProvider } from '../provider/TooltipScope'\n\n// ── Icons ───────────────────────────────────────────────────────────────────────────────────\n\nexport type ModelTierKind = 'standard' | 'wise' | 'premium'\n\nconst TIER_ICON: Record<ModelTierKind, ComponentType<{ className?: string }>> = {\n standard: Zap,\n wise: Glasses,\n premium: Crown,\n}\n\nconst TIER_TONE: Record<ModelTierKind, string> = {\n standard: 'text-secondary fill-secondary',\n wise: 'text-secondary fill-secondary',\n premium: 'text-yellow-text fill-yellow-text',\n}\n\nexport interface ModelTierIconProps {\n tier: ModelTierKind\n /** Agentic mode off: the tier glyph is greyed. */\n isGreyed?: boolean\n className?: string\n}\n\n/** The glyph of a model tier (Fast/Standard bolt, Wise glasses, Premium crown). */\nexport function ModelTierIcon({ tier, isGreyed, className }: ModelTierIconProps) {\n const Icon = TIER_ICON[tier]\n return (\n <Icon\n className={cn(\n 'size-3.5 shrink-0',\n isGreyed ? 'fill-muted-foreground text-muted-foreground' : TIER_TONE[tier],\n className\n )}\n />\n )\n}\n\n/** The Autoselect sparkle. */\nexport function ModelAutoIcon({ className }: { className?: string }) {\n return <Sparkles className={cn('size-3.5 shrink-0 fill-secondary text-secondary', className)} />\n}\n\n/** Neutral status dot for models with no tier glyph. */\nexport function ModelDot({ isGreyed }: { isGreyed?: boolean }) {\n return (\n <div\n className={cn(\n 'size-2 shrink-0 rounded-full',\n isGreyed ? 'bg-muted-foreground' : 'bg-primary'\n )}\n />\n )\n}\n\n/** Label + icon content shared by menu rows and select items. */\nexport function ModelOptionLabel({ icon, label }: { icon: ReactNode; label: ReactNode }) {\n return (\n <div className=\"flex w-full items-center gap-2\">\n {icon}\n <span className=\"min-w-0 flex-1 truncate\">{label}</span>\n </div>\n )\n}\n\n// ── Trigger ─────────────────────────────────────────────────────────────────────────────────\n\nexport interface ModelTriggerContentProps {\n icon?: ReactNode\n label: ReactNode\n}\n\n/** Icon + truncated label (used inside the compact trigger and the select trigger). */\nexport function ModelTriggerContent({ icon, label }: ModelTriggerContentProps) {\n return (\n <div className=\"flex min-w-0 items-center gap-1.5\">\n {icon}\n <span className=\"truncate\">{label}</span>\n </div>\n )\n}\n\nexport interface ModelPickerTriggerProps extends ModelTriggerContentProps {\n /** Spoken before the current model, so the button reads \"Model: Autoselect\". Default \"Model\". */\n nameLabel?: string\n className?: string\n testId?: string\n}\n\n/** The compact picker button (ghost, with a chevron). Forwards its ref for popover/tooltip triggers. */\nexport const ModelPickerTrigger = forwardRef<HTMLButtonElement, ModelPickerTriggerProps>(\n function ModelPickerTrigger(\n { icon, label, nameLabel = 'Model', className, testId = 'model-selector-compact', ...rest },\n ref\n ) {\n return (\n <Button\n ref={ref}\n variant=\"ghost\"\n size=\"sm\"\n className={cn(\n 'h-8 min-w-0 shrink gap-1 px-2 text-sm text-muted-foreground hover:bg-muted hover:text-foreground pointer-coarse:h-11',\n className\n )}\n aria-label={typeof label === 'string' ? `${nameLabel}: ${label}` : undefined}\n data-slot=\"model-picker-trigger\"\n data-testid={testId}\n {...rest}\n >\n <ModelTriggerContent icon={icon} label={label} />\n <ChevronsUpDown className=\"size-3 shrink-0 text-muted-foreground\" />\n </Button>\n )\n }\n)\n\n// ── Popover + menu ──────────────────────────────────────────────────────────────────────────\n\nexport interface ModelPickerPopoverProps {\n open: boolean\n onOpenChange: (open: boolean) => void\n /** The trigger (a ModelPickerTrigger). */\n trigger: ReactNode\n /** Hover tooltip on the trigger (hidden while open). */\n tooltip?: ReactNode\n title?: string\n /** The menu rows. */\n children: ReactNode\n}\n\n/** Popover shell: trigger + tooltip + titled, scrolling list. */\nexport function ModelPickerPopover({\n open,\n onOpenChange,\n trigger,\n tooltip,\n title = 'Select AI Model',\n children,\n}: ModelPickerPopoverProps) {\n return (\n <BlocksTooltipProvider>\n <Popover open={open} onOpenChange={onOpenChange}>\n <Tooltip>\n <TooltipTrigger asChild>\n <PopoverTrigger asChild>{trigger}</PopoverTrigger>\n </TooltipTrigger>\n {tooltip && !open && <TooltipContent side=\"top\">{tooltip}</TooltipContent>}\n </Tooltip>\n <PopoverContent side=\"top\" align=\"start\" className=\"w-[280px] p-1\" sideOffset={8}>\n <div className=\"px-2 py-1.5 text-sm font-medium text-muted-foreground\">{title}</div>\n <div className=\"flex max-h-[280px] flex-col gap-0.5 overflow-y-auto\">{children}</div>\n </PopoverContent>\n </Popover>\n </BlocksTooltipProvider>\n )\n}\n\nexport function ModelMenuDivider() {\n return <div className=\"my-0.5 border-t border-border\" role=\"separator\" />\n}\n\nexport function ModelMenuMessage({ children }: { children: ReactNode }) {\n return <div className=\"px-2 py-1.5 text-sm text-muted-foreground\">{children}</div>\n}\n\nexport interface ModelOptionProps {\n icon: ReactNode\n label: ReactNode\n isSelected: boolean\n onSelect: () => void\n testId: string\n /** Tier rows mark selection with a primary left edge and bold label. */\n emphasis?: 'plain' | 'tier'\n}\n\n/** One selectable model row. */\nexport function ModelOption({\n icon,\n label,\n isSelected,\n onSelect,\n testId,\n emphasis = 'plain',\n}: ModelOptionProps) {\n return (\n <button\n type=\"button\"\n onClick={onSelect}\n className={cn(\n 'flex w-full min-w-0 items-center gap-2 rounded-sm px-2 py-1.5 text-left text-sm transition-colors hover:bg-accent pointer-coarse:min-h-11',\n emphasis === 'tier' && 'border-l-4',\n emphasis === 'tier' && (isSelected ? 'border-l-primary' : 'border-l-transparent'),\n isSelected && 'bg-accent'\n )}\n aria-pressed={isSelected}\n data-slot=\"model-option\"\n data-testid={testId}\n >\n {icon}\n <span\n className={cn(\n 'min-w-0 flex-1 truncate',\n emphasis === 'tier' &&\n (isSelected ? 'font-semibold text-foreground' : 'font-medium text-muted-foreground')\n )}\n >\n {label}\n </span>\n {isSelected && <Check className=\"size-3 shrink-0 text-primary\" />}\n </button>\n )\n}\n\nexport interface ModelTierOptionProps {\n icon: ReactNode\n label: ReactNode\n isSelected: boolean\n /** The tier is switched off in settings: shown dimmed and not selectable. */\n isDisabled?: boolean\n onSelect: () => void\n /** Trailing control (the configure cog). */\n action?: ReactNode\n testId: string\n}\n\n/** A tier row with a trailing action (Premium + configure cog). */\nexport function ModelTierOption({\n icon,\n label,\n isSelected,\n isDisabled,\n onSelect,\n action,\n testId,\n}: ModelTierOptionProps) {\n return (\n <div\n className={cn(\n 'flex items-center gap-1 rounded-sm border-l-4 pr-1 transition-colors',\n isSelected ? 'border-l-primary bg-accent' : 'border-l-transparent'\n )}\n data-slot=\"model-tier-option\"\n >\n <button\n type=\"button\"\n onClick={() => {\n if (!isDisabled) onSelect()\n }}\n disabled={isDisabled}\n className={cn(\n 'flex min-w-0 flex-1 items-center gap-2 rounded-sm px-2 py-1.5 text-left text-sm pointer-coarse:min-h-11',\n isDisabled ? 'cursor-not-allowed opacity-50' : 'hover:bg-accent'\n )}\n data-testid={testId}\n >\n {icon}\n <span\n className={cn(\n 'min-w-0 flex-1 truncate',\n isSelected ? 'font-semibold text-foreground' : 'font-medium text-muted-foreground'\n )}\n >\n {label}\n </span>\n </button>\n {action}\n </div>\n )\n}\n\nexport interface ModelConfigureButtonProps {\n onClick: () => void\n /** Accessible name. */\n label: string\n /** Tooltip text. */\n tooltip: string\n testId?: string\n}\n\n/** Small bordered cog beside a tier row. */\nexport function ModelConfigureButton({\n onClick,\n label,\n tooltip,\n testId,\n}: ModelConfigureButtonProps) {\n return (\n <Tooltip>\n <TooltipTrigger asChild>\n <button\n type=\"button\"\n onClick={(e) => {\n e.stopPropagation()\n onClick()\n }}\n className=\"flex size-7 shrink-0 items-center justify-center rounded-md border border-border bg-background text-foreground hover:bg-accent pointer-coarse:size-11\"\n data-testid={testId}\n aria-label={label}\n >\n <Settings className=\"size-4\" />\n </button>\n </TooltipTrigger>\n <TooltipContent side=\"top\">{tooltip}</TooltipContent>\n </Tooltip>\n )\n}\n\n/** Every fixed string of the pricing tip. Pass a partial `labels` to translate or reword. */\nexport interface ModelPricingTipLabels {\n input: (credits: string) => string\n output: (credits: string) => string\n}\n\nexport const DEFAULT_MODEL_PRICING_TIP_LABELS: ModelPricingTipLabels = {\n input: (credits) => `Input: ${credits} credits/M tokens`,\n output: (credits) => `Output: ${credits} credits/M tokens`,\n}\n\nexport interface ModelPricingTipProps {\n modelName: string\n /** Credits per million tokens, formatted. */\n inputCredits?: string | null\n outputCredits?: string | null\n labels?: Partial<ModelPricingTipLabels>\n}\n\n/** Tooltip body: model name and per-million-token credit prices. */\nexport function ModelPricingTip({\n modelName,\n inputCredits,\n outputCredits,\n labels,\n}: ModelPricingTipProps) {\n const l = { ...DEFAULT_MODEL_PRICING_TIP_LABELS, ...labels }\n return (\n <div className=\"space-y-1 text-sm\">\n <div className=\"font-medium\">{modelName}</div>\n {inputCredits && <div>{l.input(inputCredits)}</div>}\n {outputCredits && <div>{l.output(outputCredits)}</div>}\n </div>\n )\n}\n","import type { ReactNode } from 'react'\nimport { Bot, Plus, Settings } from 'lucide-react'\nimport { Button, cn } from '@arbidocs/react/ui'\nimport { testIdOr } from './test-id'\n\n// ── Header actions ──────────────────────────────────────────────────────────────────────────\n\n/** Right side of the conversation tab strip. */\nexport function ConversationHeaderActions({\n children,\n className,\n}: {\n children: ReactNode\n className?: string\n}) {\n return (\n <div\n className={cn('flex items-center gap-2', className)}\n data-slot=\"conversation-header-actions\"\n >\n {children}\n </div>\n )\n}\n\n/** Every fixed string of the conversation parts. Pass a partial `labels` to a part to reword. */\nexport interface ConversationPartsLabels {\n /** \"New Chat\": `entityLabel` is the host's noun. */\n newEntity: (entityLabel: string) => string\n newPaChatTitle: string\n newPaChat: string\n paModeTitle: string\n pa: string\n}\n\nexport const DEFAULT_CONVERSATION_PARTS_LABELS: ConversationPartsLabels = {\n newEntity: (entityLabel) => `New ${entityLabel}`,\n newPaChatTitle: 'Start a new Personal Assistant chat',\n newPaChat: 'New PA Chat',\n paModeTitle: 'Personal Assistant mode',\n pa: 'PA',\n}\n\nexport interface NewChatButtonProps {\n /** Entity label, e.g. \"Chat\": names the button (\"New Chat\"). */\n entityLabel: string\n /** Narrow header: icon only. */\n isCompact: boolean\n onClick: () => void\n labels?: Partial<ConversationPartsLabels>\n testId?: string\n}\n\n/** \"+ New Chat\". */\nexport function NewChatButton({\n entityLabel,\n isCompact,\n onClick,\n labels,\n testId = 'new-conversation-button',\n}: NewChatButtonProps) {\n const text = { ...DEFAULT_CONVERSATION_PARTS_LABELS, ...labels }.newEntity(entityLabel)\n return (\n <button\n type=\"button\"\n onClick={onClick}\n className=\"flex h-8 items-center gap-1.5 rounded-md px-2 text-sm font-medium text-primary transition-colors hover:bg-primary/10 pointer-coarse:h-11! pointer-coarse:min-w-11 pointer-coarse:justify-center\"\n data-testid={testId}\n aria-label={text}\n title={text}\n >\n <Plus className=\"size-4 shrink-0\" />\n {!isCompact && <span>{text}</span>}\n </button>\n )\n}\n\n/** Starts a Personal Assistant conversation (experimental). */\nexport function NewPaChatButton({\n isCompact,\n onClick,\n labels,\n testId = 'new-pa-conversation-button',\n}: {\n isCompact: boolean\n onClick: () => void\n labels?: Partial<ConversationPartsLabels>\n testId?: string\n}) {\n const l = { ...DEFAULT_CONVERSATION_PARTS_LABELS, ...labels }\n return (\n <Button\n variant=\"outline\"\n size=\"icon\"\n onClick={onClick}\n className={cn(\n 'pointer-coarse:min-h-11',\n isCompact ? 'flex items-center' : 'flex w-auto items-center gap-2 px-4'\n )}\n data-testid={testId}\n title={l.newPaChatTitle}\n >\n <Bot className=\"size-4\" />\n {!isCompact && <span>{l.newPaChat}</span>}\n </Button>\n )\n}\n\n// ── Composer slots ──────────────────────────────────────────────────────────────────────────\n\n/** Left of the composer toolbar: borderless, muted buttons (files, facts). */\nexport function ComposerAccessories({\n children,\n className,\n}: {\n children: ReactNode\n className?: string\n}) {\n return (\n <span\n className={cn(\n 'flex items-center gap-1 [&_button]:border-transparent [&_button]:bg-transparent [&_button]:text-muted-foreground pointer-coarse:[&_button]:h-11',\n className\n )}\n data-slot=\"composer-accessories\"\n >\n {children}\n </span>\n )\n}\n\n/** Right of the composer toolbar: tools (settings, mic) around the send button. */\nexport function ComposerTools({\n children,\n className,\n}: {\n children: ReactNode\n className?: string\n}) {\n return (\n <div\n className={cn(\n 'flex items-center gap-1 [&_button:not([data-testid=send-message-button]):not([data-testid=retry-button])]:border-transparent [&_button:not([data-testid=send-message-button]):not([data-testid=retry-button])]:bg-transparent',\n className\n )}\n data-slot=\"composer-tools\"\n >\n {children}\n </div>\n )\n}\n\n/** Personal Assistant mode marker in place of the accessories. */\nexport function PaModeBadge({\n icon,\n labels,\n testId = 'pa-mode-indicator',\n}: {\n icon: ReactNode\n labels?: Partial<ConversationPartsLabels>\n testId?: string\n}) {\n const l = { ...DEFAULT_CONVERSATION_PARTS_LABELS, ...labels }\n return (\n <div\n className=\"flex h-8 shrink-0 items-center gap-1.5 rounded-md px-2.5 text-yellow-text\"\n title={l.paModeTitle}\n data-testid={testId}\n >\n {icon}\n <span className=\"text-sm font-semibold\">{l.pa}</span>\n </div>\n )\n}\n\n/** Icon-only gear for the conversation's settings (developers). */\nexport function ConversationSettingsButton({\n label,\n onClick,\n testId = 'conversation-settings-button',\n}: {\n /** e.g. \"Chat Settings\". */\n label: string\n onClick: () => void\n testId?: string\n}) {\n return (\n <Button\n type=\"button\"\n size=\"icon\"\n variant=\"ghost\"\n className=\"size-8 shrink-0 text-muted-foreground pointer-coarse:size-11\"\n onClick={onClick}\n title={label}\n aria-label={label}\n data-testid={testId}\n >\n <Settings className=\"size-4\" />\n </Button>\n )\n}\n\n/** The history (list) view area when no chat tab is active. */\nexport function ConversationHistoryPane({\n children,\n className,\n}: {\n children: ReactNode\n className?: string\n}) {\n return <div className={cn('min-h-0 flex-1 overflow-hidden', className)}>{children}</div>\n}\n","import { useMemo, type ReactNode, type Ref } from 'react'\nimport DOMPurify from 'dompurify'\nimport { Download } from 'lucide-react'\nimport { Button, cn } from '@arbidocs/react/ui'\n\n/** Every fixed string of the thread map parts. Pass a partial `labels` to a part to reword. */\nexport interface ThreadMapLabels {\n saveSvgTitle: string\n saveSvg: string\n generating: string\n /** \"Error rendering diagram: <message>\". */\n renderError: (message: string) => string\n}\n\nexport const DEFAULT_THREAD_MAP_LABELS: ThreadMapLabels = {\n saveSvgTitle: 'Save SVG as file',\n saveSvg: 'Save SVG',\n generating: 'Generating visualization...',\n renderError: (message) => `Error rendering diagram: ${message}`,\n}\n\nexport interface ThreadMapProps {\n /** Hint line above the map; omit to hide the header. */\n hint?: string\n /** Offer \"Save SVG\" (only once there is a diagram). */\n onSave?: () => void\n /** The map body (ThreadMapLoading / ThreadMapError / ThreadMapDiagram). */\n children: ReactNode\n className?: string\n labels?: Partial<ThreadMapLabels>\n testId?: string\n}\n\n/** The conversation-thread map: hint + save header over a scrolling canvas. */\nexport function ThreadMap({\n hint,\n onSave,\n children,\n className,\n labels,\n testId = 'thread-visualizer',\n}: ThreadMapProps) {\n const l = { ...DEFAULT_THREAD_MAP_LABELS, ...labels }\n return (\n <div\n className={cn('thread-visualizer flex h-full w-full flex-col', className)}\n data-slot=\"thread-map\"\n data-testid={testId}\n >\n {hint !== undefined && (\n <div className=\"mb-2 flex items-center justify-between gap-2\">\n <div className=\"text-sm italic text-muted-foreground\">{hint}</div>\n {onSave && (\n <Button\n variant=\"secondary\"\n size=\"sm\"\n onClick={onSave}\n title={l.saveSvgTitle}\n className=\"shrink-0 pointer-coarse:min-h-11\"\n >\n <Download className=\"size-3\" />\n {l.saveSvg}\n </Button>\n )}\n </div>\n )}\n <div\n className=\"mermaid-container w-full flex-1 overflow-auto rounded-lg bg-muted\"\n style={{ scrollBehavior: 'auto', contain: 'layout style' }}\n onScroll={(e) => e.stopPropagation()}\n >\n {children}\n </div>\n </div>\n )\n}\n\nexport function ThreadMapLoading({\n label,\n labels,\n}: {\n /** Text; wins over `labels.generating`. */\n label?: string\n labels?: Partial<ThreadMapLabels>\n}) {\n const text = label ?? { ...DEFAULT_THREAD_MAP_LABELS, ...labels }.generating\n return (\n <div className=\"flex h-24 items-center justify-center text-muted-foreground\" role=\"status\">\n <div className=\"flex flex-col items-center\">\n <svg\n className=\"-ml-1 mr-3 size-5 animate-spin text-primary\"\n xmlns=\"http://www.w3.org/2000/svg\"\n fill=\"none\"\n viewBox=\"0 0 24 24\"\n aria-hidden\n >\n <circle\n className=\"opacity-25\"\n cx=\"12\"\n cy=\"12\"\n r=\"10\"\n stroke=\"currentColor\"\n strokeWidth=\"4\"\n />\n <path\n className=\"opacity-75\"\n fill=\"currentColor\"\n d=\"M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z\"\n />\n </svg>\n <span>{text}</span>\n </div>\n </div>\n )\n}\n\nexport function ThreadMapError({\n message,\n labels,\n}: {\n message: string\n labels?: Partial<ThreadMapLabels>\n}) {\n const l = { ...DEFAULT_THREAD_MAP_LABELS, ...labels }\n return (\n <div className=\"p-4 text-red-text\" role=\"alert\">\n {l.renderError(message)}\n </div>\n )\n}\n\nexport interface ThreadMapDiagramProps {\n /**\n * Rendered SVG markup. Sanitised here (DOMPurify, SVG + HTML-label profile) before it is\n * injected: blocks cannot know whether the host's renderer ran in a strict security mode.\n */\n svg: string\n diagramRef?: Ref<HTMLDivElement>\n /** Accessible name of the diagram (default \"Conversation thread map\"). */\n label?: string\n}\n\n/** Strip scripts, event handlers and script URLs while keeping mermaid's `foreignObject` labels. */\nexport function sanitizeDiagramSvg(svg: string): string {\n // Without a DOM (SSR) DOMPurify cannot sanitise and would hand the input back: render nothing.\n if (!DOMPurify.isSupported) return ''\n return DOMPurify.sanitize(svg, {\n USE_PROFILES: { svg: true, svgFilters: true, html: true },\n ADD_TAGS: ['foreignobject'],\n HTML_INTEGRATION_POINTS: { foreignobject: true },\n ADD_ATTR: ['target'],\n })\n}\n\nexport function ThreadMapDiagram({\n svg,\n diagramRef,\n label = 'Conversation thread map',\n}: ThreadMapDiagramProps) {\n const safeSvg = useMemo(() => sanitizeDiagramSvg(svg), [svg])\n return (\n <div\n ref={diagramRef}\n className=\"p-4\"\n role=\"img\"\n aria-label={label}\n data-slot=\"thread-map-diagram\"\n dangerouslySetInnerHTML={{ __html: safeSvg }}\n />\n )\n}\n","import { useCallback, useState, type ClipboardEvent } from 'react'\n\nconst LONG_PASTE_CHARACTER_LIMIT = 1_000\nconst LONG_PASTE_LINE_LIMIT = 12\n\n/** True when the text is big enough that a composer should fold it behind a \"Pasted text\" chip. */\nexport function isLongPastedText(value: string): boolean {\n return (\n value.length >= LONG_PASTE_CHARACTER_LIMIT || value.split('\\n').length >= LONG_PASTE_LINE_LIMIT\n )\n}\n\nexport interface UseLongPaste {\n /** The draft is long AND the user pasted it (typing a long text never folds it). */\n isCollapsed: boolean\n /** Wire to the textarea `onPaste`. Folds when the post-paste draft is long. */\n onPaste: (event: ClipboardEvent<HTMLTextAreaElement>, currentValue: string) => void\n /** Wire to the textarea `onChange`: unfolds once the draft is short again. */\n onValueChange: (nextValue: string) => void\n /** Unfold (the \"Expand\" chip). */\n expand: () => void\n}\n\n/** Headless long-paste folding for a composer draft. */\nexport function useLongPaste(value: string): UseLongPaste {\n const [collapsed, setCollapsed] = useState(false)\n\n const onPaste = useCallback(\n (event: ClipboardEvent<HTMLTextAreaElement>, currentValue: string) => {\n const pasted = event.clipboardData.getData('text')\n const el = event.currentTarget\n const next =\n currentValue.slice(0, el.selectionStart) + pasted + currentValue.slice(el.selectionEnd)\n if (isLongPastedText(next)) setCollapsed(true)\n },\n []\n )\n\n const onValueChange = useCallback((nextValue: string) => {\n if (!isLongPastedText(nextValue)) setCollapsed(false)\n }, [])\n\n const expand = useCallback(() => setCollapsed(false), [])\n\n return { isCollapsed: collapsed && isLongPastedText(value), onPaste, onValueChange, expand }\n}\n","/**\n * PendingAnswerBar\n *\n * When the agent pauses to ask the user a question (ask_user / Human-in-the-loop),\n * this card docks directly above the message composer. It shows the FULL question\n * and lays the answer options out vertically — one full-width row each — so every\n * label is readable in full, however long. A countdown sits in the header.\n *\n * There is intentionally NO text input here: a free-text answer is typed in the\n * real composer below, which interjects the answer while a question is\n * pending. One input, where the user's cursor already is.\n */\n\nimport { useEffect, useRef, useState } from 'react'\nimport { MessageCircleQuestion, Clock, Pause, Play } from 'lucide-react'\nimport { cn } from '@arbidocs/react/ui'\n\n/** Every fixed string of the pending-answer bar. */\nexport interface PendingAnswerBarLabels {\n heading: string\n optionsLabel: string\n hint: string\n /** Pause button while the countdown runs. */\n pauseTimer: string\n /** Pause button while it is paused. */\n resumeTimer: string\n /** Name of the countdown, spoken with its value. */\n timeLeft: string\n /** Announced at 30 and 10 seconds left. */\n secondsWarning: (seconds: number) => string\n}\n\nexport const DEFAULT_PENDING_ANSWER_BAR_LABELS: PendingAnswerBarLabels = {\n heading: 'ARBI is asking',\n optionsLabel: 'Answer options',\n hint: 'Pick an option, or type your own answer below.',\n pauseTimer: 'Pause the countdown',\n resumeTimer: 'Resume the countdown',\n timeLeft: 'Time left to answer',\n secondsWarning: (seconds) => `${seconds} seconds left to answer`,\n}\n\nexport interface PendingAnswerBarProps {\n question: string\n options: string[]\n timeoutSeconds: number\n /** Called with the chosen option, the typed answer, or 'timeout' when it expires. */\n onPick: (answer: string) => void\n labels?: Partial<PendingAnswerBarLabels>\n}\n\nexport function PendingAnswerBar({\n question,\n options,\n timeoutSeconds,\n onPick,\n labels,\n}: PendingAnswerBarProps) {\n const l = { ...DEFAULT_PENDING_ANSWER_BAR_LABELS, ...labels }\n const [secondsLeft, setSecondsLeft] = useState(timeoutSeconds)\n // Once we've answered (or timed out) don't fire again as the bar unmounts.\n const firedRef = useRef(false)\n // WCAG 2.2.1: the countdown is pausable, and holds still while focus is inside the bar so a\n // keyboard or screen-reader user reading the options is never timed out under their hands.\n const [isPausedByUser, setIsPausedByUser] = useState(false)\n const [hasFocusWithin, setHasFocusWithin] = useState(false)\n const isPaused = isPausedByUser || hasFocusWithin\n // Spoken once the bar is mounted (a live region only announces changes made after it exists).\n const [announcement, setAnnouncement] = useState('')\n\n // A bare \"Other\" option is redundant — the composer is the free-text path.\n const choices = options.filter((o) => o.trim().toLowerCase() !== 'other')\n\n useEffect(() => {\n setAnnouncement(`${l.heading}: ${question}`)\n // Once per question: the bar is keyed by it in the host.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [])\n\n useEffect(() => {\n if (secondsLeft <= 0 || isPaused) return\n const t = setInterval(() => setSecondsLeft((s) => (s <= 1 ? 0 : s - 1)), 1000)\n return () => clearInterval(t)\n }, [secondsLeft, isPaused])\n\n useEffect(() => {\n if (secondsLeft === 30 || secondsLeft === 10) setAnnouncement(l.secondsWarning(secondsLeft))\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [secondsLeft])\n\n useEffect(() => {\n if (secondsLeft === 0 && !firedRef.current) {\n firedRef.current = true\n onPick('timeout')\n }\n }, [secondsLeft, onPick])\n\n const pick = (answer: string) => {\n if (firedRef.current) return\n firedRef.current = true\n onPick(answer)\n }\n\n const fmt = (s: number): string => {\n const m = Math.floor(s / 60)\n const r = s % 60\n return m > 0 ? `${m}:${r.toString().padStart(2, '0')}` : `${r}s`\n }\n const low = secondsLeft <= 30\n\n return (\n <div\n role=\"group\"\n aria-label={l.heading}\n className=\"mb-2 rounded-lg border border-theme-cyan/30 bg-theme-cyan/[0.05] px-3 py-2.5\"\n data-slot=\"pending-answer-bar\"\n data-testid=\"pending-answer-bar\"\n onFocus={() => setHasFocusWithin(true)}\n onBlur={(event) => {\n if (!event.currentTarget.contains(event.relatedTarget as Node | null)) {\n setHasFocusWithin(false)\n }\n }}\n >\n <div\n role=\"status\"\n aria-live=\"polite\"\n aria-atomic=\"true\"\n className=\"sr-only\"\n data-testid=\"pending-answer-status\"\n >\n {announcement}\n </div>\n {/* Header: label + countdown */}\n <div className=\"flex items-center justify-between gap-2\">\n <div className=\"flex min-w-0 items-center gap-2\">\n <MessageCircleQuestion aria-hidden=\"true\" className=\"h-4 w-4 shrink-0 text-theme-cyan\" />\n <span className=\"text-xs font-medium uppercase tracking-wide text-theme-cyan\">\n {l.heading}\n </span>\n </div>\n <div className=\"flex shrink-0 items-center gap-1\">\n <span\n role=\"timer\"\n aria-label={l.timeLeft}\n className={cn(\n 'flex items-center gap-1 text-xs tabular-nums',\n low ? 'text-red-text' : 'text-muted-foreground'\n )}\n data-testid=\"pending-answer-timer\"\n >\n <Clock aria-hidden=\"true\" className=\"h-3 w-3\" />\n {fmt(secondsLeft)}\n </span>\n <button\n type=\"button\"\n onClick={() => setIsPausedByUser((p) => !p)}\n aria-pressed={isPausedByUser}\n aria-label={l.pauseTimer}\n title={isPausedByUser ? l.resumeTimer : l.pauseTimer}\n className=\"flex size-6 items-center justify-center rounded-md text-muted-foreground transition-colors hover:bg-muted hover:text-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring pointer-coarse:size-11\"\n data-testid=\"pending-answer-pause\"\n >\n {isPausedByUser ? (\n <Play aria-hidden=\"true\" className=\"h-3 w-3\" />\n ) : (\n <Pause aria-hidden=\"true\" className=\"h-3 w-3\" />\n )}\n </button>\n </div>\n </div>\n\n {/* The full question — wraps freely, never truncated */}\n <p className=\"mt-1.5 whitespace-pre-line text-sm text-foreground\">{question}</p>\n\n {/* Options, stacked vertically — each row reveals its full label */}\n {choices.length > 0 && (\n <div className=\"mt-2.5 flex flex-col gap-1.5\" role=\"group\" aria-label={l.optionsLabel}>\n {choices.map((option, i) => (\n <button\n key={`${i}-${option}`}\n type=\"button\"\n onClick={() => pick(option)}\n className={cn(\n 'flex w-full items-center gap-2 rounded-md border border-border bg-background',\n 'px-3 py-2 text-left text-sm text-foreground transition-colors',\n 'hover:border-theme-cyan/50 hover:bg-theme-cyan/10',\n 'focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring pointer-coarse:min-h-11'\n )}\n data-testid={`pending-answer-option-${option}`}\n >\n <span\n aria-hidden=\"true\"\n className=\"flex h-5 w-5 shrink-0 items-center justify-center rounded-full border border-theme-cyan/40 text-xs font-medium text-theme-cyan\"\n >\n {i + 1}\n </span>\n <span className=\"min-w-0 flex-1\">{option}</span>\n </button>\n ))}\n </div>\n )}\n\n {/* Free-text affordance — points at the composer below */}\n <p className=\"mt-2 text-xs text-muted-foreground\">{l.hint}</p>\n </div>\n )\n}\n","import { useMemo, type ComponentType, type ReactNode } from 'react'\nimport { Bot, Loader2, MessageSquare, Search, User, X } from 'lucide-react'\n\nimport { Button, PassageCard } from '@arbidocs/react/ui'\n\n/** One matching message of a conversation. */\nexport interface ConversationSearchMatch {\n id: string\n role: string\n score: number\n snippet: string\n}\n\n/** A conversation with the messages that matched the query. */\nexport interface ConversationSearchGroup {\n id: string\n title?: string | null\n matches: ConversationSearchMatch[]\n}\n\n/** Every fixed string of the conversation search. */\nexport interface ConversationSearchLabels {\n placeholder: string\n search: string\n searching: string\n matched: (count: number, query: string) => string\n matchCount: (count: number) => string\n untitled: string\n you: string\n assistant: string\n clear: string\n noResults: (query: string) => string\n reindexHint: ReactNode\n backToList: string\n}\n\nexport const DEFAULT_CONVERSATION_SEARCH_LABELS: ConversationSearchLabels = {\n placeholder: 'Search your conversations...',\n search: 'Search',\n searching: 'Searching conversations…',\n matched: (count, query) => `${count} conversation${count === 1 ? '' : 's'} matched “${query}”`,\n matchCount: (count) => `${count} match${count === 1 ? '' : 'es'}`,\n untitled: 'Untitled conversation',\n you: 'You',\n assistant: 'Assistant',\n clear: 'Clear',\n noResults: (query) => `No conversations matched “${query}”.`,\n reindexHint: (\n <>\n Older conversations may need indexing — try <span className=\"font-medium\">Re-index</span>.\n </>\n ),\n backToList: 'Back to list',\n}\n\nexport interface ConversationSearchViewProps {\n query: string\n onQueryChange: (query: string) => void\n /** Enter (without Shift) or the submit button. */\n onSubmit: () => void\n canSubmit: boolean\n isSearching: boolean\n /** The query the shown results answer; empty while no search has run. */\n submittedQuery: string\n /** Results of `submittedQuery`. */\n groups: ConversationSearchGroup[]\n onOpenConversation: (conversationId: string, messageId?: string) => void\n /** Back to the idle body. */\n onClear: () => void\n /** Shown beneath the bar until a search is run (e.g. the history list). */\n children?: ReactNode\n /** Wraps the results area (e.g. an error boundary). */\n ResultsBoundary?: ComponentType<{ children: ReactNode }>\n labels?: Partial<ConversationSearchLabels>\n}\n\nfunction RoleChip({ isUser, labels }: { isUser: boolean; labels: ConversationSearchLabels }) {\n const Icon = isUser ? User : Bot\n return (\n <span className=\"inline-flex items-center gap-1 text-xs font-medium text-muted-foreground\">\n <Icon className=\"size-3\" />\n {isUser ? labels.you : labels.assistant}\n </span>\n )\n}\n\nconst Passthrough = ({ children }: { children: ReactNode }) => <>{children}</>\n\n/**\n * Search across past conversations: a search bar, then either the idle body (history list) or\n * the matches grouped by conversation. Opening a group or a hit is the host's navigation.\n */\nexport function ConversationSearchView({\n query,\n onQueryChange,\n onSubmit,\n canSubmit,\n isSearching,\n submittedQuery,\n groups,\n onOpenConversation,\n onClear,\n children,\n ResultsBoundary = Passthrough,\n labels,\n}: ConversationSearchViewProps) {\n const l = useMemo(() => ({ ...DEFAULT_CONVERSATION_SEARCH_LABELS, ...labels }), [labels])\n const hasResults = !!submittedQuery && !isSearching && groups.length > 0\n\n return (\n <div\n data-slot=\"conversation-search\"\n className=\"flex h-full flex-col\"\n data-testid=\"conversation-search-page\"\n >\n <div className=\"flex items-start gap-3 px-6 py-4\">\n <form\n onSubmit={(e) => {\n e.preventDefault()\n onSubmit()\n }}\n className=\"flex-1\"\n >\n <div className=\"flex items-start gap-2 rounded-md border border-input bg-muted px-3 py-1.5 focus-within:ring-2 focus-within:ring-ring\">\n <textarea\n rows={1}\n value={query}\n onChange={(e) => {\n onQueryChange(e.target.value)\n e.target.style.height = 'auto'\n e.target.style.height = `${e.target.scrollHeight}px`\n }}\n onKeyDown={(e) => {\n if (e.key === 'Enter' && !e.shiftKey) {\n e.preventDefault()\n onSubmit()\n }\n }}\n placeholder={l.placeholder}\n aria-label={l.search}\n className=\"flex-1 resize-none overflow-hidden border-0 bg-transparent p-0 text-base leading-relaxed text-foreground outline-none placeholder:text-muted-foreground\"\n data-testid=\"conversation-search-input\"\n />\n <div className=\"flex flex-shrink-0 items-center gap-1\">\n <Button\n type=\"submit\"\n size=\"icon\"\n disabled={!canSubmit}\n className=\"size-7 pointer-coarse:size-11\"\n data-testid=\"conversation-search-submit-button\"\n title={l.search}\n aria-label={l.search}\n >\n {isSearching ? (\n <Loader2 className=\"size-4 animate-spin\" />\n ) : (\n <Search className=\"size-4\" />\n )}\n </Button>\n </div>\n </div>\n </form>\n </div>\n\n {!submittedQuery ? (\n <div className=\"flex-1 overflow-hidden\">{children}</div>\n ) : (\n <ResultsBoundary>\n <main className=\"flex-1 overflow-auto px-6 pb-6\">\n {isSearching ? (\n <div className=\"flex items-center justify-center gap-2 py-16 text-muted-foreground\">\n <Loader2 className=\"size-5 animate-spin\" />\n {l.searching}\n </div>\n ) : hasResults ? (\n <div className=\"space-y-4\" data-testid=\"conversation-search-results\">\n <div className=\"flex items-center justify-between gap-3\">\n <p className=\"text-sm text-muted-foreground\">\n {l.matched(groups.length, submittedQuery)}\n </p>\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"sm\"\n className=\"h-7 gap-1 text-muted-foreground pointer-coarse:h-11\"\n onClick={onClear}\n data-testid=\"conversation-search-clear\"\n >\n <X className=\"size-3.5\" />\n {l.clear}\n </Button>\n </div>\n {groups.map((group) => (\n <div\n key={group.id}\n className=\"rounded-lg border border-border bg-card\"\n data-testid=\"conversation-search-group\"\n >\n <button\n type=\"button\"\n onClick={() => onOpenConversation(group.id)}\n className=\"flex w-full items-center justify-between gap-3 rounded-t-lg px-4 py-2.5 text-left transition-colors hover:bg-muted/50 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-inset focus-visible:ring-ring pointer-coarse:min-h-11\"\n >\n <span className=\"flex min-w-0 items-center gap-2\">\n <MessageSquare className=\"size-4 flex-shrink-0 text-muted-foreground\" />\n <span className=\"truncate font-medium\">{group.title || l.untitled}</span>\n </span>\n <span className=\"flex-shrink-0 text-xs text-muted-foreground\">\n {l.matchCount(group.matches.length)}\n </span>\n </button>\n <div className=\"space-y-2 border-t border-border p-3\">\n {group.matches.map((m) => (\n <PassageCard\n key={m.id}\n header={<RoleChip isUser={m.role === 'user'} labels={l} />}\n score={m.score}\n onClick={() => onOpenConversation(group.id, m.id)}\n data-testid=\"conversation-search-hit\"\n >\n <p className=\"line-clamp-3 text-sm text-foreground/90\">{m.snippet}</p>\n </PassageCard>\n ))}\n </div>\n </div>\n ))}\n </div>\n ) : (\n <div\n className=\"py-16 text-center text-muted-foreground\"\n data-testid=\"conversation-search-no-results\"\n >\n <MessageSquare className=\"mx-auto mb-3 size-8 opacity-40\" />\n <p>{l.noResults(submittedQuery)}</p>\n <p className=\"mt-1 text-sm\">{l.reindexHint}</p>\n <Button\n type=\"button\"\n variant=\"ghost\"\n size=\"sm\"\n className=\"mt-3 gap-1 text-muted-foreground pointer-coarse:h-11\"\n onClick={onClear}\n >\n <X className=\"size-3.5\" />\n {l.backToList}\n </Button>\n </div>\n )}\n </main>\n </ResultsBoundary>\n )}\n </div>\n )\n}\n","import {\n forwardRef,\n Fragment,\n type ComponentPropsWithoutRef,\n type ElementRef,\n type MouseEventHandler,\n type ReactNode,\n} from 'react'\nimport { Check, CheckCircle, Search } from 'lucide-react'\nimport {\n Badge,\n Button,\n HoverCardContent,\n Input,\n Tabs,\n TabsContent,\n TabsList,\n TabsTrigger,\n cn,\n type ButtonProps,\n} from '@arbidocs/react/ui'\n\n/**\n * Parts of the composer's \"in this chat\" panels (files, facts): a card that opens upward from the\n * composer, a grouped pick list, and below it the labels, search and bulk actions.\n */\n\n/** The card itself: width follows the chat input (`--chat-input-width`), bounded on small screens. */\nexport const ContextPanelContent = forwardRef<\n ElementRef<typeof HoverCardContent>,\n ComponentPropsWithoutRef<typeof HoverCardContent>\n>(function ContextPanelContent({ className, onClick, ...props }, ref) {\n return (\n <HoverCardContent\n ref={ref}\n side=\"top\"\n align=\"start\"\n data-slot=\"context-panel\"\n // Clicks inside must not bubble (via the React portal) to a click-to-toggle wrapper.\n onClick={(e) => {\n e.stopPropagation()\n onClick?.(e)\n }}\n className={cn(\n 'w-[var(--chat-input-width,var(--radix-hover-card-content-available-width))] max-h-[var(--radix-hover-card-content-available-height)] max-w-[95vw] overflow-y-auto overscroll-contain rounded-md border border-border bg-muted p-3 shadow-lg',\n className\n )}\n {...props}\n />\n )\n})\n\nexport interface ContextPickerGroup {\n key: string\n heading: string\n /** Id of the heading element. */\n testId?: string\n /** Shown after the heading as `(n)`. */\n count: number\n children: ReactNode\n}\n\nexport interface ContextPickerListProps {\n groups: ContextPickerGroup[]\n /** Shown instead of the groups when every group is empty. */\n emptyText: string\n testId: string\n className?: string\n}\n\n/**\n * Two (or more) headed groups, e.g. \"In this conversation\" then \"In this workspace\". Each heading\n * pins to the top of the scroller and is pushed out by the next one; the second parks below the\n * first (32px = a heading's own height), so both stay visible however far down you scroll.\n */\nexport function ContextPickerList({\n groups,\n emptyText,\n testId,\n className,\n}: ContextPickerListProps) {\n const isEmpty = groups.every((g) => g.count === 0)\n return (\n <div\n className={cn('max-h-[400px] space-y-1 overflow-y-auto', className)}\n data-slot=\"context-picker-list\"\n data-testid={testId}\n onClick={(e) => e.stopPropagation()}\n >\n {isEmpty ? (\n <p className=\"p-2 text-sm text-muted-foreground\">{emptyText}</p>\n ) : (\n groups.map((g, index) => (\n <Fragment key={g.key}>\n <div\n className={cn(\n 'sticky z-10 bg-muted px-2 py-1.5 text-sm font-medium text-muted-foreground',\n index === 0 ? 'top-0' : 'top-8'\n )}\n data-testid={g.testId}\n >\n {g.heading} ({g.count})\n </div>\n {g.children}\n </Fragment>\n ))\n )}\n </div>\n )\n}\n\nfunction CheckGlyph({ isChecked, className }: { isChecked: boolean; className?: string }) {\n return (\n <span\n className={cn(\n 'flex size-3.5 shrink-0 items-center justify-center rounded-sm border',\n isChecked ? 'border-primary bg-primary text-primary-foreground' : 'border-input',\n className\n )}\n >\n {isChecked && <Check className=\"size-3\" />}\n </span>\n )\n}\n\nexport interface ContextPickerRowProps {\n isSelected: boolean\n onToggle: () => void\n testId?: string\n children: ReactNode\n}\n\n/** A whole-row toggle (e.g. a fact): check glyph then clamped text. */\nexport function ContextPickerRow({\n isSelected,\n onToggle,\n testId,\n children,\n}: ContextPickerRowProps) {\n return (\n <button\n type=\"button\"\n onClick={(e) => {\n e.stopPropagation()\n onToggle()\n }}\n aria-pressed={isSelected}\n data-testid={testId}\n className={cn(\n 'flex w-full items-start gap-2 rounded p-2 text-left text-sm transition-colors pointer-coarse:min-h-11',\n isSelected ? 'bg-primary/10' : 'bg-card hover:bg-muted'\n )}\n >\n <CheckGlyph isChecked={isSelected} className=\"mt-0.5\" />\n <span className=\"line-clamp-2 min-w-0 text-foreground\">{children}</span>\n </button>\n )\n}\n\nexport interface ContextCheckRowProps {\n isSelected: boolean\n /** The check toggle: accessible name (e.g. \"Add to conversation\"), handler and test id. */\n toggle: { label: string; onToggle: () => void; testId?: string }\n /** Status glyph between the toggle and the content. */\n status?: ReactNode\n testId?: string\n /** The row's content (e.g. a document pill that opens the document). */\n children: ReactNode\n}\n\n/** A row with its own check toggle plus a content slot (e.g. a document, which opens on click). */\nexport function ContextCheckRow({\n isSelected,\n toggle,\n status,\n testId,\n children,\n}: ContextCheckRowProps) {\n return (\n <div\n className=\"flex items-center gap-2 rounded px-1 py-0.5\"\n data-slot=\"context-check-row\"\n data-testid={testId}\n >\n <button\n type=\"button\"\n aria-label={toggle.label}\n aria-pressed={isSelected}\n onClick={toggle.onToggle}\n data-testid={toggle.testId}\n className=\"flex shrink-0 items-center justify-center rounded-sm focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring pointer-coarse:size-11\"\n >\n <CheckGlyph isChecked={isSelected} />\n </button>\n {status}\n {children}\n </div>\n )\n}\n\nexport interface ContextSelectListProps {\n children: ReactNode\n}\n\n/** Compact single-select list (e.g. choose the document to pin). */\nexport function ContextSelectList({ children }: ContextSelectListProps) {\n return <div className=\"max-h-[150px] space-y-2 overflow-y-auto\">{children}</div>\n}\n\nexport interface ContextSelectRowProps {\n isSelected: boolean\n onSelect: MouseEventHandler<HTMLButtonElement>\n status?: ReactNode\n title: string\n testId?: string\n}\n\nexport function ContextSelectRow({\n isSelected,\n onSelect,\n status,\n title,\n testId,\n}: ContextSelectRowProps) {\n return (\n <button\n type=\"button\"\n onClick={(e) => {\n e.stopPropagation()\n onSelect(e)\n }}\n aria-pressed={isSelected}\n data-testid={testId}\n className={cn(\n 'flex w-full items-center gap-2 rounded p-2 text-left text-sm transition-colors pointer-coarse:min-h-11',\n isSelected ? 'border border-primary/30 bg-primary/10' : 'bg-card hover:bg-muted'\n )}\n >\n {status}\n <span className=\"min-w-0 flex-1 truncate text-foreground\" title={title}>\n {title}\n </span>\n {isSelected && <CheckCircle className=\"size-3.5 shrink-0 text-primary\" />}\n </button>\n )\n}\n\nexport interface ContextPanelFooterProps {\n /** Label shortcut chips (host-supplied row). */\n labels?: ReactNode\n /** The search box. */\n search: ReactNode\n /** Icon + title of the panel; omit when tabs already name it. */\n title?: ReactNode\n /** The action buttons, right aligned. */\n actions: ReactNode\n}\n\n/** Everything below the list: the panel opens upward, so its controls sit nearest the button. */\nexport function ContextPanelFooter({ labels, search, title, actions }: ContextPanelFooterProps) {\n return (\n <div className=\"mt-3 space-y-2 border-t border-border pt-3\" data-slot=\"context-panel-footer\">\n {labels}\n {search}\n <div\n className={cn(\n 'flex flex-wrap items-center gap-x-2 gap-y-1.5',\n title ? 'justify-between' : 'justify-end'\n )}\n >\n {title && (\n <div className=\"flex min-w-0 items-center gap-2 text-sm font-medium text-foreground\">\n {title}\n </div>\n )}\n <div className=\"flex flex-wrap items-center gap-1.5\">{actions}</div>\n </div>\n </div>\n )\n}\n\nexport const ContextSearchInput = forwardRef<\n HTMLInputElement,\n ComponentPropsWithoutRef<typeof Input>\n>(function ContextSearchInput({ className, onClick, ...props }, ref) {\n return (\n <div className=\"relative\" onClick={(e) => e.stopPropagation()}>\n <Search className=\"pointer-events-none absolute left-2 top-1/2 size-3.5 -translate-y-1/2 text-muted-foreground\" />\n <Input\n ref={ref}\n className={cn('h-7 bg-background pl-7 text-sm', className)}\n onClick={onClick}\n {...props}\n />\n </div>\n )\n})\n\nexport interface ContextActionButtonProps extends Omit<ButtonProps, 'size'> {\n icon?: ReactNode\n /** Badge after the label; hidden at 0 / undefined. */\n count?: number\n /** Put the icon after the label (bulk Add / Remove) rather than before it. */\n isIconTrailing?: boolean\n}\n\n/** Compact action of the panel footer (stops click propagation so the card stays open). */\nexport const ContextActionButton = forwardRef<HTMLButtonElement, ContextActionButtonProps>(\n function ContextActionButton(\n { icon, count, isIconTrailing, onClick, children, className, variant = 'outline', ...props },\n ref\n ) {\n return (\n <Button\n ref={ref}\n variant={variant}\n size=\"sm\"\n className={cn('flex h-6 items-center gap-1 px-2 text-sm pointer-coarse:h-11', className)}\n onClick={(e) => {\n e.stopPropagation()\n onClick?.(e)\n }}\n {...props}\n >\n {!isIconTrailing && icon}\n {children}\n {isIconTrailing && icon}\n {count != null && count > 0 && (\n <Badge variant=\"outline\" className=\"badge-count ml-1\">\n {count}\n </Badge>\n )}\n </Button>\n )\n }\n)\n\nexport interface ContextTab {\n value: string\n /** Visible tab name, e.g. \"Documents\". */\n label: string\n /** Count shown in the tab label. */\n count: number\n testId?: string\n content: ReactNode\n}\n\nexport interface ContextPanelTabsProps {\n tabs: ContextTab[]\n value: string\n onValueChange: (value: string) => void\n testId?: string\n /** Extra classes for the tab strip (e.g. leave room for a sheet's close button). */\n listClassName?: string\n}\n\n/** The panel's tab strip (Radix tabs: roving tabindex, arrow keys) and the active tab's content. */\nexport function ContextPanelTabs({\n tabs,\n value,\n onValueChange,\n testId,\n listClassName,\n}: ContextPanelTabsProps) {\n return (\n <Tabs value={value} onValueChange={onValueChange} data-testid={testId}>\n <TabsList\n className={cn('grid h-auto w-full grid-cols-2 pointer-coarse:h-auto', listClassName)}\n >\n {tabs.map((t) => (\n <TabsTrigger key={t.value} value={t.value} data-testid={t.testId} className=\"gap-1.5\">\n {t.label}\n <Badge variant=\"outline\" className=\"badge-count\">\n {t.count}\n </Badge>\n </TabsTrigger>\n ))}\n </TabsList>\n {tabs.map((t) => (\n <TabsContent key={t.value} value={t.value} className=\"mt-3\">\n {t.content}\n </TabsContent>\n ))}\n </Tabs>\n )\n}\n","import { useEffect, type RefObject } from 'react'\n\nexport interface UseDismissibleCardOptions {\n isOpen: boolean\n onClose: () => void\n /** The card's content: clicks inside never dismiss. */\n contentRef: RefObject<HTMLElement | null>\n /** Focused when the card opens (the panel is opened to find something: typing just works). */\n focusRef?: RefObject<HTMLElement | null>\n}\n\n/**\n * Behaviour of a click-opened card: focus its search box on open, Escape closes it, and a press\n * outside it (or outside any portaled popper that belongs to it, e.g. a dropdown menu opened from\n * inside) closes it too. Bound only while open.\n */\nexport function useDismissibleCard({\n isOpen,\n onClose,\n contentRef,\n focusRef,\n}: UseDismissibleCardOptions): void {\n // rAF lets the portaled content mount before focusing.\n useEffect(() => {\n if (!isOpen) return\n const id = requestAnimationFrame(() => focusRef?.current?.focus())\n return () => cancelAnimationFrame(id)\n }, [isOpen, focusRef])\n\n useEffect(() => {\n if (!isOpen) return\n const onKeyDown = (e: KeyboardEvent) => {\n if (e.key !== 'Escape') return\n e.stopPropagation()\n onClose()\n }\n document.addEventListener('keydown', onKeyDown)\n return () => document.removeEventListener('keydown', onKeyDown)\n }, [isOpen, onClose])\n\n useEffect(() => {\n if (!isOpen) return\n const onPointerDown = (e: MouseEvent) => {\n const target = e.target as HTMLElement | null\n if (!target) return\n if (contentRef.current?.contains(target)) return\n if (target.closest('[data-radix-popper-content-wrapper]')) return\n onClose()\n }\n document.addEventListener('mousedown', onPointerDown)\n return () => document.removeEventListener('mousedown', onPointerDown)\n }, [isOpen, onClose, contentRef])\n}\n","import { Tag as TagIcon } from 'lucide-react'\nimport { cn } from '@arbidocs/react/ui'\n\nexport interface PinnableLabel {\n id: string\n name: string\n /** The label's own colour (any CSS colour): the same hue everywhere the label appears. */\n color: string\n /** Ids of the items carrying this label. */\n itemIds: string[]\n}\n\nexport interface LabelPinRowLabels {\n remove: (count: number, name: string) => string\n add: (count: number, name: string) => string\n}\n\nexport const DEFAULT_LABEL_PIN_ROW_LABELS: LabelPinRowLabels = {\n remove: (count, name) => `Remove the ${count} “${name}” item(s) from this chat`,\n add: (count, name) => `Add the ${count} “${name}” item(s) to this chat`,\n}\n\nexport interface LabelPinRowProps {\n labels: PinnableLabel[]\n /** Ids currently in the conversation. */\n selectedIds: string[]\n /** Add every id (already de-duplicated against the chat). */\n onAdd: (ids: string[]) => void\n /** Remove every id. */\n onRemove: (ids: string[]) => void\n testId?: string\n copy?: Partial<LabelPinRowLabels>\n}\n\n/**\n * Label shortcuts inside the in-chat panels: one chip per label in use; clicking it pins\n * everything carrying that label. A chip whose items are ALL in the chat reads as active and\n * clicking it takes them back out, so a label is a toggle rather than a one-way add.\n */\nexport function LabelPinRow({\n labels,\n selectedIds,\n onAdd,\n onRemove,\n testId = 'label-pin-row',\n copy,\n}: LabelPinRowProps) {\n const l = { ...DEFAULT_LABEL_PIN_ROW_LABELS, ...copy }\n const usable = labels.filter((label) => label.itemIds.length > 0)\n if (usable.length === 0) return null\n\n const selectedSet = new Set(selectedIds)\n\n return (\n <div\n className=\"flex flex-wrap items-center gap-1\"\n data-slot=\"label-pin-row\"\n data-testid={testId}\n >\n <TagIcon className=\"size-3.5 shrink-0 text-muted-foreground\" aria-hidden />\n {usable.map((label) => {\n const allIn = label.itemIds.every((id) => selectedSet.has(id))\n return (\n <button\n key={label.id}\n type=\"button\"\n aria-pressed={allIn}\n title={\n allIn\n ? l.remove(label.itemIds.length, label.name)\n : l.add(label.itemIds.length, label.name)\n }\n onClick={() =>\n allIn\n ? onRemove(label.itemIds)\n : onAdd(label.itemIds.filter((id) => !selectedSet.has(id)))\n }\n className={cn(\n 'flex items-center gap-1 rounded-full border px-2 py-0.5 text-xs font-medium transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring pointer-coarse:min-h-11',\n allIn ? 'text-white' : 'bg-muted text-foreground hover:brightness-95'\n )}\n // Pinned reads as the label filled in with its own colour; at rest it's the muted\n // pill with the colour on the dot, matching the label pills on documents and facts.\n style={\n allIn\n ? { backgroundColor: label.color, borderColor: label.color }\n : { borderColor: `${label.color}66` }\n }\n data-testid={`${testId}-${label.id}`}\n >\n {!allIn && (\n <span\n className=\"size-1.5 shrink-0 rounded-full\"\n style={{ backgroundColor: label.color }}\n aria-hidden\n />\n )}\n <span className=\"max-w-[120px] truncate\">{label.name}</span>\n <span className=\"tabular-nums opacity-70\">{label.itemIds.length}</span>\n </button>\n )\n })}\n </div>\n )\n}\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/files/grid-test-ids.ts","../src/files/GridView.tsx","../src/files/ViewToggle.tsx"],"names":["useRef","jsxs","jsx"],"mappings":"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","file":"chunk-QXEJXIP4.js","sourcesContent":["/**\n * Test-id hooks for AG Grid, which owns its row and cell DOM. AG Grid stamps every row with a\n * `row-id` attribute and every cell with `col-id`; these helpers turn them into `data-testid`s\n * a host chooses, so a custom UI keeps its own test-id scheme.\n */\n\nexport interface GridTestIdOptions<T> {\n /** Test id of the row for `item` (set on the centre-column row element). */\n getRowTestId?: (item: T) => string\n /** Test id of the cell in column `colId` of `item`. */\n getCellTestId?: (colId: string, item: T) => string\n}\n\n/** Stamp `data-testid`s onto the rows and cells under `root`. Idempotent. */\nexport function applyGridTestIds<T>(\n root: ParentNode,\n itemsById: Map<string, T>,\n { getRowTestId, getCellTestId }: GridTestIdOptions<T>\n): void {\n if (!getRowTestId && !getCellTestId) return\n root.querySelectorAll<HTMLElement>('.ag-center-cols-container .ag-row[row-id]').forEach((row) => {\n const item = itemsById.get(row.getAttribute('row-id') ?? '')\n if (item === undefined) return\n if (getRowTestId) row.setAttribute('data-testid', getRowTestId(item))\n if (getCellTestId) {\n row.querySelectorAll<HTMLElement>('.ag-cell[col-id]').forEach((cell) => {\n cell.setAttribute('data-testid', getCellTestId(cell.getAttribute('col-id') ?? '', item))\n })\n }\n })\n}\n\n/**\n * Keep the ids applied as AG Grid creates and recycles rows (it virtualises). Returns the\n * disconnect function.\n */\nexport function watchGridTestIds<T>(\n root: HTMLElement,\n getItemsById: () => Map<string, T>,\n options: GridTestIdOptions<T>\n): () => void {\n if (!options.getRowTestId && !options.getCellTestId) return () => {}\n const run = () => applyGridTestIds(root, getItemsById(), options)\n run()\n if (typeof MutationObserver === 'undefined') return () => {}\n const observer = new MutationObserver(run)\n observer.observe(root, { childList: true, subtree: true })\n return () => observer.disconnect()\n}\n","/**\n * GridView — a flexible AG Grid presentational core.\n *\n * Pure and app-agnostic: it owns no global state and pulls in no store. Column\n * state persistence (order / width / visibility / sort / filter) is exposed as a\n * controlled/uncontrolled prop pair — `gridState` (initial state, read once at\n * mount) and `onGridStateChange` (called whenever AG Grid's state changes). An\n * app wires those to wherever it keeps the state (Zustand, localStorage, a URL,\n * a server) via a thin adapter; the core stays decoupled.\n *\n * Themed here (colours/fonts/borders via the host CSS variables, so it inherits the host's\n * light/dark theme). The structural helper classes (cell-numeric, multiline clamp, scrollbars,\n * row kebabs) live in `@arbidocs/blocks/grid.css`, which the consuming app imports globally.\n */\n\nimport React, { useRef, useCallback, useMemo, useEffect, useSyncExternalStore } from 'react'\nimport { AgGridReact } from 'ag-grid-react'\nimport {\n ColDef,\n GridOptions,\n GridApi,\n GridState,\n themeQuartz,\n CellValueChangedEvent,\n GridReadyEvent,\n RowClickedEvent,\n} from 'ag-grid-community'\nimport { AllCommunityModule } from 'ag-grid-community'\nimport { watchGridTestIds } from './grid-test-ids'\n\n// Create the custom ARBI theme using themeQuartz\n// Colours reference the host CSS variables (hsl(var(--token))), so dark mode follows the app.\n// This enables dark mode support and consistent theming\nconst cssVar = (name: string, alpha?: number): string =>\n alpha === undefined ? `hsl(var(--${name}))` : `hsl(var(--${name}) / ${alpha})`\n\nconst arbiTheme = themeQuartz.withParams({\n // Variant B palette: white canvas, quiet header, muted hover nudge, accent-tint selection.\n // Every colour is a host CSS variable, so light/dark follow the app with no .dark overrides.\n backgroundColor: cssVar('background'),\n foregroundColor: cssVar('foreground'),\n borderColor: cssVar('border'),\n headerBackgroundColor: cssVar('background'),\n headerTextColor: cssVar('muted-foreground'),\n oddRowBackgroundColor: cssVar('background'),\n rowHoverColor: cssVar('muted', 0.6),\n // Checkbox-selected rows: a light accent tint. A row opened elsewhere (e.g. the viewer) may take\n // the full accent, so the two states stay distinguishable.\n selectedRowBackgroundColor: cssVar('accent', 0.6),\n rangeSelectionBackgroundColor: cssVar('accent'),\n accentColor: cssVar('primary'),\n inputFocusBorder: { color: cssVar('primary') },\n headerColumnBorder: false,\n headerColumnResizeHandleColor: 'transparent', // still draggable, no visible divider\n\n // Font settings — inherit the host app's font. A googleFont here never\n // loaded under the apps' CSP, so every grid silently fell back to the\n // browser's default SERIF and read as unstyled.\n fontFamily: 'inherit',\n fontSize: 14,\n headerFontSize: 12.5,\n headerFontWeight: 500,\n\n // Sizing\n headerHeight: 44,\n rowHeight: 40,\n cellHorizontalPadding: 16,\n\n // Borders - structural settings only.\n // Row border is a real hairline in the theme border colour (not hardcoded\n // white, which was invisible on the light-mode background and wrong in dark\n // mode) so adjacent rows are clearly separated — important now that rows can\n // be tall and multi-line (e.g. the Abstract column).\n rowBorder: { style: 'solid', width: 1, color: 'hsl(var(--border))' },\n columnBorder: false, // Row hairlines only\n wrapperBorder: false,\n\n // No rounded corners for clean look (except checkboxes)\n borderRadius: 0,\n wrapperBorderRadius: 0,\n checkboxBorderRadius: 2, // Keep checkboxes square\n})\n\n// Selection configuration\nexport interface GridViewSelection<T> {\n mode: 'single' | 'multiple'\n selected: T[]\n onSelectionChange: (items: T[]) => void\n}\n\n// Empty state configuration\nexport interface GridViewEmptyState {\n icon?: React.ReactNode\n title?: string\n message?: string\n action?: React.ReactNode\n}\n\n// Generic props to make this grid reusable with different data types\nexport interface GridViewProps<T> {\n // Core data\n items: T[]\n // Column configuration\n columnDefs: ColDef<T>[]\n // Row identity function\n getItemId: (item: T) => string\n // Selection handling\n selection?: GridViewSelection<T>\n // Empty state\n emptyState?: GridViewEmptyState\n // Loading state\n isLoading?: boolean\n loadingMessage?: string\n // Grid options\n gridOptions?: Partial<GridOptions<T>>\n // Grid initialization\n onGridReady?: (params: { api: GridApi<T> }) => void\n // Cell value changes\n onCellValueChanged?: (event: CellValueChangedEvent<T>) => void\n // Row click handler\n onRowClick?: (item: T) => void\n // State persistence.\n // The core is decoupled from any store: when `persistState` is on it seeds\n // AG Grid from `gridState` (read once at mount) and reports every subsequent\n // state change through `onGridStateChange`. An app-adapter wires these to its\n // own store. `gridId` is retained as an opaque identity hint for adapters\n // (the core itself does not read it).\n persistState?: boolean\n gridId?: string\n // Persisted column/sort/filter state to restore at mount (controlled input).\n gridState?: GridState\n // Called whenever AG Grid's state changes so an adapter can persist it.\n onGridStateChange?: (state: GridState) => void\n // Initial visible columns (applied when no saved state exists)\n initialVisibleColumns?: string[]\n // Basic styling\n className?: string\n height?: string | number\n // Per-instance row height. Applied via the theme (not just gridOptions) so the\n // theme's calculated line-height tracks it and cell content stays vertically\n // centered. Fixed height — keeps row virtualization on the fast path.\n rowHeight?: number\n testId?: string\n // Pinned rows\n pinnedBottomRowData?: T[]\n pinnedTopRowData?: T[]\n // Pagination (disabled by default)\n pagination?: boolean\n paginationPageSizeSelector?: number[]\n // Test-id hooks: the grid owns its row/cell DOM, so ids are stamped onto it after render.\n // `getRowTestId` names a row; `getCellTestId` a cell (by colId). Without them AG Grid's own\n // `row-id` / `col-id` attributes are still there to select by.\n getRowTestId?: (item: T) => string\n getCellTestId?: (colId: string, item: T) => string\n // Force empty-state UI even when items.length > 0.\n // Used when rows are present but all hidden by an external filter.\n showEmpty?: boolean\n}\n\n/** Minimum row height on coarse pointers: 44px touch target + the 1px row border + breathing room. */\nconst TOUCH_ROW_HEIGHT = 52\n\nconst COARSE_QUERY = '(pointer: coarse)'\nconst queryCoarsePointer = (): MediaQueryList | undefined =>\n typeof window !== 'undefined' && typeof window.matchMedia === 'function'\n ? (window.matchMedia(COARSE_QUERY) ?? undefined)\n : undefined\nconst getCoarsePointer = () => queryCoarsePointer()?.matches ?? false\nfunction subscribeCoarsePointer(onChange: () => void): () => void {\n const mq = queryCoarsePointer()\n mq?.addEventListener?.('change', onChange)\n return () => mq?.removeEventListener?.('change', onChange)\n}\n\nexport function GridView<T>({\n items,\n columnDefs,\n getItemId,\n selection,\n emptyState,\n isLoading = false,\n loadingMessage = 'Loading...',\n gridOptions,\n onGridReady,\n onCellValueChanged,\n onRowClick,\n persistState = false,\n gridState,\n onGridStateChange,\n initialVisibleColumns,\n className = 'w-full',\n height = 500,\n rowHeight: rowHeightProp,\n testId = 'grid-view',\n pinnedBottomRowData,\n pinnedTopRowData,\n pagination = false,\n paginationPageSizeSelector,\n getRowTestId,\n getCellTestId,\n showEmpty,\n}: GridViewProps<T>) {\n // Reference to the grid API\n const gridApiRef = useRef<GridApi<T> | null>(null)\n\n // On touch screens rows grow to a 44px-hit-area-friendly height: AG Grid clips cell content\n // (pills, filename buttons, avatar chips) to the row, so a taller hit area needs a taller row.\n const isCoarsePointer = useSyncExternalStore(\n subscribeCoarsePointer,\n getCoarsePointer,\n () => false\n )\n const rowHeight = isCoarsePointer\n ? Math.max(rowHeightProp ?? gridOptions?.rowHeight ?? 40, TOUCH_ROW_HEIGHT)\n : rowHeightProp\n\n // Initial row height, captured once so it can live in the (stable) default\n // grid options. rowHeight is NOT passed as a reactive prop — that would make\n // the AgGridReact wrapper re-process grid options on every change and snap\n // manually-resized columns back to their colDef widths. Subsequent changes are\n // applied imperatively (see effect below).\n const initialRowHeightRef = useRef(rowHeight)\n\n // Persisted state to seed the grid with — captured once at mount so a reactive\n // `gridState` prop (e.g. an adapter re-reading its store each render) can never\n // re-initialise the grid mid-session. Mirrors AG Grid's own initialState,\n // which is read once.\n const initialGridStateRef = useRef(gridState)\n\n // Get initial state for the grid (read once at mount)\n const initialState = useMemo(() => {\n if (!persistState) return undefined\n return initialGridStateRef.current\n }, [persistState])\n\n // Save grid state via the adapter using modern AG Grid state API\n const saveGridState = useCallback(() => {\n if (!persistState || !onGridStateChange || !gridApiRef.current) return\n\n // Use AG Grid's comprehensive state API to capture complete state\n // This includes: filters, sort, column order, column visibility, column widths, etc.\n const state = gridApiRef.current.getState()\n\n onGridStateChange(state)\n }, [persistState, onGridStateChange])\n\n // Ensure selection column is visible after grid initialization\n const ensureSelectionColumnVisible = useCallback(() => {\n if (!gridApiRef.current || !selection?.mode) return\n\n // IMPORTANT: Force selection column to be visible after state restoration\n // This ensures even old saved states don't hide the selection column\n // Also handles case where selection column is completely missing from state\n const currentState = gridApiRef.current.getColumnState()\n const selectionColumn = currentState.find((col) => col.colId === 'ag-Grid-SelectionColumn')\n const selectionColumnIndex = currentState.findIndex(\n (col) => col.colId === 'ag-Grid-SelectionColumn'\n )\n\n // Fix if column is hidden OR missing entirely OR not in first position\n if (!selectionColumn || selectionColumn.hide || selectionColumnIndex !== 0) {\n // Use setColumnsVisible for more reliable visibility control\n gridApiRef.current.setColumnsVisible(['ag-Grid-SelectionColumn'], true)\n\n // Also apply state to ensure proper width\n gridApiRef.current.applyColumnState({\n state: [\n {\n colId: 'ag-Grid-SelectionColumn',\n hide: false,\n width: selectionColumn?.width || 48,\n pinned: null, // Ensure not pinned in wrong position\n },\n ],\n defaultState: { hide: undefined },\n applyOrder: false,\n })\n\n // Move selection column to first position if it's not there\n if (selectionColumnIndex !== 0) {\n gridApiRef.current.moveColumns(['ag-Grid-SelectionColumn'], 0)\n }\n }\n }, [selection?.mode])\n\n // Stamp host test ids onto AG Grid's rows and cells (it virtualises, so keep watching).\n const containerRef = useRef<HTMLDivElement>(null)\n const itemsRef = useRef(items)\n itemsRef.current = items\n const getItemIdRef = useRef(getItemId)\n getItemIdRef.current = getItemId\n const hasTestIdHooks = Boolean(getRowTestId || getCellTestId)\n useEffect(() => {\n const root = containerRef.current\n if (!root || !hasTestIdHooks) return\n return watchGridTestIds(\n root,\n () => new Map(itemsRef.current.map((item) => [getItemIdRef.current(item), item])),\n { getRowTestId, getCellTestId }\n )\n }, [hasTestIdHooks, getRowTestId, getCellTestId, isLoading])\n\n // Handle row ID\n const getRowId = useCallback(\n (params: { data: T }) => {\n return getItemId(params.data)\n },\n [getItemId]\n )\n\n // Refs for selection — avoids handleGridReady/handleSelectionChanged recreating\n // when selection object changes (which happens on every selectionConfig recompute)\n const selectionRef = useRef(selection)\n selectionRef.current = selection\n\n const onSelectionChangeRef = useRef(selection?.onSelectionChange)\n onSelectionChangeRef.current = selection?.onSelectionChange\n\n const handleSelectionChanged = useCallback(() => {\n if (!onSelectionChangeRef.current || !gridApiRef.current) return\n\n const selectedNodes = gridApiRef.current.getSelectedNodes()\n const selectedData = selectedNodes\n .map((node) => node.data)\n .filter((item): item is T => item !== undefined)\n\n onSelectionChangeRef.current(selectedData)\n }, [])\n\n // Handle row clicks\n const handleRowClicked = useCallback(\n (event: RowClickedEvent<T>) => {\n if (!onRowClick || !event.data) return\n // Don't fire when the click originated from an interactive element inside the cell\n // (e.g. action buttons). AG Grid fires rowClicked regardless of DOM stopPropagation.\n const target = event.event?.target as HTMLElement | null\n if (target?.closest('button, input, a, select, textarea, [role=\"button\"]')) return\n onRowClick(event.data)\n },\n [onRowClick]\n )\n\n // The visibility the user actually intends, per colId. AG Grid re-processes the\n // column definitions on some React re-renders even when the `columnDefs`\n // reference is unchanged, and that reset restores each colDef's `hide` — so a\n // column the user turned on (e.g. via a fields menu) silently disappears the\n // next time the host re-renders (opening an editor, selecting a row, …). We\n // remember the intended visibility and restore it whenever such a reset fires.\n // A Map (not a Set of hidden ids) so a genuinely NEW column from a real\n // columnDefs change — one we've never seen — is left at its colDef default\n // rather than force-shown.\n const desiredHiddenRef = useRef<Map<string, boolean> | null>(null)\n\n const snapshotDesiredHidden = useCallback(() => {\n const api = gridApiRef.current\n if (!api) return\n desiredHiddenRef.current = new Map(api.getColumnState().map((c) => [c.colId, !!c.hide]))\n }, [])\n\n // Handle grid ready\n const handleGridReady = useCallback(\n (event: GridReadyEvent<T>) => {\n gridApiRef.current = event.api\n\n // Apply initial visible columns when no saved state exists\n // This prevents showing all columns by default for new users\n if (!initialState && initialVisibleColumns?.length) {\n const currentState = event.api.getColumnState()\n const stateMap = new Map(currentState.map((col) => [col.colId, col]))\n const visibleSet = new Set(initialVisibleColumns)\n\n // Build ordered state: selection column first (always visible), then visible columns, then hidden\n const selectionCol = stateMap.get('ag-Grid-SelectionColumn')\n const orderedState = [\n // Selection column first - ALWAYS visible, create if not in state\n selectionCol\n ? { ...selectionCol, hide: false }\n : { colId: 'ag-Grid-SelectionColumn', hide: false, width: 48 },\n // Visible columns in specified order\n ...initialVisibleColumns\n .filter((colId) => colId !== 'ag-Grid-SelectionColumn') // Don't duplicate selection column\n .map((colId) => {\n const col = stateMap.get(colId)\n return col ? { ...col, hide: false } : undefined\n }),\n // Hidden columns (everything else)\n ...currentState\n .filter((col) => col.colId !== 'ag-Grid-SelectionColumn' && !visibleSet.has(col.colId))\n .map((col) => ({ ...col, hide: true })),\n ].filter((col): col is NonNullable<typeof col> => col !== undefined)\n\n event.api.applyColumnState({ state: orderedState, applyOrder: true })\n }\n\n // When restoring persisted state, detect columns from columnDefs that\n // aren't in the saved state (e.g. newly added columns) and append them.\n // AG Grid's maintainColumnOrder adds them but may place them inconsistently;\n // this ensures they appear as hidden at the end so the navigator picks them up.\n if (initialState && initialVisibleColumns?.length) {\n const currentState = event.api.getColumnState()\n const savedColIds = new Set(\n initialState.columnOrder?.orderedColIds ?? currentState.map((c) => c.colId)\n )\n const newCols = currentState.filter(\n (col) => !savedColIds.has(col.colId) && col.colId !== 'ag-Grid-SelectionColumn'\n )\n if (newCols.length > 0) {\n // Make new columns visible if they're in the default visible set\n const defaultVisible = new Set(initialVisibleColumns)\n event.api.applyColumnState({\n state: newCols.map((col) => ({\n ...col,\n hide: !defaultVisible.has(col.colId),\n })),\n })\n }\n }\n\n // Ensure selection column is visible (in case saved state hides it)\n ensureSelectionColumnVisible()\n\n // Seed the intended column visibility from the state AG Grid settled on\n // (colDefs + restored persisted state) so a later colDef-driven reset can\n // be undone rather than silently hiding a user-shown column.\n snapshotDesiredHidden()\n\n // Call the provided onGridReady callback\n if (onGridReady) {\n onGridReady({ api: event.api })\n }\n\n // Restore selection state if needed (read from ref to keep callback stable)\n const sel = selectionRef.current\n if (sel && sel.selected.length > 0) {\n const selectedIds = new Set(sel.selected.map(getItemId))\n event.api.forEachNode((node) => {\n if (node.data && selectedIds.has(getItemId(node.data))) {\n node.setSelected(true)\n }\n })\n }\n },\n [\n onGridReady,\n getItemId,\n ensureSelectionColumnVisible,\n snapshotDesiredHidden,\n initialState,\n initialVisibleColumns,\n ]\n )\n\n // Undo AG Grid's colDef-driven visibility reset; record genuine user changes.\n const handleColumnVisible = useCallback(\n (event: { source?: string }) => {\n const api = gridApiRef.current\n if (!api) return\n // A columnDefs re-apply reports `gridOptionsChanged`; a real toggle reports\n // an interaction source (api, toolPanelUi, columnMenu, …).\n if (event.source === 'gridOptionsChanged') {\n const desired = desiredHiddenRef.current\n if (!desired) return\n // Only correct columns we've seen before (in the snapshot); a brand-new\n // column keeps its colDef default.\n const fixes = api\n .getColumnState()\n .filter(\n (c) =>\n c.colId !== 'ag-Grid-SelectionColumn' &&\n desired.has(c.colId) &&\n desired.get(c.colId) !== !!c.hide\n )\n .map((c) => ({ colId: c.colId, hide: desired.get(c.colId) }))\n if (fixes.length) api.applyColumnState({ state: fixes })\n } else {\n // Genuine change — this is now the intended visibility.\n snapshotDesiredHidden()\n }\n },\n [snapshotDesiredHidden]\n )\n\n // Handle first data rendered - no auto-sizing, let flex columns handle it\n const handleFirstDataRendered = useCallback(() => {\n // Columns with flex will auto-fill, columns with width stay fixed\n // Also ensure selection column is visible as a backup (handles timing issues with initialState)\n ensureSelectionColumnVisible()\n // Seed the intended visibility from the state AG Grid settled on (colDefs +\n // any restored persisted state), so later resets can be undone.\n snapshotDesiredHidden()\n }, [ensureSelectionColumnVisible, snapshotDesiredHidden])\n\n // Track when AG Grid processes row updates\n const handleModelUpdated = useCallback(() => {\n // AG Grid handles model updates internally\n }, [])\n\n // Track row data changes for AG Grid updates\n const prevItemsRef = useRef<T[]>([])\n useEffect(() => {\n prevItemsRef.current = items\n }, [items])\n\n // Handle state updates - save state when it changes (modern AG Grid approach)\n const handleStateUpdated = useCallback(() => {\n saveGridState()\n }, [saveGridState])\n\n // Removed problematic useEffect that caused unnecessary re-renders\n // AG Grid handles selection internally, only sync on initial load\n\n // Default grid options with minimal settings - memoized to prevent re-renders\n const defaultOptions: GridOptions<T> = useMemo(() => {\n return {\n // Initial row height (stable — captured once). Live changes go through the\n // imperative effect, not this option, to avoid column-state churn.\n rowHeight: initialRowHeightRef.current,\n suppressMenuHide: true, // Prevent hiding columns since we don't have enterprise sidebar\n maintainColumnOrder: true, // Preserve column order when columns are added/removed\n\n // Row virtualization: Render rows as needed for performance\n // rowBuffer renders extra rows above/below viewport for smoother scrolling\n rowBuffer: 10, // Render 10 extra rows above/below viewport for smooth scrolling\n suppressColumnVirtualisation: false, // Keep column virtualization enabled\n suppressRowVirtualisation: false, // ENABLE row virtualization - only render visible rows\n animateRows: false, // Disable row animations\n suppressColumnMoveAnimation: true, // Disable column move/resize animations\n\n // Efficient updates with React Query cache\n // getRowId enables change detection - grid only re-renders changed rows\n // Works perfectly with React Query's cache updates\n getRowId: getRowId,\n\n rowSelection: selection?.mode\n ? {\n mode: selection.mode === 'single' ? 'singleRow' : 'multiRow',\n selectAll: 'filtered', // Header checkbox selects all filtered rows (across all pages)\n // In multi-row mode, only checkboxes should toggle selection (clicking row body would replace selection)\n enableClickSelection: selection.mode === 'single',\n checkboxes: true,\n headerCheckbox: selection.mode === 'multiple',\n }\n : undefined,\n selectionColumnDef: selection?.mode\n ? {\n sortable: selection.mode === 'multiple',\n width: 48,\n lockVisible: true, // Cannot be hidden\n suppressMovable: true, // Cannot be moved\n }\n : undefined,\n // Use normal layout for better performance - autoHeight causes forced reflows\n domLayout: 'normal',\n // Stop editing when clicking outside the cell/grid\n stopEditingWhenCellsLoseFocus: true,\n // Additional performance optimizations\n suppressCellFocus: true, // Don't focus cells on click (faster)\n suppressRowHoverHighlight: true, // Disable hover highlight - reduces DOM manipulation during scroll\n suppressScrollOnNewData: true, // Don't scroll when data updates\n suppressAggFuncInHeader: true, // Don't show aggregation functions (faster)\n // Tooltip UX: the AG Grid default show-delay is 2 s which hurts\n // discoverability for cells where tooltips carry the \"reveal full\n // content\" affordance for non-editable users. 300 ms is snappy\n // without being accidental. tooltipInteraction lets users hover\n // onto the tooltip itself (e.g. to select / copy long text).\n // These are AG Grid's native tooltip controls — no React / Radix\n // provider involved, zero per-row cost; tooltip DOM is created on\n // demand when hover-delay elapses and destroyed on mouseout.\n tooltipShowDelay: 300,\n tooltipHideDelay: 4000,\n tooltipInteraction: true,\n // Pagination (disabled by default)\n pagination,\n paginationPageSizeSelector,\n defaultColDef: {\n sortable: true,\n resizable: true,\n unSortIcon: false, // Sort glyph only on the sorted column (every header carrying one was noise)\n sortingOrder: ['asc', 'desc', null], // 3-way sorting: asc → desc → unsorted (AG Grid default)\n wrapText: false, // Disable text wrapping for cleaner display\n autoHeight: false, // Use fixed row height from theme\n wrapHeaderText: false, // Disable header text wrapping for cleaner look\n autoHeaderHeight: false, // Fixed header height\n filterParams: {\n maxNumConditions: 1,\n buttons: ['reset'],\n },\n },\n }\n }, [selection?.mode, getRowId, pagination, paginationPageSizeSelector])\n\n // Combine default options with passed options - memoized to prevent re-renders\n const combinedOptions = useMemo(\n () => ({ ...defaultOptions, ...gridOptions }),\n [defaultOptions, gridOptions]\n )\n\n // Apply fixed height for better performance — autoHeight causes forced\n // reflows by measuring all rows, avoid it.\n //\n // Also derive the geometry the wrapping multiline columns (.cell-multiline —\n // Abstract, Author, custom text fields) need so their overflow clip lands on\n // a WHOLE-line boundary (never mid-line, which reads as a half-line\n // \"bleeding\" into the neighbouring row). All computed once here per\n // row-height change and handed to CSS as variables — zero per-row cost on the\n // million-row grid:\n // --multiline-line-clamp : whole number of lines that fit — drives the CSS\n // line-clamp that hides overflow lines entirely.\n // --multiline-pad-y : vertical cell padding, shrunk on very short rows so\n // at least one whole line always fits.\n // --multiline-max-h : cap of exactly N whole lines + TOP padding + borders.\n // Deliberately excludes the bottom padding: AG Grid\n // forces cell height, so overflow clips at the\n // padding-box edge and any bottom padding becomes a\n // window onto the next (clamped-away) line. Ending the\n // box right at line N's bottom puts the clip on the\n // line boundary; the row supplies the visual gap below.\n const containerStyle = useMemo(() => {\n const style: React.CSSProperties = { height }\n if (rowHeight) {\n const LINE_PX = 14 * 1.35 // grid font-size × multiline line-height (18.9px)\n const BORDER = 2 // multiline cell top + bottom border (1px each, border-box)\n const PREFERRED_PAD = 16 // preferred total vertical padding (8px top + 8px bottom)\n // Don't let padding eat the room a single line needs on short rows.\n const padTotal = Math.max(0, Math.min(PREFERRED_PAD, rowHeight - BORDER - LINE_PX))\n const lines = Math.max(1, Math.floor((rowHeight - BORDER - padTotal) / LINE_PX))\n const vars = style as Record<string, string | number>\n vars['--multiline-line-clamp'] = `${lines}`\n vars['--multiline-pad-y'] = `${padTotal / 2}px`\n vars['--multiline-max-h'] = `${lines * LINE_PX + padTotal / 2 + BORDER}px`\n }\n return style\n }, [height, rowHeight])\n\n // Apply rowHeight changes imperatively via the grid option (not the theme —\n // recreating the theme would re-initialise the grid). This only re-lays-out\n // rows; columns, row virtualization, and the transaction bus are untouched.\n useEffect(() => {\n const api = gridApiRef.current\n if (!api || api.isDestroyed() || !rowHeight) return\n api.setGridOption('rowHeight', rowHeight)\n api.resetRowHeights()\n }, [rowHeight])\n\n // Add professional shadow for 3D effect\n // Add overflow-visible only for autoHeight layout\n const containerClassName = useMemo(() => {\n const baseClass = className || ''\n const shadowClass = 'shadow-sm' // Tailwind shadow for professional look\n // Height-adjustable grids vertically center cell content (CSS) so a\n // one-line cell or a lone pill sits in the middle of the row, and multi-line\n // text (e.g. Abstract) is balanced top-to-bottom — flagged here, applied in\n // grid.css.\n const alignClass = rowHeight ? 'ag-cells-centered' : ''\n return [baseClass, shadowClass, alignClass].filter(Boolean).join(' ')\n }, [className, rowHeight])\n\n // Show loading state — grey skeleton rows so the page transition feels instant\n if (isLoading) {\n const skeletonRowCount = 12\n return (\n <div\n data-testid={`${testId}-loading`}\n className={containerClassName}\n style={containerStyle}\n aria-busy=\"true\"\n aria-label={loadingMessage}\n >\n {/* Header skeleton */}\n <div className=\"flex h-11 items-center gap-4 border-b border-border/40 px-4\">\n <div className=\"h-3 w-6 rounded bg-muted animate-pulse\" />\n <div className=\"h-3 w-32 rounded bg-muted animate-pulse\" />\n <div className=\"h-3 w-24 rounded bg-muted animate-pulse\" />\n <div className=\"h-3 w-20 rounded bg-muted animate-pulse\" />\n <div className=\"h-3 w-28 rounded bg-muted animate-pulse\" />\n <div className=\"h-3 w-16 rounded bg-muted animate-pulse ml-auto\" />\n </div>\n {/* Row skeletons */}\n {Array.from({ length: skeletonRowCount }).map((_, rowIdx) => (\n <div key={rowIdx} className=\"flex h-10 items-center gap-4 border-b border-border/20 px-4\">\n <div className=\"h-4 w-4 rounded-sm bg-muted/70 animate-pulse\" />\n <div\n className=\"h-3 rounded bg-muted/70 animate-pulse\"\n style={{ width: `${20 + ((rowIdx * 17) % 40)}%` }}\n />\n <div\n className=\"h-3 rounded bg-muted/60 animate-pulse\"\n style={{ width: `${8 + ((rowIdx * 11) % 12)}%` }}\n />\n <div\n className=\"h-3 rounded bg-muted/60 animate-pulse\"\n style={{ width: `${6 + ((rowIdx * 7) % 10)}%` }}\n />\n <div\n className=\"h-3 rounded bg-muted/50 animate-pulse ml-auto\"\n style={{ width: `${5 + ((rowIdx * 5) % 8)}%` }}\n />\n </div>\n ))}\n </div>\n )\n }\n\n // Show empty state\n // showEmpty lets callers force this UI (e.g. when an external filter hid\n // every row but the underlying items array is non-empty).\n if ((showEmpty ?? items.length === 0) && emptyState) {\n return (\n <div\n data-testid={`${testId}-empty`}\n // Capped by its container (a landscape phone is shorter than 24rem) and scrollable, with the\n // content centred by auto margins so a tall one still starts at the top.\n className=\"flex h-96 max-h-full flex-col items-center overflow-y-auto p-6 text-center\"\n >\n <div className=\"my-auto flex flex-col items-center\">\n {emptyState.icon && (\n <div className=\"text-muted-foreground/60 mb-4\">{emptyState.icon}</div>\n )}\n {emptyState.title && <h3 className=\"text-xl font-medium mb-2\">{emptyState.title}</h3>}\n {emptyState.message && (\n <p className=\"text-muted-foreground mb-6 max-w-md\">{emptyState.message}</p>\n )}\n {emptyState.action}\n </div>\n </div>\n )\n }\n\n return (\n <div\n ref={containerRef}\n className={containerClassName}\n style={containerStyle}\n data-testid={testId}\n >\n <AgGridReact\n theme={arbiTheme}\n modules={[AllCommunityModule]}\n columnDefs={columnDefs}\n rowData={items}\n pinnedBottomRowData={pinnedBottomRowData}\n pinnedTopRowData={pinnedTopRowData}\n getRowId={getRowId}\n initialState={initialState}\n onGridReady={handleGridReady}\n onFirstDataRendered={handleFirstDataRendered}\n onModelUpdated={handleModelUpdated}\n onSelectionChanged={handleSelectionChanged}\n onCellValueChanged={onCellValueChanged}\n onRowClicked={handleRowClicked}\n onStateUpdated={handleStateUpdated}\n onColumnVisible={handleColumnVisible}\n {...combinedOptions}\n />\n </div>\n )\n}\n","import { useRef, useState, type ReactNode } from 'react'\nimport { BookOpen, FileImage, Search, Table2 } from 'lucide-react'\nimport {\n Select,\n SelectContent,\n SelectItem,\n SelectTrigger,\n SelectValue,\n ToggleGroup,\n ToggleGroupItem,\n Tooltip,\n TooltipContent,\n TooltipTrigger,\n cn,\n} from '@arbidocs/react/ui'\nimport { testIdOr } from '../chat/test-id'\n\n/** Names of the four document view modes. Pass a partial `labels` to translate or reword. */\nexport interface DocumentViewToggleLabels {\n gallery: string\n table: string\n review: string\n smartSearch: string\n}\n\nexport const DEFAULT_DOCUMENT_VIEW_TOGGLE_LABELS: DocumentViewToggleLabels = {\n gallery: 'Gallery',\n table: 'Table',\n review: 'Review',\n smartSearch: 'Smart Search',\n}\n\nexport interface ViewToggleOption {\n value: string\n icon: ReactNode\n label: string\n /** Overrides this item's test id (default `${testIdPrefix}-${value}-button`). */\n testId?: string\n}\n\nexport interface ViewToggleProps {\n options: ViewToggleOption[]\n value: string\n onChange: (value: string) => void\n /** Item test ids are `${testIdPrefix}-${value}-button` unless an option sets its own `testId`. */\n testIdPrefix?: string\n showLabels?: boolean\n hideTooltips?: boolean\n size?: 'default' | 'sm'\n /**\n * Collapse labels to icons by the width of the nearest `@container` ancestor instead of the\n * viewport. The consumer must mark that region `@container`.\n */\n containerCollapse?: boolean\n className?: string\n}\n\ninterface ViewToggleItemProps {\n option: ViewToggleOption\n size: 'default' | 'sm'\n testIdPrefix: string\n showLabel: boolean\n labelClassName: string\n hideTooltip: boolean\n}\n\nfunction ViewToggleItem({\n option,\n size,\n testIdPrefix,\n showLabel,\n labelClassName,\n hideTooltip,\n}: ViewToggleItemProps) {\n const labelRef = useRef<HTMLSpanElement>(null)\n const [isTipNeeded, setIsTipNeeded] = useState(true)\n // A control that shows its own text needs no tooltip repeating it; when the container is too\n // narrow and the label collapses to the icon, the tooltip is the label.\n const isLabelShown = () => !!labelRef.current && labelRef.current.offsetParent !== null\n const content = (\n <span\n className=\"flex items-center gap-1.5\"\n onPointerEnter={() => setIsTipNeeded(!isLabelShown())}\n onFocus={() => setIsTipNeeded(!isLabelShown())}\n >\n {option.icon}\n {showLabel && (\n <span ref={labelRef} className={labelClassName}>\n {option.label}\n </span>\n )}\n </span>\n )\n return (\n // The tooltip lives INSIDE the item: wrapping the ToggleGroupItem would make Radix\n // Tooltip's data-state collide with the toggle's on/off state.\n <ToggleGroupItem\n value={option.value}\n aria-label={option.label}\n size={size}\n className=\"rounded-[5px] border-0 bg-transparent text-muted-foreground pointer-coarse:min-h-11 data-[state=off]:hover:bg-background/60 data-[state=off]:hover:text-foreground data-[state=on]:bg-accent data-[state=on]:text-accent-foreground data-[state=on]:hover:bg-accent data-[state=on]:hover:text-accent-foreground\"\n data-testid={option.testId ?? `${testIdPrefix}-${option.value}-button`}\n >\n {hideTooltip ? (\n content\n ) : (\n <Tooltip>\n <TooltipTrigger asChild>{content}</TooltipTrigger>\n {isTipNeeded && <TooltipContent>{option.label}</TooltipContent>}\n </Tooltip>\n )}\n </ToggleGroupItem>\n )\n}\n\n/** Segmented view switch: selected = accent tint, tone-only hover, 44px targets on touch. */\nexport function ViewToggle({\n options,\n value,\n onChange,\n testIdPrefix = 'view',\n showLabels = false,\n hideTooltips = false,\n size = 'default',\n containerCollapse = false,\n className,\n}: ViewToggleProps) {\n const labelClassName = containerCollapse\n ? 'hidden @lg:inline text-sm'\n : 'hidden md:inline text-sm'\n return (\n <ToggleGroup\n variant=\"default\"\n type=\"single\"\n value={value}\n onValueChange={(next) => next && onChange(next)}\n className={cn('gap-0.5 rounded-md bg-muted p-0.5', className)}\n >\n {options.map((option) => (\n <ViewToggleItem\n key={option.value}\n option={option}\n size={size}\n testIdPrefix={testIdPrefix}\n showLabel={showLabels}\n labelClassName={labelClassName}\n hideTooltip={hideTooltips}\n />\n ))}\n </ToggleGroup>\n )\n}\n\nexport type DocumentViewMode = 'grid' | 'explorer' | 'navigator' | 'search'\n\nfunction documentViewOptions(l: DocumentViewToggleLabels): ViewToggleOption[] {\n return [\n // \"Gallery\" (page-preview grid) reads more conventionally than \"Tiles\".\n { value: 'explorer', icon: <FileImage className=\"size-3.5\" />, label: l.gallery },\n { value: 'grid', icon: <Table2 className=\"size-3.5\" />, label: l.table },\n { value: 'navigator', icon: <BookOpen className=\"size-3.5\" />, label: l.review },\n { value: 'search', icon: <Search className=\"size-3.5\" />, label: l.smartSearch },\n ]\n}\n\nexport interface DocumentViewToggleProps {\n viewMode: DocumentViewMode\n onChange: (mode: DocumentViewMode) => void\n /** Collapse the four modes into one select trigger (narrow viewports). */\n compact?: boolean\n labels?: Partial<DocumentViewToggleLabels>\n /** Overrides the segmented items' prefix (default `documents-layout`: `<prefix>-<mode>-button`). */\n testIdPrefix?: string\n /** Per-mode item ids, for hosts that keep their own (e.g. `documents-view-gallery`). */\n testIds?: Partial<Record<DocumentViewMode, string>>\n /** Overrides the compact select test ids (defaults keep the current ids). */\n compactTestIds?: Partial<{ select: string; option: (mode: DocumentViewMode) => string }>\n}\n\n/** The Documents page's Gallery / Table / Review / Smart Search switch. */\nexport function DocumentViewToggle({\n viewMode,\n onChange,\n compact,\n labels,\n testIdPrefix,\n testIds,\n compactTestIds,\n}: DocumentViewToggleProps) {\n const options = documentViewOptions({ ...DEFAULT_DOCUMENT_VIEW_TOGGLE_LABELS, ...labels }).map(\n (o) => ({ ...o, testId: testIds?.[o.value as DocumentViewMode] })\n )\n if (compact) {\n const current = options.find((o) => o.value === viewMode) ?? options[0]\n return (\n <Select value={viewMode} onValueChange={(v) => onChange(v as DocumentViewMode)}>\n <SelectTrigger\n className=\"h-7 w-10 justify-center gap-0 border-input p-0 pointer-coarse:h-11! pointer-coarse:w-11! shrink-0 [&>svg]:hidden\"\n aria-label={current.label}\n data-testid={testIdOr(compactTestIds?.select, {\n testId: 'documents-layout-compact-select',\n })}\n >\n <SelectValue>{current.icon}</SelectValue>\n </SelectTrigger>\n <SelectContent align=\"center\">\n {options.map((option) => (\n <SelectItem\n key={option.value}\n value={option.value}\n data-testid={testIdOr(compactTestIds?.option?.(option.value as DocumentViewMode), {\n testId: `documents-layout-compact-${option.value}-option`,\n })}\n >\n <span className=\"flex items-center gap-2\">\n {option.icon}\n {option.label}\n </span>\n </SelectItem>\n ))}\n </SelectContent>\n </Select>\n )\n }\n return (\n <ViewToggle\n options={options}\n value={viewMode}\n onChange={(v) => onChange(v as DocumentViewMode)}\n testIdPrefix={testIdPrefix ?? 'documents-layout'}\n showLabels\n containerCollapse\n size=\"sm\"\n />\n )\n}\n"]}