@tradalab/lyra 2.4.0 → 2.6.0
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.
- package/dist/blocks/index.js +18 -2
- package/dist/blocks/index.js.map +1 -1
- package/dist/{chunk-CV3UXQBT.js → chunk-L6AHYXII.js} +60 -4
- package/dist/chunk-L6AHYXII.js.map +1 -0
- package/dist/data-table/index.d.ts +32 -2
- package/dist/data-table/index.js +104 -5
- package/dist/data-table/index.js.map +1 -1
- package/dist/ui/index.js +2 -57
- package/dist/ui/index.js.map +1 -1
- package/package.json +1 -1
- package/dist/chunk-CV3UXQBT.js.map +0 -1
package/dist/blocks/index.js
CHANGED
|
@@ -432,6 +432,18 @@ var FALLBACK_ZONES = [
|
|
|
432
432
|
"America/New_York",
|
|
433
433
|
"America/Los_Angeles"
|
|
434
434
|
];
|
|
435
|
+
var IANA_PRIMARY = {
|
|
436
|
+
"America/Buenos_Aires": "America/Argentina/Buenos_Aires",
|
|
437
|
+
"America/Godthab": "America/Nuuk",
|
|
438
|
+
"Asia/Calcutta": "Asia/Kolkata",
|
|
439
|
+
"Asia/Katmandu": "Asia/Kathmandu",
|
|
440
|
+
"Asia/Rangoon": "Asia/Yangon",
|
|
441
|
+
"Asia/Saigon": "Asia/Ho_Chi_Minh",
|
|
442
|
+
"Atlantic/Faeroe": "Atlantic/Faroe",
|
|
443
|
+
"Europe/Kiev": "Europe/Kyiv",
|
|
444
|
+
"Pacific/Ponape": "Pacific/Pohnpei",
|
|
445
|
+
"Pacific/Truk": "Pacific/Chuuk"
|
|
446
|
+
};
|
|
435
447
|
var cachedZones = null;
|
|
436
448
|
function allZones() {
|
|
437
449
|
if (cachedZones) return cachedZones;
|
|
@@ -442,7 +454,10 @@ function allZones() {
|
|
|
442
454
|
} catch {
|
|
443
455
|
names = FALLBACK_ZONES;
|
|
444
456
|
}
|
|
445
|
-
cachedZones = names.map((name) =>
|
|
457
|
+
cachedZones = names.map((name) => {
|
|
458
|
+
const primary = IANA_PRIMARY[name] ?? name;
|
|
459
|
+
return { name: primary, offset: offsetOf(primary) };
|
|
460
|
+
});
|
|
446
461
|
return cachedZones;
|
|
447
462
|
}
|
|
448
463
|
function offsetOf(tz) {
|
|
@@ -458,7 +473,8 @@ function offsetOf(tz) {
|
|
|
458
473
|
}
|
|
459
474
|
function browserTz() {
|
|
460
475
|
try {
|
|
461
|
-
|
|
476
|
+
const tz = Intl.DateTimeFormat().resolvedOptions().timeZone || "UTC";
|
|
477
|
+
return IANA_PRIMARY[tz] ?? tz;
|
|
462
478
|
} catch {
|
|
463
479
|
return "UTC";
|
|
464
480
|
}
|
package/dist/blocks/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/blocks/form.tsx","../../src/blocks/panel.tsx","../../src/blocks/confirm/confirm-dialog.tsx","../../src/blocks/confirm/confirm-provider.tsx","../../src/blocks/confirm/use-confirm.tsx","../../src/blocks/tree/index.tsx","../../src/blocks/tz-picker.tsx","../../src/blocks/option-picker.tsx"],"names":["jsx","jsxs","createContext","useState","useContext","useId","React2","React3"],"mappings":"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","file":"index.js","sourcesContent":["\nimport * as React from \"react\"\nimport { type Label as LabelPrimitive, Slot } from \"radix-ui\"\nimport { Controller, FormProvider, useFormContext, type ControllerProps, type FieldPath, type FieldValues } from \"react-hook-form\"\n\nimport { cn } from \"~/utils/cn.js\"\nimport { Label } from \"~/ui/primitives/label.js\"\n\nconst Form = FormProvider\n\ntype FormFieldContextValue<TFieldValues extends FieldValues = FieldValues, TName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>> = {\n name: TName\n}\n\nconst FormFieldContext = React.createContext<FormFieldContextValue | null>(null)\n\nconst FormField = <TFieldValues extends FieldValues = FieldValues, TName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>>({\n ...props\n}: ControllerProps<TFieldValues, TName>) => {\n return (\n <FormFieldContext.Provider value={{ name: props.name }}>\n <Controller {...props} />\n </FormFieldContext.Provider>\n )\n}\n\nconst useFormField = () => {\n const fieldContext = React.useContext(FormFieldContext)\n const itemContext = React.useContext(FormItemContext)\n const { getFieldState, formState } = useFormContext()\n\n if (!fieldContext) {\n throw new Error(\"useFormField should be used within <FormField>\")\n }\n\n const fieldState = getFieldState(fieldContext.name, formState)\n\n const { id } = itemContext || {}\n\n return {\n id,\n name: fieldContext.name,\n formItemId: `${id}-form-item`,\n formDescriptionId: `${id}-form-item-description`,\n formMessageId: `${id}-form-item-message`,\n ...fieldState,\n }\n}\n\ntype FormItemContextValue = {\n id: string\n}\n\nconst FormItemContext = React.createContext<FormItemContextValue | null>(null)\n\nfunction FormItem({ className, ...props }: React.ComponentProps<\"div\">) {\n const id = React.useId()\n\n return (\n <FormItemContext.Provider value={{ id }}>\n <div data-slot=\"form-item\" className={cn(\"grid gap-2\", className)} {...props} />\n </FormItemContext.Provider>\n )\n}\n\nfunction FormLabel({ className, ...props }: React.ComponentProps<typeof LabelPrimitive.Root>) {\n const { error, formItemId } = useFormField()\n\n return <Label data-slot=\"form-label\" data-error={!!error} className={cn(\"data-[error=true]:text-destructive\", className)} htmlFor={formItemId} {...props} />\n}\n\nfunction FormControl({ ...props }: React.ComponentProps<typeof Slot.Root>) {\n const { error, formItemId, formDescriptionId, formMessageId } = useFormField()\n\n return (\n <Slot.Root\n data-slot=\"form-control\"\n id={formItemId}\n aria-describedby={!error ? `${formDescriptionId}` : `${formDescriptionId} ${formMessageId}`}\n aria-invalid={!!error}\n {...props}\n />\n )\n}\n\nfunction FormDescription({ className, ...props }: React.ComponentProps<\"p\">) {\n const { formDescriptionId } = useFormField()\n\n return <p data-slot=\"form-description\" id={formDescriptionId} className={cn(\"text-muted-foreground text-sm\", className)} {...props} />\n}\n\nfunction FormMessage({ className, ...props }: React.ComponentProps<\"p\">) {\n const { error, formMessageId } = useFormField()\n const body = error ? String(error?.message ?? \"\") : props.children\n\n if (!body) {\n return null\n }\n\n return (\n <p data-slot=\"form-message\" id={formMessageId} className={cn(\"text-destructive text-sm\", className)} {...props}>\n {body}\n </p>\n )\n}\n\nexport { useFormField, Form, FormItem, FormLabel, FormControl, FormDescription, FormMessage, FormField }\n","\nimport { type ReactNode, useEffect, useMemo, useState } from \"react\"\nimport { useRouter, useSearchParams } from \"next/navigation\"\nimport { type LucideIcon } from \"lucide-react\"\nimport { Card, CardContent, CardDescription, CardFooter, CardHeader, CardTitle } from \"~/ui/primitives/card.js\"\nimport { cn } from \"~/utils/cn.js\"\n\ntype PanelItemType = {\n key: string\n label: string\n icon?: LucideIcon\n danger?: boolean\n hasError?: boolean\n content: ReactNode\n}\n\nexport function Panel({ name, items, enable_url }: { name?: string; items: PanelItemType[]; enable_url?: boolean }) {\n const router = useRouter()\n const params = useSearchParams()\n\n const defaultKey = items[0]?.key\n\n const panelKey = useMemo(() => `panel${name ? \"-\" + name : \"\"}`, [name])\n\n // get panel from url\n const panelFromUrl = useMemo(() => {\n if (!enable_url) return defaultKey\n return params.get(panelKey) ?? defaultKey\n }, [enable_url, params, defaultKey, panelKey])\n\n // set active\n const [active, setActive] = useState(panelFromUrl)\n\n // sync URL → state\n useEffect(() => {\n if (!enable_url) return\n setActive(panelFromUrl)\n }, [panelFromUrl, enable_url])\n\n const current = items.find(s => s.key === active) ?? items[0]\n if (!current) return null\n\n const navigate = (key: string) => {\n if (key === active) return\n setActive(key)\n if (!enable_url) return\n router.replace(`?${panelKey}=${key}`, { scroll: false })\n }\n\n return (\n <div className=\"space-y-6 h-full min-h-0 flex flex-col\">\n {/* Mobi */}\n <div className=\"lg:hidden\">\n <div className=\"inline-flex rounded-lg bg-muted p-1\">\n {items?.map(s => (\n <button\n key={s.key}\n onClick={() => navigate(s.key)}\n className={cn(\n \"rounded-md px-3 py-1.5 text-sm transition-all\",\n active === s.key ? \"bg-background text-foreground shadow-sm\" : s.danger ? \"text-destructive\" : \"text-muted-foreground hover:text-foreground\"\n )}\n >\n <span className=\"relative flex items-center gap-2\">\n {s.icon && <s.icon className=\"h-4 w-4\" />}\n {s.label}\n {s.hasError && <span className=\"absolute -top-1 -right-2 flex h-2 w-2 rounded-full bg-destructive\" />}\n </span>\n </button>\n ))}\n </div>\n </div>\n\n {/* Desktop */}\n <div className=\"grid grid-cols-1 gap-8 lg:grid-cols-[240px_1fr] flex-1 min-h-0\">\n {/* Sidebar */}\n <aside className=\"hidden space-y-1 lg:block overflow-y-auto min-h-0 pr-1 [overflow:overlay]\">\n {items?.map(s => (\n <PanelItem key={s.key} active={active === s.key} icon={s.icon} danger={s.danger} hasError={s.hasError} onClick={() => navigate(s.key)}>\n {s.label}\n </PanelItem>\n ))}\n </aside>\n {/* Content */}\n <div className=\"space-y-6 overflow-y-auto min-h-0 pr-1 [overflow:overlay]\">{current.content}</div>\n </div>\n </div>\n )\n}\n\nexport interface PanelItemProps {\n children: ReactNode\n active?: boolean\n icon?: LucideIcon\n danger?: boolean\n hasError?: boolean\n onClick?: () => void\n}\n\nfunction PanelItem({ children, active, icon: Icon, danger, hasError, onClick }: PanelItemProps) {\n return (\n <div\n onClick={onClick}\n className={cn(\n \"cursor-pointer rounded-md px-3 py-2 text-sm transition-colors flex items-center justify-between\",\n active ? \"bg-muted font-medium\" : danger ? \"text-destructive hover:bg-destructive/10\" : \"text-muted-foreground hover:bg-muted\"\n )}\n >\n <span className=\"flex items-center gap-2\">\n {Icon && <Icon className=\"h-4 w-4 shrink-0\" />}\n {children}\n </span>\n {hasError && <span className=\"h-2 w-2 rounded-full bg-destructive\" />}\n </div>\n )\n}\n\nexport interface PanelCardProps {\n title: string\n description?: string\n hint?: string\n action?: ReactNode\n children?: ReactNode\n}\n\nexport function PanelCard({ title, description, hint, action, children }: PanelCardProps) {\n return (\n <Card className={cn({ \"pb-3\": hint || action })}>\n <CardHeader>\n <CardTitle className=\"text-base\">{title}</CardTitle>\n {description && <CardDescription className=\"max-w-2xl\">{description}</CardDescription>}\n </CardHeader>\n {children && <CardContent>{children}</CardContent>}\n {(hint || action) && (\n <CardFooter className=\"flex items-center justify-between border-t !pt-3 !pb-0\">\n <p className=\"text-sm text-muted-foreground\">{hint}</p>\n {action}\n </CardFooter>\n )}\n </Card>\n )\n}\n","\nimport { Dialog, DialogContent, DialogDescription, DialogOverlay, DialogTitle } from \"~/ui/primitives/dialog.js\"\nimport { Button } from \"~/ui/primitives/button.js\"\nimport { type ConfirmOptions } from \"./types.js\"\nimport { cn } from \"~/utils/cn.js\"\n\ntype Props = {\n options: ConfirmOptions\n onConfirm: () => void\n onCancel: () => void\n}\n\nexport function ConfirmDialog({ options, onConfirm, onCancel }: Props) {\n return (\n <Dialog open onOpenChange={val => !val && onCancel()}>\n <DialogOverlay className=\"fixed inset-0 bg-white/10\" />\n <DialogContent className={cn(\"fixed top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2\", \"p-4 w-[400px]\", \"focus:outline-none\")}>\n <DialogTitle className=\"text-sm font-medium\">{options.title}</DialogTitle>\n {options.description != null && (\n <DialogDescription asChild>\n <div className=\"mt-2 text-sm text-muted-foreground\">{options.description}</div>\n </DialogDescription>\n )}\n\n <div className=\"mt-2 flex justify-end gap-2\">\n <Button variant=\"outline\" size=\"sm\" onClick={onCancel}>\n {options.cancelText ?? \"Cancel\"}\n </Button>\n <Button size=\"sm\" onClick={onConfirm} className={cn(options.danger && \"bg-red-600 hover:bg-red-700 text-white\")}>\n {options.confirmText ?? \"Confirm\"}\n </Button>\n </div>\n </DialogContent>\n </Dialog>\n )\n}\n","\nimport { createContext, type ReactNode, useState } from \"react\"\nimport { type ConfirmOptions } from \"./types.js\"\nimport { ConfirmDialog } from \"./confirm-dialog.js\"\n\nexport type ConfirmFn = (options: ConfirmOptions) => Promise<boolean>\n\nexport const ConfirmContext = createContext<ConfirmFn | null>(null)\n\nexport function ConfirmProvider({ children }: { children: ReactNode }) {\n const [state, setState] = useState<{\n options: ConfirmOptions\n resolve: (v: boolean) => void\n } | null>(null)\n\n const confirm: ConfirmFn = options => new Promise<boolean>(resolve => setState({ options, resolve }))\n\n const close = (result: boolean) => {\n state?.resolve(result)\n setState(null)\n }\n\n return (\n <ConfirmContext.Provider value={confirm}>\n {children}\n\n {state && <ConfirmDialog options={state.options} onConfirm={() => close(true)} onCancel={() => close(false)} />}\n </ConfirmContext.Provider>\n )\n}\n","\nimport { useContext } from \"react\"\nimport { ConfirmContext } from \"./confirm-provider.js\"\n\nexport const useConfirm = () => {\n const ctx = useContext(ConfirmContext)\n if (!ctx) {\n throw new Error(\"useConfirm must be used inside ConfirmProvider\")\n }\n return ctx\n}\n","\nimport { ChevronRight, File, Folder, FolderOpen } from \"lucide-react\"\nimport { createContext, type HTMLAttributes, type ReactNode, useCallback, useContext, useId, useState } from \"react\"\nimport { cn } from \"~/utils/cn.js\"\n\ntype TreeContextType = {\n expandedIds: Set<string>\n selectedIds: string[]\n toggleExpanded: (nodeId: string) => void\n handleSelection: (nodeId: string, ctrlKey: boolean) => void\n showLines?: boolean\n showIcons?: boolean\n selectable?: boolean\n multiSelect?: boolean\n indent?: number\n animateExpand?: boolean\n}\n\nconst TreeContext = createContext<TreeContextType | undefined>(undefined)\n\nconst useTree = () => {\n const context = useContext(TreeContext)\n if (!context) {\n throw new Error(\"Tree components must be used within a TreeProvider\")\n }\n return context\n}\n\ntype TreeNodeContextType = {\n nodeId: string\n level: number\n isLast: boolean\n parentPath: boolean[]\n}\n\nconst TreeNodeContext = createContext<TreeNodeContextType | undefined>(undefined)\n\nconst useTreeNode = () => {\n const context = useContext(TreeNodeContext)\n if (!context) {\n throw new Error(\"TreeNode components must be used within a TreeNode\")\n }\n return context\n}\n\nexport type TreeProviderProps = {\n children: ReactNode\n defaultExpandedIds?: string[]\n showLines?: boolean\n showIcons?: boolean\n selectable?: boolean\n multiSelect?: boolean\n selectedIds?: string[]\n onSelectionChange?: (selectedIds: string[]) => void\n expandedIds?: Set<string>\n onExpandedChange?: (expandedIds: Set<string>) => void\n indent?: number\n animateExpand?: boolean\n className?: string\n}\n\nexport const TreeProvider = ({\n children,\n defaultExpandedIds = [],\n showLines = true,\n showIcons = true,\n selectable = true,\n multiSelect = false,\n selectedIds,\n onSelectionChange,\n indent = 20,\n animateExpand = true,\n className,\n expandedIds,\n onExpandedChange,\n}: TreeProviderProps) => {\n const [internalExpandedIds, setInternalExpandedIds] = useState<Set<string>>(new Set(defaultExpandedIds))\n const [internalSelectedIds, setInternalSelectedIds] = useState<string[]>(selectedIds ?? [])\n\n const isControlledSelected = selectedIds !== undefined && onSelectionChange !== undefined\n const currentSelectedIds = isControlledSelected ? selectedIds : internalSelectedIds\n\n const isControlledExpanded = expandedIds !== undefined && onExpandedChange !== undefined\n const currentExpandedIds = isControlledExpanded ? expandedIds : internalExpandedIds\n\n const toggleExpanded = useCallback(\n (nodeId: string) => {\n const newSet = new Set<string>(currentExpandedIds)\n if (newSet.has(nodeId)) {\n newSet.delete(nodeId)\n } else {\n newSet.add(nodeId)\n }\n\n if (isControlledExpanded) {\n onExpandedChange?.(newSet)\n } else {\n setInternalExpandedIds(newSet)\n }\n },\n [currentExpandedIds, isControlledExpanded, onExpandedChange]\n )\n\n const handleSelection = useCallback(\n (nodeId: string, ctrlKey = false) => {\n if (!selectable) {\n return\n }\n\n let newSelection: string[]\n\n if (multiSelect && ctrlKey) {\n newSelection = currentSelectedIds.includes(nodeId) ? currentSelectedIds.filter(id => id !== nodeId) : [...currentSelectedIds, nodeId]\n } else {\n newSelection = currentSelectedIds.includes(nodeId) ? [] : [nodeId]\n }\n\n if (isControlledSelected) {\n onSelectionChange?.(newSelection)\n } else {\n setInternalSelectedIds(newSelection)\n }\n },\n [selectable, multiSelect, currentSelectedIds, isControlledSelected, onSelectionChange]\n )\n\n return (\n <TreeContext.Provider\n value={{\n expandedIds: currentExpandedIds,\n selectedIds: currentSelectedIds,\n toggleExpanded,\n handleSelection,\n showLines,\n showIcons,\n selectable,\n multiSelect,\n indent,\n animateExpand,\n }}\n >\n <div className={cn(\"w-full\", className)}>{children}</div>\n </TreeContext.Provider>\n )\n}\n\nexport type TreeViewProps = HTMLAttributes<HTMLDivElement>\n\nexport const TreeView = ({ className, children, ...props }: TreeViewProps) => (\n <div className={cn(\"p-2\", className)} {...props}>\n {children}\n </div>\n)\n\nexport type TreeNodeProps = HTMLAttributes<HTMLDivElement> & {\n nodeId?: string\n level?: number\n isLast?: boolean\n parentPath?: boolean[]\n children?: ReactNode\n}\n\nexport const TreeNode = ({ nodeId: providedNodeId, level = 0, isLast = false, parentPath = [], children, className, onClick: _onClick, ...props }: TreeNodeProps) => {\n const generatedId = useId()\n const nodeId = providedNodeId ?? generatedId\n\n // Build the parent path - mark positions where the parent was the last child\n const currentPath = level === 0 ? [] : [...parentPath]\n if (level > 0 && parentPath.length < level - 1) {\n // Fill in missing levels with false (not last)\n while (currentPath.length < level - 1) {\n currentPath.push(false)\n }\n }\n if (level > 0) {\n currentPath[level - 1] = isLast\n }\n\n return (\n <TreeNodeContext.Provider\n value={{\n nodeId,\n level,\n isLast,\n parentPath: currentPath,\n }}\n >\n <div className={cn(\"select-none\", className)} {...props}>\n {children}\n </div>\n </TreeNodeContext.Provider>\n )\n}\n\nexport type TreeNodeTriggerProps = HTMLAttributes<HTMLDivElement> & {\n expandOnClick?: boolean\n}\n\nexport const TreeNodeTrigger = ({ children, className, onClick, expandOnClick = false, ...props }: TreeNodeTriggerProps) => {\n const { selectedIds, handleSelection, toggleExpanded, indent } = useTree()\n const { nodeId, level } = useTreeNode()\n const isSelected = selectedIds.includes(nodeId)\n\n return (\n <div\n className={cn(\n \"group relative mx-1 flex cursor-pointer items-center rounded-md px-3 transition-all duration-200\",\n \"hover:bg-accent/50\",\n isSelected && \"bg-accent/80\",\n className\n )}\n style={{ paddingLeft: level * (indent ?? 0) + 8, paddingTop: \"var(--tree-item-py)\", paddingBottom: \"var(--tree-item-py)\" }}\n onClick={e => {\n handleSelection(nodeId, e.ctrlKey || e.metaKey)\n if (expandOnClick) toggleExpanded(nodeId)\n onClick?.(e)\n }}\n onDoubleClick={e => {\n if (e.ctrlKey || e.metaKey) return\n toggleExpanded(nodeId)\n }}\n {...props}\n >\n <TreeLines />\n {children}\n </div>\n )\n}\n\nexport const TreeLines = () => {\n const { showLines, indent } = useTree()\n const { level, isLast, parentPath } = useTreeNode()\n\n if (!showLines || level === 0) {\n return null\n }\n\n return (\n <div className=\"pointer-events-none absolute top-0 bottom-0 left-0\">\n {/* Render vertical lines for all parent levels */}\n {Array.from({ length: level }, (_, index) => {\n const shouldHideLine = parentPath[index] === true\n if (shouldHideLine && index === level - 1) {\n return null\n }\n\n return (\n <div\n className=\"absolute top-0 bottom-0 border-border/40 border-l\"\n key={index.toString()}\n style={{\n left: index * (indent ?? 0) + 12,\n display: shouldHideLine ? \"none\" : \"block\",\n }}\n />\n )\n })}\n\n {/* Horizontal connector line */}\n <div\n className=\"absolute top-1/2 border-border/40 border-t\"\n style={{\n left: (level - 1) * (indent ?? 0) + 12,\n width: (indent ?? 0) - 4,\n transform: \"translateY(-1px)\",\n }}\n />\n\n {/* Vertical line to midpoint for last items */}\n {isLast && (\n <div\n className=\"absolute top-0 border-border/40 border-l\"\n style={{\n left: (level - 1) * (indent ?? 0) + 12,\n height: \"50%\",\n }}\n />\n )}\n </div>\n )\n}\n\nexport type TreeNodeContentProps = HTMLAttributes<HTMLDivElement> & {\n hasChildren?: boolean\n}\n\nexport const TreeNodeContent = ({ children, hasChildren = false, className, ...props }: TreeNodeContentProps) => {\n const { expandedIds } = useTree()\n const { nodeId } = useTreeNode()\n const isExpanded = expandedIds.has(nodeId)\n\n if (!hasChildren || !isExpanded) {\n return null\n }\n\n return (\n <div className={className} {...props}>\n {children}\n </div>\n )\n}\n\nexport type TreeExpanderProps = HTMLAttributes<HTMLDivElement> & {\n hasChildren?: boolean\n}\n\nexport const TreeExpander = ({ hasChildren = false, className, onClick, ...props }: TreeExpanderProps) => {\n const { expandedIds, toggleExpanded } = useTree()\n const { nodeId } = useTreeNode()\n const isExpanded = expandedIds.has(nodeId)\n\n if (!hasChildren) {\n return <div className=\"mr-1 h-4 w-4\" />\n }\n\n return (\n <div\n className={cn(\"mr-1 flex h-4 w-4 items-center justify-center transition-transform duration-150\", isExpanded && \"rotate-90\", className)}\n onClick={e => {\n e.stopPropagation()\n toggleExpanded(nodeId)\n onClick?.(e)\n }}\n {...props}\n >\n <ChevronRight className=\"h-3 w-3 text-muted-foreground\" />\n </div>\n )\n}\n\nexport type TreeIconProps = HTMLAttributes<HTMLDivElement> & {\n icon?: ReactNode\n hasChildren?: boolean\n}\n\nexport const TreeIcon = ({ icon, hasChildren = false, className, ...props }: TreeIconProps) => {\n const { showIcons, expandedIds } = useTree()\n const { nodeId } = useTreeNode()\n const isExpanded = expandedIds.has(nodeId)\n\n if (!showIcons) {\n return null\n }\n\n const getDefaultIcon = () => (hasChildren ? isExpanded ? <FolderOpen className=\"h-4 w-4\" /> : <Folder className=\"h-4 w-4\" /> : <File className=\"h-4 w-4\" />)\n\n return (\n <div className={cn(\"mr-2 flex h-4 w-4 items-center justify-center text-muted-foreground transition-transform\", className)} {...props}>\n {icon || getDefaultIcon()}\n </div>\n )\n}\n\nexport type TreeLabelProps = HTMLAttributes<HTMLSpanElement>\n\nexport const TreeLabel = ({ className, ...props }: TreeLabelProps) => <span className={cn(\"font flex-1 truncate text-sm\", className)} {...props} />\n","\"use client\"\n\nimport * as React from \"react\"\n\nimport {\n Combobox,\n ComboboxContent,\n ComboboxEmpty,\n ComboboxInput,\n ComboboxItem,\n ComboboxList,\n} from \"~/ui/primitives/combobox.js\"\n\n/**\n * Pick an IANA timezone instead of typing one.\n *\n * A zone is a spelling test with silent failure: `Asia/HoChiMinh`, `GMT+7` and `ICT` all look\n * right and none of them is a zone. Go's `time.LoadLocation` does not reject a wrong one\n * loudly - it fails, logs, and the caller falls back to UTC - so a typo becomes a whole site's\n * timesheet shifted by seven hours, which nobody reads as a spelling mistake.\n *\n * ⚠️ `Asia/Saigon` is NOT one of those typos, contrary to what the copies of this component in\n * people/web and attendance/web claimed. `Intl.supportedValuesOf(\"timeZone\")` returns the CLDR\n * canonical names, and CLDR canonical for Vietnam IS `Asia/Saigon` - `Asia/Ho_Chi_Minh` does\n * not appear in the list at all (measured: 418 zones, `Asia/Saigon` present, `Asia/Ho_Chi_Minh`\n * absent). Same for `Asia/Calcutta` over `Asia/Kolkata` and `Europe/Kiev` over `Europe/Kyiv`.\n *\n * So a value stored as `Asia/Ho_Chi_Minh` - which is what tzdata and most backends prefer - is\n * NOT in the offered list, and must still render as itself with a correct offset rather than\n * as an unrecognised string. `Intl` accepts the alias even though the list omits it, which is\n * what makes that possible.\n *\n * Lives in lyra rather than nekit even though it carries domain logic, because the rule that\n * decides is not \"UI vs logic\" - it is whether the component knows where its data comes from.\n * `PeoplePicker` next door takes an injected `search` for exactly that reason. This one reads\n * `Intl`, which is in the runtime: no network, no session, nothing an app has to hand it.\n *\n * Every zone is shown WITH its current offset. Four hundred names sorted alphabetically is\n * unusable; \"Asia/Ho_Chi_Minh · GMT+7\" is something a person can confirm at a glance, and that\n * glance is the only check standing between a typo and a wrong month.\n */\n\n/** A curated fallback for a runtime without `Intl.supportedValuesOf` (pre-2022 browsers).\n * Short on purpose - it exists so the control still works, not to be a tz database. */\nconst FALLBACK_ZONES = [\n \"UTC\",\n \"Asia/Ho_Chi_Minh\",\n \"Asia/Bangkok\",\n \"Asia/Singapore\",\n \"Asia/Tokyo\",\n \"Asia/Seoul\",\n \"Asia/Shanghai\",\n \"Asia/Kolkata\",\n \"Europe/London\",\n \"Europe/Berlin\",\n \"America/New_York\",\n \"America/Los_Angeles\",\n]\n\nexport interface TzPickerLabels {\n /** Shown when the value is empty and `allowInherit`. Default: \"Inherit\". */\n inherit?: string\n /** Placeholder for the search input. Default: \"Search timezone\". */\n search?: string\n /** Shown when the filter matches nothing. Default: \"No match\". */\n noMatch?: string\n // No `suggested`/`all` headings: the list is one flat group now. Declaring labels nothing\n // renders is how a message file ends up with keys three translators maintain for no screen.\n}\n\ninterface Zone {\n name: string\n offset: string\n}\n\n/**\n * Built once per page load, not per render: resolving the offset of ~420 zones means ~420\n * `Intl.DateTimeFormat` constructions, cheap once and visible on every keystroke.\n */\nlet cachedZones: Zone[] | null = null\n\nfunction allZones(): Zone[] {\n if (cachedZones) return cachedZones\n let names: string[]\n try {\n const supported = (Intl as unknown as { supportedValuesOf?: (k: string) => string[] })\n .supportedValuesOf\n names = supported ? supported(\"timeZone\") : FALLBACK_ZONES\n } catch {\n names = FALLBACK_ZONES\n }\n cachedZones = names.map((name) => ({ name, offset: offsetOf(name) }))\n return cachedZones\n}\n\n/** The zone's offset right now, as ICU spells it: \"GMT+7\", not \"UTC+7\". DST makes it a\n * snapshot, which is what a person recognising their own zone needs - not a promise about\n * January. */\nfunction offsetOf(tz: string): string {\n try {\n const parts = new Intl.DateTimeFormat(\"en-US\", {\n timeZone: tz,\n timeZoneName: \"shortOffset\",\n }).formatToParts(new Date())\n return parts.find((p) => p.type === \"timeZoneName\")?.value ?? \"\"\n } catch {\n return \"\"\n }\n}\n\nfunction browserTz(): string {\n try {\n return Intl.DateTimeFormat().resolvedOptions().timeZone || \"UTC\"\n } catch {\n return \"UTC\"\n }\n}\n\nexport interface TzPickerProps {\n /** IANA zone name, or \"\" for inherit. */\n value: string\n onChange: (tz: string) => void\n /**\n * Whether an empty value is meaningful here. It usually is: a device inherits from its site,\n * a site from its unit, a unit from its parent. Set false where a zone must be chosen.\n */\n allowInherit?: boolean\n labels?: TzPickerLabels\n disabled?: boolean\n id?: string\n className?: string\n}\n\n/**\n * Field names are `tz`/`name`, NOT `value`/`label`, on purpose: Base UI treats an item shaped\n * `{ value, label }` as self-describing and renders `label` directly, silently ignoring\n * `itemToStringLabel`. The offset would then vanish from the input - which is the one part of\n * the label that makes a zone recognisable.\n */\ninterface Entry {\n tz: string\n name: string\n offset: string\n}\n\nexport function TzPicker({\n value,\n onChange,\n allowInherit = true,\n labels,\n disabled,\n id,\n className,\n}: TzPickerProps) {\n const l = {\n inherit: labels?.inherit ?? \"Inherit\",\n search: labels?.search ?? \"Search timezone\",\n noMatch: labels?.noMatch ?? \"No match\",\n }\n const own = React.useMemo(() => browserTz(), [])\n\n const entries = React.useMemo<Entry[]>(() => {\n const zones = allZones()\n const out: Entry[] = []\n if (allowInherit) out.push({ tz: \"\", name: l.inherit, offset: \"\" })\n // The person filling this form is almost always near the place they are describing, so\n // their own zone is the likeliest answer - and the one hardest to find by scrolling.\n const ownZone = zones.find((z) => z.name === own)\n if (ownZone) out.push({ tz: own, name: own, offset: ownZone.offset })\n for (const z of zones) {\n if (z.name === own) continue\n out.push({ tz: z.name, name: z.name, offset: z.offset })\n }\n // A stored zone the LIST does not contain - an alias CLDR canonicalises away\n // (`Asia/Ho_Chi_Minh`), or one dropped from a later release. It keeps its own name, so the\n // control never misreports what is saved, and it still gets an offset: `Intl` resolves the\n // alias fine even though `supportedValuesOf` omits it. Only a genuinely invalid zone ends\n // up with an empty offset here.\n if (value !== \"\" && !zones.some((z) => z.name === value)) {\n out.push({ tz: value, name: value, offset: offsetOf(value) })\n }\n return out\n }, [allowInherit, l.inherit, own, value])\n\n const selected = entries.find((e) => e.tz === value) ?? entries[0]\n\n return (\n <Combobox\n items={entries}\n value={selected}\n onValueChange={(item: Entry | null) => onChange(item?.tz ?? \"\")}\n // Searchable by name AND offset: somebody who knows \"+7\" but not the city can still land\n // on it.\n itemToStringLabel={(e: Entry) => (e.offset ? `${e.name} · ${e.offset}` : e.name)}\n itemToStringValue={(e: Entry) => e.tz}\n isItemEqualToValue={(a: Entry, b: Entry) => a.tz === b.tz}\n disabled={disabled}\n >\n {/* w-full, not the default w-fit: a combobox trigger sized to its content renders short\n and clipped inside a form column, which reads as a different kind of field. */}\n <ComboboxInput\n id={id}\n placeholder={l.search}\n className={className ?? \"w-full\"}\n // A clear button only where empty is a legitimate answer. Where a zone is required,\n // clearing would offer a state the form cannot save.\n showClear={allowInherit}\n />\n <ComboboxContent>\n <ComboboxEmpty>{l.noMatch}</ComboboxEmpty>\n <ComboboxList>\n {(entry: Entry) => (\n <ComboboxItem key={entry.tz || \"__inherit\"} value={entry}>\n <span className=\"flex-1 truncate\">{entry.name}</span>\n <span className=\"text-muted-foreground text-xs\">{entry.offset}</span>\n </ComboboxItem>\n )}\n </ComboboxList>\n </ComboboxContent>\n </Combobox>\n )\n}\n","\"use client\"\n\nimport * as React from \"react\"\n\nimport {\n Combobox,\n ComboboxContent,\n ComboboxEmpty,\n ComboboxInput,\n ComboboxItem,\n ComboboxList,\n} from \"~/ui/primitives/combobox.js\"\n\n/**\n * Pick one id from a known set.\n *\n * The set is INJECTED. That is what lets this live in lyra: it never learns where the\n * options came from, so it works the same for org members, groups, or anything else the app\n * has already loaded - which is exactly how the three copies it replaces differed.\n *\n * Why it exists at all: the screens that use it used to ask for raw uuids typed into a text\n * box. Nobody knows a uuid, so the only way anyone filled those fields was by copying from\n * somewhere else, and a copy can be off by one row. In `people` that attached a personnel\n * record to the wrong account - a wrong-but-valid uid passes every server check and is found\n * by whoever opens someone else's file under their own name.\n *\n * Filtering is client-side, deliberately: every set here is org-scoped and already loaded for\n * the surrounding screen, so matching locally is instant and costs no round trip. A picker\n * paging over every account that exists (admin's platform-wide search) is a different\n * component with a different failure mode - see `PeoplePicker` in `@tradalab/lyra/people`,\n * which takes an async `search` and does not hold a controlled value.\n */\n\n/** One choosable thing: an id plus what a person actually recognises it by. */\nexport interface PickOption {\n id: string\n label: string\n /** Secondary line - an email, a status. Searchable along with the label. */\n hint?: string\n}\n\nexport interface OptionPickerLabels {\n /** Shown when nothing is selected. */\n placeholder?: string\n /** Placeholder inside the search box. */\n search?: string\n /** Shown when the filter matches nothing. */\n empty?: string\n}\n\nconst FALLBACK: Required<OptionPickerLabels> = {\n placeholder: \"Select…\",\n search: \"Search\",\n empty: \"No match\",\n}\n\n/**\n * Field names are `id`/`label`, and `label` is what Base UI renders when an item is shaped\n * `{ value, label }`. This shape uses `id`, so `itemToStringLabel` below is what actually\n * decides the input text - the same trap TzPicker documents.\n */\ninterface Entry extends PickOption {\n /** Present only for the empty selection, so `value` can round-trip \"\" safely. */\n none?: boolean\n}\n\nexport function OptionPicker({\n value,\n onChange,\n options,\n labels,\n disabled,\n id,\n className,\n}: {\n value: string\n onChange: (id: string) => void\n options: PickOption[]\n labels?: OptionPickerLabels\n disabled?: boolean\n id?: string\n className?: string\n}) {\n const t = (k: keyof OptionPickerLabels) => labels?.[k] ?? FALLBACK[k]\n const placeholder = labels?.placeholder ?? FALLBACK.placeholder\n\n const entries = React.useMemo<Entry[]>(() => {\n const out: Entry[] = [{ id: \"\", label: placeholder, none: true }, ...options]\n // A stored id that is nobody on the list: the account left the org, or the record was\n // linked before this control existed. Show the raw id rather than an empty box - the\n // field is NOT empty, and rendering it as empty invites overwriting it by accident.\n if (value !== \"\" && !options.some((o) => o.id === value)) {\n out.push({ id: value, label: value })\n }\n return out\n }, [options, value, placeholder])\n\n const selected = entries.find((e) => e.id === value) ?? entries[0]\n\n return (\n <Combobox\n items={entries}\n value={selected}\n onValueChange={(e: Entry | null) => onChange(e?.id ?? \"\")}\n // The id is part of the searchable text, not only the label: somebody holding a uid\n // from a log must still be able to find the person it belongs to.\n itemToStringLabel={(e: Entry) => (e.none ? e.label : `${e.label} ${e.hint ?? \"\"} ${e.id}`)}\n isItemEqualToValue={(a: Entry, b: Entry) => a.id === b.id}\n disabled={disabled}\n >\n {/* w-full, not the default w-fit: sized to content it renders short and clipped inside\n a form column. */}\n <ComboboxInput id={id} placeholder={t(\"search\")} className={className ?? \"w-full\"} />\n <ComboboxContent>\n <ComboboxEmpty>{t(\"empty\")}</ComboboxEmpty>\n <ComboboxList>\n {(entry: Entry) => (\n <ComboboxItem key={entry.id || \"__none\"} value={entry}>\n <div className=\"flex min-w-0 flex-1 flex-col\">\n <span className=\"truncate text-sm\">{entry.label}</span>\n {entry.hint ? (\n <span className=\"text-muted-foreground truncate text-xs\">{entry.hint}</span>\n ) : null}\n </div>\n </ComboboxItem>\n )}\n </ComboboxList>\n </ComboboxContent>\n </Combobox>\n )\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../../src/blocks/form.tsx","../../src/blocks/panel.tsx","../../src/blocks/confirm/confirm-dialog.tsx","../../src/blocks/confirm/confirm-provider.tsx","../../src/blocks/confirm/use-confirm.tsx","../../src/blocks/tree/index.tsx","../../src/blocks/tz-picker.tsx","../../src/blocks/option-picker.tsx"],"names":["jsx","jsxs","createContext","useState","useContext","useId","React2","React3"],"mappings":"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","file":"index.js","sourcesContent":["\nimport * as React from \"react\"\nimport { type Label as LabelPrimitive, Slot } from \"radix-ui\"\nimport { Controller, FormProvider, useFormContext, type ControllerProps, type FieldPath, type FieldValues } from \"react-hook-form\"\n\nimport { cn } from \"~/utils/cn.js\"\nimport { Label } from \"~/ui/primitives/label.js\"\n\nconst Form = FormProvider\n\ntype FormFieldContextValue<TFieldValues extends FieldValues = FieldValues, TName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>> = {\n name: TName\n}\n\nconst FormFieldContext = React.createContext<FormFieldContextValue | null>(null)\n\nconst FormField = <TFieldValues extends FieldValues = FieldValues, TName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>>({\n ...props\n}: ControllerProps<TFieldValues, TName>) => {\n return (\n <FormFieldContext.Provider value={{ name: props.name }}>\n <Controller {...props} />\n </FormFieldContext.Provider>\n )\n}\n\nconst useFormField = () => {\n const fieldContext = React.useContext(FormFieldContext)\n const itemContext = React.useContext(FormItemContext)\n const { getFieldState, formState } = useFormContext()\n\n if (!fieldContext) {\n throw new Error(\"useFormField should be used within <FormField>\")\n }\n\n const fieldState = getFieldState(fieldContext.name, formState)\n\n const { id } = itemContext || {}\n\n return {\n id,\n name: fieldContext.name,\n formItemId: `${id}-form-item`,\n formDescriptionId: `${id}-form-item-description`,\n formMessageId: `${id}-form-item-message`,\n ...fieldState,\n }\n}\n\ntype FormItemContextValue = {\n id: string\n}\n\nconst FormItemContext = React.createContext<FormItemContextValue | null>(null)\n\nfunction FormItem({ className, ...props }: React.ComponentProps<\"div\">) {\n const id = React.useId()\n\n return (\n <FormItemContext.Provider value={{ id }}>\n <div data-slot=\"form-item\" className={cn(\"grid gap-2\", className)} {...props} />\n </FormItemContext.Provider>\n )\n}\n\nfunction FormLabel({ className, ...props }: React.ComponentProps<typeof LabelPrimitive.Root>) {\n const { error, formItemId } = useFormField()\n\n return <Label data-slot=\"form-label\" data-error={!!error} className={cn(\"data-[error=true]:text-destructive\", className)} htmlFor={formItemId} {...props} />\n}\n\nfunction FormControl({ ...props }: React.ComponentProps<typeof Slot.Root>) {\n const { error, formItemId, formDescriptionId, formMessageId } = useFormField()\n\n return (\n <Slot.Root\n data-slot=\"form-control\"\n id={formItemId}\n aria-describedby={!error ? `${formDescriptionId}` : `${formDescriptionId} ${formMessageId}`}\n aria-invalid={!!error}\n {...props}\n />\n )\n}\n\nfunction FormDescription({ className, ...props }: React.ComponentProps<\"p\">) {\n const { formDescriptionId } = useFormField()\n\n return <p data-slot=\"form-description\" id={formDescriptionId} className={cn(\"text-muted-foreground text-sm\", className)} {...props} />\n}\n\nfunction FormMessage({ className, ...props }: React.ComponentProps<\"p\">) {\n const { error, formMessageId } = useFormField()\n const body = error ? String(error?.message ?? \"\") : props.children\n\n if (!body) {\n return null\n }\n\n return (\n <p data-slot=\"form-message\" id={formMessageId} className={cn(\"text-destructive text-sm\", className)} {...props}>\n {body}\n </p>\n )\n}\n\nexport { useFormField, Form, FormItem, FormLabel, FormControl, FormDescription, FormMessage, FormField }\n","\nimport { type ReactNode, useEffect, useMemo, useState } from \"react\"\nimport { useRouter, useSearchParams } from \"next/navigation\"\nimport { type LucideIcon } from \"lucide-react\"\nimport { Card, CardContent, CardDescription, CardFooter, CardHeader, CardTitle } from \"~/ui/primitives/card.js\"\nimport { cn } from \"~/utils/cn.js\"\n\ntype PanelItemType = {\n key: string\n label: string\n icon?: LucideIcon\n danger?: boolean\n hasError?: boolean\n content: ReactNode\n}\n\nexport function Panel({ name, items, enable_url }: { name?: string; items: PanelItemType[]; enable_url?: boolean }) {\n const router = useRouter()\n const params = useSearchParams()\n\n const defaultKey = items[0]?.key\n\n const panelKey = useMemo(() => `panel${name ? \"-\" + name : \"\"}`, [name])\n\n // get panel from url\n const panelFromUrl = useMemo(() => {\n if (!enable_url) return defaultKey\n return params.get(panelKey) ?? defaultKey\n }, [enable_url, params, defaultKey, panelKey])\n\n // set active\n const [active, setActive] = useState(panelFromUrl)\n\n // sync URL → state\n useEffect(() => {\n if (!enable_url) return\n setActive(panelFromUrl)\n }, [panelFromUrl, enable_url])\n\n const current = items.find(s => s.key === active) ?? items[0]\n if (!current) return null\n\n const navigate = (key: string) => {\n if (key === active) return\n setActive(key)\n if (!enable_url) return\n router.replace(`?${panelKey}=${key}`, { scroll: false })\n }\n\n return (\n <div className=\"space-y-6 h-full min-h-0 flex flex-col\">\n {/* Mobi */}\n <div className=\"lg:hidden\">\n <div className=\"inline-flex rounded-lg bg-muted p-1\">\n {items?.map(s => (\n <button\n key={s.key}\n onClick={() => navigate(s.key)}\n className={cn(\n \"rounded-md px-3 py-1.5 text-sm transition-all\",\n active === s.key ? \"bg-background text-foreground shadow-sm\" : s.danger ? \"text-destructive\" : \"text-muted-foreground hover:text-foreground\"\n )}\n >\n <span className=\"relative flex items-center gap-2\">\n {s.icon && <s.icon className=\"h-4 w-4\" />}\n {s.label}\n {s.hasError && <span className=\"absolute -top-1 -right-2 flex h-2 w-2 rounded-full bg-destructive\" />}\n </span>\n </button>\n ))}\n </div>\n </div>\n\n {/* Desktop */}\n <div className=\"grid grid-cols-1 gap-8 lg:grid-cols-[240px_1fr] flex-1 min-h-0\">\n {/* Sidebar */}\n <aside className=\"hidden space-y-1 lg:block overflow-y-auto min-h-0 pr-1 [overflow:overlay]\">\n {items?.map(s => (\n <PanelItem key={s.key} active={active === s.key} icon={s.icon} danger={s.danger} hasError={s.hasError} onClick={() => navigate(s.key)}>\n {s.label}\n </PanelItem>\n ))}\n </aside>\n {/* Content */}\n <div className=\"space-y-6 overflow-y-auto min-h-0 pr-1 [overflow:overlay]\">{current.content}</div>\n </div>\n </div>\n )\n}\n\nexport interface PanelItemProps {\n children: ReactNode\n active?: boolean\n icon?: LucideIcon\n danger?: boolean\n hasError?: boolean\n onClick?: () => void\n}\n\nfunction PanelItem({ children, active, icon: Icon, danger, hasError, onClick }: PanelItemProps) {\n return (\n <div\n onClick={onClick}\n className={cn(\n \"cursor-pointer rounded-md px-3 py-2 text-sm transition-colors flex items-center justify-between\",\n active ? \"bg-muted font-medium\" : danger ? \"text-destructive hover:bg-destructive/10\" : \"text-muted-foreground hover:bg-muted\"\n )}\n >\n <span className=\"flex items-center gap-2\">\n {Icon && <Icon className=\"h-4 w-4 shrink-0\" />}\n {children}\n </span>\n {hasError && <span className=\"h-2 w-2 rounded-full bg-destructive\" />}\n </div>\n )\n}\n\nexport interface PanelCardProps {\n title: string\n description?: string\n hint?: string\n action?: ReactNode\n children?: ReactNode\n}\n\nexport function PanelCard({ title, description, hint, action, children }: PanelCardProps) {\n return (\n <Card className={cn({ \"pb-3\": hint || action })}>\n <CardHeader>\n <CardTitle className=\"text-base\">{title}</CardTitle>\n {description && <CardDescription className=\"max-w-2xl\">{description}</CardDescription>}\n </CardHeader>\n {children && <CardContent>{children}</CardContent>}\n {(hint || action) && (\n <CardFooter className=\"flex items-center justify-between border-t !pt-3 !pb-0\">\n <p className=\"text-sm text-muted-foreground\">{hint}</p>\n {action}\n </CardFooter>\n )}\n </Card>\n )\n}\n","\nimport { Dialog, DialogContent, DialogDescription, DialogOverlay, DialogTitle } from \"~/ui/primitives/dialog.js\"\nimport { Button } from \"~/ui/primitives/button.js\"\nimport { type ConfirmOptions } from \"./types.js\"\nimport { cn } from \"~/utils/cn.js\"\n\ntype Props = {\n options: ConfirmOptions\n onConfirm: () => void\n onCancel: () => void\n}\n\nexport function ConfirmDialog({ options, onConfirm, onCancel }: Props) {\n return (\n <Dialog open onOpenChange={val => !val && onCancel()}>\n <DialogOverlay className=\"fixed inset-0 bg-white/10\" />\n <DialogContent className={cn(\"fixed top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2\", \"p-4 w-[400px]\", \"focus:outline-none\")}>\n <DialogTitle className=\"text-sm font-medium\">{options.title}</DialogTitle>\n {options.description != null && (\n <DialogDescription asChild>\n <div className=\"mt-2 text-sm text-muted-foreground\">{options.description}</div>\n </DialogDescription>\n )}\n\n <div className=\"mt-2 flex justify-end gap-2\">\n <Button variant=\"outline\" size=\"sm\" onClick={onCancel}>\n {options.cancelText ?? \"Cancel\"}\n </Button>\n <Button size=\"sm\" onClick={onConfirm} className={cn(options.danger && \"bg-red-600 hover:bg-red-700 text-white\")}>\n {options.confirmText ?? \"Confirm\"}\n </Button>\n </div>\n </DialogContent>\n </Dialog>\n )\n}\n","\nimport { createContext, type ReactNode, useState } from \"react\"\nimport { type ConfirmOptions } from \"./types.js\"\nimport { ConfirmDialog } from \"./confirm-dialog.js\"\n\nexport type ConfirmFn = (options: ConfirmOptions) => Promise<boolean>\n\nexport const ConfirmContext = createContext<ConfirmFn | null>(null)\n\nexport function ConfirmProvider({ children }: { children: ReactNode }) {\n const [state, setState] = useState<{\n options: ConfirmOptions\n resolve: (v: boolean) => void\n } | null>(null)\n\n const confirm: ConfirmFn = options => new Promise<boolean>(resolve => setState({ options, resolve }))\n\n const close = (result: boolean) => {\n state?.resolve(result)\n setState(null)\n }\n\n return (\n <ConfirmContext.Provider value={confirm}>\n {children}\n\n {state && <ConfirmDialog options={state.options} onConfirm={() => close(true)} onCancel={() => close(false)} />}\n </ConfirmContext.Provider>\n )\n}\n","\nimport { useContext } from \"react\"\nimport { ConfirmContext } from \"./confirm-provider.js\"\n\nexport const useConfirm = () => {\n const ctx = useContext(ConfirmContext)\n if (!ctx) {\n throw new Error(\"useConfirm must be used inside ConfirmProvider\")\n }\n return ctx\n}\n","\nimport { ChevronRight, File, Folder, FolderOpen } from \"lucide-react\"\nimport { createContext, type HTMLAttributes, type ReactNode, useCallback, useContext, useId, useState } from \"react\"\nimport { cn } from \"~/utils/cn.js\"\n\ntype TreeContextType = {\n expandedIds: Set<string>\n selectedIds: string[]\n toggleExpanded: (nodeId: string) => void\n handleSelection: (nodeId: string, ctrlKey: boolean) => void\n showLines?: boolean\n showIcons?: boolean\n selectable?: boolean\n multiSelect?: boolean\n indent?: number\n animateExpand?: boolean\n}\n\nconst TreeContext = createContext<TreeContextType | undefined>(undefined)\n\nconst useTree = () => {\n const context = useContext(TreeContext)\n if (!context) {\n throw new Error(\"Tree components must be used within a TreeProvider\")\n }\n return context\n}\n\ntype TreeNodeContextType = {\n nodeId: string\n level: number\n isLast: boolean\n parentPath: boolean[]\n}\n\nconst TreeNodeContext = createContext<TreeNodeContextType | undefined>(undefined)\n\nconst useTreeNode = () => {\n const context = useContext(TreeNodeContext)\n if (!context) {\n throw new Error(\"TreeNode components must be used within a TreeNode\")\n }\n return context\n}\n\nexport type TreeProviderProps = {\n children: ReactNode\n defaultExpandedIds?: string[]\n showLines?: boolean\n showIcons?: boolean\n selectable?: boolean\n multiSelect?: boolean\n selectedIds?: string[]\n onSelectionChange?: (selectedIds: string[]) => void\n expandedIds?: Set<string>\n onExpandedChange?: (expandedIds: Set<string>) => void\n indent?: number\n animateExpand?: boolean\n className?: string\n}\n\nexport const TreeProvider = ({\n children,\n defaultExpandedIds = [],\n showLines = true,\n showIcons = true,\n selectable = true,\n multiSelect = false,\n selectedIds,\n onSelectionChange,\n indent = 20,\n animateExpand = true,\n className,\n expandedIds,\n onExpandedChange,\n}: TreeProviderProps) => {\n const [internalExpandedIds, setInternalExpandedIds] = useState<Set<string>>(new Set(defaultExpandedIds))\n const [internalSelectedIds, setInternalSelectedIds] = useState<string[]>(selectedIds ?? [])\n\n const isControlledSelected = selectedIds !== undefined && onSelectionChange !== undefined\n const currentSelectedIds = isControlledSelected ? selectedIds : internalSelectedIds\n\n const isControlledExpanded = expandedIds !== undefined && onExpandedChange !== undefined\n const currentExpandedIds = isControlledExpanded ? expandedIds : internalExpandedIds\n\n const toggleExpanded = useCallback(\n (nodeId: string) => {\n const newSet = new Set<string>(currentExpandedIds)\n if (newSet.has(nodeId)) {\n newSet.delete(nodeId)\n } else {\n newSet.add(nodeId)\n }\n\n if (isControlledExpanded) {\n onExpandedChange?.(newSet)\n } else {\n setInternalExpandedIds(newSet)\n }\n },\n [currentExpandedIds, isControlledExpanded, onExpandedChange]\n )\n\n const handleSelection = useCallback(\n (nodeId: string, ctrlKey = false) => {\n if (!selectable) {\n return\n }\n\n let newSelection: string[]\n\n if (multiSelect && ctrlKey) {\n newSelection = currentSelectedIds.includes(nodeId) ? currentSelectedIds.filter(id => id !== nodeId) : [...currentSelectedIds, nodeId]\n } else {\n newSelection = currentSelectedIds.includes(nodeId) ? [] : [nodeId]\n }\n\n if (isControlledSelected) {\n onSelectionChange?.(newSelection)\n } else {\n setInternalSelectedIds(newSelection)\n }\n },\n [selectable, multiSelect, currentSelectedIds, isControlledSelected, onSelectionChange]\n )\n\n return (\n <TreeContext.Provider\n value={{\n expandedIds: currentExpandedIds,\n selectedIds: currentSelectedIds,\n toggleExpanded,\n handleSelection,\n showLines,\n showIcons,\n selectable,\n multiSelect,\n indent,\n animateExpand,\n }}\n >\n <div className={cn(\"w-full\", className)}>{children}</div>\n </TreeContext.Provider>\n )\n}\n\nexport type TreeViewProps = HTMLAttributes<HTMLDivElement>\n\nexport const TreeView = ({ className, children, ...props }: TreeViewProps) => (\n <div className={cn(\"p-2\", className)} {...props}>\n {children}\n </div>\n)\n\nexport type TreeNodeProps = HTMLAttributes<HTMLDivElement> & {\n nodeId?: string\n level?: number\n isLast?: boolean\n parentPath?: boolean[]\n children?: ReactNode\n}\n\nexport const TreeNode = ({ nodeId: providedNodeId, level = 0, isLast = false, parentPath = [], children, className, onClick: _onClick, ...props }: TreeNodeProps) => {\n const generatedId = useId()\n const nodeId = providedNodeId ?? generatedId\n\n // Build the parent path - mark positions where the parent was the last child\n const currentPath = level === 0 ? [] : [...parentPath]\n if (level > 0 && parentPath.length < level - 1) {\n // Fill in missing levels with false (not last)\n while (currentPath.length < level - 1) {\n currentPath.push(false)\n }\n }\n if (level > 0) {\n currentPath[level - 1] = isLast\n }\n\n return (\n <TreeNodeContext.Provider\n value={{\n nodeId,\n level,\n isLast,\n parentPath: currentPath,\n }}\n >\n <div className={cn(\"select-none\", className)} {...props}>\n {children}\n </div>\n </TreeNodeContext.Provider>\n )\n}\n\nexport type TreeNodeTriggerProps = HTMLAttributes<HTMLDivElement> & {\n expandOnClick?: boolean\n}\n\nexport const TreeNodeTrigger = ({ children, className, onClick, expandOnClick = false, ...props }: TreeNodeTriggerProps) => {\n const { selectedIds, handleSelection, toggleExpanded, indent } = useTree()\n const { nodeId, level } = useTreeNode()\n const isSelected = selectedIds.includes(nodeId)\n\n return (\n <div\n className={cn(\n \"group relative mx-1 flex cursor-pointer items-center rounded-md px-3 transition-all duration-200\",\n \"hover:bg-accent/50\",\n isSelected && \"bg-accent/80\",\n className\n )}\n style={{ paddingLeft: level * (indent ?? 0) + 8, paddingTop: \"var(--tree-item-py)\", paddingBottom: \"var(--tree-item-py)\" }}\n onClick={e => {\n handleSelection(nodeId, e.ctrlKey || e.metaKey)\n if (expandOnClick) toggleExpanded(nodeId)\n onClick?.(e)\n }}\n onDoubleClick={e => {\n if (e.ctrlKey || e.metaKey) return\n toggleExpanded(nodeId)\n }}\n {...props}\n >\n <TreeLines />\n {children}\n </div>\n )\n}\n\nexport const TreeLines = () => {\n const { showLines, indent } = useTree()\n const { level, isLast, parentPath } = useTreeNode()\n\n if (!showLines || level === 0) {\n return null\n }\n\n return (\n <div className=\"pointer-events-none absolute top-0 bottom-0 left-0\">\n {/* Render vertical lines for all parent levels */}\n {Array.from({ length: level }, (_, index) => {\n const shouldHideLine = parentPath[index] === true\n if (shouldHideLine && index === level - 1) {\n return null\n }\n\n return (\n <div\n className=\"absolute top-0 bottom-0 border-border/40 border-l\"\n key={index.toString()}\n style={{\n left: index * (indent ?? 0) + 12,\n display: shouldHideLine ? \"none\" : \"block\",\n }}\n />\n )\n })}\n\n {/* Horizontal connector line */}\n <div\n className=\"absolute top-1/2 border-border/40 border-t\"\n style={{\n left: (level - 1) * (indent ?? 0) + 12,\n width: (indent ?? 0) - 4,\n transform: \"translateY(-1px)\",\n }}\n />\n\n {/* Vertical line to midpoint for last items */}\n {isLast && (\n <div\n className=\"absolute top-0 border-border/40 border-l\"\n style={{\n left: (level - 1) * (indent ?? 0) + 12,\n height: \"50%\",\n }}\n />\n )}\n </div>\n )\n}\n\nexport type TreeNodeContentProps = HTMLAttributes<HTMLDivElement> & {\n hasChildren?: boolean\n}\n\nexport const TreeNodeContent = ({ children, hasChildren = false, className, ...props }: TreeNodeContentProps) => {\n const { expandedIds } = useTree()\n const { nodeId } = useTreeNode()\n const isExpanded = expandedIds.has(nodeId)\n\n if (!hasChildren || !isExpanded) {\n return null\n }\n\n return (\n <div className={className} {...props}>\n {children}\n </div>\n )\n}\n\nexport type TreeExpanderProps = HTMLAttributes<HTMLDivElement> & {\n hasChildren?: boolean\n}\n\nexport const TreeExpander = ({ hasChildren = false, className, onClick, ...props }: TreeExpanderProps) => {\n const { expandedIds, toggleExpanded } = useTree()\n const { nodeId } = useTreeNode()\n const isExpanded = expandedIds.has(nodeId)\n\n if (!hasChildren) {\n return <div className=\"mr-1 h-4 w-4\" />\n }\n\n return (\n <div\n className={cn(\"mr-1 flex h-4 w-4 items-center justify-center transition-transform duration-150\", isExpanded && \"rotate-90\", className)}\n onClick={e => {\n e.stopPropagation()\n toggleExpanded(nodeId)\n onClick?.(e)\n }}\n {...props}\n >\n <ChevronRight className=\"h-3 w-3 text-muted-foreground\" />\n </div>\n )\n}\n\nexport type TreeIconProps = HTMLAttributes<HTMLDivElement> & {\n icon?: ReactNode\n hasChildren?: boolean\n}\n\nexport const TreeIcon = ({ icon, hasChildren = false, className, ...props }: TreeIconProps) => {\n const { showIcons, expandedIds } = useTree()\n const { nodeId } = useTreeNode()\n const isExpanded = expandedIds.has(nodeId)\n\n if (!showIcons) {\n return null\n }\n\n const getDefaultIcon = () => (hasChildren ? isExpanded ? <FolderOpen className=\"h-4 w-4\" /> : <Folder className=\"h-4 w-4\" /> : <File className=\"h-4 w-4\" />)\n\n return (\n <div className={cn(\"mr-2 flex h-4 w-4 items-center justify-center text-muted-foreground transition-transform\", className)} {...props}>\n {icon || getDefaultIcon()}\n </div>\n )\n}\n\nexport type TreeLabelProps = HTMLAttributes<HTMLSpanElement>\n\nexport const TreeLabel = ({ className, ...props }: TreeLabelProps) => <span className={cn(\"font flex-1 truncate text-sm\", className)} {...props} />\n","\"use client\"\n\nimport * as React from \"react\"\n\nimport {\n Combobox,\n ComboboxContent,\n ComboboxEmpty,\n ComboboxInput,\n ComboboxItem,\n ComboboxList,\n} from \"~/ui/primitives/combobox.js\"\n\n/**\n * Pick an IANA timezone instead of typing one.\n *\n * A zone is a spelling test with silent failure: `Asia/HoChiMinh`, `GMT+7` and `ICT` all look\n * right and none of them is a zone. Go's `time.LoadLocation` does not reject a wrong one\n * loudly - it fails, logs, and the caller falls back to UTC - so a typo becomes a whole site's\n * timesheet shifted by seven hours, which nobody reads as a spelling mistake.\n *\n * ⚠️ `Asia/Saigon` is NOT one of those typos. `Intl.supportedValuesOf(\"timeZone\")` returns the\n * CLDR canonical names, and CLDR canonical for Vietnam IS `Asia/Saigon` - `Asia/Ho_Chi_Minh`\n * does not appear in that list at all. Same for `Asia/Calcutta` over `Asia/Kolkata` and\n * `Europe/Kiev` over `Europe/Kyiv`; see IANA_PRIMARY below for the measured set.\n *\n * The offered names are RENAMED to their IANA primaries anyway, because the offered name is the\n * STORED name, and the stored name is what every backend, log line and export then carries. Go\n * tzdata, this platform, and the people reading a Vietnamese timesheet all say\n * `Asia/Ho_Chi_Minh`; a control that can only offer `Asia/Saigon` reads as broken to all three,\n * and being technically correct did not stop somebody asking why the city was missing.\n *\n * A value stored under EITHER spelling still renders as itself with a correct offset: `Intl`\n * resolves both, and the entry list appends whatever is stored when the offered list omits it.\n *\n * Lives in lyra rather than nekit even though it carries domain logic, because the rule that\n * decides is not \"UI vs logic\" - it is whether the component knows where its data comes from.\n * `PeoplePicker` next door takes an injected `search` for exactly that reason. This one reads\n * `Intl`, which is in the runtime: no network, no session, nothing an app has to hand it.\n *\n * Every zone is shown WITH its current offset. Four hundred names sorted alphabetically is\n * unusable; \"Asia/Ho_Chi_Minh · GMT+7\" is something a person can confirm at a glance, and that\n * glance is the only check standing between a typo and a wrong month.\n */\n\n/** A curated fallback for a runtime without `Intl.supportedValuesOf` (pre-2022 browsers).\n * Short on purpose - it exists so the control still works, not to be a tz database. */\nconst FALLBACK_ZONES = [\n \"UTC\",\n \"Asia/Ho_Chi_Minh\",\n \"Asia/Bangkok\",\n \"Asia/Singapore\",\n \"Asia/Tokyo\",\n \"Asia/Seoul\",\n \"Asia/Shanghai\",\n \"Asia/Kolkata\",\n \"Europe/London\",\n \"Europe/Berlin\",\n \"America/New_York\",\n \"America/Los_Angeles\",\n]\n\n/**\n * CLDR canonical name -> the IANA primary name, for the zones where they disagree.\n *\n * MEASURED, not recalled: Node 22 / ICU reports 417 zones, and for each pair below the CLDR\n * spelling is present, the IANA spelling is absent, and `Intl` resolves the IANA spelling\n * anyway. That last fact is what makes the rename safe - the offset lookup does not care which\n * name it is handed.\n *\n * ⚠️ Renaming the OFFERED name, not the accepted one. A site already saved as `Asia/Saigon`\n * keeps working and keeps showing `Asia/Saigon`, because the entry list appends a stored value\n * the offered list does not contain. Nothing is rewritten behind anybody.\n *\n * This list changes about once a decade, when IANA renames a zone and CLDR declines to follow.\n * If a pair here ever starts appearing under both spellings, delete that row rather than\n * shadowing a real entry.\n */\nconst IANA_PRIMARY: Record<string, string> = {\n \"America/Buenos_Aires\": \"America/Argentina/Buenos_Aires\",\n \"America/Godthab\": \"America/Nuuk\",\n \"Asia/Calcutta\": \"Asia/Kolkata\",\n \"Asia/Katmandu\": \"Asia/Kathmandu\",\n \"Asia/Rangoon\": \"Asia/Yangon\",\n \"Asia/Saigon\": \"Asia/Ho_Chi_Minh\",\n \"Atlantic/Faeroe\": \"Atlantic/Faroe\",\n \"Europe/Kiev\": \"Europe/Kyiv\",\n \"Pacific/Ponape\": \"Pacific/Pohnpei\",\n \"Pacific/Truk\": \"Pacific/Chuuk\",\n}\n\nexport interface TzPickerLabels {\n /** Shown when the value is empty and `allowInherit`. Default: \"Inherit\". */\n inherit?: string\n /** Placeholder for the search input. Default: \"Search timezone\". */\n search?: string\n /** Shown when the filter matches nothing. Default: \"No match\". */\n noMatch?: string\n // No `suggested`/`all` headings: the list is one flat group now. Declaring labels nothing\n // renders is how a message file ends up with keys three translators maintain for no screen.\n}\n\ninterface Zone {\n name: string\n offset: string\n}\n\n/**\n * Built once per page load, not per render: resolving the offset of ~420 zones means ~420\n * `Intl.DateTimeFormat` constructions, cheap once and visible on every keystroke.\n */\nlet cachedZones: Zone[] | null = null\n\nfunction allZones(): Zone[] {\n if (cachedZones) return cachedZones\n let names: string[]\n try {\n const supported = (Intl as unknown as { supportedValuesOf?: (k: string) => string[] })\n .supportedValuesOf\n names = supported ? supported(\"timeZone\") : FALLBACK_ZONES\n } catch {\n names = FALLBACK_ZONES\n }\n cachedZones = names.map((name) => {\n const primary = IANA_PRIMARY[name] ?? name\n // The offset is resolved from the name being SHOWN, so a wrong row in the table above\n // surfaces as a wrong offset next to the name rather than as a silently different zone.\n return { name: primary, offset: offsetOf(primary) }\n })\n return cachedZones\n}\n\n/** The zone's offset right now, as ICU spells it: \"GMT+7\", not \"UTC+7\". DST makes it a\n * snapshot, which is what a person recognising their own zone needs - not a promise about\n * January. */\nfunction offsetOf(tz: string): string {\n try {\n const parts = new Intl.DateTimeFormat(\"en-US\", {\n timeZone: tz,\n timeZoneName: \"shortOffset\",\n }).formatToParts(new Date())\n return parts.find((p) => p.type === \"timeZoneName\")?.value ?? \"\"\n } catch {\n return \"\"\n }\n}\n\n/**\n * The viewer\\u2019s own zone, under the SAME spelling the offered list uses.\n *\n * \\u26a0\\ufe0f The mapping is not optional. `resolvedOptions().timeZone` reports the CLDR canonical name\n * even when the machine is set to the IANA one - a laptop on `Asia/Ho_Chi_Minh` answers\n * `Asia/Saigon` - so without this the lookup below misses, and the \"your own zone first\"\n * shortcut silently stops working for exactly the countries IANA_PRIMARY covers. Silently,\n * because the control still renders a perfectly good list; it just no longer helps.\n */\nfunction browserTz(): string {\n try {\n const tz = Intl.DateTimeFormat().resolvedOptions().timeZone || \"UTC\"\n return IANA_PRIMARY[tz] ?? tz\n } catch {\n return \"UTC\"\n }\n}\n\nexport interface TzPickerProps {\n /** IANA zone name, or \"\" for inherit. */\n value: string\n onChange: (tz: string) => void\n /**\n * Whether an empty value is meaningful here. It usually is: a device inherits from its site,\n * a site from its unit, a unit from its parent. Set false where a zone must be chosen.\n */\n allowInherit?: boolean\n labels?: TzPickerLabels\n disabled?: boolean\n id?: string\n className?: string\n}\n\n/**\n * Field names are `tz`/`name`, NOT `value`/`label`, on purpose: Base UI treats an item shaped\n * `{ value, label }` as self-describing and renders `label` directly, silently ignoring\n * `itemToStringLabel`. The offset would then vanish from the input - which is the one part of\n * the label that makes a zone recognisable.\n */\ninterface Entry {\n tz: string\n name: string\n offset: string\n}\n\nexport function TzPicker({\n value,\n onChange,\n allowInherit = true,\n labels,\n disabled,\n id,\n className,\n}: TzPickerProps) {\n const l = {\n inherit: labels?.inherit ?? \"Inherit\",\n search: labels?.search ?? \"Search timezone\",\n noMatch: labels?.noMatch ?? \"No match\",\n }\n const own = React.useMemo(() => browserTz(), [])\n\n const entries = React.useMemo<Entry[]>(() => {\n const zones = allZones()\n const out: Entry[] = []\n if (allowInherit) out.push({ tz: \"\", name: l.inherit, offset: \"\" })\n // The person filling this form is almost always near the place they are describing, so\n // their own zone is the likeliest answer - and the one hardest to find by scrolling.\n const ownZone = zones.find((z) => z.name === own)\n if (ownZone) out.push({ tz: own, name: own, offset: ownZone.offset })\n for (const z of zones) {\n if (z.name === own) continue\n out.push({ tz: z.name, name: z.name, offset: z.offset })\n }\n // A stored zone the LIST does not contain - an alias CLDR canonicalises away\n // (`Asia/Ho_Chi_Minh`), or one dropped from a later release. It keeps its own name, so the\n // control never misreports what is saved, and it still gets an offset: `Intl` resolves the\n // alias fine even though `supportedValuesOf` omits it. Only a genuinely invalid zone ends\n // up with an empty offset here.\n if (value !== \"\" && !zones.some((z) => z.name === value)) {\n out.push({ tz: value, name: value, offset: offsetOf(value) })\n }\n return out\n }, [allowInherit, l.inherit, own, value])\n\n const selected = entries.find((e) => e.tz === value) ?? entries[0]\n\n return (\n <Combobox\n items={entries}\n value={selected}\n onValueChange={(item: Entry | null) => onChange(item?.tz ?? \"\")}\n // Searchable by name AND offset: somebody who knows \"+7\" but not the city can still land\n // on it.\n itemToStringLabel={(e: Entry) => (e.offset ? `${e.name} · ${e.offset}` : e.name)}\n itemToStringValue={(e: Entry) => e.tz}\n isItemEqualToValue={(a: Entry, b: Entry) => a.tz === b.tz}\n disabled={disabled}\n >\n {/* w-full, not the default w-fit: a combobox trigger sized to its content renders short\n and clipped inside a form column, which reads as a different kind of field. */}\n <ComboboxInput\n id={id}\n placeholder={l.search}\n className={className ?? \"w-full\"}\n // A clear button only where empty is a legitimate answer. Where a zone is required,\n // clearing would offer a state the form cannot save.\n showClear={allowInherit}\n />\n <ComboboxContent>\n <ComboboxEmpty>{l.noMatch}</ComboboxEmpty>\n <ComboboxList>\n {(entry: Entry) => (\n <ComboboxItem key={entry.tz || \"__inherit\"} value={entry}>\n <span className=\"flex-1 truncate\">{entry.name}</span>\n <span className=\"text-muted-foreground text-xs\">{entry.offset}</span>\n </ComboboxItem>\n )}\n </ComboboxList>\n </ComboboxContent>\n </Combobox>\n )\n}\n","\"use client\"\n\nimport * as React from \"react\"\n\nimport {\n Combobox,\n ComboboxContent,\n ComboboxEmpty,\n ComboboxInput,\n ComboboxItem,\n ComboboxList,\n} from \"~/ui/primitives/combobox.js\"\n\n/**\n * Pick one id from a known set.\n *\n * The set is INJECTED. That is what lets this live in lyra: it never learns where the\n * options came from, so it works the same for org members, groups, or anything else the app\n * has already loaded - which is exactly how the three copies it replaces differed.\n *\n * Why it exists at all: the screens that use it used to ask for raw uuids typed into a text\n * box. Nobody knows a uuid, so the only way anyone filled those fields was by copying from\n * somewhere else, and a copy can be off by one row. In `people` that attached a personnel\n * record to the wrong account - a wrong-but-valid uid passes every server check and is found\n * by whoever opens someone else's file under their own name.\n *\n * Filtering is client-side, deliberately: every set here is org-scoped and already loaded for\n * the surrounding screen, so matching locally is instant and costs no round trip. A picker\n * paging over every account that exists (admin's platform-wide search) is a different\n * component with a different failure mode - see `PeoplePicker` in `@tradalab/lyra/people`,\n * which takes an async `search` and does not hold a controlled value.\n */\n\n/** One choosable thing: an id plus what a person actually recognises it by. */\nexport interface PickOption {\n id: string\n label: string\n /** Secondary line - an email, a status. Searchable along with the label. */\n hint?: string\n}\n\nexport interface OptionPickerLabels {\n /** Shown when nothing is selected. */\n placeholder?: string\n /** Placeholder inside the search box. */\n search?: string\n /** Shown when the filter matches nothing. */\n empty?: string\n}\n\nconst FALLBACK: Required<OptionPickerLabels> = {\n placeholder: \"Select…\",\n search: \"Search\",\n empty: \"No match\",\n}\n\n/**\n * Field names are `id`/`label`, and `label` is what Base UI renders when an item is shaped\n * `{ value, label }`. This shape uses `id`, so `itemToStringLabel` below is what actually\n * decides the input text - the same trap TzPicker documents.\n */\ninterface Entry extends PickOption {\n /** Present only for the empty selection, so `value` can round-trip \"\" safely. */\n none?: boolean\n}\n\nexport function OptionPicker({\n value,\n onChange,\n options,\n labels,\n disabled,\n id,\n className,\n}: {\n value: string\n onChange: (id: string) => void\n options: PickOption[]\n labels?: OptionPickerLabels\n disabled?: boolean\n id?: string\n className?: string\n}) {\n const t = (k: keyof OptionPickerLabels) => labels?.[k] ?? FALLBACK[k]\n const placeholder = labels?.placeholder ?? FALLBACK.placeholder\n\n const entries = React.useMemo<Entry[]>(() => {\n const out: Entry[] = [{ id: \"\", label: placeholder, none: true }, ...options]\n // A stored id that is nobody on the list: the account left the org, or the record was\n // linked before this control existed. Show the raw id rather than an empty box - the\n // field is NOT empty, and rendering it as empty invites overwriting it by accident.\n if (value !== \"\" && !options.some((o) => o.id === value)) {\n out.push({ id: value, label: value })\n }\n return out\n }, [options, value, placeholder])\n\n const selected = entries.find((e) => e.id === value) ?? entries[0]\n\n return (\n <Combobox\n items={entries}\n value={selected}\n onValueChange={(e: Entry | null) => onChange(e?.id ?? \"\")}\n // The id is part of the searchable text, not only the label: somebody holding a uid\n // from a log must still be able to find the person it belongs to.\n itemToStringLabel={(e: Entry) => (e.none ? e.label : `${e.label} ${e.hint ?? \"\"} ${e.id}`)}\n isItemEqualToValue={(a: Entry, b: Entry) => a.id === b.id}\n disabled={disabled}\n >\n {/* w-full, not the default w-fit: sized to content it renders short and clipped inside\n a form column. */}\n <ComboboxInput id={id} placeholder={t(\"search\")} className={className ?? \"w-full\"} />\n <ComboboxContent>\n <ComboboxEmpty>{t(\"empty\")}</ComboboxEmpty>\n <ComboboxList>\n {(entry: Entry) => (\n <ComboboxItem key={entry.id || \"__none\"} value={entry}>\n <div className=\"flex min-w-0 flex-1 flex-col\">\n <span className=\"truncate text-sm\">{entry.label}</span>\n {entry.hint ? (\n <span className=\"text-muted-foreground truncate text-xs\">{entry.hint}</span>\n ) : null}\n </div>\n </ComboboxItem>\n )}\n </ComboboxList>\n </ComboboxContent>\n </Combobox>\n )\n}\n"]}
|
|
@@ -1,7 +1,63 @@
|
|
|
1
1
|
import { cn } from './chunk-XH55BHUU.js';
|
|
2
2
|
import 'react';
|
|
3
|
-
import {
|
|
3
|
+
import { ChevronDownIcon } from 'lucide-react';
|
|
4
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
4
5
|
|
|
6
|
+
function NativeSelect({
|
|
7
|
+
className,
|
|
8
|
+
size = "default",
|
|
9
|
+
...props
|
|
10
|
+
}) {
|
|
11
|
+
return /* @__PURE__ */ jsxs(
|
|
12
|
+
"div",
|
|
13
|
+
{
|
|
14
|
+
className: cn(
|
|
15
|
+
"group/native-select relative w-fit has-[select:disabled]:opacity-50",
|
|
16
|
+
className
|
|
17
|
+
),
|
|
18
|
+
"data-slot": "native-select-wrapper",
|
|
19
|
+
"data-size": size,
|
|
20
|
+
children: [
|
|
21
|
+
/* @__PURE__ */ jsx(
|
|
22
|
+
"select",
|
|
23
|
+
{
|
|
24
|
+
"data-slot": "native-select",
|
|
25
|
+
"data-size": size,
|
|
26
|
+
className: "h-8 w-full min-w-0 appearance-none rounded-none border border-input bg-transparent py-1 pr-8 pl-2.5 text-xs transition-colors outline-none select-none selection:bg-primary selection:text-primary-foreground placeholder:text-muted-foreground focus-visible:border-ring focus-visible:ring-1 focus-visible:ring-ring/50 disabled:pointer-events-none disabled:cursor-not-allowed aria-invalid:border-destructive aria-invalid:ring-1 aria-invalid:ring-destructive/20 data-[size=sm]:h-7 data-[size=sm]:rounded-none data-[size=sm]:py-0.5 dark:bg-input/30 dark:hover:bg-input/50 dark:aria-invalid:border-destructive/50 dark:aria-invalid:ring-destructive/40",
|
|
27
|
+
...props
|
|
28
|
+
}
|
|
29
|
+
),
|
|
30
|
+
/* @__PURE__ */ jsx(ChevronDownIcon, { className: "pointer-events-none absolute top-1/2 right-2.5 size-4 -translate-y-1/2 text-muted-foreground select-none", "aria-hidden": "true", "data-slot": "native-select-icon" })
|
|
31
|
+
]
|
|
32
|
+
}
|
|
33
|
+
);
|
|
34
|
+
}
|
|
35
|
+
function NativeSelectOption({
|
|
36
|
+
className,
|
|
37
|
+
...props
|
|
38
|
+
}) {
|
|
39
|
+
return /* @__PURE__ */ jsx(
|
|
40
|
+
"option",
|
|
41
|
+
{
|
|
42
|
+
"data-slot": "native-select-option",
|
|
43
|
+
className: cn("bg-[Canvas] text-[CanvasText]", className),
|
|
44
|
+
...props
|
|
45
|
+
}
|
|
46
|
+
);
|
|
47
|
+
}
|
|
48
|
+
function NativeSelectOptGroup({
|
|
49
|
+
className,
|
|
50
|
+
...props
|
|
51
|
+
}) {
|
|
52
|
+
return /* @__PURE__ */ jsx(
|
|
53
|
+
"optgroup",
|
|
54
|
+
{
|
|
55
|
+
"data-slot": "native-select-optgroup",
|
|
56
|
+
className: cn("bg-[Canvas] text-[CanvasText]", className),
|
|
57
|
+
...props
|
|
58
|
+
}
|
|
59
|
+
);
|
|
60
|
+
}
|
|
5
61
|
function Table({ className, ...props }) {
|
|
6
62
|
return /* @__PURE__ */ jsx(
|
|
7
63
|
"div",
|
|
@@ -105,6 +161,6 @@ function TableCaption({
|
|
|
105
161
|
);
|
|
106
162
|
}
|
|
107
163
|
|
|
108
|
-
export { Table, TableBody, TableCaption, TableCell, TableFooter, TableHead, TableHeader, TableRow };
|
|
109
|
-
//# sourceMappingURL=chunk-
|
|
110
|
-
//# sourceMappingURL=chunk-
|
|
164
|
+
export { NativeSelect, NativeSelectOptGroup, NativeSelectOption, Table, TableBody, TableCaption, TableCell, TableFooter, TableHead, TableHeader, TableRow };
|
|
165
|
+
//# sourceMappingURL=chunk-L6AHYXII.js.map
|
|
166
|
+
//# sourceMappingURL=chunk-L6AHYXII.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/ui/primitives/native-select.tsx","../src/ui/primitives/table.tsx"],"names":["jsx"],"mappings":";;;;;AASA,SAAS,YAAA,CAAa;AAAA,EACpB,SAAA;AAAA,EACA,IAAA,GAAO,SAAA;AAAA,EACP,GAAG;AACL,CAAA,EAAsB;AACpB,EAAA,uBACE,IAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAW,EAAA;AAAA,QACT,qEAAA;AAAA,QACA;AAAA,OACF;AAAA,MACA,WAAA,EAAU,uBAAA;AAAA,MACV,WAAA,EAAW,IAAA;AAAA,MAEX,QAAA,EAAA;AAAA,wBAAA,GAAA;AAAA,UAAC,QAAA;AAAA,UAAA;AAAA,YACC,WAAA,EAAU,eAAA;AAAA,YACV,WAAA,EAAW,IAAA;AAAA,YACX,SAAA,EAAU,ooBAAA;AAAA,YACT,GAAG;AAAA;AAAA,SACN;AAAA,4BACC,eAAA,EAAA,EAAgB,SAAA,EAAU,4GAA2G,aAAA,EAAY,MAAA,EAAO,aAAU,oBAAA,EAAqB;AAAA;AAAA;AAAA,GAC1L;AAEJ;AAEA,SAAS,kBAAA,CAAmB;AAAA,EAC1B,SAAA;AAAA,EACA,GAAG;AACL,CAAA,EAAmC;AACjC,EAAA,uBACE,GAAA;AAAA,IAAC,QAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,sBAAA;AAAA,MACV,SAAA,EAAW,EAAA,CAAG,+BAAA,EAAiC,SAAS,CAAA;AAAA,MACvD,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,oBAAA,CAAqB;AAAA,EAC5B,SAAA;AAAA,EACA,GAAG;AACL,CAAA,EAAqC;AACnC,EAAA,uBACE,GAAA;AAAA,IAAC,UAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,wBAAA;AAAA,MACV,SAAA,EAAW,EAAA,CAAG,+BAAA,EAAiC,SAAS,CAAA;AAAA,MACvD,GAAG;AAAA;AAAA,GACN;AAEJ;ACtDA,SAAS,KAAA,CAAM,EAAE,SAAA,EAAW,GAAG,OAAM,EAAkC;AACrE,EAAA,uBACEA,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,iBAAA;AAAA,MACV,SAAA,EAAU,iCAAA;AAAA,MAEV,QAAA,kBAAAA,GAAAA;AAAA,QAAC,OAAA;AAAA,QAAA;AAAA,UACC,WAAA,EAAU,OAAA;AAAA,UACV,SAAA,EAAW,EAAA,CAAG,+BAAA,EAAiC,SAAS,CAAA;AAAA,UACvD,GAAG;AAAA;AAAA;AACN;AAAA,GACF;AAEJ;AAEA,SAAS,WAAA,CAAY,EAAE,SAAA,EAAW,GAAG,OAAM,EAAkC;AAC3E,EAAA,uBACEA,GAAAA;AAAA,IAAC,OAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,cAAA;AAAA,MACV,SAAA,EAAW,EAAA,CAAG,iBAAA,EAAmB,SAAS,CAAA;AAAA,MACzC,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,SAAA,CAAU,EAAE,SAAA,EAAW,GAAG,OAAM,EAAkC;AACzE,EAAA,uBACEA,GAAAA;AAAA,IAAC,OAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,YAAA;AAAA,MACV,SAAA,EAAW,EAAA,CAAG,4BAAA,EAA8B,SAAS,CAAA;AAAA,MACpD,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,WAAA,CAAY,EAAE,SAAA,EAAW,GAAG,OAAM,EAAkC;AAC3E,EAAA,uBACEA,GAAAA;AAAA,IAAC,OAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,cAAA;AAAA,MACV,SAAA,EAAW,EAAA;AAAA,QACT,yDAAA;AAAA,QACA;AAAA,OACF;AAAA,MACC,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,QAAA,CAAS,EAAE,SAAA,EAAW,GAAG,OAAM,EAA+B;AACrE,EAAA,uBACEA,GAAAA;AAAA,IAAC,IAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,WAAA;AAAA,MACV,SAAA,EAAW,EAAA;AAAA,QACT,2GAAA;AAAA,QACA;AAAA,OACF;AAAA,MACC,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,SAAA,CAAU,EAAE,SAAA,EAAW,GAAG,OAAM,EAA+B;AACtE,EAAA,uBACEA,GAAAA;AAAA,IAAC,IAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,YAAA;AAAA,MACV,SAAA,EAAW,EAAA;AAAA,QACT,8GAAA;AAAA,QACA;AAAA,OACF;AAAA,MACC,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,SAAA,CAAU,EAAE,SAAA,EAAW,GAAG,OAAM,EAA+B;AACtE,EAAA,uBACEA,GAAAA;AAAA,IAAC,IAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,YAAA;AAAA,MACV,SAAA,EAAW,EAAA;AAAA,QACT,kEAAA;AAAA,QACA;AAAA,OACF;AAAA,MACC,GAAG;AAAA;AAAA,GACN;AAEJ;AAEA,SAAS,YAAA,CAAa;AAAA,EACpB,SAAA;AAAA,EACA,GAAG;AACL,CAAA,EAAoC;AAClC,EAAA,uBACEA,GAAAA;AAAA,IAAC,SAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,eAAA;AAAA,MACV,SAAA,EAAW,EAAA,CAAG,oCAAA,EAAsC,SAAS,CAAA;AAAA,MAC5D,GAAG;AAAA;AAAA,GACN;AAEJ","file":"chunk-L6AHYXII.js","sourcesContent":["import * as React from \"react\"\nimport { ChevronDownIcon } from \"lucide-react\"\n\nimport { cn } from \"~/utils/cn.js\"\n\ntype NativeSelectProps = Omit<React.ComponentProps<\"select\">, \"size\"> & {\n size?: \"sm\" | \"default\"\n}\n\nfunction NativeSelect({\n className,\n size = \"default\",\n ...props\n}: NativeSelectProps) {\n return (\n <div\n className={cn(\n \"group/native-select relative w-fit has-[select:disabled]:opacity-50\",\n className\n )}\n data-slot=\"native-select-wrapper\"\n data-size={size}\n >\n <select\n data-slot=\"native-select\"\n data-size={size}\n className=\"h-8 w-full min-w-0 appearance-none rounded-none border border-input bg-transparent py-1 pr-8 pl-2.5 text-xs transition-colors outline-none select-none selection:bg-primary selection:text-primary-foreground placeholder:text-muted-foreground focus-visible:border-ring focus-visible:ring-1 focus-visible:ring-ring/50 disabled:pointer-events-none disabled:cursor-not-allowed aria-invalid:border-destructive aria-invalid:ring-1 aria-invalid:ring-destructive/20 data-[size=sm]:h-7 data-[size=sm]:rounded-none data-[size=sm]:py-0.5 dark:bg-input/30 dark:hover:bg-input/50 dark:aria-invalid:border-destructive/50 dark:aria-invalid:ring-destructive/40\"\n {...props}\n />\n <ChevronDownIcon className=\"pointer-events-none absolute top-1/2 right-2.5 size-4 -translate-y-1/2 text-muted-foreground select-none\" aria-hidden=\"true\" data-slot=\"native-select-icon\" />\n </div>\n )\n}\n\nfunction NativeSelectOption({\n className,\n ...props\n}: React.ComponentProps<\"option\">) {\n return (\n <option\n data-slot=\"native-select-option\"\n className={cn(\"bg-[Canvas] text-[CanvasText]\", className)}\n {...props}\n />\n )\n}\n\nfunction NativeSelectOptGroup({\n className,\n ...props\n}: React.ComponentProps<\"optgroup\">) {\n return (\n <optgroup\n data-slot=\"native-select-optgroup\"\n className={cn(\"bg-[Canvas] text-[CanvasText]\", className)}\n {...props}\n />\n )\n}\n\nexport { NativeSelect, NativeSelectOptGroup, NativeSelectOption }\n","import * as React from \"react\"\n\nimport { cn } from \"~/utils/cn.js\"\n\nfunction Table({ className, ...props }: React.ComponentProps<\"table\">) {\n return (\n <div\n data-slot=\"table-container\"\n className=\"relative w-full overflow-x-auto\"\n >\n <table\n data-slot=\"table\"\n className={cn(\"w-full caption-bottom text-xs\", className)}\n {...props}\n />\n </div>\n )\n}\n\nfunction TableHeader({ className, ...props }: React.ComponentProps<\"thead\">) {\n return (\n <thead\n data-slot=\"table-header\"\n className={cn(\"[&_tr]:border-b\", className)}\n {...props}\n />\n )\n}\n\nfunction TableBody({ className, ...props }: React.ComponentProps<\"tbody\">) {\n return (\n <tbody\n data-slot=\"table-body\"\n className={cn(\"[&_tr:last-child]:border-0\", className)}\n {...props}\n />\n )\n}\n\nfunction TableFooter({ className, ...props }: React.ComponentProps<\"tfoot\">) {\n return (\n <tfoot\n data-slot=\"table-footer\"\n className={cn(\n \"border-t bg-muted/50 font-medium [&>tr]:last:border-b-0\",\n className\n )}\n {...props}\n />\n )\n}\n\nfunction TableRow({ className, ...props }: React.ComponentProps<\"tr\">) {\n return (\n <tr\n data-slot=\"table-row\"\n className={cn(\n \"border-b transition-colors hover:bg-muted/50 has-aria-expanded:bg-muted/50 data-[state=selected]:bg-muted\",\n className\n )}\n {...props}\n />\n )\n}\n\nfunction TableHead({ className, ...props }: React.ComponentProps<\"th\">) {\n return (\n <th\n data-slot=\"table-head\"\n className={cn(\n \"h-10 px-2 text-left align-middle font-medium whitespace-nowrap text-foreground [&:has([role=checkbox])]:pr-0\",\n className\n )}\n {...props}\n />\n )\n}\n\nfunction TableCell({ className, ...props }: React.ComponentProps<\"td\">) {\n return (\n <td\n data-slot=\"table-cell\"\n className={cn(\n \"p-2 align-middle whitespace-nowrap [&:has([role=checkbox])]:pr-0\",\n className\n )}\n {...props}\n />\n )\n}\n\nfunction TableCaption({\n className,\n ...props\n}: React.ComponentProps<\"caption\">) {\n return (\n <caption\n data-slot=\"table-caption\"\n className={cn(\"mt-4 text-xs text-muted-foreground\", className)}\n {...props}\n />\n )\n}\n\nexport {\n Table,\n TableHeader,\n TableBody,\n TableFooter,\n TableHead,\n TableRow,\n TableCell,\n TableCaption,\n}\n"]}
|
|
@@ -94,7 +94,37 @@ interface DataTableProps<TData, TValue> {
|
|
|
94
94
|
loadingMore?: boolean;
|
|
95
95
|
/** Label beside the bottom spinner. */
|
|
96
96
|
loadingMoreText?: string;
|
|
97
|
+
/** Zero-based index of the page being shown. */
|
|
98
|
+
pageIndex?: number;
|
|
99
|
+
/** How many pages exist. The table cannot work this out: only the server knows the total. */
|
|
100
|
+
pageCount?: number;
|
|
101
|
+
/** Called with a zero-based page index. */
|
|
102
|
+
onPageChange?: (index: number) => void;
|
|
103
|
+
/** Sizes offered in the selector. Omit to leave the size fixed and hide the control. */
|
|
104
|
+
pageSizeOptions?: number[];
|
|
105
|
+
/** Called with the chosen size. The caller is expected to return to page 1. */
|
|
106
|
+
onPageSizeChange?: (size: number) => void;
|
|
107
|
+
/** Free text beside the pager, e.g. "1-50 of 4,231". lyra ships no copy and no number
|
|
108
|
+
* formatting, so the caller builds it. */
|
|
109
|
+
rangeLabel?: ReactNode;
|
|
110
|
+
/** Accessible labels for the pager buttons. */
|
|
111
|
+
pageLabels?: {
|
|
112
|
+
first?: string;
|
|
113
|
+
previous?: string;
|
|
114
|
+
next?: string;
|
|
115
|
+
last?: string;
|
|
116
|
+
size?: string;
|
|
117
|
+
};
|
|
97
118
|
}
|
|
98
|
-
|
|
119
|
+
/**
|
|
120
|
+
* Which page numbers to show: always the first, the last, and a couple either side of the
|
|
121
|
+
* current one, with `null` where a gap is elided.
|
|
122
|
+
*
|
|
123
|
+
* A pager that renders every page is unusable at forty pages and absurd at four hundred, and
|
|
124
|
+
* one that renders only prev/next hides how long the list is - which is the question the
|
|
125
|
+
* reader opened it with.
|
|
126
|
+
*/
|
|
127
|
+
declare function pageWindow(index: number, count: number, radius?: number): (number | null)[];
|
|
128
|
+
declare function DataTable<TData, TValue>({ columns, data, loading, emptyText, loadingText, previousLabel, nextLabel, pageSize, className, searchable, searchPlaceholder, onReload, reloadLabel, toolbar, onLoadMore, hasMore, loadingMore, loadingMoreText, pageIndex, pageCount, onPageChange, pageSizeOptions, onPageSizeChange, rangeLabel, pageLabels, }: DataTableProps<TData, TValue>): React.JSX.Element;
|
|
99
129
|
|
|
100
|
-
export { DataTable, type DataTableProps, TableBody, type TableBodyProps, TableCell, type TableCellProps, TableColumnHeader, type TableColumnHeaderProps, TableContext, TableHead, type TableHeadProps, TableHeader, TableHeaderGroup, type TableHeaderGroupProps, type TableHeaderProps, TableProvider, type TableProviderProps, TableRow, type TableRowProps };
|
|
130
|
+
export { DataTable, type DataTableProps, TableBody, type TableBodyProps, TableCell, type TableCellProps, TableColumnHeader, type TableColumnHeaderProps, TableContext, TableHead, type TableHeadProps, TableHeader, TableHeaderGroup, type TableHeaderGroupProps, type TableHeaderProps, TableProvider, type TableProviderProps, TableRow, type TableRowProps, pageWindow };
|
package/dist/data-table/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import { TableHead, Table, TableRow, TableHeader, TableCell, TableBody } from '../chunk-
|
|
2
|
+
import { TableHead, Table, TableRow, TableHeader, TableCell, TableBody, NativeSelect, NativeSelectOption } from '../chunk-L6AHYXII.js';
|
|
3
3
|
import { DropdownMenu, DropdownMenuTrigger, DropdownMenuContent, DropdownMenuItem } from '../chunk-VEWKPOMS.js';
|
|
4
4
|
import { Button, Input } from '../chunk-VGOGWZCF.js';
|
|
5
5
|
import { cn } from '../chunk-XH55BHUU.js';
|
|
@@ -80,6 +80,23 @@ var TableBody2 = ({ children, className }) => {
|
|
|
80
80
|
const rows = table?.getRowModel().rows;
|
|
81
81
|
return /* @__PURE__ */ jsx(TableBody, { className, children: rows?.length ? rows.map((row) => children({ row })) : /* @__PURE__ */ jsx(TableRow, { children: /* @__PURE__ */ jsx(TableCell, { className: "h-24 text-center", colSpan: columns.length, children: "No results." }) }) });
|
|
82
82
|
};
|
|
83
|
+
function pageWindow(index, count, radius = 1) {
|
|
84
|
+
if (count <= 0) return [];
|
|
85
|
+
const want = /* @__PURE__ */ new Set([0, count - 1]);
|
|
86
|
+
for (let p = index - radius; p <= index + radius; p++) {
|
|
87
|
+
if (p >= 0 && p < count) want.add(p);
|
|
88
|
+
}
|
|
89
|
+
const sorted = [...want].sort((a, b) => a - b);
|
|
90
|
+
const out = [];
|
|
91
|
+
let prev = -1;
|
|
92
|
+
for (const p of sorted) {
|
|
93
|
+
if (prev >= 0 && p - prev === 2) out.push(p - 1);
|
|
94
|
+
else if (prev >= 0 && p - prev > 2) out.push(null);
|
|
95
|
+
out.push(p);
|
|
96
|
+
prev = p;
|
|
97
|
+
}
|
|
98
|
+
return out;
|
|
99
|
+
}
|
|
83
100
|
function DataTable({
|
|
84
101
|
columns,
|
|
85
102
|
data,
|
|
@@ -98,10 +115,18 @@ function DataTable({
|
|
|
98
115
|
onLoadMore,
|
|
99
116
|
hasMore,
|
|
100
117
|
loadingMore,
|
|
101
|
-
loadingMoreText = "Loading more\u2026"
|
|
118
|
+
loadingMoreText = "Loading more\u2026",
|
|
119
|
+
pageIndex = 0,
|
|
120
|
+
pageCount = 0,
|
|
121
|
+
onPageChange,
|
|
122
|
+
pageSizeOptions,
|
|
123
|
+
onPageSizeChange,
|
|
124
|
+
rangeLabel,
|
|
125
|
+
pageLabels
|
|
102
126
|
}) {
|
|
103
127
|
const [globalFilter, setGlobalFilter] = useState("");
|
|
104
128
|
const infinite = Boolean(onLoadMore);
|
|
129
|
+
const served = !infinite && Boolean(onPageChange);
|
|
105
130
|
const table = useReactTable({
|
|
106
131
|
data,
|
|
107
132
|
columns,
|
|
@@ -111,7 +136,7 @@ function DataTable({
|
|
|
111
136
|
getFilteredRowModel: getFilteredRowModel(),
|
|
112
137
|
// Infinite mode renders every accumulated row; pagination is only wired for
|
|
113
138
|
// the default finite table.
|
|
114
|
-
...infinite ? {} : { getPaginationRowModel: getPaginationRowModel(), initialState: { pagination: { pageSize } } }
|
|
139
|
+
...infinite || served ? {} : { getPaginationRowModel: getPaginationRowModel(), initialState: { pagination: { pageSize } } }
|
|
115
140
|
});
|
|
116
141
|
const rows = table.getRowModel().rows;
|
|
117
142
|
const showBar = Boolean(searchable || onReload || toolbar);
|
|
@@ -191,13 +216,87 @@ function DataTable({
|
|
|
191
216
|
] }) : null,
|
|
192
217
|
infinite ? /* @__PURE__ */ jsx("div", { ref: sentinelRef, "aria-hidden": true, className: "h-px w-full" }) : null
|
|
193
218
|
] }),
|
|
194
|
-
|
|
219
|
+
served ? /* @__PURE__ */ jsxs("div", { className: "flex flex-wrap items-center justify-between gap-3 py-4", children: [
|
|
220
|
+
/* @__PURE__ */ jsxs("div", { className: "text-muted-foreground flex items-center gap-3 text-sm", children: [
|
|
221
|
+
rangeLabel,
|
|
222
|
+
pageSizeOptions && pageSizeOptions.length > 0 ? /* @__PURE__ */ jsx(
|
|
223
|
+
NativeSelect,
|
|
224
|
+
{
|
|
225
|
+
"aria-label": pageLabels?.size ?? "Rows per page",
|
|
226
|
+
className: "h-8 w-auto",
|
|
227
|
+
value: String(pageSize),
|
|
228
|
+
onChange: (e) => onPageSizeChange?.(Number(e.target.value)),
|
|
229
|
+
children: pageSizeOptions.map((n) => /* @__PURE__ */ jsx(NativeSelectOption, { value: String(n), children: n }, n))
|
|
230
|
+
}
|
|
231
|
+
) : null
|
|
232
|
+
] }),
|
|
233
|
+
/* @__PURE__ */ jsxs("div", { className: "flex items-center gap-1", children: [
|
|
234
|
+
/* @__PURE__ */ jsx(
|
|
235
|
+
Button,
|
|
236
|
+
{
|
|
237
|
+
variant: "outline",
|
|
238
|
+
size: "sm",
|
|
239
|
+
"aria-label": pageLabels?.first ?? "First page",
|
|
240
|
+
onClick: () => onPageChange?.(0),
|
|
241
|
+
disabled: pageIndex <= 0,
|
|
242
|
+
children: "\xAB"
|
|
243
|
+
}
|
|
244
|
+
),
|
|
245
|
+
/* @__PURE__ */ jsx(
|
|
246
|
+
Button,
|
|
247
|
+
{
|
|
248
|
+
variant: "outline",
|
|
249
|
+
size: "sm",
|
|
250
|
+
"aria-label": pageLabels?.previous ?? previousLabel,
|
|
251
|
+
onClick: () => onPageChange?.(pageIndex - 1),
|
|
252
|
+
disabled: pageIndex <= 0,
|
|
253
|
+
children: "\u2039"
|
|
254
|
+
}
|
|
255
|
+
),
|
|
256
|
+
pageWindow(pageIndex, pageCount).map(
|
|
257
|
+
(p, i) => p === null ? /* @__PURE__ */ jsx("span", { className: "text-muted-foreground px-1 text-sm", children: "\u2026" }, `gap${i}`) : /* @__PURE__ */ jsx(
|
|
258
|
+
Button,
|
|
259
|
+
{
|
|
260
|
+
variant: p === pageIndex ? "default" : "outline",
|
|
261
|
+
size: "sm",
|
|
262
|
+
"aria-current": p === pageIndex ? "page" : void 0,
|
|
263
|
+
onClick: () => onPageChange?.(p),
|
|
264
|
+
children: p + 1
|
|
265
|
+
},
|
|
266
|
+
p
|
|
267
|
+
)
|
|
268
|
+
),
|
|
269
|
+
/* @__PURE__ */ jsx(
|
|
270
|
+
Button,
|
|
271
|
+
{
|
|
272
|
+
variant: "outline",
|
|
273
|
+
size: "sm",
|
|
274
|
+
"aria-label": pageLabels?.next ?? nextLabel,
|
|
275
|
+
onClick: () => onPageChange?.(pageIndex + 1),
|
|
276
|
+
disabled: pageIndex >= pageCount - 1,
|
|
277
|
+
children: "\u203A"
|
|
278
|
+
}
|
|
279
|
+
),
|
|
280
|
+
/* @__PURE__ */ jsx(
|
|
281
|
+
Button,
|
|
282
|
+
{
|
|
283
|
+
variant: "outline",
|
|
284
|
+
size: "sm",
|
|
285
|
+
"aria-label": pageLabels?.last ?? "Last page",
|
|
286
|
+
onClick: () => onPageChange?.(pageCount - 1),
|
|
287
|
+
disabled: pageIndex >= pageCount - 1,
|
|
288
|
+
children: "\xBB"
|
|
289
|
+
}
|
|
290
|
+
)
|
|
291
|
+
] })
|
|
292
|
+
] }) : null,
|
|
293
|
+
!infinite && !served && table.getPageCount() > 1 ? /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-end gap-2 py-4", children: [
|
|
195
294
|
/* @__PURE__ */ jsx(Button, { variant: "outline", size: "sm", onClick: () => table.previousPage(), disabled: !table.getCanPreviousPage(), children: previousLabel }),
|
|
196
295
|
/* @__PURE__ */ jsx(Button, { variant: "outline", size: "sm", onClick: () => table.nextPage(), disabled: !table.getCanNextPage(), children: nextLabel })
|
|
197
296
|
] }) : null
|
|
198
297
|
] });
|
|
199
298
|
}
|
|
200
299
|
|
|
201
|
-
export { DataTable, TableBody2 as TableBody, TableCell2 as TableCell, TableColumnHeader, TableContext, TableHead2 as TableHead, TableHeader2 as TableHeader, TableHeaderGroup, TableProvider, TableRow2 as TableRow };
|
|
300
|
+
export { DataTable, TableBody2 as TableBody, TableCell2 as TableCell, TableColumnHeader, TableContext, TableHead2 as TableHead, TableHeader2 as TableHeader, TableHeaderGroup, TableProvider, TableRow2 as TableRow, pageWindow };
|
|
202
301
|
//# sourceMappingURL=index.js.map
|
|
203
302
|
//# sourceMappingURL=index.js.map
|