UNPKG

analytica-frontend-lib

Version:

Repositório público dos componentes utilizados nas plataformas da Analytica Ensino

1 lines 44 kB
{"version":3,"sources":["../../src/utils/utils.ts","../../src/components/Text/Text.tsx","../../src/components/Button/Button.tsx","../../src/components/Select/Select.tsx","../../src/components/StatisticsCard/StatisticsCard.tsx"],"sourcesContent":["import { clsx, type ClassValue } from 'clsx';\nimport { twMerge } from 'tailwind-merge';\n\nexport function cn(...inputs: ClassValue[]) {\n return twMerge(clsx(inputs));\n}\n\nexport { syncDropdownState } from './dropdown';\nexport {\n getSelectedIdsFromCategories,\n toggleArrayItem,\n toggleSingleValue,\n areFiltersEqual,\n} from './activityFilters';\nexport {\n mapQuestionTypeToEnum,\n mapQuestionTypeToEnumRequired,\n} from './questionTypeUtils';\nexport {\n getStatusBadgeConfig,\n formatTimeSpent,\n formatQuestionNumbers,\n formatDateToBrazilian,\n} from './activityDetailsUtils';\n\n/**\n * Retorna a cor hexadecimal com opacidade 0.3 (4d) se não estiver em dark mode.\n * Se estiver em dark mode, retorna a cor original.\n *\n * @param hexColor - Cor hexadecimal (ex: \"#0066b8\" ou \"0066b8\")\n * @param isDark - booleano indicando se está em dark mode\n * @returns string - cor hexadecimal com opacidade se necessário\n */\nexport function getSubjectColorWithOpacity(\n hexColor: string | undefined,\n isDark: boolean\n): string | undefined {\n if (!hexColor) return undefined;\n // Remove o '#' se existir\n let color = hexColor.replace(/^#/, '').toLowerCase();\n\n if (isDark) {\n // Se está em dark mode, sempre remove opacidade se existir\n if (color.length === 8) {\n color = color.slice(0, 6);\n }\n return `#${color}`;\n } else {\n // Se não está em dark mode (light mode)\n let resultColor: string;\n if (color.length === 6) {\n // Adiciona opacidade 0.3 (4D) para cores de 6 dígitos\n resultColor = `#${color}4d`;\n } else if (color.length === 8) {\n // Já tem opacidade, retorna como está\n resultColor = `#${color}`;\n } else {\n // Para outros tamanhos (3, 4, 5 dígitos), retorna como está\n resultColor = `#${color}`;\n }\n return resultColor;\n }\n}\n","import { ComponentPropsWithoutRef, ElementType, ReactNode } from 'react';\nimport { cn } from '../../utils/utils';\n\n/**\n * Base text component props\n */\ntype BaseTextProps = {\n /** Content to be displayed */\n children?: ReactNode;\n /** Text size variant */\n size?:\n | '2xs'\n | 'xs'\n | 'sm'\n | 'md'\n | 'lg'\n | 'xl'\n | '2xl'\n | '3xl'\n | '4xl'\n | '5xl'\n | '6xl';\n /** Font weight variant */\n weight?:\n | 'hairline'\n | 'light'\n | 'normal'\n | 'medium'\n | 'semibold'\n | 'bold'\n | 'extrabold'\n | 'black';\n /** Color variant - white for light backgrounds, black for dark backgrounds */\n color?: string;\n /** Additional CSS classes to apply */\n className?: string;\n};\n\n/**\n * Polymorphic text component props that ensures type safety based on the 'as' prop\n */\ntype TextProps<T extends ElementType = 'p'> = BaseTextProps & {\n /** HTML tag to render */\n as?: T;\n} & Omit<ComponentPropsWithoutRef<T>, keyof BaseTextProps>;\n\n/**\n * Text component for Analytica Ensino platforms\n *\n * A flexible polymorphic text component with multiple sizes, weights, and colors.\n * Automatically adapts to dark and light themes with full type safety.\n *\n * @param children - The content to display\n * @param size - The text size variant (2xs, xs, sm, md, lg, xl, 2xl, 3xl, 4xl, 5xl, 6xl)\n * @param weight - The font weight variant (hairline, light, normal, medium, semibold, bold, extrabold, black)\n * @param color - The color variant - adapts to theme\n * @param as - The HTML tag to render - determines allowed attributes via TypeScript\n * @param className - Additional CSS classes\n * @param props - HTML attributes valid for the chosen tag only\n * @returns A styled text element with type-safe attributes\n *\n * @example\n * ```tsx\n * <Text size=\"lg\" weight=\"bold\" color=\"text-info-800\">\n * This is a large, bold text\n * </Text>\n *\n * <Text as=\"a\" href=\"/link\" target=\"_blank\">\n * Link with type-safe anchor attributes\n * </Text>\n *\n * <Text as=\"button\" onClick={handleClick} disabled>\n * Button with type-safe button attributes\n * </Text>\n * ```\n */\nconst Text = <T extends ElementType = 'p'>({\n children,\n size = 'md',\n weight = 'normal',\n color = 'text-text-950',\n as,\n className = '',\n ...props\n}: TextProps<T>) => {\n let sizeClasses = '';\n let weightClasses = '';\n\n // Text size classes mapping\n const sizeClassMap = {\n '2xs': 'text-2xs',\n xs: 'text-xs',\n sm: 'text-sm',\n md: 'text-md',\n lg: 'text-lg',\n xl: 'text-xl',\n '2xl': 'text-2xl',\n '3xl': 'text-3xl',\n '4xl': 'text-4xl',\n '5xl': 'text-5xl',\n '6xl': 'text-6xl',\n } as const;\n\n sizeClasses = sizeClassMap[size] ?? sizeClassMap.md;\n\n // Font weight classes mapping\n const weightClassMap = {\n hairline: 'font-hairline',\n light: 'font-light',\n normal: 'font-normal',\n medium: 'font-medium',\n semibold: 'font-semibold',\n bold: 'font-bold',\n extrabold: 'font-extrabold',\n black: 'font-black',\n } as const;\n\n weightClasses = weightClassMap[weight] ?? weightClassMap.normal;\n\n const baseClasses = 'font-primary';\n const Component = as ?? ('p' as ElementType);\n\n return (\n <Component\n className={cn(baseClasses, sizeClasses, weightClasses, color, className)}\n {...props}\n >\n {children}\n </Component>\n );\n};\n\nexport default Text;\n","import { ButtonHTMLAttributes, ReactNode } from 'react';\nimport { cn } from '../../utils/utils';\n\n/**\n * Lookup table for variant and action class combinations\n */\nconst VARIANT_ACTION_CLASSES = {\n solid: {\n primary:\n 'bg-primary-950 text-text border border-primary-950 hover:bg-primary-800 hover:border-primary-800 focus-visible:outline-none focus-visible:bg-primary-950 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:bg-primary-700 active:border-primary-700 disabled:bg-primary-500 disabled:border-primary-500 disabled:opacity-40 disabled:cursor-not-allowed',\n positive:\n 'bg-success-500 text-text border border-success-500 hover:bg-success-600 hover:border-success-600 focus-visible:outline-none focus-visible:bg-success-500 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:bg-success-700 active:border-success-700 disabled:bg-success-500 disabled:border-success-500 disabled:opacity-40 disabled:cursor-not-allowed',\n negative:\n 'bg-error-500 text-text border border-error-500 hover:bg-error-600 hover:border-error-600 focus-visible:outline-none focus-visible:bg-error-500 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:bg-error-700 active:border-error-700 disabled:bg-error-500 disabled:border-error-500 disabled:opacity-40 disabled:cursor-not-allowed',\n },\n outline: {\n primary:\n 'bg-transparent text-primary-950 border border-primary-950 hover:bg-background-50 hover:text-primary-400 hover:border-primary-400 focus-visible:border-0 focus-visible:outline-none focus-visible:text-primary-600 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:text-primary-700 active:border-primary-700 disabled:opacity-40 disabled:cursor-not-allowed',\n positive:\n 'bg-transparent text-success-500 border border-success-300 hover:bg-background-50 hover:text-success-400 hover:border-success-400 focus-visible:border-0 focus-visible:outline-none focus-visible:text-success-600 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:text-success-700 active:border-success-700 disabled:opacity-40 disabled:cursor-not-allowed',\n negative:\n 'bg-transparent text-error-500 border border-error-300 hover:bg-background-50 hover:text-error-400 hover:border-error-400 focus-visible:border-0 focus-visible:outline-none focus-visible:text-error-600 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:text-error-700 active:border-error-700 disabled:opacity-40 disabled:cursor-not-allowed',\n },\n link: {\n primary:\n 'bg-transparent text-primary-950 hover:text-primary-400 focus-visible:outline-none focus-visible:text-primary-600 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:text-primary-700 disabled:opacity-40 disabled:cursor-not-allowed',\n positive:\n 'bg-transparent text-success-500 hover:text-success-400 focus-visible:outline-none focus-visible:text-success-600 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:text-success-700 disabled:opacity-40 disabled:cursor-not-allowed',\n negative:\n 'bg-transparent text-error-500 hover:text-error-400 focus-visible:outline-none focus-visible:text-error-600 focus-visible:ring-2 focus-visible:ring-offset-0 focus-visible:ring-indicator-info active:text-error-700 disabled:opacity-40 disabled:cursor-not-allowed',\n },\n} as const;\n\n/**\n * Lookup table for size classes\n */\nconst SIZE_CLASSES = {\n 'extra-small': 'text-xs px-3.5 py-2',\n small: 'text-sm px-4 py-2.5',\n medium: 'text-md px-5 py-2.5',\n large: 'text-lg px-6 py-3',\n 'extra-large': 'text-lg px-7 py-3.5',\n} as const;\n\n/**\n * Button component props interface\n */\ntype ButtonProps = {\n /** Content to be displayed inside the button */\n children: ReactNode;\n /** Ícone à esquerda do texto */\n iconLeft?: ReactNode;\n /** Ícone à direita do texto */\n iconRight?: ReactNode;\n /** Size of the button */\n size?: 'extra-small' | 'small' | 'medium' | 'large' | 'extra-large';\n /** Visual variant of the button */\n variant?: 'solid' | 'outline' | 'link';\n /** Action type of the button */\n action?: 'primary' | 'positive' | 'negative';\n /** Additional CSS classes to apply */\n className?: string;\n} & ButtonHTMLAttributes<HTMLButtonElement>;\n\n/**\n * Button component for Analytica Ensino platforms\n *\n * A flexible button component with multiple variants, sizes and actions.\n *\n * @param children - The content to display inside the button\n * @param size - The size variant (extra-small, small, medium, large, extra-large)\n * @param variant - The visual style variant (solid, outline, link)\n * @param action - The action type (primary, positive, negative)\n * @param className - Additional CSS classes\n * @param props - All other standard button HTML attributes\n * @returns A styled button element\n *\n * @example\n * ```tsx\n * <Button variant=\"solid\" action=\"primary\" size=\"medium\" onClick={() => console.log('clicked')}>\n * Click me\n * </Button>\n * ```\n */\nconst Button = ({\n children,\n iconLeft,\n iconRight,\n size = 'medium',\n variant = 'solid',\n action = 'primary',\n className = '',\n disabled,\n type = 'button',\n ...props\n}: ButtonProps) => {\n // Get classes from lookup tables\n const sizeClasses = SIZE_CLASSES[size];\n const variantClasses = VARIANT_ACTION_CLASSES[variant][action];\n\n const baseClasses =\n 'inline-flex items-center justify-center rounded-full cursor-pointer font-medium';\n\n return (\n <button\n className={cn(baseClasses, variantClasses, sizeClasses, className)}\n disabled={disabled}\n type={type}\n {...props}\n >\n {iconLeft && <span className=\"mr-2 flex items-center\">{iconLeft}</span>}\n {children}\n {iconRight && <span className=\"ml-2 flex items-center\">{iconRight}</span>}\n </button>\n );\n};\n\nexport default Button;\n","import { create, StoreApi, useStore } from 'zustand';\nimport {\n ReactNode,\n useEffect,\n useRef,\n ButtonHTMLAttributes,\n forwardRef,\n HTMLAttributes,\n KeyboardEvent,\n MouseEvent,\n ReactElement,\n isValidElement,\n Children,\n cloneElement,\n useId,\n} from 'react';\nimport { CaretDown, Check, WarningCircle } from 'phosphor-react';\nimport { cn } from '../../utils/utils';\n\nconst VARIANT_CLASSES = {\n outlined: 'border-2 rounded-lg focus:border-primary-950',\n underlined: 'border-b-2 focus:border-primary-950',\n rounded: 'border-2 rounded-full focus:border-primary-950',\n} as const;\n\nconst SIZE_CLASSES = {\n small: 'text-sm',\n medium: 'text-md',\n large: 'text-lg',\n 'extra-large': 'text-lg',\n} as const;\n\nconst HEIGHT_CLASSES = {\n small: 'h-8',\n medium: 'h-9',\n large: 'h-10',\n 'extra-large': 'h-12',\n} as const;\n\nconst PADDING_CLASSES = {\n small: 'px-2 py-1',\n medium: 'px-3 py-2',\n large: 'px-4 py-3',\n 'extra-large': 'px-5 py-4',\n} as const;\n\nconst SIDE_CLASSES = {\n top: 'bottom-full -translate-y-1',\n right: 'top-full translate-y-1',\n bottom: 'top-full translate-y-1',\n left: 'top-full translate-y-1',\n};\nconst ALIGN_CLASSES = {\n start: 'left-0',\n center: 'left-1/2 -translate-x-1/2',\n end: 'right-0',\n};\n\ninterface SelectStore {\n open: boolean;\n setOpen: (open: boolean) => void;\n value: string;\n setValue: (value: string) => void;\n selectedLabel: ReactNode;\n setSelectedLabel: (label: ReactNode) => void;\n onValueChange?: (value: string) => void;\n}\n\ntype SelectStoreApi = StoreApi<SelectStore>;\n\nexport function createSelectStore(\n onValueChange?: (value: string) => void\n): SelectStoreApi {\n return create<SelectStore>((set) => ({\n open: false,\n setOpen: (open) => set({ open }),\n value: '',\n setValue: (value) => set({ value }),\n selectedLabel: '',\n setSelectedLabel: (label) => set({ selectedLabel: label }),\n onValueChange,\n }));\n}\n\nexport const useSelectStore = (externalStore?: SelectStoreApi) => {\n if (!externalStore) {\n throw new Error(\n 'Component must be used within a Select (store is missing)'\n );\n }\n\n return externalStore;\n};\n\nexport function getLabelAsNode(children: ReactNode): ReactNode {\n if (typeof children === 'string' || typeof children === 'number') {\n return children;\n }\n const flattened = Children.toArray(children);\n\n if (flattened.length === 1) return flattened[0];\n\n return <>{flattened}</>;\n}\n\ninterface SelectProps {\n className?: string;\n children: ReactNode;\n defaultValue?: string;\n value?: string;\n onValueChange?: (value: string) => void;\n size?: 'small' | 'medium' | 'large' | 'extra-large';\n label?: string;\n helperText?: string;\n errorMessage?: string;\n id?: string;\n}\n\nconst injectStore = (\n children: ReactNode,\n store: SelectStoreApi,\n size: string,\n selectId: string\n): ReactNode => {\n return Children.map(children, (child) => {\n if (isValidElement(child)) {\n const typedChild = child as ReactElement<{\n store?: SelectStoreApi;\n children?: ReactNode;\n size?: string;\n selectId?: string;\n }>;\n\n const newProps: Partial<{\n store: SelectStoreApi;\n children: ReactNode;\n size: string;\n selectId: string;\n }> = {\n store,\n };\n\n // Only pass size and selectId to SelectTrigger\n if (typedChild.type === SelectTrigger) {\n newProps.size = size;\n newProps.selectId = selectId;\n }\n\n if (typedChild.props.children) {\n newProps.children = injectStore(\n typedChild.props.children,\n store,\n size,\n selectId\n );\n }\n\n return cloneElement(typedChild, newProps);\n }\n return child;\n });\n};\n\nconst Select = ({\n children,\n defaultValue = '',\n className,\n value: propValue,\n onValueChange,\n size = 'small',\n label,\n helperText,\n errorMessage,\n id,\n}: SelectProps) => {\n const storeRef = useRef<SelectStoreApi | null>(null);\n storeRef.current ??= createSelectStore(onValueChange);\n const store = storeRef.current;\n\n const selectRef = useRef<HTMLDivElement>(null);\n const { open, setOpen, setValue, selectedLabel } = useStore(store, (s) => s);\n\n // Generate unique ID if not provided\n const generatedId = useId();\n const selectId = id ?? `select-${generatedId}`;\n\n const findLabelForValue = (\n children: ReactNode,\n targetValue: string\n ): string | null => {\n let found: string | null = null;\n const search = (nodes: ReactNode) => {\n Children.forEach(nodes, (child) => {\n if (!isValidElement(child)) return;\n const typedChild = child as ReactElement<{\n value?: string;\n children?: ReactNode;\n }>;\n if (\n typedChild.type === SelectItem &&\n typedChild.props.value === targetValue\n ) {\n if (typeof typedChild.props.children === 'string')\n found = typedChild.props.children;\n }\n if (typedChild.props.children && !found)\n search(typedChild.props.children);\n });\n };\n search(children);\n return found;\n };\n\n useEffect(() => {\n if (!selectedLabel && defaultValue) {\n const label = findLabelForValue(children, defaultValue);\n if (label) store.setState({ selectedLabel: label });\n }\n }, [children, defaultValue, selectedLabel]);\n\n useEffect(() => {\n const handleClickOutside = (event: globalThis.MouseEvent) => {\n if (\n selectRef.current &&\n !selectRef.current.contains(event.target as Node)\n ) {\n setOpen(false);\n }\n };\n\n const handleArrowKeys = (event: globalThis.KeyboardEvent) => {\n const selectContent = selectRef.current?.querySelector('[role=\"menu\"]');\n if (selectContent) {\n event.preventDefault();\n const items = Array.from(\n selectContent.querySelectorAll(\n '[role=\"menuitem\"]:not([aria-disabled=\"true\"])'\n )\n ).filter((el): el is HTMLElement => el instanceof HTMLElement);\n\n const focused = document.activeElement as HTMLElement;\n const currentIndex = items.findIndex((item) => item === focused);\n\n let nextIndex = 0;\n if (event.key === 'ArrowDown') {\n nextIndex =\n currentIndex === -1 ? 0 : (currentIndex + 1) % items.length;\n } else {\n nextIndex =\n currentIndex === -1\n ? items.length - 1\n : (currentIndex - 1 + items.length) % items.length;\n }\n items[nextIndex]?.focus();\n }\n };\n\n if (open) {\n document.addEventListener('mousedown', handleClickOutside);\n document.addEventListener('keydown', handleArrowKeys);\n }\n return () => {\n document.removeEventListener('mousedown', handleClickOutside);\n document.removeEventListener('keydown', handleArrowKeys);\n };\n }, [open]);\n\n useEffect(() => {\n if (propValue) {\n setValue(propValue);\n const label = findLabelForValue(children, propValue);\n if (label) store.setState({ selectedLabel: label });\n }\n }, [propValue]);\n\n const sizeClasses = SIZE_CLASSES[size];\n\n return (\n <div className={cn('w-full', className)}>\n {/* Label */}\n {label && (\n <label\n htmlFor={selectId}\n className={cn('block font-bold text-text-900 mb-1.5', sizeClasses)}\n >\n {label}\n </label>\n )}\n\n {/* Select Container */}\n <div className={cn('relative w-full')} ref={selectRef}>\n {injectStore(children, store, size, selectId)}\n </div>\n\n {/* Helper Text or Error Message */}\n {(helperText || errorMessage) && (\n <div className=\"mt-1.5 gap-1.5\">\n {helperText && <p className=\"text-sm text-text-500\">{helperText}</p>}\n {errorMessage && (\n <p className=\"flex gap-1 items-center text-sm text-indicator-error\">\n <WarningCircle size={16} /> {errorMessage}\n </p>\n )}\n </div>\n )}\n </div>\n );\n};\n\nconst SelectValue = ({\n placeholder,\n store: externalStore,\n}: {\n placeholder?: string;\n store?: SelectStoreApi;\n}) => {\n const store = useSelectStore(externalStore);\n\n const selectedLabel = useStore(store, (s) => s.selectedLabel);\n const value = useStore(store, (s) => s.value);\n return (\n <span className=\"text-inherit flex gap-2 items-center\">\n {selectedLabel || placeholder || value}\n </span>\n );\n};\n\ninterface SelectTriggerProps extends ButtonHTMLAttributes<HTMLButtonElement> {\n className?: string;\n invalid?: boolean;\n variant?: 'outlined' | 'underlined' | 'rounded';\n store?: SelectStoreApi;\n size?: 'small' | 'medium' | 'large' | 'extra-large';\n selectId?: string;\n}\n\nconst SelectTrigger = forwardRef<HTMLButtonElement, SelectTriggerProps>(\n (\n {\n className,\n invalid = false,\n variant = 'outlined',\n store: externalStore,\n disabled,\n size = 'medium',\n selectId,\n ...props\n },\n ref\n ) => {\n const store = useSelectStore(externalStore);\n const open = useStore(store, (s) => s.open);\n const toggleOpen = () => store.setState({ open: !open });\n\n const variantClasses = VARIANT_CLASSES[variant];\n const heightClasses = HEIGHT_CLASSES[size];\n const paddingClasses = PADDING_CLASSES[size];\n\n return (\n <button\n ref={ref}\n id={selectId}\n className={cn(\n 'flex w-full items-center justify-between border-border-300',\n heightClasses,\n paddingClasses,\n invalid &&\n `${variant == 'underlined' ? 'border-b-2' : 'border-2'} border-indicator-error text-text-600`,\n disabled\n ? 'cursor-not-allowed text-text-400 pointer-events-none opacity-50'\n : 'cursor-pointer hover:bg-background-50 focus:bg-accent focus:text-accent-foreground hover:bg-accent hover:text-accent-foreground',\n !invalid && !disabled ? 'text-text-700' : '',\n variantClasses,\n className\n )}\n onClick={toggleOpen}\n aria-expanded={open}\n aria-haspopup=\"listbox\"\n aria-controls={open ? 'select-content' : undefined}\n {...props}\n >\n {props.children}\n <CaretDown\n className={cn(\n 'h-[1em] w-[1em] opacity-50 transition-transform',\n open ? 'rotate-180' : ''\n )}\n />\n </button>\n );\n }\n);\nSelectTrigger.displayName = 'SelectTrigger';\n\ninterface SelectContentProps extends HTMLAttributes<HTMLDivElement> {\n className?: string;\n align?: 'start' | 'center' | 'end';\n side?: 'top' | 'right' | 'bottom' | 'left';\n store?: SelectStoreApi;\n}\n\nconst SelectContent = forwardRef<HTMLDivElement, SelectContentProps>(\n (\n {\n children,\n className,\n align = 'start',\n side = 'bottom',\n store: externalStore,\n ...props\n },\n ref\n ) => {\n const store = useSelectStore(externalStore);\n\n const open = useStore(store, (s) => s.open);\n if (!open) return null;\n\n const getPositionClasses = () =>\n `w-full min-w-full absolute ${SIDE_CLASSES[side]} ${ALIGN_CLASSES[align]}`;\n\n return (\n <div\n role=\"menu\"\n ref={ref}\n className={cn(\n 'bg-secondary z-50 min-w-[210px] max-h-[300px] overflow-y-auto overflow-x-hidden rounded-md border p-1 shadow-md border-border-100',\n getPositionClasses(),\n className\n )}\n {...props}\n >\n {children}\n </div>\n );\n }\n);\nSelectContent.displayName = 'SelectContent';\n\ninterface SelectItemProps extends HTMLAttributes<HTMLDivElement> {\n value: string;\n disabled?: boolean;\n store?: SelectStoreApi;\n}\n\nconst SelectItem = forwardRef<HTMLDivElement, SelectItemProps>(\n (\n {\n className,\n children,\n value,\n disabled = false,\n store: externalStore,\n ...props\n },\n ref\n ) => {\n const store = useSelectStore(externalStore);\n const {\n value: selectedValue,\n setValue,\n setOpen,\n setSelectedLabel,\n onValueChange,\n } = useStore(store, (s) => s);\n\n const handleClick = (\n e: MouseEvent<HTMLDivElement> | KeyboardEvent<HTMLDivElement>\n ) => {\n const labelNode = getLabelAsNode(children);\n if (!disabled) {\n // Always set the clicked value, even if it's already selected\n setValue(value);\n setSelectedLabel(labelNode);\n setOpen(false);\n onValueChange?.(value);\n }\n props.onClick?.(e as MouseEvent<HTMLDivElement>);\n };\n\n return (\n <div\n role=\"menuitem\"\n aria-disabled={disabled}\n ref={ref}\n className={`\n bg-secondary focus-visible:bg-background-50\n relative flex select-none items-center gap-2 rounded-sm p-3 outline-none transition-colors [&>svg]:size-4 [&>svg]:shrink-0\n ${className}\n ${\n disabled\n ? 'cursor-not-allowed text-text-400 pointer-events-none opacity-50'\n : 'cursor-pointer hover:bg-background-50 text-text-700 focus:bg-accent focus:text-accent-foreground hover:bg-accent hover:text-accent-foreground'\n }\n ${selectedValue === value && 'bg-background-50'}\n `}\n onClick={handleClick}\n onKeyDown={(e) => {\n if (e.key === 'Enter' || e.key === ' ') handleClick(e);\n }}\n tabIndex={disabled ? -1 : 0}\n {...props}\n >\n <span className=\"absolute right-2 flex h-3.5 w-3.5 items-center justify-center\">\n {selectedValue === value && <Check className=\"\" />}\n </span>\n {children}\n </div>\n );\n }\n);\n\nSelectItem.displayName = 'SelectItem';\n\nexport default Select;\nexport { SelectTrigger, SelectContent, SelectItem, SelectValue };\n","import Text from '../Text/Text';\nimport Button from '../Button/Button';\nimport Select, {\n SelectTrigger,\n SelectValue,\n SelectContent,\n SelectItem,\n} from '../Select/Select';\nimport { Plus } from 'phosphor-react';\n\n/**\n * Statistics data item\n */\ninterface StatItem {\n /** Statistic label */\n label: string;\n /** Statistic value */\n value: string | number;\n /** Color variant */\n variant: 'high' | 'medium' | 'low' | 'total';\n}\n\n/**\n * Props for StatisticsCard component\n */\ninterface StatisticsCardProps {\n /** Title displayed at the top of the card */\n title: string;\n /** Statistics data to display */\n data?: StatItem[];\n /** Show placeholder \"-\" in values when true (for created items without data yet) */\n showPlaceholder?: boolean;\n /** Message shown in empty state */\n emptyStateMessage?: string;\n /** Text for the empty state button */\n emptyStateButtonText?: string;\n /** Callback when empty state button is clicked */\n onEmptyStateButtonClick?: () => void;\n /** Optional dropdown options for filtering */\n dropdownOptions?: Array<{\n label: string;\n value: string;\n }>;\n /** Currently selected dropdown value */\n selectedDropdownValue?: string;\n /** Callback when dropdown value changes */\n onDropdownChange?: (value: string) => void;\n /** Placeholder text for the dropdown select */\n selectPlaceholder?: string;\n /** Accessible label for the dropdown select */\n dropdownAriaLabel?: string;\n /** Additional CSS classes */\n className?: string;\n}\n\n/**\n * Variant styles mapping\n */\nconst VARIANT_STYLES = {\n high: 'bg-success-background',\n medium: 'bg-warning-background',\n low: 'bg-error-background',\n total: 'bg-info-background',\n} as const;\n\n/**\n * Value text colors mapping\n */\nconst VALUE_TEXT_COLORS = {\n high: 'text-success-700',\n medium: 'text-warning-600',\n low: 'text-error-700',\n total: 'text-info-700',\n} as const;\n\n/**\n * Internal StatCard component\n */\ninterface StatCardProps {\n item: StatItem;\n showPlaceholder?: boolean;\n}\n\nconst StatCard = ({ item, showPlaceholder = false }: StatCardProps) => {\n return (\n <div\n className={`rounded-xl py-[17px] px-6 min-h-[105px] flex flex-col justify-center items-start gap-1 ${VARIANT_STYLES[item.variant]}`}\n >\n <Text\n size=\"4xl\"\n weight=\"bold\"\n className={`${VALUE_TEXT_COLORS[item.variant]} leading-[42px] tracking-[0.2px] self-stretch`}\n >\n {showPlaceholder ? '-' : item.value}\n </Text>\n <Text\n size=\"xs\"\n weight=\"bold\"\n className=\"uppercase text-[8px] leading-[9px] text-text-800 whitespace-nowrap\"\n >\n {item.label}\n </Text>\n </div>\n );\n};\n\n/**\n * Get grid column class based on number of items\n */\nconst getGridColumnsClass = (itemCount: number): string => {\n if (itemCount === 4) return 'lg:grid-cols-4';\n if (itemCount === 3) return 'lg:grid-cols-3';\n if (itemCount === 2) return 'lg:grid-cols-2';\n return 'lg:grid-cols-1';\n};\n\n/**\n * StatisticsCard component - displays statistics with empty state support\n *\n * @example\n * ```tsx\n * // With data\n * <StatisticsCard\n * title=\"Estatística das atividades\"\n * data={[\n * { label: 'Acertos', value: '85%', variant: 'high' },\n * { label: 'Em andamento', value: 12, variant: 'medium' },\n * { label: 'Erros', value: '15%', variant: 'low' },\n * { label: 'Concluídas', value: 24, variant: 'total' }\n * ]}\n * dropdownOptions={[\n * { label: '1 ano', value: '1year' },\n * { label: '6 meses', value: '6months' }\n * ]}\n * selectedDropdownValue=\"1year\"\n * onDropdownChange={(value) => console.log(value)}\n * />\n *\n * // Empty state\n * <StatisticsCard\n * title=\"Estatística das atividades\"\n * emptyStateMessage=\"Sem dados por enquanto. Crie uma atividade para que os resultados apareçam aqui.\"\n * emptyStateButtonText=\"Criar atividade\"\n * onEmptyStateButtonClick={() => console.log('Create activity')}\n * />\n * ```\n */\nexport const StatisticsCard = ({\n title,\n data,\n showPlaceholder = false,\n emptyStateMessage,\n emptyStateButtonText,\n onEmptyStateButtonClick,\n dropdownOptions,\n selectedDropdownValue,\n onDropdownChange,\n selectPlaceholder = 'Selecione um período',\n dropdownAriaLabel = 'Filtro de período',\n className = '',\n}: StatisticsCardProps) => {\n const hasData = data && data.length > 0;\n const gridColumnsClass = hasData ? getGridColumnsClass(data.length) : '';\n\n return (\n <div\n className={`bg-background rounded-xl p-4 h-auto lg:h-[185px] flex flex-col gap-2 ${className}`}\n >\n {/* Header with title and optional dropdown */}\n <div className=\"flex flex-row justify-between items-center gap-4\">\n <Text\n as=\"h3\"\n size=\"sm\"\n weight=\"medium\"\n color=\"text-text-600\"\n className=\"flex-1 min-w-0\"\n >\n {title}\n </Text>\n\n {dropdownOptions && dropdownOptions.length > 0 && (\n <div className=\"w-[120px] min-w-[90px] sm:shrink-0\">\n <Select\n value={selectedDropdownValue}\n onValueChange={onDropdownChange}\n size=\"medium\"\n >\n <SelectTrigger\n className=\"border border-border-300 rounded [&>span]:whitespace-nowrap [&>span]:overflow-hidden [&>span]:text-ellipsis\"\n aria-label={dropdownAriaLabel}\n >\n <SelectValue placeholder={selectPlaceholder} />\n </SelectTrigger>\n <SelectContent className=\"min-w-[120px]\">\n {dropdownOptions.map((option) => (\n <SelectItem\n key={option.value}\n value={option.value}\n className=\"whitespace-nowrap\"\n >\n {option.label}\n </SelectItem>\n ))}\n </SelectContent>\n </Select>\n </div>\n )}\n </div>\n\n {/* Content: Data Grid or Empty State */}\n {hasData ? (\n <div\n className={`grid grid-cols-1 sm:grid-cols-2 gap-[13px] ${gridColumnsClass}`}\n >\n {data.map((item, index) => (\n <StatCard\n key={`${item.variant}-${item.label}-${index}`}\n item={item}\n showPlaceholder={showPlaceholder}\n />\n ))}\n </div>\n ) : (\n <div className=\"border border-dashed border-border-300 rounded-lg p-6 min-h-[105px] flex flex-col items-center justify-center gap-2\">\n <Text\n size=\"sm\"\n color=\"text-text-600\"\n className=\"text-center max-w-md\"\n >\n {emptyStateMessage}\n </Text>\n\n {onEmptyStateButtonClick && (\n <Button\n variant=\"outline\"\n action=\"primary\"\n size=\"small\"\n onClick={onEmptyStateButtonClick}\n iconLeft={<Plus size={16} weight=\"bold\" />}\n >\n {emptyStateButtonText}\n </Button>\n )}\n </div>\n )}\n </div>\n );\n};\n"],"mappings":"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","names":["jsx","jsx","jsxs","SIZE_CLASSES","children","label","jsx","jsxs"]}