@camstack/ui-library 0.1.25

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.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/theme/defaults.ts","../src/theme/create-theme.ts","../src/theme/theme-to-css.ts","../src/theme/theme-provider.tsx","../src/theme/use-theme-mode.ts","../src/lib/cn.ts","../src/icons/provider-icons.ts","../src/icons/status-icons.ts","../src/primitives/button.tsx","../src/primitives/icon-button.tsx","../src/primitives/badge.tsx","../src/primitives/card.tsx","../src/primitives/label.tsx","../src/primitives/separator.tsx","../src/primitives/skeleton.tsx","../src/primitives/input.tsx","../src/primitives/select.tsx","../src/primitives/checkbox.tsx","../src/primitives/switch.tsx","../src/primitives/dialog.tsx","../src/primitives/dropdown.tsx","../src/primitives/tooltip.tsx","../src/primitives/popover.tsx","../src/primitives/tabs.tsx","../src/primitives/scroll-area.tsx","../src/primitives/floating-panel.tsx","../src/composites/status-badge.tsx","../src/composites/provider-badge.tsx","../src/composites/form-field.tsx","../src/composites/page-header.tsx","../src/composites/empty-state.tsx","../src/composites/confirm-dialog.tsx","../src/composites/stat-card.tsx","../src/composites/key-value-list.tsx","../src/composites/code-block.tsx","../src/composites/filter-bar.tsx","../src/composites/app-shell/sidebar-item.tsx","../src/composites/app-shell/sidebar.tsx","../src/composites/app-shell/app-shell.tsx","../src/composites/data-table/data-table.tsx","../src/composites/data-table/data-table-header.tsx","../src/composites/data-table/data-table-row.tsx","../src/composites/data-table/data-table-pagination.tsx","../src/composites/device-card.tsx","../src/composites/device-grid.tsx"],"sourcesContent":["import type { CamStackColorTokens, CamStackTheme } from './types'\n\nconst providerColors: CamStackColorTokens['provider'] = {\n frigate: '#3b82f6',\n scrypted: '#a855f7',\n reolink: '#06b6d4',\n homeAssistant: '#22d3ee',\n rtsp: '#78716c',\n}\n\nexport const darkColors: CamStackColorTokens = {\n primary: '#f59e42',\n primaryForeground: '#0c0a09',\n background: '#0c0a09',\n backgroundElevated: '#1c1917',\n surface: '#1c1917',\n surfaceHover: '#292524',\n border: '#292524',\n borderSubtle: '#1c1917',\n foreground: '#fafaf9',\n foregroundMuted: '#a8a29e',\n foregroundSubtle: '#78716c',\n foregroundDisabled: '#57534e',\n success: '#4ade80',\n warning: '#fbbf24',\n danger: '#f87171',\n info: '#60a5fa',\n provider: providerColors,\n}\n\nexport const lightColors: CamStackColorTokens = {\n primary: '#e67e22',\n primaryForeground: '#ffffff',\n background: '#fafaf9',\n backgroundElevated: '#ffffff',\n surface: '#f5f5f4',\n surfaceHover: '#e7e5e4',\n border: '#d6d3d1',\n borderSubtle: '#e7e5e4',\n foreground: '#1c1917',\n foregroundMuted: '#57534e',\n foregroundSubtle: '#78716c',\n foregroundDisabled: '#a8a29e',\n success: '#16a34a',\n warning: '#d97706',\n danger: '#dc2626',\n info: '#2563eb',\n provider: providerColors,\n}\n\nexport const defaultTheme: CamStackTheme = {\n colors: {\n dark: darkColors,\n light: lightColors,\n },\n spacing: {\n xs: 2,\n sm: 4,\n md: 8,\n lg: 12,\n xl: 16,\n '2xl': 24,\n '3xl': 32,\n },\n radius: {\n sm: 4,\n md: 6,\n lg: 8,\n xl: 12,\n },\n typography: {\n fontFamily: '-apple-system, BlinkMacSystemFont, \"Segoe UI\", sans-serif',\n sizes: {\n xs: { fontSize: 10, lineHeight: 14 },\n sm: { fontSize: 11, lineHeight: 16 },\n base: { fontSize: 12, lineHeight: 18 },\n lg: { fontSize: 13, lineHeight: 18 },\n xl: { fontSize: 14, lineHeight: 20 },\n '2xl': { fontSize: 16, lineHeight: 22 },\n '3xl': { fontSize: 20, lineHeight: 28 },\n },\n weights: {\n regular: 400,\n medium: 500,\n semibold: 600,\n bold: 700,\n },\n },\n table: {\n rowHeight: 28,\n headerHeight: 24,\n cellPaddingX: 8,\n cellPaddingY: 6,\n },\n sidebar: {\n width: 176,\n itemHeight: 28,\n iconSize: 14,\n },\n}\n","import type { CamStackTheme, DeepPartial } from './types'\nimport { defaultTheme } from './defaults'\n\nfunction deepMerge<T extends object>(target: T, source: DeepPartial<T>): T {\n const result = { ...target }\n for (const key in source) {\n const sourceVal = source[key]\n const targetVal = target[key]\n if (\n sourceVal !== undefined &&\n typeof sourceVal === 'object' &&\n sourceVal !== null &&\n !Array.isArray(sourceVal) &&\n typeof targetVal === 'object' &&\n targetVal !== null\n ) {\n result[key] = deepMerge(\n targetVal as Record<string, unknown>,\n sourceVal as Record<string, unknown>,\n ) as T[typeof key]\n } else if (sourceVal !== undefined) {\n result[key] = sourceVal as T[typeof key]\n }\n }\n return result\n}\n\nexport function createTheme(overrides?: DeepPartial<CamStackTheme>): CamStackTheme {\n if (!overrides) return structuredClone(defaultTheme)\n return deepMerge(structuredClone(defaultTheme), overrides)\n}\n","import type { CamStackColorTokens, CamStackTheme } from './types'\n\nfunction camelToKebab(str: string): string {\n return str.replace(/[A-Z]/g, (m) => `-${m.toLowerCase()}`)\n}\n\nfunction colorTokenToCssVar(key: string): string {\n return `--color-${camelToKebab(key)}`\n}\n\nfunction generateColorBlock(colors: CamStackColorTokens): string {\n const lines: string[] = []\n for (const [key, value] of Object.entries(colors)) {\n if (key === 'provider') continue\n lines.push(` ${colorTokenToCssVar(key)}: ${value};`)\n }\n return lines.join('\\n')\n}\n\nfunction generateProviderColors(provider: CamStackColorTokens['provider']): string {\n const lines: string[] = []\n for (const [key, value] of Object.entries(provider)) {\n lines.push(` --color-provider-${camelToKebab(key)}: ${value};`)\n }\n return lines.join('\\n')\n}\n\nfunction generateSpacingTokens(spacing: CamStackTheme['spacing']): string {\n const lines: string[] = []\n for (const [key, value] of Object.entries(spacing)) {\n lines.push(` --spacing-${key}: ${value}px;`)\n }\n return lines.join('\\n')\n}\n\nfunction generateRadiusTokens(radius: CamStackTheme['radius']): string {\n const lines: string[] = []\n for (const [key, value] of Object.entries(radius)) {\n lines.push(` --radius-${key}: ${value}px;`)\n }\n return lines.join('\\n')\n}\n\nexport function themeToCss(theme: CamStackTheme): string {\n const darkColorBlock = generateColorBlock(theme.colors.dark)\n const lightColorBlock = generateColorBlock(theme.colors.light)\n const providerBlock = generateProviderColors(theme.colors.dark.provider)\n const spacingBlock = generateSpacingTokens(theme.spacing)\n const radiusBlock = generateRadiusTokens(theme.radius)\n\n return `@theme {\n${providerBlock}\n${spacingBlock}\n${radiusBlock}\n}\n\n.dark {\n${darkColorBlock}\n}\n\n.light {\n${lightColorBlock}\n}\n\n@media (prefers-color-scheme: dark) {\n :root {\n${darkColorBlock.replace(/^ /gm, ' ')}\n }\n}\n\n@media (prefers-color-scheme: light) {\n :root {\n${lightColorBlock.replace(/^ /gm, ' ')}\n }\n}\n`\n}\n","import { createContext, useCallback, useEffect, useMemo, useState } from 'react'\nimport type { ReactNode } from 'react'\nimport type { ThemeMode, UseThemeModeReturn } from './types'\n\nexport const ThemeContext = createContext<UseThemeModeReturn | null>(null)\n\ninterface ThemeProviderProps {\n children: ReactNode\n defaultMode?: ThemeMode\n storageKey?: string\n}\n\nconst TOGGLE_ORDER: readonly ThemeMode[] = ['dark', 'light', 'system'] as const\n\nfunction getSystemPreference(): 'dark' | 'light' {\n if (typeof window === 'undefined') return 'dark'\n return window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light'\n}\n\nfunction getInitialMode(storageKey: string, defaultMode: ThemeMode): ThemeMode {\n if (typeof window === 'undefined') return defaultMode\n const stored = localStorage.getItem(storageKey)\n if (stored === 'dark' || stored === 'light' || stored === 'system') {\n return stored\n }\n return defaultMode\n}\n\nfunction resolveMode(mode: ThemeMode): 'dark' | 'light' {\n if (mode === 'system') return getSystemPreference()\n return mode\n}\n\nexport function ThemeProvider({\n children,\n defaultMode = 'system',\n storageKey = 'camstack-theme-mode',\n}: ThemeProviderProps) {\n const [mode, setModeState] = useState<ThemeMode>(() => getInitialMode(storageKey, defaultMode))\n const [resolvedMode, setResolvedMode] = useState<'dark' | 'light'>(() => resolveMode(mode))\n\n const setMode = useCallback(\n (newMode: ThemeMode) => {\n setModeState(newMode)\n setResolvedMode(resolveMode(newMode))\n if (typeof window !== 'undefined') {\n localStorage.setItem(storageKey, newMode)\n }\n },\n [storageKey],\n )\n\n const toggleMode = useCallback(() => {\n const currentIndex = TOGGLE_ORDER.indexOf(mode)\n const nextIndex = (currentIndex + 1) % TOGGLE_ORDER.length\n setMode(TOGGLE_ORDER[nextIndex] ?? 'dark')\n }, [mode, setMode])\n\n // Apply CSS class on document.documentElement\n useEffect(() => {\n if (typeof document === 'undefined') return\n\n const root = document.documentElement\n root.classList.remove('dark', 'light')\n // Always apply the resolved class — even in 'system' mode, the CSS\n // variables need the .dark or .light class to activate\n root.classList.add(resolvedMode)\n }, [mode, resolvedMode])\n\n // Listen for system theme changes when in 'system' mode\n useEffect(() => {\n if (typeof window === 'undefined' || mode !== 'system') return\n\n const mediaQuery = window.matchMedia('(prefers-color-scheme: dark)')\n const handleChange = () => {\n setResolvedMode(getSystemPreference())\n }\n\n mediaQuery.addEventListener('change', handleChange)\n return () => mediaQuery.removeEventListener('change', handleChange)\n }, [mode])\n\n const value = useMemo<UseThemeModeReturn>(\n () => ({ mode, resolvedMode, setMode, toggleMode }),\n [mode, resolvedMode, setMode, toggleMode],\n )\n\n return <ThemeContext.Provider value={value}>{children}</ThemeContext.Provider>\n}\n","import { useContext } from 'react'\nimport { ThemeContext } from './theme-provider'\nimport type { UseThemeModeReturn } from './types'\n\nexport function useThemeMode(): UseThemeModeReturn {\n const context = useContext(ThemeContext)\n if (!context) {\n throw new Error('useThemeMode must be used within a ThemeProvider')\n }\n return context\n}\n","import { type ClassValue, clsx } from 'clsx'\nimport { twMerge } from 'tailwind-merge'\n\nexport function cn(...inputs: ClassValue[]) {\n return twMerge(clsx(inputs))\n}\n","import { Ship, Shield, Radio, Home, Cast, type LucideIcon } from 'lucide-react'\n\nexport type ProviderType = 'frigate' | 'scrypted' | 'reolink' | 'homeAssistant' | 'rtsp'\n\nexport const providerIcons: Record<ProviderType, LucideIcon> = {\n frigate: Ship,\n scrypted: Shield,\n reolink: Radio,\n homeAssistant: Home,\n rtsp: Cast,\n}\n","import { CircleCheck, CircleX, CircleAlert, CircleHelp, type LucideIcon } from 'lucide-react'\n\nexport type StatusType = 'online' | 'offline' | 'degraded' | 'unknown'\n\nexport const statusIcons: Record<StatusType, LucideIcon> = {\n online: CircleCheck,\n offline: CircleX,\n degraded: CircleAlert,\n unknown: CircleHelp,\n}\n","import { type ButtonHTMLAttributes, forwardRef } from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { cn } from '../lib/cn'\n\nconst buttonVariants = cva(\n 'inline-flex items-center justify-center rounded-md font-medium transition-colors disabled:opacity-50 disabled:pointer-events-none',\n {\n variants: {\n variant: {\n primary: 'bg-primary text-primary-foreground hover:bg-primary/90',\n secondary: 'bg-surface text-foreground hover:bg-surface-hover',\n ghost: 'hover:bg-surface-hover text-foreground-muted',\n danger: 'bg-danger text-white hover:bg-danger/90',\n outline: 'border border-border bg-transparent hover:bg-surface-hover',\n },\n size: {\n sm: 'h-7 px-2.5 text-xs gap-1.5',\n md: 'h-8 px-3 text-sm gap-2',\n lg: 'h-9 px-4 text-sm gap-2',\n },\n },\n defaultVariants: {\n variant: 'primary',\n size: 'sm',\n },\n }\n)\n\nexport interface ButtonProps\n extends ButtonHTMLAttributes<HTMLButtonElement>,\n VariantProps<typeof buttonVariants> {}\n\nexport const Button = forwardRef<HTMLButtonElement, ButtonProps>(\n ({ className, variant, size, ...props }, ref) => {\n return (\n <button\n ref={ref}\n className={cn(buttonVariants({ variant, size }), className)}\n {...props}\n />\n )\n }\n)\n\nButton.displayName = 'Button'\n","import { type ButtonHTMLAttributes, forwardRef } from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { type LucideIcon } from 'lucide-react'\nimport { cn } from '../lib/cn'\n\nconst iconButtonVariants = cva(\n 'inline-flex items-center justify-center rounded-md font-medium transition-colors disabled:opacity-50 disabled:pointer-events-none',\n {\n variants: {\n variant: {\n primary: 'bg-primary text-primary-foreground hover:bg-primary/90',\n secondary: 'bg-surface text-foreground hover:bg-surface-hover',\n ghost: 'hover:bg-surface-hover text-foreground-muted',\n danger: 'bg-danger text-white hover:bg-danger/90',\n outline: 'border border-border bg-transparent hover:bg-surface-hover',\n },\n size: {\n sm: 'h-7 w-7',\n md: 'h-8 w-8',\n lg: 'h-9 w-9',\n },\n },\n defaultVariants: {\n variant: 'primary',\n size: 'sm',\n },\n }\n)\n\nexport interface IconButtonProps\n extends Omit<ButtonHTMLAttributes<HTMLButtonElement>, 'children'>,\n VariantProps<typeof iconButtonVariants> {\n icon: LucideIcon\n 'aria-label': string\n}\n\nexport const IconButton = forwardRef<HTMLButtonElement, IconButtonProps>(\n ({ className, variant, size, icon: Icon, ...props }, ref) => {\n return (\n <button\n ref={ref}\n className={cn(iconButtonVariants({ variant, size }), className)}\n {...props}\n >\n <Icon className=\"h-4 w-4\" />\n </button>\n )\n }\n)\n\nIconButton.displayName = 'IconButton'\n","import { type HTMLAttributes, forwardRef } from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { cn } from '../lib/cn'\n\nconst badgeVariants = cva(\n 'inline-flex items-center rounded-full text-xs font-medium px-2 py-0.5',\n {\n variants: {\n variant: {\n default: 'bg-surface-hover text-foreground',\n success: 'bg-success/15 text-success',\n warning: 'bg-warning/15 text-warning',\n danger: 'bg-danger/15 text-danger',\n info: 'bg-info/15 text-info',\n },\n styleVariant: {\n solid: '',\n outline: 'border bg-transparent',\n },\n },\n defaultVariants: {\n variant: 'default',\n styleVariant: 'solid',\n },\n }\n)\n\nexport interface BadgeProps\n extends Omit<HTMLAttributes<HTMLSpanElement>, 'style'>,\n VariantProps<typeof badgeVariants> {\n style?: 'solid' | 'outline'\n}\n\nexport const Badge = forwardRef<HTMLSpanElement, BadgeProps>(\n ({ className, variant, style, ...props }, ref) => {\n return (\n <span\n ref={ref}\n className={cn(badgeVariants({ variant, styleVariant: style }), className)}\n {...props}\n />\n )\n }\n)\n\nBadge.displayName = 'Badge'\n","import { type HTMLAttributes, forwardRef } from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { cn } from '../lib/cn'\n\nconst cardVariants = cva('rounded-lg p-3', {\n variants: {\n variant: {\n flat: 'bg-surface',\n bordered: 'bg-surface border border-border',\n },\n },\n defaultVariants: {\n variant: 'bordered',\n },\n})\n\nexport interface CardProps\n extends HTMLAttributes<HTMLDivElement>,\n VariantProps<typeof cardVariants> {}\n\nexport const Card = forwardRef<HTMLDivElement, CardProps>(\n ({ className, variant, ...props }, ref) => {\n return (\n <div\n ref={ref}\n className={cn(cardVariants({ variant }), className)}\n {...props}\n />\n )\n }\n)\n\nCard.displayName = 'Card'\n","import { type LabelHTMLAttributes, forwardRef } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface LabelProps extends LabelHTMLAttributes<HTMLLabelElement> {}\n\nexport const Label = forwardRef<HTMLLabelElement, LabelProps>(\n ({ className, ...props }, ref) => {\n return (\n <label\n ref={ref}\n className={cn(\n 'text-[10px] uppercase tracking-wider text-foreground-muted font-medium',\n className\n )}\n {...props}\n />\n )\n }\n)\n\nLabel.displayName = 'Label'\n","import { type HTMLAttributes, forwardRef } from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { cn } from '../lib/cn'\n\nconst separatorVariants = cva('', {\n variants: {\n orientation: {\n horizontal: 'h-px w-full bg-border-subtle',\n vertical: 'w-px h-full bg-border-subtle',\n },\n },\n defaultVariants: {\n orientation: 'horizontal',\n },\n})\n\nexport interface SeparatorProps\n extends HTMLAttributes<HTMLDivElement>,\n VariantProps<typeof separatorVariants> {}\n\nexport const Separator = forwardRef<HTMLDivElement, SeparatorProps>(\n ({ className, orientation, ...props }, ref) => {\n return (\n <div\n ref={ref}\n role=\"separator\"\n className={cn(separatorVariants({ orientation }), className)}\n {...props}\n />\n )\n }\n)\n\nSeparator.displayName = 'Separator'\n","import { type HTMLAttributes, forwardRef } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface SkeletonProps extends HTMLAttributes<HTMLDivElement> {}\n\nexport const Skeleton = forwardRef<HTMLDivElement, SkeletonProps>(\n ({ className, ...props }, ref) => {\n return (\n <div\n ref={ref}\n className={cn('animate-pulse bg-surface-hover rounded-md h-4 w-full', className)}\n {...props}\n />\n )\n }\n)\n\nSkeleton.displayName = 'Skeleton'\n","import { type InputHTMLAttributes, type ReactNode, forwardRef } from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { cn } from '../lib/cn'\n\nconst inputVariants = cva(\n 'h-7 w-full px-2.5 text-xs bg-surface border rounded-md text-foreground placeholder:text-foreground-subtle focus:outline-none focus:ring-1 focus:ring-primary transition-colors',\n {\n variants: {\n state: {\n default: 'border-border',\n error: 'border-danger',\n },\n },\n defaultVariants: {\n state: 'default',\n },\n }\n)\n\nexport interface InputProps\n extends InputHTMLAttributes<HTMLInputElement>,\n VariantProps<typeof inputVariants> {\n leftSlot?: ReactNode\n rightSlot?: ReactNode\n}\n\nexport const Input = forwardRef<HTMLInputElement, InputProps>(\n ({ className, state, leftSlot, rightSlot, ...props }, ref) => {\n if (leftSlot || rightSlot) {\n return (\n <div className=\"relative flex items-center w-full\">\n {leftSlot && (\n <div className=\"absolute left-2.5 flex items-center pointer-events-none\">\n {leftSlot}\n </div>\n )}\n <input\n ref={ref}\n className={cn(\n inputVariants({ state }),\n leftSlot ? 'pl-7' : '',\n rightSlot ? 'pr-7' : '',\n className\n )}\n {...props}\n />\n {rightSlot && (\n <div className=\"absolute right-2.5 flex items-center pointer-events-none\">\n {rightSlot}\n </div>\n )}\n </div>\n )\n }\n\n return (\n <input\n ref={ref}\n className={cn(inputVariants({ state }), className)}\n {...props}\n />\n )\n }\n)\n\nInput.displayName = 'Input'\n","import { type SelectHTMLAttributes, forwardRef } from 'react'\nimport { ChevronDown } from 'lucide-react'\nimport { cn } from '../lib/cn'\n\nexport interface SelectOption {\n value: string\n label: string\n}\n\nexport interface SelectProps extends SelectHTMLAttributes<HTMLSelectElement> {\n options: SelectOption[]\n}\n\nexport const Select = forwardRef<HTMLSelectElement, SelectProps>(\n ({ className, options, ...props }, ref) => {\n return (\n <div className=\"relative w-full\">\n <select\n ref={ref}\n className={cn(\n 'h-7 w-full px-2.5 text-xs bg-surface border border-border rounded-md text-foreground appearance-none pr-7 focus:outline-none focus:ring-1 focus:ring-primary',\n className\n )}\n {...props}\n >\n {options.map((option) => (\n <option key={option.value} value={option.value}>\n {option.label}\n </option>\n ))}\n </select>\n <div className=\"absolute right-2 top-1/2 -translate-y-1/2 pointer-events-none text-foreground-muted\">\n <ChevronDown className=\"h-3.5 w-3.5\" />\n </div>\n </div>\n )\n }\n)\n\nSelect.displayName = 'Select'\n","import { type InputHTMLAttributes, forwardRef } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface CheckboxProps extends Omit<InputHTMLAttributes<HTMLInputElement>, 'type'> {}\n\nexport const Checkbox = forwardRef<HTMLInputElement, CheckboxProps>(\n ({ className, ...props }, ref) => {\n return (\n <input\n ref={ref}\n type=\"checkbox\"\n className={cn(\n 'w-3.5 h-3.5 rounded-sm border border-border accent-primary',\n className\n )}\n {...props}\n />\n )\n }\n)\n\nCheckbox.displayName = 'Checkbox'\n","import { type ButtonHTMLAttributes, forwardRef } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface SwitchProps extends Omit<ButtonHTMLAttributes<HTMLButtonElement>, 'onClick'> {\n checked: boolean\n onCheckedChange: (checked: boolean) => void\n label?: string\n}\n\nexport const Switch = forwardRef<HTMLButtonElement, SwitchProps>(\n ({ className, checked, onCheckedChange, label, ...props }, ref) => {\n return (\n <button\n ref={ref}\n role=\"switch\"\n aria-checked={checked}\n type=\"button\"\n onClick={() => onCheckedChange(!checked)}\n className={cn('inline-flex items-center gap-2', className)}\n {...props}\n >\n <span\n className={cn(\n 'w-8 h-4 rounded-full transition-colors',\n checked ? 'bg-primary' : 'bg-surface-hover'\n )}\n >\n <span\n className={cn(\n 'block w-3.5 h-3.5 rounded-full bg-white transition-transform',\n checked ? 'translate-x-4' : 'translate-x-0.5'\n )}\n />\n </span>\n {label && <span className=\"text-xs text-foreground\">{label}</span>}\n </button>\n )\n }\n)\n\nSwitch.displayName = 'Switch'\n","import {\n type HTMLAttributes,\n type ReactNode,\n createContext,\n forwardRef,\n useCallback,\n useContext,\n useEffect,\n useId,\n useRef,\n useState,\n} from 'react'\nimport { cva, type VariantProps } from 'class-variance-authority'\nimport { cn } from '../lib/cn'\n\ninterface DialogContextValue {\n open: boolean\n setOpen: (open: boolean) => void\n contentId: string\n}\n\nconst DialogContext = createContext<DialogContextValue | null>(null)\n\nfunction useDialogContext() {\n const ctx = useContext(DialogContext)\n if (!ctx) throw new Error('Dialog compound components must be used within <Dialog>')\n return ctx\n}\n\n/* ── Root ── */\n\ninterface DialogProps {\n children: ReactNode\n open?: boolean\n onOpenChange?: (open: boolean) => void\n}\n\nexport function Dialog({ children, open: controlledOpen, onOpenChange }: DialogProps) {\n const [uncontrolledOpen, setUncontrolledOpen] = useState(false)\n const open = controlledOpen ?? uncontrolledOpen\n const contentId = useId()\n\n const setOpen = useCallback(\n (next: boolean) => {\n onOpenChange?.(next)\n if (controlledOpen === undefined) setUncontrolledOpen(next)\n },\n [controlledOpen, onOpenChange]\n )\n\n return (\n <DialogContext.Provider value={{ open, setOpen, contentId }}>\n {children}\n </DialogContext.Provider>\n )\n}\n\n/* ── Trigger ── */\n\nexport function DialogTrigger({ children, ...props }: HTMLAttributes<HTMLButtonElement>) {\n const { setOpen } = useDialogContext()\n return (\n <button type=\"button\" onClick={() => setOpen(true)} {...props}>\n {children}\n </button>\n )\n}\n\n/* ── Content ── */\n\nconst contentVariants = cva(\n 'bg-background-elevated border border-border rounded-lg p-4 backdrop:bg-black/50 backdrop:backdrop-blur-sm',\n {\n variants: {\n width: {\n sm: 'max-w-sm',\n md: 'max-w-md',\n lg: 'max-w-lg',\n },\n },\n defaultVariants: { width: 'md' },\n }\n)\n\nexport interface DialogContentProps\n extends HTMLAttributes<HTMLDialogElement>,\n VariantProps<typeof contentVariants> {}\n\nexport const DialogContent = forwardRef<HTMLDialogElement, DialogContentProps>(\n ({ className, width, children, ...props }, ref) => {\n const { open, setOpen, contentId } = useDialogContext()\n const innerRef = useRef<HTMLDialogElement>(null)\n const dialogRef = (ref as React.RefObject<HTMLDialogElement>) ?? innerRef\n\n useEffect(() => {\n const el = dialogRef.current\n if (!el) return\n if (open && !el.open) el.showModal()\n if (!open && el.open) el.close()\n }, [open, dialogRef])\n\n const handleClick = (e: React.MouseEvent<HTMLDialogElement>) => {\n if (e.target === e.currentTarget) setOpen(false)\n }\n\n return (\n <dialog\n ref={dialogRef}\n id={contentId}\n className={cn(contentVariants({ width }), 'w-full', className)}\n onClick={handleClick}\n onClose={() => setOpen(false)}\n {...props}\n >\n {children}\n </dialog>\n )\n }\n)\n\nDialogContent.displayName = 'DialogContent'\n\n/* ── Header / Footer / Title / Description ── */\n\nexport function DialogHeader({ className, ...props }: HTMLAttributes<HTMLDivElement>) {\n return <div className={cn('flex flex-col gap-1 mb-3', className)} {...props} />\n}\n\nexport function DialogFooter({ className, ...props }: HTMLAttributes<HTMLDivElement>) {\n return <div className={cn('flex justify-end gap-2 mt-4', className)} {...props} />\n}\n\nexport function DialogTitle({ className, ...props }: HTMLAttributes<HTMLHeadingElement>) {\n return <h2 className={cn('text-sm font-semibold text-foreground', className)} {...props} />\n}\n\nexport function DialogDescription({ className, ...props }: HTMLAttributes<HTMLParagraphElement>) {\n return <p className={cn('text-xs text-foreground-muted', className)} {...props} />\n}\n","import {\n type ButtonHTMLAttributes,\n type HTMLAttributes,\n type ReactNode,\n createContext,\n useCallback,\n useContext,\n useEffect,\n useId,\n useRef,\n useState,\n} from 'react'\nimport { type LucideIcon } from 'lucide-react'\nimport { cn } from '../lib/cn'\n\ninterface DropdownContextValue {\n open: boolean\n setOpen: (open: boolean) => void\n triggerId: string\n contentId: string\n}\n\nconst DropdownContext = createContext<DropdownContextValue | null>(null)\n\nfunction useDropdownContext() {\n const ctx = useContext(DropdownContext)\n if (!ctx) throw new Error('Dropdown compound components must be used within <Dropdown>')\n return ctx\n}\n\n/* ── Root ── */\n\nexport function Dropdown({ children }: { children: ReactNode }) {\n const [open, setOpen] = useState(false)\n const triggerId = useId()\n const contentId = useId()\n\n return (\n <DropdownContext.Provider value={{ open, setOpen, triggerId, contentId }}>\n <div className=\"relative inline-block\">{children}</div>\n </DropdownContext.Provider>\n )\n}\n\n/* ── Trigger ── */\n\nexport function DropdownTrigger({ children, ...props }: ButtonHTMLAttributes<HTMLButtonElement>) {\n const { open, setOpen, triggerId, contentId } = useDropdownContext()\n return (\n <button\n type=\"button\"\n id={triggerId}\n aria-haspopup=\"menu\"\n aria-expanded={open}\n aria-controls={open ? contentId : undefined}\n onClick={() => setOpen(!open)}\n {...props}\n >\n {children}\n </button>\n )\n}\n\n/* ── Content ── */\n\nexport function DropdownContent({ className, children, ...props }: HTMLAttributes<HTMLDivElement>) {\n const { open, setOpen, contentId, triggerId } = useDropdownContext()\n const ref = useRef<HTMLDivElement>(null)\n\n useEffect(() => {\n if (!open) return\n const handler = (e: MouseEvent) => {\n const el = ref.current\n const trigger = document.getElementById(triggerId)\n if (el && !el.contains(e.target as Node) && !trigger?.contains(e.target as Node)) {\n setOpen(false)\n }\n }\n const escHandler = (e: KeyboardEvent) => {\n if (e.key === 'Escape') setOpen(false)\n }\n document.addEventListener('mousedown', handler)\n document.addEventListener('keydown', escHandler)\n return () => {\n document.removeEventListener('mousedown', handler)\n document.removeEventListener('keydown', escHandler)\n }\n }, [open, setOpen, triggerId])\n\n if (!open) return null\n\n return (\n <div\n ref={ref}\n id={contentId}\n role=\"menu\"\n aria-labelledby={triggerId}\n className={cn(\n 'absolute left-0 top-full z-50 mt-1 bg-background-elevated border border-border rounded-md shadow-lg py-1 min-w-[160px]',\n className\n )}\n {...props}\n >\n {children}\n </div>\n )\n}\n\n/* ── Item ── */\n\ninterface DropdownItemProps extends ButtonHTMLAttributes<HTMLButtonElement> {\n icon?: LucideIcon\n variant?: 'default' | 'danger'\n}\n\nexport function DropdownItem({\n className,\n icon: Icon,\n variant = 'default',\n children,\n onClick,\n ...props\n}: DropdownItemProps) {\n const { setOpen } = useDropdownContext()\n\n const handleClick = useCallback(\n (e: React.MouseEvent<HTMLButtonElement>) => {\n onClick?.(e)\n setOpen(false)\n },\n [onClick, setOpen]\n )\n\n return (\n <button\n type=\"button\"\n role=\"menuitem\"\n className={cn(\n 'h-7 text-xs px-2 w-full text-left flex items-center gap-2',\n variant === 'danger'\n ? 'text-danger hover:bg-danger/10'\n : 'text-foreground hover:bg-surface-hover',\n className\n )}\n onClick={handleClick}\n {...props}\n >\n {Icon && <Icon size={14} />}\n {children}\n </button>\n )\n}\n","import {\n type HTMLAttributes,\n type ReactNode,\n createContext,\n useContext,\n useId,\n useRef,\n useState,\n} from 'react'\nimport { cn } from '../lib/cn'\n\ninterface TooltipContextValue {\n open: boolean\n show: () => void\n hide: () => void\n tooltipId: string\n}\n\nconst TooltipContext = createContext<TooltipContextValue | null>(null)\n\nfunction useTooltipContext() {\n const ctx = useContext(TooltipContext)\n if (!ctx) throw new Error('Tooltip compound components must be used within <Tooltip>')\n return ctx\n}\n\n/* ── Root ── */\n\nexport function Tooltip({ children }: { children: ReactNode }) {\n const [open, setOpen] = useState(false)\n const timerRef = useRef<ReturnType<typeof setTimeout>>(null)\n const tooltipId = useId()\n\n const show = () => {\n timerRef.current = setTimeout(() => setOpen(true), 300)\n }\n\n const hide = () => {\n if (timerRef.current) clearTimeout(timerRef.current)\n setOpen(false)\n }\n\n return (\n <TooltipContext.Provider value={{ open, show, hide, tooltipId }}>\n <div className=\"relative inline-block\">{children}</div>\n </TooltipContext.Provider>\n )\n}\n\n/* ── Trigger ── */\n\nexport function TooltipTrigger({ children, ...props }: HTMLAttributes<HTMLDivElement>) {\n const { show, hide, tooltipId, open } = useTooltipContext()\n\n return (\n <div\n onMouseEnter={show}\n onMouseLeave={hide}\n onFocus={show}\n onBlur={hide}\n aria-describedby={open ? tooltipId : undefined}\n {...props}\n >\n {children}\n </div>\n )\n}\n\n/* ── Content ── */\n\nexport function TooltipContent({ className, children, ...props }: HTMLAttributes<HTMLDivElement>) {\n const { open, tooltipId } = useTooltipContext()\n\n return (\n <div\n id={tooltipId}\n role=\"tooltip\"\n className={cn(\n 'absolute bottom-full left-1/2 -translate-x-1/2 mb-2 bg-foreground text-background text-xs px-2 py-1 rounded-md shadow-md whitespace-nowrap pointer-events-none transition-opacity duration-150',\n open ? 'opacity-100' : 'opacity-0',\n className\n )}\n {...props}\n >\n {children}\n </div>\n )\n}\n","import {\n type ButtonHTMLAttributes,\n type HTMLAttributes,\n type ReactNode,\n createContext,\n useCallback,\n useContext,\n useEffect,\n useId,\n useRef,\n useState,\n} from 'react'\nimport { cn } from '../lib/cn'\n\ninterface PopoverContextValue {\n open: boolean\n setOpen: (open: boolean) => void\n triggerId: string\n contentId: string\n}\n\nconst PopoverContext = createContext<PopoverContextValue | null>(null)\n\nfunction usePopoverContext() {\n const ctx = useContext(PopoverContext)\n if (!ctx) throw new Error('Popover compound components must be used within <Popover>')\n return ctx\n}\n\n/* ── Root ── */\n\ninterface PopoverProps {\n children: ReactNode\n open?: boolean\n onOpenChange?: (open: boolean) => void\n}\n\nexport function Popover({ children, open: controlledOpen, onOpenChange }: PopoverProps) {\n const [uncontrolledOpen, setUncontrolledOpen] = useState(false)\n const open = controlledOpen ?? uncontrolledOpen\n const triggerId = useId()\n const contentId = useId()\n\n const setOpen = useCallback(\n (next: boolean) => {\n onOpenChange?.(next)\n if (controlledOpen === undefined) setUncontrolledOpen(next)\n },\n [controlledOpen, onOpenChange]\n )\n\n return (\n <PopoverContext.Provider value={{ open, setOpen, triggerId, contentId }}>\n <div className=\"relative inline-block\">{children}</div>\n </PopoverContext.Provider>\n )\n}\n\n/* ── Trigger ── */\n\nexport function PopoverTrigger({ children, ...props }: ButtonHTMLAttributes<HTMLButtonElement>) {\n const { open, setOpen, triggerId, contentId } = usePopoverContext()\n return (\n <button\n type=\"button\"\n id={triggerId}\n aria-haspopup=\"dialog\"\n aria-expanded={open}\n aria-controls={open ? contentId : undefined}\n onClick={() => setOpen(!open)}\n {...props}\n >\n {children}\n </button>\n )\n}\n\n/* ── Content ── */\n\nexport function PopoverContent({ className, children, ...props }: HTMLAttributes<HTMLDivElement>) {\n const { open, setOpen, contentId, triggerId } = usePopoverContext()\n const ref = useRef<HTMLDivElement>(null)\n\n useEffect(() => {\n if (!open) return\n const handler = (e: MouseEvent) => {\n const el = ref.current\n const trigger = document.getElementById(triggerId)\n if (el && !el.contains(e.target as Node) && !trigger?.contains(e.target as Node)) {\n setOpen(false)\n }\n }\n const escHandler = (e: KeyboardEvent) => {\n if (e.key === 'Escape') setOpen(false)\n }\n document.addEventListener('mousedown', handler)\n document.addEventListener('keydown', escHandler)\n return () => {\n document.removeEventListener('mousedown', handler)\n document.removeEventListener('keydown', escHandler)\n }\n }, [open, setOpen, triggerId])\n\n if (!open) return null\n\n return (\n <div\n ref={ref}\n id={contentId}\n role=\"dialog\"\n aria-labelledby={triggerId}\n className={cn(\n 'absolute left-0 top-full z-50 mt-1 bg-background-elevated border border-border rounded-lg shadow-lg p-3',\n className\n )}\n {...props}\n >\n {children}\n </div>\n )\n}\n","import {\n type ButtonHTMLAttributes,\n type HTMLAttributes,\n type ReactNode,\n createContext,\n useCallback,\n useContext,\n useState,\n} from 'react'\nimport { cn } from '../lib/cn'\n\ninterface TabsContextValue {\n value: string\n setValue: (value: string) => void\n}\n\nconst TabsContext = createContext<TabsContextValue | null>(null)\n\nfunction useTabsContext() {\n const ctx = useContext(TabsContext)\n if (!ctx) throw new Error('Tabs compound components must be used within <Tabs>')\n return ctx\n}\n\n/* ── Root ── */\n\ninterface TabsProps extends HTMLAttributes<HTMLDivElement> {\n value?: string\n onValueChange?: (value: string) => void\n defaultValue?: string\n}\n\nexport function Tabs({\n value: controlledValue,\n onValueChange,\n defaultValue = '',\n className,\n ...props\n}: TabsProps) {\n const [uncontrolledValue, setUncontrolledValue] = useState(defaultValue)\n const value = controlledValue ?? uncontrolledValue\n\n const setValue = useCallback(\n (next: string) => {\n onValueChange?.(next)\n if (controlledValue === undefined) setUncontrolledValue(next)\n },\n [controlledValue, onValueChange]\n )\n\n return (\n <TabsContext.Provider value={{ value, setValue }}>\n <div className={className} {...props} />\n </TabsContext.Provider>\n )\n}\n\n/* ── TabsList ── */\n\nexport function TabsList({ className, ...props }: HTMLAttributes<HTMLDivElement>) {\n return (\n <div\n role=\"tablist\"\n className={cn('flex flex-row border-b border-border-subtle', className)}\n {...props}\n />\n )\n}\n\n/* ── TabsTrigger ── */\n\ninterface TabsTriggerProps extends ButtonHTMLAttributes<HTMLButtonElement> {\n value: string\n}\n\nexport function TabsTrigger({ value, className, ...props }: TabsTriggerProps) {\n const { value: activeValue, setValue } = useTabsContext()\n const isActive = value === activeValue\n const panelId = `tabpanel-${value}`\n\n return (\n <button\n type=\"button\"\n role=\"tab\"\n aria-selected={isActive}\n aria-controls={panelId}\n tabIndex={isActive ? 0 : -1}\n className={cn(\n 'h-7 text-xs px-3 transition-colors',\n isActive\n ? 'border-b-2 border-primary text-foreground font-medium'\n : 'text-foreground-muted hover:text-foreground',\n className\n )}\n onClick={() => setValue(value)}\n {...props}\n />\n )\n}\n\n/* ── TabsContent ── */\n\ninterface TabsContentProps extends HTMLAttributes<HTMLDivElement> {\n value: string\n}\n\nexport function TabsContent({ value, className, ...props }: TabsContentProps) {\n const { value: activeValue } = useTabsContext()\n if (value !== activeValue) return null\n\n return (\n <div\n role=\"tabpanel\"\n id={`tabpanel-${value}`}\n className={cn('pt-3', className)}\n {...props}\n />\n )\n}\n","import { type HTMLAttributes, forwardRef } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface ScrollAreaProps extends HTMLAttributes<HTMLDivElement> {}\n\nexport const ScrollArea = forwardRef<HTMLDivElement, ScrollAreaProps>(\n ({ className, ...props }, ref) => {\n return (\n <div\n ref={ref}\n className={cn(\n 'overflow-auto [&::-webkit-scrollbar]:w-1 [&::-webkit-scrollbar-track]:bg-transparent [&::-webkit-scrollbar-thumb]:bg-surface-hover [&::-webkit-scrollbar-thumb]:rounded-full',\n className\n )}\n {...props}\n />\n )\n }\n)\n\nScrollArea.displayName = 'ScrollArea'\n","import { useRef, useState, useCallback, useEffect, type ReactNode } from 'react';\nimport { X, Minimize2, Maximize2, GripHorizontal } from 'lucide-react';\nimport { cn } from '../lib/cn';\n\nexport interface FloatingPanelProps {\n /** Panel title displayed in the title bar */\n title: string;\n /** Called when the close button is clicked */\n onClose: () => void;\n /** Panel content */\n children: ReactNode;\n /** Default width in pixels */\n defaultWidth?: number;\n /** Default height in pixels */\n defaultHeight?: number;\n /** Minimum width in pixels */\n minWidth?: number;\n /** Minimum height in pixels */\n minHeight?: number;\n /** Offset index to stagger multiple panels (adds 30px offset per index) */\n offsetIndex?: number;\n /** Additional CSS classes for the panel container */\n className?: string;\n}\n\nexport function FloatingPanel({\n title,\n onClose,\n children,\n defaultWidth = 360,\n defaultHeight = 280,\n minWidth = 280,\n minHeight = 160,\n offsetIndex = 0,\n className,\n}: FloatingPanelProps) {\n const [pos, setPos] = useState({ x: 80 + offsetIndex * 30, y: 80 + offsetIndex * 30 });\n const [size, setSize] = useState({ w: defaultWidth, h: defaultHeight });\n const [minimized, setMinimized] = useState(false);\n const dragging = useRef(false);\n const resizing = useRef(false);\n const offset = useRef({ x: 0, y: 0 });\n\n const onDragStart = useCallback((e: React.MouseEvent) => {\n e.preventDefault();\n dragging.current = true;\n offset.current = { x: e.clientX - pos.x, y: e.clientY - pos.y };\n }, [pos]);\n\n const onResizeStart = useCallback((e: React.MouseEvent) => {\n e.preventDefault();\n e.stopPropagation();\n resizing.current = true;\n offset.current = { x: e.clientX, y: e.clientY };\n }, []);\n\n useEffect(() => {\n const onMouseMove = (e: MouseEvent) => {\n if (dragging.current) setPos({ x: e.clientX - offset.current.x, y: e.clientY - offset.current.y });\n if (resizing.current) {\n const dx = e.clientX - offset.current.x;\n const dy = e.clientY - offset.current.y;\n offset.current = { x: e.clientX, y: e.clientY };\n setSize(prev => ({ w: Math.max(minWidth, prev.w + dx), h: Math.max(minHeight, prev.h + dy) }));\n }\n };\n const onMouseUp = () => { dragging.current = false; resizing.current = false; };\n window.addEventListener('mousemove', onMouseMove);\n window.addEventListener('mouseup', onMouseUp);\n return () => { window.removeEventListener('mousemove', onMouseMove); window.removeEventListener('mouseup', onMouseUp); };\n }, [minWidth, minHeight]);\n\n return (\n <div\n className={cn(\n 'fixed z-50 rounded-lg border border-border bg-background-elevated shadow-2xl flex flex-col overflow-hidden',\n className\n )}\n style={{ left: pos.x, top: pos.y, width: minimized ? 280 : size.w, height: minimized ? 'auto' : size.h }}\n >\n {/* Title bar — draggable */}\n <div\n onMouseDown={onDragStart}\n className=\"flex items-center justify-between gap-2 px-3 py-2 border-b border-border cursor-move select-none shrink-0 bg-surface\"\n >\n <div className=\"flex items-center gap-2 min-w-0\">\n <GripHorizontal size={12} className=\"text-foreground-subtle shrink-0\" />\n <span className=\"text-[11px] font-medium truncate\">{title}</span>\n </div>\n <div className=\"flex items-center gap-1 shrink-0\">\n <button\n onClick={() => setMinimized(!minimized)}\n className=\"p-0.5 rounded hover:bg-surface-hover text-foreground-muted transition-colors\"\n title={minimized ? 'Restore' : 'Minimize'}\n >\n {minimized ? <Maximize2 size={12} /> : <Minimize2 size={12} />}\n </button>\n <button\n onClick={onClose}\n className=\"p-0.5 rounded hover:bg-danger/20 text-foreground-muted hover:text-danger transition-colors\"\n title=\"Close\"\n >\n <X size={12} />\n </button>\n </div>\n </div>\n\n {/* Content */}\n {!minimized && (\n <div className=\"flex-1 min-h-0 overflow-y-auto relative\">\n {children}\n {/* Resize handle */}\n <div\n onMouseDown={onResizeStart}\n className=\"absolute bottom-0 right-0 w-4 h-4 cursor-nwse-resize\"\n style={{ background: 'linear-gradient(135deg, transparent 50%, var(--color-foreground-subtle) 50%)', opacity: 0.4 }}\n />\n </div>\n )}\n </div>\n );\n}\n","import { cn } from '../lib/cn'\n\ntype Status = 'online' | 'offline' | 'degraded' | 'unknown'\n\nexport interface StatusBadgeProps {\n status: Status\n showDot?: boolean\n showLabel?: boolean\n size?: 'sm' | 'md'\n className?: string\n}\n\nconst statusConfig: Record<Status, { colorClass: string; label: string }> = {\n online: { colorClass: 'bg-success', label: 'Online' },\n offline: { colorClass: 'bg-danger', label: 'Offline' },\n degraded: { colorClass: 'bg-warning', label: 'Degraded' },\n unknown: { colorClass: 'bg-foreground-subtle', label: 'Unknown' },\n}\n\nexport function StatusBadge({\n status,\n showDot = true,\n showLabel = true,\n size = 'sm',\n className,\n}: StatusBadgeProps) {\n const config = statusConfig[status]\n\n return (\n <span\n className={cn(\n 'inline-flex items-center gap-1.5',\n size === 'sm' ? 'text-xs' : 'text-sm',\n className\n )}\n >\n {showDot && (\n <span\n className={cn('h-1.5 w-1.5 shrink-0 rounded-full', config.colorClass)}\n aria-hidden=\"true\"\n />\n )}\n {showLabel && (\n <span className=\"text-foreground\">{config.label}</span>\n )}\n </span>\n )\n}\n","import { cn } from '../lib/cn'\nimport type { ProviderType } from '../icons'\n\nexport interface ProviderBadgeProps {\n provider: ProviderType\n showLabel?: boolean\n className?: string\n}\n\nconst providerConfig: Record<ProviderType, { colorClass: string; label: string }> = {\n frigate: { colorClass: 'bg-provider-frigate', label: 'Frigate' },\n scrypted: { colorClass: 'bg-provider-scrypted', label: 'Scrypted' },\n reolink: { colorClass: 'bg-provider-reolink', label: 'Reolink' },\n homeAssistant: { colorClass: 'bg-provider-homeAssistant', label: 'Home Assistant' },\n rtsp: { colorClass: 'bg-provider-rtsp', label: 'RTSP' },\n}\n\nexport function ProviderBadge({\n provider,\n showLabel = true,\n className,\n}: ProviderBadgeProps) {\n const config = providerConfig[provider]\n\n return (\n <span className={cn('inline-flex items-center gap-1.5 text-xs', className)}>\n <span\n className={cn('h-1.5 w-1.5 shrink-0 rounded-sm', config.colorClass)}\n aria-hidden=\"true\"\n />\n {showLabel && (\n <span className=\"text-foreground\">{config.label}</span>\n )}\n </span>\n )\n}\n","import { type ReactNode } from 'react'\nimport { cn } from '../lib/cn'\nimport { Label } from '../primitives'\n\nexport interface FormFieldProps {\n label: string\n description?: string\n error?: string\n required?: boolean\n children: ReactNode\n orientation?: 'vertical' | 'horizontal'\n className?: string\n}\n\nexport function FormField({\n label,\n description,\n error,\n required,\n children,\n orientation = 'vertical',\n className,\n}: FormFieldProps) {\n const isHorizontal = orientation === 'horizontal'\n\n return (\n <div\n className={cn(\n 'flex gap-2',\n isHorizontal ? 'flex-row items-center justify-between' : 'flex-col',\n className\n )}\n >\n <div className={cn(isHorizontal ? 'flex-1' : '')}>\n <Label>\n {label}\n {required && <span className=\"text-danger ml-0.5\">*</span>}\n </Label>\n {description && (\n <p className=\"text-foreground-subtle text-xs mt-0.5\">{description}</p>\n )}\n </div>\n <div className={cn(isHorizontal ? 'shrink-0' : '')}>\n {children}\n </div>\n {error && (\n <p className=\"text-danger text-xs\">{error}</p>\n )}\n </div>\n )\n}\n","import { type ReactNode } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface PageHeaderProps {\n title: string\n subtitle?: string\n actions?: ReactNode\n className?: string\n}\n\nexport function PageHeader({ title, subtitle, actions, className }: PageHeaderProps) {\n return (\n <div className={cn('flex items-center justify-between mb-3', className)}>\n <div>\n <h1 className=\"text-sm font-semibold text-foreground\">{title}</h1>\n {subtitle && (\n <p className=\"text-foreground-subtle text-xs\">{subtitle}</p>\n )}\n </div>\n {actions && <div className=\"flex items-center gap-2\">{actions}</div>}\n </div>\n )\n}\n","import { type ReactNode } from 'react'\nimport { type LucideIcon } from 'lucide-react'\nimport { cn } from '../lib/cn'\n\nexport interface EmptyStateProps {\n icon?: LucideIcon\n title: string\n description?: string\n action?: ReactNode\n className?: string\n}\n\nexport function EmptyState({\n icon: Icon,\n title,\n description,\n action,\n className,\n}: EmptyStateProps) {\n return (\n <div className={cn('flex flex-col items-center justify-center gap-3 py-12', className)}>\n {Icon && (\n <Icon className=\"h-12 w-12 text-foreground-subtle\" aria-hidden=\"true\" />\n )}\n <div className=\"flex flex-col items-center gap-1 text-center\">\n <p className=\"text-foreground-muted text-sm font-medium\">{title}</p>\n {description && (\n <p className=\"text-foreground-subtle text-xs max-w-xs\">{description}</p>\n )}\n </div>\n {action && <div className=\"mt-1\">{action}</div>}\n </div>\n )\n}\n","import {\n Dialog,\n DialogContent,\n DialogHeader,\n DialogTitle,\n DialogDescription,\n DialogFooter,\n Button,\n} from '../primitives'\n\nexport interface ConfirmDialogProps {\n title: string\n message: string\n confirmLabel?: string\n cancelLabel?: string\n onConfirm: () => void\n onCancel: () => void\n variant?: 'danger' | 'default'\n open: boolean\n onOpenChange: (open: boolean) => void\n}\n\nexport function ConfirmDialog({\n title,\n message,\n confirmLabel = 'Confirm',\n cancelLabel = 'Cancel',\n onConfirm,\n onCancel,\n variant = 'default',\n open,\n onOpenChange,\n}: ConfirmDialogProps) {\n return (\n <Dialog open={open} onOpenChange={onOpenChange}>\n <DialogContent>\n <DialogHeader>\n <DialogTitle>{title}</DialogTitle>\n <DialogDescription>{message}</DialogDescription>\n </DialogHeader>\n <DialogFooter>\n <Button variant=\"ghost\" onClick={onCancel}>\n {cancelLabel}\n </Button>\n <Button\n variant={variant === 'danger' ? 'danger' : 'primary'}\n onClick={onConfirm}\n >\n {confirmLabel}\n </Button>\n </DialogFooter>\n </DialogContent>\n </Dialog>\n )\n}\n","import { TrendingUp, TrendingDown } from 'lucide-react'\nimport { cn } from '../lib/cn'\nimport { Card } from '../primitives'\n\nexport interface StatCardProps {\n value: string | number\n label: string\n trend?: { value: number; direction: 'up' | 'down' }\n className?: string\n}\n\nexport function StatCard({ value, label, trend, className }: StatCardProps) {\n return (\n <Card className={cn('flex flex-col gap-1', className)}>\n <div className=\"flex items-baseline gap-2\">\n <span className=\"text-2xl font-semibold text-foreground\">{value}</span>\n {trend && (\n <span\n className={cn(\n 'inline-flex items-center gap-0.5 text-xs font-medium',\n trend.direction === 'up' ? 'text-success' : 'text-danger'\n )}\n >\n {trend.direction === 'up' ? (\n <TrendingUp className=\"h-3 w-3\" />\n ) : (\n <TrendingDown className=\"h-3 w-3\" />\n )}\n {trend.value}%\n </span>\n )}\n </div>\n <span className=\"text-xs text-foreground-muted\">{label}</span>\n </Card>\n )\n}\n","import { type ReactNode } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface KeyValueListProps {\n items: { key: string; value: ReactNode }[]\n className?: string\n}\n\nexport function KeyValueList({ items, className }: KeyValueListProps) {\n return (\n <dl className={cn('flex flex-col', className)}>\n {items.map((item) => (\n <div\n key={item.key}\n className=\"flex items-center h-7\"\n >\n <dt className=\"text-foreground-subtle text-xs w-1/3 shrink-0\">\n {item.key}\n </dt>\n <dd className=\"text-foreground text-xs\">{item.value}</dd>\n </div>\n ))}\n </dl>\n )\n}\n","import { useCallback, useState } from 'react'\nimport { Copy, Check } from 'lucide-react'\nimport { cn } from '../lib/cn'\nimport { ScrollArea, IconButton } from '../primitives'\n\nexport interface CodeBlockProps {\n children: string\n maxHeight?: number\n className?: string\n}\n\nexport function CodeBlock({ children, maxHeight = 300, className }: CodeBlockProps) {\n const [copied, setCopied] = useState(false)\n\n const handleCopy = useCallback(() => {\n navigator.clipboard.writeText(children).then(() => {\n setCopied(true)\n setTimeout(() => setCopied(false), 2000)\n })\n }, [children])\n\n return (\n <div className={cn('relative group', className)}>\n <ScrollArea style={{ maxHeight }}>\n <pre className=\"font-mono text-xs bg-surface p-3 rounded-md border border-border-subtle\">\n <code>{children}</code>\n </pre>\n </ScrollArea>\n <div className=\"absolute top-2 right-2 opacity-0 group-hover:opacity-100 transition-opacity\">\n <IconButton\n icon={copied ? Check : Copy}\n aria-label=\"Copy code\"\n variant=\"ghost\"\n size=\"sm\"\n onClick={handleCopy}\n />\n </div>\n </div>\n )\n}\n","import { Search } from 'lucide-react'\nimport { cn } from '../lib/cn'\nimport { Input, Select, Badge } from '../primitives'\n\ntype FilterDef =\n | { type: 'search'; key: string; placeholder?: string }\n | { type: 'select'; key: string; label: string; options: { value: string; label: string }[] }\n | { type: 'badge-toggle'; key: string; options: { value: string; label: string }[] }\n\nexport type { FilterDef }\n\nexport interface FilterBarProps {\n filters: FilterDef[]\n values: Record<string, unknown>\n onChange: (values: Record<string, unknown>) => void\n className?: string\n}\n\nexport function FilterBar({ filters, values, onChange, className }: FilterBarProps) {\n const handleChange = (key: string, value: unknown) => {\n onChange({ ...values, [key]: value })\n }\n\n return (\n <div className={cn('flex items-center gap-2 flex-wrap', className)}>\n {filters.map((filter) => {\n switch (filter.type) {\n case 'search':\n return (\n <Input\n key={filter.key}\n placeholder={filter.placeholder ?? 'Search...'}\n value={(values[filter.key] as string) ?? ''}\n onChange={(e) => handleChange(filter.key, e.target.value)}\n leftSlot={<Search className=\"h-3 w-3 text-foreground-subtle\" />}\n className=\"w-48\"\n />\n )\n\n case 'select':\n return (\n <Select\n key={filter.key}\n options={filter.options}\n value={(values[filter.key] as string) ?? ''}\n onChange={(e) => handleChange(filter.key, e.target.value)}\n className=\"w-36\"\n />\n )\n\n case 'badge-toggle':\n return (\n <div key={filter.key} className=\"flex items-center gap-1\">\n {filter.options.map((option) => {\n const currentValue = values[filter.key]\n const isActive = currentValue === option.value\n\n return (\n <button\n key={option.value}\n type=\"button\"\n onClick={() =>\n handleChange(\n filter.key,\n isActive ? undefined : option.value\n )\n }\n >\n <Badge\n variant={isActive ? 'info' : 'default'}\n className=\"cursor-pointer\"\n >\n {option.label}\n </Badge>\n </button>\n )\n })}\n </div>\n )\n\n default:\n return null\n }\n })}\n </div>\n )\n}\n","import { type LucideIcon } from 'lucide-react'\nimport { cn } from '../../lib/cn'\nimport { Badge } from '../../primitives'\n\nexport interface SidebarItemProps {\n label: string\n icon: LucideIcon\n href: string\n badge?: string | number\n active?: boolean\n className?: string\n}\n\nexport function SidebarItem({\n label,\n icon: Icon,\n href,\n badge,\n active = false,\n className,\n}: SidebarItemProps) {\n return (\n <a\n href={href}\n className={cn(\n 'flex items-center gap-2 h-7 px-2 text-[11px] transition-colors',\n active\n ? 'border-l-2 border-primary bg-primary/[0.08] text-foreground rounded-r-md'\n : 'text-foreground-subtle hover:bg-surface-hover rounded-md',\n className\n )}\n >\n <Icon className=\"h-3.5 w-3.5 shrink-0\" />\n <span className=\"truncate flex-1\">{label}</span>\n {badge !== undefined && (\n <Badge className=\"ml-auto text-[10px] px-1.5 py-0\">{badge}</Badge>\n )}\n </a>\n )\n}\n","import { type ReactNode } from 'react'\nimport { cn } from '../../lib/cn'\nimport { Separator } from '../../primitives'\nimport { SidebarItem, type SidebarItemProps } from './sidebar-item'\n\nexport interface SidebarSection {\n label?: string\n items: SidebarItemProps[]\n}\n\nexport interface SidebarProps {\n logo?: ReactNode\n sections: SidebarSection[]\n footer?: SidebarItemProps[]\n className?: string\n}\n\nexport function Sidebar({ logo, sections, footer, className }: SidebarProps) {\n return (\n <nav\n className={cn(\n 'w-44 bg-surface border-r border-border h-full flex flex-col',\n className\n )}\n >\n {logo && <div className=\"px-3 py-2 shrink-0\">{logo}</div>}\n\n <div className=\"flex-1 overflow-auto px-1 py-1\">\n {sections.map((section, sectionIndex) => (\n <div key={sectionIndex} className={cn(sectionIndex > 0 ? 'mt-3' : '')}>\n {section.label && (\n <span className=\"text-[10px] text-foreground-disabled uppercase tracking-wider px-2 mb-1 block\">\n {section.label}\n </span>\n )}\n <div className=\"flex flex-col gap-0.5\">\n {section.items.map((item) => (\n <SidebarItem key={item.href} {...item} />\n ))}\n </div>\n </div>\n ))}\n </div>\n\n {footer && footer.length > 0 && (\n <div className=\"shrink-0 px-1 pb-1\">\n <Separator className=\"mb-1\" />\n <div className=\"flex flex-col gap-0.5\">\n {footer.map((item) => (\n <SidebarItem key={item.href} {...item} />\n ))}\n </div>\n </div>\n )}\n </nav>\n )\n}\n","import { type ReactNode } from 'react'\nimport { ChevronRight } from 'lucide-react'\nimport { cn } from '../../lib/cn'\nimport { Sidebar, type SidebarProps } from './sidebar'\n\nexport interface AppShellProps {\n sidebar: SidebarProps\n header?: {\n breadcrumbs?: { label: string; href?: string }[]\n actions?: ReactNode\n }\n children: ReactNode\n className?: string\n}\n\nexport function AppShell({ sidebar, header, children, className }: AppShellProps) {\n return (\n <div className={cn('flex h-screen', className)}>\n <Sidebar {...sidebar} />\n\n <div className=\"flex flex-1 flex-col min-w-0\">\n {header && (\n <header className=\"flex items-center h-10 border-b border-border px-4 shrink-0\">\n {header.breadcrumbs && header.breadcrumbs.length > 0 && (\n <nav className=\"flex items-center gap-1 text-xs flex-1 min-w-0\">\n {header.breadcrumbs.map((crumb, index) => {\n const isLast = index === header.breadcrumbs!.length - 1\n return (\n <span key={index} className=\"flex items-center gap-1\">\n {index > 0 && (\n <ChevronRight className=\"h-3 w-3 text-foreground-subtle shrink-0\" />\n )}\n {crumb.href && !isLast ? (\n <a\n href={crumb.href}\n className=\"text-foreground-subtle hover:text-foreground transition-colors truncate\"\n >\n {crumb.label}\n </a>\n ) : (\n <span className=\"text-foreground truncate\">{crumb.label}</span>\n )}\n </span>\n )\n })}\n </nav>\n )}\n {header.actions && (\n <div className=\"flex items-center gap-2 ml-auto shrink-0\">\n {header.actions}\n </div>\n )}\n </header>\n )}\n\n <main className=\"flex-1 overflow-auto p-4\">{children}</main>\n </div>\n </div>\n )\n}\n","import { useMemo } from 'react'\nimport {\n useReactTable,\n getCoreRowModel,\n getSortedRowModel,\n getFilteredRowModel,\n getPaginationRowModel,\n flexRender,\n type ColumnDef,\n} from '@tanstack/react-table'\nimport { cn } from '../../lib/cn'\nimport { Skeleton } from '../../primitives/skeleton'\nimport { Checkbox } from '../../primitives/checkbox'\nimport { DataTableHeader } from './data-table-header'\nimport { DataTableRow } from './data-table-row'\nimport { DataTablePagination } from './data-table-pagination'\nimport type { DataTableProps } from './types'\n\nexport function DataTable<T>({\n data,\n columns: userColumns,\n sorting,\n onSortingChange,\n filtering,\n onFilteringChange,\n pagination,\n onPaginationChange,\n loading = false,\n emptyState,\n rowActions,\n onRowClick,\n selectable = false,\n compact = true,\n stickyHeader = false,\n className,\n}: DataTableProps<T>) {\n const columns = useMemo(() => {\n if (!selectable) return userColumns\n\n const selectColumn: ColumnDef<T, unknown> = {\n id: '__select',\n header: ({ table }) => (\n <Checkbox\n checked={table.getIsAllPageRowsSelected()}\n onChange={table.getToggleAllPageRowsSelectedHandler()}\n aria-label=\"Select all\"\n />\n ),\n cell: ({ row }) => (\n <Checkbox\n checked={row.getIsSelected()}\n onChange={row.getToggleSelectedHandler()}\n aria-label=\"Select row\"\n />\n ),\n enableSorting: false,\n }\n\n return [selectColumn, ...userColumns]\n }, [userColumns, selectable])\n\n const table = useReactTable({\n data,\n columns,\n state: {\n ...(sorting !== undefined && { sorting }),\n ...(filtering !== undefined && { columnFilters: filtering }),\n ...(pagination !== undefined && {\n pagination: { pageIndex: pagination.page, pageSize: pagination.pageSize },\n }),\n },\n onSortingChange: onSortingChange\n ? (updater) => {\n const next = typeof updater === 'function' ? updater(sorting ?? []) : updater\n onSortingChange(next)\n }\n : undefined,\n onColumnFiltersChange: onFilteringChange\n ? (updater) => {\n const next = typeof updater === 'function' ? updater(filtering ?? []) : updater\n onFilteringChange(next)\n }\n : undefined,\n getCoreRowModel: getCoreRowModel(),\n getSortedRowModel: getSortedRowModel(),\n getFilteredRowModel: getFilteredRowModel(),\n getPaginationRowModel: pagination ? getPaginationRowModel() : undefined,\n manualPagination: pagination !== undefined,\n pageCount: pagination ? Math.ceil(pagination.total / pagination.pageSize) : undefined,\n })\n\n const hasActions = !!rowActions\n\n return (\n <div className={cn('overflow-auto', className)}>\n <table className=\"w-full border-collapse\">\n <DataTableHeader\n headerGroups={table.getHeaderGroups()}\n onSortingChange={onSortingChange}\n stickyHeader={stickyHeader}\n flexRender={flexRender}\n />\n <tbody>\n {loading ? (\n <LoadingRows colSpan={columns.length + (hasActions ? 1 : 0)} compact={compact} />\n ) : table.getRowModel().rows.length === 0 ? (\n <tr>\n <td\n colSpan={columns.length + (hasActions ? 1 : 0)}\n className=\"text-center py-8 text-xs text-foreground-muted\"\n >\n {emptyState ?? 'No data'}\n </td>\n </tr>\n ) : (\n table.getRowModel().rows.map((row) => (\n <DataTableRow\n key={row.id}\n row={row}\n onRowClick={onRowClick}\n rowActions={rowActions}\n flexRender={flexRender}\n />\n ))\n )}\n </tbody>\n </table>\n {pagination && (\n <DataTablePagination\n page={pagination.page}\n pageSize={pagination.pageSize}\n total={pagination.total}\n onPaginationChange={onPaginationChange}\n />\n )}\n </div>\n )\n}\n\nfunction LoadingRows({ colSpan, compact }: { colSpan: number; compact: boolean }) {\n return (\n <>\n {Array.from({ length: 5 }).map((_, rowIdx) => (\n <tr key={rowIdx} className={compact ? 'h-7' : 'h-9'}>\n {Array.from({ length: colSpan }).map((_, colIdx) => (\n <td key={colIdx} className=\"px-2 py-1.5\">\n <Skeleton className=\"h-3 w-full\" />\n </td>\n ))}\n </tr>\n ))}\n </>\n )\n}\n","import type { HeaderGroup, Header, flexRender } from '@tanstack/react-table'\nimport { ArrowUpDown, ArrowUp, ArrowDown } from 'lucide-react'\nimport { cn } from '../../lib/cn'\nimport type { SortingState } from './types'\n\ninterface DataTableHeaderProps<T> {\n headerGroups: HeaderGroup<T>[]\n onSortingChange?: (sorting: SortingState) => void\n stickyHeader?: boolean\n flexRender: typeof flexRender\n}\n\nexport function DataTableHeader<T>({\n headerGroups,\n onSortingChange,\n stickyHeader,\n flexRender: render,\n}: DataTableHeaderProps<T>) {\n return (\n <thead\n className={cn(\n stickyHeader && 'sticky top-0 z-10 bg-background',\n )}\n >\n {headerGroups.map((headerGroup) => (\n <tr key={headerGroup.id} className=\"h-6\">\n {headerGroup.headers.map((header) => (\n <HeaderCell\n key={header.id}\n header={header}\n sortable={header.column.getCanSort() && !!onSortingChange}\n flexRender={render}\n />\n ))}\n </tr>\n ))}\n </thead>\n )\n}\n\ninterface HeaderCellProps<T> {\n header: Header<T, unknown>\n sortable: boolean\n flexRender: typeof flexRender\n}\n\nfunction HeaderCell<T>({ header, sortable, flexRender: render }: HeaderCellProps<T>) {\n const sorted = header.column.getIsSorted()\n\n const SortIcon = sorted === 'asc' ? ArrowUp : sorted === 'desc' ? ArrowDown : ArrowUpDown\n\n return (\n <th\n className={cn(\n 'px-2 py-1 text-left text-[10px] text-foreground-subtle uppercase tracking-wider font-medium',\n sortable && 'cursor-pointer select-none',\n )}\n onClick={sortable ? header.column.getToggleSortingHandler() : undefined}\n >\n <span className=\"inline-flex items-center gap-1\">\n {header.isPlaceholder\n ? null\n : render(header.column.columnDef.header, header.getContext())}\n {sortable && <SortIcon className=\"h-3 w-3\" />}\n </span>\n </th>\n )\n}\n","import type { Row, Cell, flexRender } from '@tanstack/react-table'\nimport { MoreHorizontal } from 'lucide-react'\nimport { cn } from '../../lib/cn'\nimport { Dropdown, DropdownTrigger, DropdownContent, DropdownItem as DropdownMenuItem } from '../../primitives/dropdown'\nimport type { DataTableAction } from './types'\n\ninterface DataTableRowProps<T> {\n row: Row<T>\n onRowClick?: (row: T) => void\n rowActions?: (row: T) => DataTableAction[]\n flexRender: typeof flexRender\n}\n\nexport function DataTableRow<T>({\n row,\n onRowClick,\n rowActions,\n flexRender: render,\n}: DataTableRowProps<T>) {\n const actions = rowActions ? rowActions(row.original) : []\n\n return (\n <tr\n className={cn(\n 'h-7 border-b border-border/50',\n onRowClick && 'cursor-pointer',\n 'hover:bg-surface-hover',\n )}\n onClick={onRowClick ? () => onRowClick(row.original) : undefined}\n >\n {row.getVisibleCells().map((cell) => (\n <DataTableCell key={cell.id} cell={cell} flexRender={render} />\n ))}\n {actions.length > 0 && (\n <td className=\"px-2 py-1.5 w-8\">\n <Dropdown>\n <DropdownTrigger\n className=\"p-0.5 rounded hover:bg-surface-hover\"\n onClick={(e) => e.stopPropagation()}\n >\n <MoreHorizontal className=\"h-3.5 w-3.5 text-foreground-muted\" />\n </DropdownTrigger>\n <DropdownContent className=\"right-0 left-auto\">\n {actions.map((action) => (\n <DropdownMenuItem\n key={action.label}\n icon={action.icon}\n variant={action.variant}\n onClick={(e) => {\n e.stopPropagation()\n action.onClick()\n }}\n >\n {action.label}\n </DropdownMenuItem>\n ))}\n </DropdownContent>\n </Dropdown>\n </td>\n )}\n </tr>\n )\n}\n\ninterface DataTableCellProps<T> {\n cell: Cell<T, unknown>\n flexRender: typeof flexRender\n}\n\nfunction DataTableCell<T>({ cell, flexRender: render }: DataTableCellProps<T>) {\n return (\n <td className=\"px-2 py-1.5 text-xs text-foreground\">\n {render(cell.column.columnDef.cell, cell.getContext())}\n </td>\n )\n}\n","import { ChevronLeft, ChevronRight } from 'lucide-react'\nimport { IconButton } from '../../primitives/icon-button'\nimport { Select } from '../../primitives/select'\nimport type { PaginationState } from './types'\n\ninterface DataTablePaginationProps {\n page: number\n pageSize: number\n total: number\n onPaginationChange?: (pagination: PaginationState) => void\n}\n\nconst PAGE_SIZE_OPTIONS = [\n { value: '10', label: '10' },\n { value: '25', label: '25' },\n { value: '50', label: '50' },\n { value: '100', label: '100' },\n]\n\nexport function DataTablePagination({\n page,\n pageSize,\n total,\n onPaginationChange,\n}: DataTablePaginationProps) {\n const totalPages = Math.max(1, Math.ceil(total / pageSize))\n const currentPage = page + 1\n\n return (\n <div className=\"flex items-center justify-between px-2 py-2 text-xs text-foreground-muted\">\n <div className=\"flex items-center gap-2\">\n <span>Rows per page</span>\n <div className=\"w-16\">\n <Select\n options={PAGE_SIZE_OPTIONS}\n value={String(pageSize)}\n onChange={(e) =>\n onPaginationChange?.({\n pageIndex: 0,\n pageSize: Number(e.target.value),\n })\n }\n />\n </div>\n </div>\n <div className=\"flex items-center gap-2\">\n <span>\n Page {currentPage} of {totalPages}\n </span>\n <IconButton\n icon={ChevronLeft}\n aria-label=\"Previous page\"\n variant=\"ghost\"\n size=\"sm\"\n disabled={page <= 0}\n onClick={() =>\n onPaginationChange?.({ pageIndex: page - 1, pageSize })\n }\n />\n <IconButton\n icon={ChevronRight}\n aria-label=\"Next page\"\n variant=\"ghost\"\n size=\"sm\"\n disabled={currentPage >= totalPages}\n onClick={() =>\n onPaginationChange?.({ pageIndex: page + 1, pageSize })\n }\n />\n </div>\n </div>\n )\n}\n","import { type ReactNode } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface DeviceCardBadge {\n /** Badge label text */\n label: string\n /** Optional icon rendered before the label */\n icon?: ReactNode\n /** Click handler — makes the badge interactive */\n onClick?: () => void\n}\n\nexport interface DeviceCardAction {\n /** Icon to render */\n icon: ReactNode\n /** Tooltip / aria-label */\n label: string\n /** Click handler */\n onClick: () => void\n}\n\nexport interface DeviceCardProps {\n /** Primary title (e.g., device name) */\n title: string\n /** Secondary text (e.g., model, IP) */\n subtitle?: string\n /** Status: determines the color of the status dot */\n status?: 'online' | 'offline' | 'warning' | 'unknown'\n /** Whether this card is currently selected */\n selected?: boolean\n /** Click handler for the card body */\n onClick?: () => void\n /** Clickable badges (e.g., stream profiles) */\n badges?: DeviceCardBadge[]\n /** Action icons shown at the bottom (e.g., PTZ, events) */\n actions?: DeviceCardAction[]\n /** Content rendered at the bottom when status is offline (e.g., Connect button) */\n offlineAction?: ReactNode\n /** Additional CSS classes */\n className?: string\n}\n\nconst STATUS_COLORS = {\n online: 'bg-success',\n offline: 'bg-danger',\n warning: 'bg-warning',\n unknown: 'bg-foreground-subtle',\n} as const\n\nexport function DeviceCard({\n title,\n subtitle,\n status,\n selected,\n onClick,\n badges,\n actions,\n offlineAction,\n className,\n}: DeviceCardProps) {\n const isOffline = status === 'offline'\n\n return (\n <div\n onClick={onClick}\n className={cn(\n 'w-full rounded-lg border p-3 text-left transition-colors',\n onClick && 'cursor-pointer',\n selected\n ? 'border-primary bg-primary/10'\n : 'border-border bg-surface hover:bg-surface-hover',\n isOffline && !selected && 'opacity-50',\n className,\n )}\n >\n {/* Header: title + status dot */}\n <div className=\"flex items-center justify-between mb-2\">\n <span className=\"text-sm font-medium truncate\">{title}</span>\n {status && (\n <span className={cn('h-2 w-2 rounded-full shrink-0', STATUS_COLORS[status])} />\n )}\n </div>\n\n {/* Subtitle */}\n {subtitle && (\n <div className=\"text-[11px] text-foreground-muted\">{subtitle}</div>\n )}\n\n {/* Badges */}\n {badges && badges.length > 0 && (\n <div className=\"flex flex-wrap gap-1 mt-2\">\n {badges.map((badge, i) => {\n const cls = cn(\n 'rounded px-1.5 py-0.5 text-[10px] flex items-center gap-0.5',\n selected ? 'bg-primary/20' : 'bg-surface-hover',\n badge.onClick && 'hover:opacity-80 transition-opacity cursor-pointer',\n )\n return badge.onClick ? (\n <button\n key={i}\n onClick={(e) => { e.stopPropagation(); badge.onClick!(); }}\n className={cls}\n >\n {badge.icon}{badge.label}\n </button>\n ) : (\n <span key={i} className={cls}>\n {badge.icon}{badge.label}\n </span>\n )\n })}\n </div>\n )}\n\n {/* Actions (online) or offline action */}\n {!isOffline && actions && actions.length > 0 && (\n <div className=\"flex items-center gap-0.5 mt-2 -mb-1\">\n {actions.map((action, i) => (\n <button\n key={i}\n onClick={(e) => { e.stopPropagation(); action.onClick(); }}\n className=\"p-1 rounded hover:bg-surface-hover text-foreground-subtle hover:text-foreground transition-colors\"\n title={action.label}\n aria-label={action.label}\n >\n {action.icon}\n </button>\n ))}\n </div>\n )}\n\n {isOffline && offlineAction && (\n <div className=\"mt-2\" onClick={(e) => e.stopPropagation()}>\n {offlineAction}\n </div>\n )}\n </div>\n )\n}\n","import { type ReactNode } from 'react'\nimport { cn } from '../lib/cn'\n\nexport interface DeviceGridProps {\n /** Grid items */\n children: ReactNode\n /** Minimum card width in pixels (default 220) */\n minCardWidth?: number\n /** Gap between cards in Tailwind spacing units (default 3) */\n gap?: number\n /** Additional CSS classes */\n className?: string\n}\n\nexport function DeviceGrid({\n children,\n minCardWidth = 220,\n gap = 3,\n className,\n}: DeviceGridProps) {\n return (\n <div\n className={cn(\n 'p-4 overflow-y-auto flex-1 content-start',\n className,\n )}\n style={{\n display: 'grid',\n gridTemplateColumns: `repeat(auto-fill, minmax(${minCardWidth}px, 1fr))`,\n gap: `${gap * 4}px`,\n }}\n >\n {children}\n </div>\n )\n}\n"],"mappings":"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","names":["jsx","forwardRef","cva","jsx","cva","forwardRef","forwardRef","cva","jsx","cva","forwardRef","forwardRef","cva","jsx","cva","forwardRef","forwardRef","jsx","forwardRef","forwardRef","cva","jsx","cva","forwardRef","forwardRef","jsx","forwardRef","forwardRef","cva","jsx","cva","forwardRef","forwardRef","jsx","jsxs","forwardRef","forwardRef","jsx","forwardRef","forwardRef","jsx","jsxs","forwardRef","createContext","forwardRef","useCallback","useContext","useEffect","useState","cva","jsx","createContext","useContext","useState","useCallback","cva","forwardRef","useEffect","createContext","useCallback","useContext","useEffect","useId","useRef","useState","jsx","jsxs","createContext","useContext","useState","useId","useRef","useEffect","useCallback","createContext","useContext","useId","useRef","useState","jsx","createContext","useContext","useState","useRef","useId","createContext","useCallback","useContext","useEffect","useId","useRef","useState","jsx","createContext","useContext","useState","useId","useCallback","useRef","useEffect","createContext","useCallback","useContext","useState","jsx","createContext","useContext","useState","useCallback","forwardRef","jsx","forwardRef","useRef","useState","useCallback","useEffect","jsx","jsxs","useState","useRef","useCallback","useEffect","jsx","jsxs","jsx","jsxs","jsx","jsxs","jsx","jsxs","jsx","jsxs","jsx","jsxs","jsx","jsxs","jsx","jsxs","useCallback","useState","jsx","jsxs","useState","useCallback","jsx","jsx","jsxs","jsx","jsxs","jsx","jsxs","useMemo","jsx","jsxs","jsx","jsxs","ChevronRight","jsx","jsxs","ChevronRight","jsx","jsxs","useMemo","table","_","jsx","jsxs","jsx"]}
@@ -0,0 +1,306 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/theme/index.ts
21
+ var theme_exports = {};
22
+ __export(theme_exports, {
23
+ ThemeProvider: () => ThemeProvider,
24
+ createTheme: () => createTheme,
25
+ darkColors: () => darkColors,
26
+ defaultTheme: () => defaultTheme,
27
+ lightColors: () => lightColors,
28
+ themeToCss: () => themeToCss,
29
+ useThemeMode: () => useThemeMode
30
+ });
31
+ module.exports = __toCommonJS(theme_exports);
32
+
33
+ // src/theme/defaults.ts
34
+ var providerColors = {
35
+ frigate: "#3b82f6",
36
+ scrypted: "#a855f7",
37
+ reolink: "#06b6d4",
38
+ homeAssistant: "#22d3ee",
39
+ rtsp: "#78716c"
40
+ };
41
+ var darkColors = {
42
+ primary: "#f59e42",
43
+ primaryForeground: "#0c0a09",
44
+ background: "#0c0a09",
45
+ backgroundElevated: "#1c1917",
46
+ surface: "#1c1917",
47
+ surfaceHover: "#292524",
48
+ border: "#292524",
49
+ borderSubtle: "#1c1917",
50
+ foreground: "#fafaf9",
51
+ foregroundMuted: "#a8a29e",
52
+ foregroundSubtle: "#78716c",
53
+ foregroundDisabled: "#57534e",
54
+ success: "#4ade80",
55
+ warning: "#fbbf24",
56
+ danger: "#f87171",
57
+ info: "#60a5fa",
58
+ provider: providerColors
59
+ };
60
+ var lightColors = {
61
+ primary: "#e67e22",
62
+ primaryForeground: "#ffffff",
63
+ background: "#fafaf9",
64
+ backgroundElevated: "#ffffff",
65
+ surface: "#f5f5f4",
66
+ surfaceHover: "#e7e5e4",
67
+ border: "#d6d3d1",
68
+ borderSubtle: "#e7e5e4",
69
+ foreground: "#1c1917",
70
+ foregroundMuted: "#57534e",
71
+ foregroundSubtle: "#78716c",
72
+ foregroundDisabled: "#a8a29e",
73
+ success: "#16a34a",
74
+ warning: "#d97706",
75
+ danger: "#dc2626",
76
+ info: "#2563eb",
77
+ provider: providerColors
78
+ };
79
+ var defaultTheme = {
80
+ colors: {
81
+ dark: darkColors,
82
+ light: lightColors
83
+ },
84
+ spacing: {
85
+ xs: 2,
86
+ sm: 4,
87
+ md: 8,
88
+ lg: 12,
89
+ xl: 16,
90
+ "2xl": 24,
91
+ "3xl": 32
92
+ },
93
+ radius: {
94
+ sm: 4,
95
+ md: 6,
96
+ lg: 8,
97
+ xl: 12
98
+ },
99
+ typography: {
100
+ fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif',
101
+ sizes: {
102
+ xs: { fontSize: 10, lineHeight: 14 },
103
+ sm: { fontSize: 11, lineHeight: 16 },
104
+ base: { fontSize: 12, lineHeight: 18 },
105
+ lg: { fontSize: 13, lineHeight: 18 },
106
+ xl: { fontSize: 14, lineHeight: 20 },
107
+ "2xl": { fontSize: 16, lineHeight: 22 },
108
+ "3xl": { fontSize: 20, lineHeight: 28 }
109
+ },
110
+ weights: {
111
+ regular: 400,
112
+ medium: 500,
113
+ semibold: 600,
114
+ bold: 700
115
+ }
116
+ },
117
+ table: {
118
+ rowHeight: 28,
119
+ headerHeight: 24,
120
+ cellPaddingX: 8,
121
+ cellPaddingY: 6
122
+ },
123
+ sidebar: {
124
+ width: 176,
125
+ itemHeight: 28,
126
+ iconSize: 14
127
+ }
128
+ };
129
+
130
+ // src/theme/create-theme.ts
131
+ function deepMerge(target, source) {
132
+ const result = { ...target };
133
+ for (const key in source) {
134
+ const sourceVal = source[key];
135
+ const targetVal = target[key];
136
+ if (sourceVal !== void 0 && typeof sourceVal === "object" && sourceVal !== null && !Array.isArray(sourceVal) && typeof targetVal === "object" && targetVal !== null) {
137
+ result[key] = deepMerge(
138
+ targetVal,
139
+ sourceVal
140
+ );
141
+ } else if (sourceVal !== void 0) {
142
+ result[key] = sourceVal;
143
+ }
144
+ }
145
+ return result;
146
+ }
147
+ function createTheme(overrides) {
148
+ if (!overrides) return structuredClone(defaultTheme);
149
+ return deepMerge(structuredClone(defaultTheme), overrides);
150
+ }
151
+
152
+ // src/theme/theme-to-css.ts
153
+ function camelToKebab(str) {
154
+ return str.replace(/[A-Z]/g, (m) => `-${m.toLowerCase()}`);
155
+ }
156
+ function colorTokenToCssVar(key) {
157
+ return `--color-${camelToKebab(key)}`;
158
+ }
159
+ function generateColorBlock(colors) {
160
+ const lines = [];
161
+ for (const [key, value] of Object.entries(colors)) {
162
+ if (key === "provider") continue;
163
+ lines.push(` ${colorTokenToCssVar(key)}: ${value};`);
164
+ }
165
+ return lines.join("\n");
166
+ }
167
+ function generateProviderColors(provider) {
168
+ const lines = [];
169
+ for (const [key, value] of Object.entries(provider)) {
170
+ lines.push(` --color-provider-${camelToKebab(key)}: ${value};`);
171
+ }
172
+ return lines.join("\n");
173
+ }
174
+ function generateSpacingTokens(spacing) {
175
+ const lines = [];
176
+ for (const [key, value] of Object.entries(spacing)) {
177
+ lines.push(` --spacing-${key}: ${value}px;`);
178
+ }
179
+ return lines.join("\n");
180
+ }
181
+ function generateRadiusTokens(radius) {
182
+ const lines = [];
183
+ for (const [key, value] of Object.entries(radius)) {
184
+ lines.push(` --radius-${key}: ${value}px;`);
185
+ }
186
+ return lines.join("\n");
187
+ }
188
+ function themeToCss(theme) {
189
+ const darkColorBlock = generateColorBlock(theme.colors.dark);
190
+ const lightColorBlock = generateColorBlock(theme.colors.light);
191
+ const providerBlock = generateProviderColors(theme.colors.dark.provider);
192
+ const spacingBlock = generateSpacingTokens(theme.spacing);
193
+ const radiusBlock = generateRadiusTokens(theme.radius);
194
+ return `@theme {
195
+ ${providerBlock}
196
+ ${spacingBlock}
197
+ ${radiusBlock}
198
+ }
199
+
200
+ .dark {
201
+ ${darkColorBlock}
202
+ }
203
+
204
+ .light {
205
+ ${lightColorBlock}
206
+ }
207
+
208
+ @media (prefers-color-scheme: dark) {
209
+ :root {
210
+ ${darkColorBlock.replace(/^ /gm, " ")}
211
+ }
212
+ }
213
+
214
+ @media (prefers-color-scheme: light) {
215
+ :root {
216
+ ${lightColorBlock.replace(/^ /gm, " ")}
217
+ }
218
+ }
219
+ `;
220
+ }
221
+
222
+ // src/theme/theme-provider.tsx
223
+ var import_react = require("react");
224
+ var import_jsx_runtime = require("react/jsx-runtime");
225
+ var ThemeContext = (0, import_react.createContext)(null);
226
+ var TOGGLE_ORDER = ["dark", "light", "system"];
227
+ function getSystemPreference() {
228
+ if (typeof window === "undefined") return "dark";
229
+ return window.matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light";
230
+ }
231
+ function getInitialMode(storageKey, defaultMode) {
232
+ if (typeof window === "undefined") return defaultMode;
233
+ const stored = localStorage.getItem(storageKey);
234
+ if (stored === "dark" || stored === "light" || stored === "system") {
235
+ return stored;
236
+ }
237
+ return defaultMode;
238
+ }
239
+ function resolveMode(mode) {
240
+ if (mode === "system") return getSystemPreference();
241
+ return mode;
242
+ }
243
+ function ThemeProvider({
244
+ children,
245
+ defaultMode = "system",
246
+ storageKey = "camstack-theme-mode"
247
+ }) {
248
+ const [mode, setModeState] = (0, import_react.useState)(() => getInitialMode(storageKey, defaultMode));
249
+ const [resolvedMode, setResolvedMode] = (0, import_react.useState)(() => resolveMode(mode));
250
+ const setMode = (0, import_react.useCallback)(
251
+ (newMode) => {
252
+ setModeState(newMode);
253
+ setResolvedMode(resolveMode(newMode));
254
+ if (typeof window !== "undefined") {
255
+ localStorage.setItem(storageKey, newMode);
256
+ }
257
+ },
258
+ [storageKey]
259
+ );
260
+ const toggleMode = (0, import_react.useCallback)(() => {
261
+ const currentIndex = TOGGLE_ORDER.indexOf(mode);
262
+ const nextIndex = (currentIndex + 1) % TOGGLE_ORDER.length;
263
+ setMode(TOGGLE_ORDER[nextIndex] ?? "dark");
264
+ }, [mode, setMode]);
265
+ (0, import_react.useEffect)(() => {
266
+ if (typeof document === "undefined") return;
267
+ const root = document.documentElement;
268
+ root.classList.remove("dark", "light");
269
+ root.classList.add(resolvedMode);
270
+ }, [mode, resolvedMode]);
271
+ (0, import_react.useEffect)(() => {
272
+ if (typeof window === "undefined" || mode !== "system") return;
273
+ const mediaQuery = window.matchMedia("(prefers-color-scheme: dark)");
274
+ const handleChange = () => {
275
+ setResolvedMode(getSystemPreference());
276
+ };
277
+ mediaQuery.addEventListener("change", handleChange);
278
+ return () => mediaQuery.removeEventListener("change", handleChange);
279
+ }, [mode]);
280
+ const value = (0, import_react.useMemo)(
281
+ () => ({ mode, resolvedMode, setMode, toggleMode }),
282
+ [mode, resolvedMode, setMode, toggleMode]
283
+ );
284
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(ThemeContext.Provider, { value, children });
285
+ }
286
+
287
+ // src/theme/use-theme-mode.ts
288
+ var import_react2 = require("react");
289
+ function useThemeMode() {
290
+ const context = (0, import_react2.useContext)(ThemeContext);
291
+ if (!context) {
292
+ throw new Error("useThemeMode must be used within a ThemeProvider");
293
+ }
294
+ return context;
295
+ }
296
+ // Annotate the CommonJS export names for ESM import in node:
297
+ 0 && (module.exports = {
298
+ ThemeProvider,
299
+ createTheme,
300
+ darkColors,
301
+ defaultTheme,
302
+ lightColors,
303
+ themeToCss,
304
+ useThemeMode
305
+ });
306
+ //# sourceMappingURL=index.cjs.map