@humain/ui 2.1.62 → 2.1.65
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/organisms/ai/AIToolCall/AIToolCall.d.ts +9 -3
- package/dist/components/organisms/ai/AIToolRun/index.d.ts +1 -1
- package/dist/components/organisms/ai/AIToolRun/validation.d.ts +24 -3
- package/dist/components/organisms/ai/_shared/format-ai-duration.d.ts +1 -0
- package/dist/components/organisms/ai/_shared/workflow-step-renderer.d.ts +1 -0
- package/dist/index.js +52 -52
- package/dist/index151.js +1 -1
- package/dist/index174.js +10 -333
- package/dist/index174.js.map +1 -1
- package/dist/index175.js +310 -137
- package/dist/index175.js.map +1 -1
- package/dist/index176.js +148 -174
- package/dist/index176.js.map +1 -1
- package/dist/index177.js +186 -78
- package/dist/index177.js.map +1 -1
- package/dist/index178.js +74 -124
- package/dist/index178.js.map +1 -1
- package/dist/index179.js +133 -1
- package/dist/index179.js.map +1 -0
- package/dist/index180.js +2 -201
- package/dist/index181.js +201 -0
- package/dist/{index180.js.map → index181.js.map} +1 -1
- package/dist/index183.js +130 -166
- package/dist/index183.js.map +1 -1
- package/dist/index184.js +195 -983
- package/dist/index184.js.map +1 -1
- package/dist/index185.js +1069 -369
- package/dist/index185.js.map +1 -1
- package/dist/index186.js +395 -197
- package/dist/index186.js.map +1 -1
- package/dist/index187.js +198 -243
- package/dist/index187.js.map +1 -1
- package/dist/index188.js +263 -3
- package/dist/index188.js.map +1 -1
- package/dist/index189.js +3 -209
- package/dist/index189.js.map +1 -1
- package/dist/index190.js +190 -777
- package/dist/index190.js.map +1 -1
- package/dist/index191.js +771 -252
- package/dist/index191.js.map +1 -1
- package/dist/index192.js +250 -65
- package/dist/index192.js.map +1 -1
- package/dist/index193.js +72 -523
- package/dist/index193.js.map +1 -1
- package/dist/index194.js +537 -144
- package/dist/index194.js.map +1 -1
- package/dist/index195.js +139 -720
- package/dist/index195.js.map +1 -1
- package/dist/index196.js +707 -167
- package/dist/index196.js.map +1 -1
- package/dist/index197.js +175 -151
- package/dist/index197.js.map +1 -1
- package/dist/index198.js +152 -487
- package/dist/index198.js.map +1 -1
- package/dist/index199.js +472 -225
- package/dist/index199.js.map +1 -1
- package/dist/index200.js +236 -260
- package/dist/index200.js.map +1 -1
- package/dist/index201.js +265 -215
- package/dist/index201.js.map +1 -1
- package/dist/index202.js +207 -307
- package/dist/index202.js.map +1 -1
- package/dist/index203.js +302 -135
- package/dist/index203.js.map +1 -1
- package/dist/index204.js +140 -271
- package/dist/index204.js.map +1 -1
- package/dist/index205.js +263 -253
- package/dist/index205.js.map +1 -1
- package/dist/index206.js +244 -137
- package/dist/index206.js.map +1 -1
- package/dist/index207.js +100 -238
- package/dist/index207.js.map +1 -1
- package/dist/index208.js +278 -74
- package/dist/index208.js.map +1 -1
- package/dist/index209.js +56 -97
- package/dist/index209.js.map +1 -1
- package/dist/index210.js +142 -47
- package/dist/index210.js.map +1 -1
- package/dist/index211.js +38 -84
- package/dist/index211.js.map +1 -1
- package/dist/index212.js +72 -252
- package/dist/index212.js.map +1 -1
- package/dist/index213.js +274 -26
- package/dist/index213.js.map +1 -1
- package/dist/index214.js +29 -94
- package/dist/index214.js.map +1 -1
- package/dist/index215.js +98 -25
- package/dist/index215.js.map +1 -1
- package/dist/index216.js +20 -565
- package/dist/index216.js.map +1 -1
- package/dist/index217.js +564 -17
- package/dist/index217.js.map +1 -1
- package/dist/index218.js +20 -23
- package/dist/index218.js.map +1 -1
- package/dist/index219.js +20 -95
- package/dist/index219.js.map +1 -1
- package/dist/index220.js +92 -88
- package/dist/index220.js.map +1 -1
- package/dist/index221.js +97 -29
- package/dist/index221.js.map +1 -1
- package/dist/index222.js +24 -470
- package/dist/index222.js.map +1 -1
- package/dist/index223.js +446 -196
- package/dist/index223.js.map +1 -1
- package/dist/index224.js +199 -729
- package/dist/index224.js.map +1 -1
- package/dist/index225.js +750 -61
- package/dist/index225.js.map +1 -1
- package/dist/index226.js +58 -181
- package/dist/index226.js.map +1 -1
- package/dist/index227.js +175 -259
- package/dist/index227.js.map +1 -1
- package/dist/index228.js +246 -172
- package/dist/index228.js.map +1 -1
- package/dist/index229.js +195 -32
- package/dist/index229.js.map +1 -1
- package/dist/index230.js +12 -40
- package/dist/index230.js.map +1 -1
- package/dist/index231.js +23 -26
- package/dist/index231.js.map +1 -1
- package/dist/index232.js +45 -22
- package/dist/index232.js.map +1 -1
- package/dist/index233.js +27 -48
- package/dist/index233.js.map +1 -1
- package/dist/index234.js +52 -26
- package/dist/index234.js.map +1 -1
- package/dist/index235.js +40 -225
- package/dist/index235.js.map +1 -1
- package/dist/index236.js +217 -39
- package/dist/index236.js.map +1 -1
- package/dist/index237.js +50 -0
- package/dist/index237.js.map +1 -0
- package/dist/styles.css +1 -1
- package/dist/wc/AIToolCall.js +218 -0
- package/dist/wc/AIToolCall.js.map +1 -0
- package/dist/wc/hf-ai-tool-call.js +34 -219
- package/dist/wc/hf-ai-tool-call.js.map +1 -1
- package/dist/wc/hf-ai-tool-run.js +673 -576
- package/dist/wc/hf-ai-tool-run.js.map +1 -1
- package/dist/wc/workflow-step-renderer.js +94 -86
- package/dist/wc/workflow-step-renderer.js.map +1 -1
- package/dist/wc-react/AIToolCall.js +218 -0
- package/dist/wc-react/AIToolCall.js.map +1 -0
- package/dist/wc-react/hf-ai-tool-call.js +32 -217
- package/dist/wc-react/hf-ai-tool-call.js.map +1 -1
- package/dist/wc-react/hf-ai-tool-run.js +698 -601
- package/dist/wc-react/hf-ai-tool-run.js.map +1 -1
- package/dist/wc-react/workflow-step-renderer.js +76 -68
- package/dist/wc-react/workflow-step-renderer.js.map +1 -1
- package/package.json +1 -1
- package/skills/humain-ui/SKILL.md +1 -1
- package/skills/humain-ui-wc/SKILL.md +1 -1
- package/skills/humain-ui-wc.skill +0 -0
- package/skills/humain-ui.skill +0 -0
- package/dist/index182.js +0 -143
- package/dist/index182.js.map +0 -1
- package/dist/wc/wrench.js +0 -10
- package/dist/wc/wrench.js.map +0 -1
- package/dist/wc-react/wrench.js +0 -10
- package/dist/wc-react/wrench.js.map +0 -1
package/dist/index199.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index199.js","names":[],"sources":["../src/components/organisms/content/NotificationItem/NotificationItem.tsx"],"sourcesContent":["import { cva, type VariantProps } from 'class-variance-authority';\nimport { AlertCircle, AlertTriangle, CheckCircle, Info, X } from 'lucide-react';\nimport * as React from 'react';\nimport { Progress } from '@/components/atoms/display/Progress';\nimport type { AvatarProps } from '@/components/molecules/data/Avatar';\nimport { Avatar } from '@/components/molecules/data/Avatar';\nimport { cn } from '@/lib/utils';\n\nconst notificationItemVariants = cva(\n 'relative flex gap-4 items-start overflow-hidden p-4 rounded-xl border bg-card shadow-sm',\n {\n variants: {\n variant: {\n primary: '',\n success: '',\n warning: '',\n error: '',\n gray: '',\n avatar: '',\n image: '',\n progress: '',\n none: '',\n },\n },\n defaultVariants: {\n variant: 'primary',\n },\n },\n);\n\n// Featured icon with concentric circle outlines (for primary, success, warning, error)\nconst outlineIconVariants = cva('', {\n variants: {\n variant: {\n primary: 'border-primary text-primary',\n success: 'border-success text-success',\n warning: 'border-warning text-warning',\n error: 'border-destructive text-destructive',\n },\n },\n defaultVariants: {\n variant: 'primary',\n },\n});\n\nexport type NotificationVariant = NonNullable<\n VariantProps<typeof notificationItemVariants>['variant']\n>;\n\nexport interface NotificationAction {\n /** Button label */\n label: string;\n /** Click handler */\n onClick?: () => void;\n}\n\nexport interface NotificationItemProps\n extends Omit<React.HTMLAttributes<HTMLDivElement>, 'title'> {\n /** Visual style variant */\n variant?: NotificationVariant;\n /** Notification title */\n title: string;\n /** Supporting description text */\n supportingText?: string;\n /** Show the close button */\n showCloseButton?: boolean;\n /** Callback when close button is clicked */\n onClose?: () => void;\n /** Primary action (displayed first, brand color) */\n primaryAction?: NotificationAction;\n /** Secondary action (displayed second, neutral color) */\n secondaryAction?: NotificationAction;\n /** Custom icon for gray variant */\n icon?: React.ReactNode;\n /** Avatar props for avatar variant */\n avatarProps?: AvatarProps;\n /** Timestamp for avatar variant */\n timestamp?: string;\n /** Image source for image variant */\n imageSrc?: string;\n /** Image alt text */\n imageAlt?: string;\n /** Progress value (0-100) for progress variant */\n progressValue?: number;\n /** Progress label for progress variant */\n progressLabel?: string;\n /** Stack action buttons vertically instead of horizontally */\n stackedActions?: boolean;\n}\n\n/** Featured icon with concentric circle outlines */\nconst OutlineIcon = ({\n variant,\n}: {\n variant: 'primary' | 'success' | 'warning' | 'error';\n}) => {\n const iconClasses = outlineIconVariants({ variant });\n\n const Icon = {\n primary: Info,\n success: CheckCircle,\n warning: AlertTriangle,\n error: AlertCircle,\n }[variant];\n\n return (\n <div className=\"relative size-5 shrink-0\">\n {/* Outer ring */}\n <div\n className={cn(\n 'absolute -inset-[45%] rounded-full border-2 opacity-10',\n iconClasses,\n )}\n />\n {/* Inner ring */}\n <div\n className={cn(\n 'absolute -inset-[20%] rounded-full border-2 opacity-30',\n iconClasses,\n )}\n />\n {/* Icon */}\n <Icon className={cn('size-5', iconClasses)} />\n </div>\n );\n};\n\n/** Modern boxed featured icon */\nconst BoxedIcon = ({ children }: { children: React.ReactNode }) => (\n <div className=\"flex size-10 shrink-0 items-center justify-center rounded-lg border border-border bg-card shadow-sm\">\n <div className=\"text-secondary-foreground\">{children}</div>\n </div>\n);\n\n/** Close button */\nconst CloseButton = ({ onClick }: { onClick?: () => void }) => (\n <button\n type=\"button\"\n onClick={onClick}\n className=\"absolute end-1 top-1 flex size-11 items-center justify-center rounded-lg text-muted-foreground transition-colors hover:bg-accent hover:text-muted-foreground\"\n aria-label=\"Close notification\"\n >\n <X className=\"size-5\" />\n </button>\n);\n\n/** Action buttons */\nconst ActionButtons = ({\n primaryAction,\n secondaryAction,\n stacked = false,\n}: {\n primaryAction?: NotificationAction;\n secondaryAction?: NotificationAction;\n stacked?: boolean;\n}) => {\n if (!primaryAction && !secondaryAction) return null;\n\n if (stacked) {\n return (\n <div className=\"flex flex-col gap-2\">\n {primaryAction && (\n <button\n type=\"button\"\n onClick={primaryAction.onClick}\n className=\"w-full rounded-lg bg-primary px-3 py-2 text-sm font-semibold text-primary-foreground hover:bg-primary/90 transition-colors duration-150 ease-out focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 focus-visible:ring-offset-background\"\n >\n {primaryAction.label}\n </button>\n )}\n {secondaryAction && (\n <button\n type=\"button\"\n onClick={secondaryAction.onClick}\n className=\"w-full rounded-lg border border-border bg-card px-3 py-2 text-sm font-semibold text-secondary-foreground hover:bg-surface-2 transition-colors duration-150 ease-out focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 focus-visible:ring-offset-background\"\n >\n {secondaryAction.label}\n </button>\n )}\n </div>\n );\n }\n\n return (\n <div className=\"flex items-center gap-3\">\n {primaryAction && (\n <button\n type=\"button\"\n onClick={primaryAction.onClick}\n className=\"min-h-9 py-1.5 text-sm font-semibold text-primary hover:text-primary/80 rounded-sm transition-colors duration-150 ease-out focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 focus-visible:ring-offset-background\"\n >\n {primaryAction.label}\n </button>\n )}\n {secondaryAction && (\n <button\n type=\"button\"\n onClick={secondaryAction.onClick}\n className=\"min-h-9 py-1.5 text-sm font-semibold text-secondary-foreground hover:text-foreground rounded-sm transition-colors duration-150 ease-out focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 focus-visible:ring-offset-background\"\n >\n {secondaryAction.label}\n </button>\n )}\n </div>\n );\n};\n\ninterface NotificationLeadingElementProps {\n variant: NotificationVariant;\n icon?: React.ReactNode;\n avatarProps?: AvatarProps;\n imageSrc?: string;\n imageAlt?: string;\n}\n\nfunction NotificationLeadingElement({\n variant,\n icon,\n avatarProps,\n imageSrc,\n imageAlt,\n}: NotificationLeadingElementProps) {\n switch (variant) {\n case 'primary':\n case 'success':\n case 'warning':\n case 'error':\n return <OutlineIcon variant={variant} />;\n\n case 'gray':\n return icon ? (\n <BoxedIcon>{icon}</BoxedIcon>\n ) : (\n <BoxedIcon>\n <Info className=\"size-5\" />\n </BoxedIcon>\n );\n\n case 'avatar':\n return (\n <div className=\"relative\">\n <Avatar size=\"md\" indicator=\"online\" {...avatarProps} />\n </div>\n );\n\n case 'image':\n return imageSrc ? (\n <div className=\"size-[72px] shrink-0 overflow-hidden rounded-lg\">\n <img\n src={imageSrc}\n alt={imageAlt || 'Notification image'}\n loading=\"lazy\"\n className=\"size-full object-cover\"\n />\n </div>\n ) : null;\n\n case 'progress':\n return icon ? (\n <BoxedIcon>{icon}</BoxedIcon>\n ) : (\n <BoxedIcon>\n <Info className=\"size-5\" />\n </BoxedIcon>\n );\n\n default:\n return null;\n }\n}\n\ninterface NotificationContentProps {\n variant: NotificationVariant;\n title: string;\n supportingText?: string;\n timestamp?: string;\n imageSrc?: string;\n imageAlt?: string;\n progressValue: number;\n progressLabel?: string;\n primaryAction?: NotificationAction;\n secondaryAction?: NotificationAction;\n stackedActions: boolean;\n}\n\nfunction NotificationContent({\n variant,\n title,\n supportingText,\n timestamp,\n imageSrc,\n imageAlt,\n progressValue,\n progressLabel,\n primaryAction,\n secondaryAction,\n stackedActions,\n}: NotificationContentProps) {\n const hasActions = primaryAction || secondaryAction;\n\n if (variant === 'progress') {\n return (\n <div className=\"flex min-w-0 flex-1 flex-col gap-4 pe-10\">\n <div className=\"flex flex-col gap-1\">\n <h3 className=\"text-sm font-semibold text-foreground\">{title}</h3>\n {supportingText && (\n <p className=\"text-sm text-secondary-foreground\">\n {supportingText}\n </p>\n )}\n </div>\n\n <Progress\n value={progressValue}\n size=\"md\"\n showValue\n labelPosition=\"inline\"\n valueFormat={(value) => progressLabel || `${value}%`}\n />\n\n {hasActions && (\n <ActionButtons\n primaryAction={primaryAction}\n secondaryAction={secondaryAction}\n stacked={stackedActions}\n />\n )}\n </div>\n );\n }\n\n if (variant === 'avatar') {\n return (\n <div className=\"flex min-w-0 flex-1 flex-col gap-3 pe-10\">\n <div className=\"flex flex-col gap-1\">\n <div className=\"flex items-center gap-2\">\n <h3 className=\"text-sm font-semibold text-foreground\">{title}</h3>\n {timestamp && (\n <span className=\"text-sm text-text-quaternary\">{timestamp}</span>\n )}\n </div>\n {supportingText && (\n <p className=\"text-sm text-secondary-foreground\">\n {supportingText}\n </p>\n )}\n </div>\n\n {hasActions && (\n <ActionButtons\n primaryAction={primaryAction}\n secondaryAction={secondaryAction}\n stacked={stackedActions}\n />\n )}\n </div>\n );\n }\n\n if (variant === 'image') {\n return (\n <div className=\"flex min-w-0 flex-1 flex-col gap-3 pe-10\">\n <div className=\"flex flex-col gap-1\">\n <h3 className=\"text-sm font-semibold text-foreground\">{title}</h3>\n {supportingText && (\n <p className=\"text-sm text-secondary-foreground\">\n {supportingText}\n </p>\n )}\n </div>\n\n {imageSrc && (\n <div className=\"w-full aspect-video overflow-hidden rounded-lg\">\n <img\n src={imageSrc}\n alt={imageAlt || 'Notification image'}\n loading=\"lazy\"\n className=\"size-full object-cover\"\n />\n </div>\n )}\n\n {hasActions && (\n <ActionButtons\n primaryAction={primaryAction}\n secondaryAction={secondaryAction}\n stacked={stackedActions}\n />\n )}\n </div>\n );\n }\n\n return (\n <div className=\"flex min-w-0 flex-1 flex-col gap-3 pe-10 pt-0.5\">\n <div className=\"flex flex-col gap-1\">\n <h3 className=\"text-sm font-semibold text-foreground\">{title}</h3>\n {supportingText && (\n <p className=\"text-sm text-secondary-foreground\">{supportingText}</p>\n )}\n </div>\n\n {hasActions && (\n <ActionButtons\n primaryAction={primaryAction}\n secondaryAction={secondaryAction}\n />\n )}\n </div>\n );\n}\n\nconst NotificationItem = React.memo(function NotificationItem({\n variant = 'primary',\n title,\n supportingText,\n showCloseButton = true,\n onClose,\n primaryAction,\n secondaryAction,\n icon,\n avatarProps,\n timestamp,\n imageSrc,\n imageAlt,\n progressValue = 0,\n progressLabel,\n stackedActions = false,\n className,\n ...props\n}: NotificationItemProps) {\n return (\n <article\n data-slot=\"notification-item\"\n className={cn(\n notificationItemVariants({ variant }),\n 'transition-shadow duration-200 ease-out hover:shadow-md motion-reduce:transition-none',\n className,\n )}\n {...props}\n >\n <NotificationLeadingElement\n variant={variant}\n icon={icon}\n avatarProps={avatarProps}\n imageSrc={imageSrc}\n imageAlt={imageAlt}\n />\n <NotificationContent\n variant={variant}\n title={title}\n supportingText={supportingText}\n timestamp={timestamp}\n imageSrc={imageSrc}\n imageAlt={imageAlt}\n progressValue={progressValue}\n progressLabel={progressLabel}\n primaryAction={primaryAction}\n secondaryAction={secondaryAction}\n stackedActions={stackedActions}\n />\n {showCloseButton && <CloseButton onClick={onClose} />}\n </article>\n );\n});\n\nNotificationItem.displayName = 'NotificationItem';\n\nexport { NotificationItem, notificationItemVariants };\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index199.js","names":[],"sources":["../src/components/organisms/content/MetricItem/MetricItem.tsx"],"sourcesContent":["import { cva, type VariantProps } from 'class-variance-authority';\nimport {\n ArrowUp,\n ArrowUpRight,\n Eye,\n MoreVertical,\n TrendingUp,\n} from 'lucide-react';\nimport * as React from 'react';\nimport { Area, AreaChart, Line, LineChart } from 'recharts';\nimport { Button } from '@/components/atoms/buttons/Button';\nimport { type ChartConfig, ChartContainer } from '@/components/ui/chart';\nimport { useReducedMotion } from '@/hooks/use-reduced-motion';\nimport { cn } from '@/lib/utils';\n\nconst MINI_CHART_MARGIN = { top: 0, right: 0, bottom: 0, left: 0 };\n\nfunction getFiniteMetricNumber(value: number, fallback = 0): number {\n return Number.isFinite(value) ? value : fallback;\n}\n\nfunction getFinitePositiveMetricNumber(\n value: number | undefined,\n fallback: number,\n): number {\n return typeof value === 'number' && Number.isFinite(value) && value > 0\n ? value\n : fallback;\n}\n\nfunction getFinitePositiveMetricNumberOrUndefined(\n value: number | undefined,\n): number | undefined {\n return typeof value === 'number' && Number.isFinite(value) && value > 0\n ? value\n : undefined;\n}\n\nfunction formatMetricValue(value: string | number): string | number {\n return typeof value === 'number'\n ? getFiniteMetricNumber(value).toLocaleString()\n : value;\n}\n\n// ============================================\n// MetricMiniChart - Sparkline chart component\n// ============================================\n\nconst metricMiniChartVariants = cva('relative shrink-0', {\n variants: {\n variant: {\n line: '',\n area: '',\n layers: '',\n },\n },\n defaultVariants: {\n variant: 'line',\n },\n});\n\nexport interface MetricMiniChartProps\n extends React.HTMLAttributes<HTMLDivElement>,\n VariantProps<typeof metricMiniChartVariants> {\n /** Data points for the sparkline */\n data: number[];\n /** Color of the chart line/area */\n color?: string;\n /** Width of the chart */\n width?: number;\n /** Height of the chart */\n height?: number;\n /** Show marker dot at the end */\n showMarker?: boolean;\n /** Trend direction for styling */\n trend?: 'positive' | 'negative';\n}\n\nfunction MetricMiniChart({\n data,\n color,\n width,\n height = 56,\n variant = 'line',\n showMarker = true,\n trend = 'positive',\n className,\n ...props\n}: MetricMiniChartProps) {\n const gradientId = React.useId();\n const prefersReducedMotion = useReducedMotion();\n const shouldAnimate = !prefersReducedMotion;\n const trendColor =\n trend === 'positive' ? 'var(--success)' : 'var(--destructive)';\n const chartColor = color || trendColor;\n const chartWidth = getFinitePositiveMetricNumberOrUndefined(width);\n const chartHeight = getFinitePositiveMetricNumber(height, 56);\n const safeData = React.useMemo(\n () => data.map((value) => getFiniteMetricNumber(value)),\n [data],\n );\n\n // Transform data for recharts\n const chartData = React.useMemo(\n () => safeData.map((value, index) => ({ index, value })),\n [safeData],\n );\n\n const chartConfig: ChartConfig = React.useMemo(\n () => ({\n value: {\n color: chartColor,\n },\n }),\n [chartColor],\n );\n\n // Find the max value index for marker positioning\n const lastIndex = safeData.length - 1;\n const lastValue = safeData[lastIndex] ?? 0;\n const markerTop = React.useMemo(() => {\n const maxValue = safeData.length > 0 ? Math.max(...safeData) : 0;\n return maxValue <= 0\n ? 50\n : Math.max(10, Math.min(90, 100 - (lastValue / maxValue) * 100));\n }, [safeData, lastValue]);\n const rootStyle = React.useMemo(\n () => ({ width: chartWidth, height: chartHeight }),\n [chartHeight, chartWidth],\n );\n\n // Width can be undefined to allow CSS classes (like w-full) to control responsive width\n return (\n <div\n data-slot=\"metric-mini-chart\"\n aria-hidden=\"true\"\n inert={true}\n className={cn(metricMiniChartVariants({ variant }), className)}\n style={rootStyle}\n {...props}\n >\n <ChartContainer config={chartConfig} className=\"size-full\">\n {variant === 'layers' ? (\n <AreaChart data={chartData} margin={MINI_CHART_MARGIN}>\n <defs>\n <linearGradient\n id={`fillArea${gradientId}`}\n x1=\"0\"\n y1=\"0\"\n x2=\"0\"\n y2=\"1\"\n >\n <stop offset=\"0%\" stopColor={chartColor} stopOpacity={0.3} />\n <stop offset=\"100%\" stopColor={chartColor} stopOpacity={0.05} />\n </linearGradient>\n </defs>\n <Area\n type=\"monotone\"\n dataKey=\"value\"\n stroke={chartColor}\n strokeWidth={2}\n fill={`url(#fillArea${gradientId})`}\n isAnimationActive={shouldAnimate}\n />\n </AreaChart>\n ) : (\n <LineChart data={chartData} margin={MINI_CHART_MARGIN}>\n {variant === 'area' && (\n <>\n <defs>\n <linearGradient\n id={`fillLine${gradientId}`}\n x1=\"0\"\n y1=\"0\"\n x2=\"0\"\n y2=\"1\"\n >\n <stop\n offset=\"0%\"\n stopColor={chartColor}\n stopOpacity={0.15}\n />\n <stop\n offset=\"100%\"\n stopColor={chartColor}\n stopOpacity={0.02}\n />\n </linearGradient>\n </defs>\n <Area\n type=\"monotone\"\n dataKey=\"value\"\n stroke=\"none\"\n fill={`url(#fillLine${gradientId})`}\n isAnimationActive={shouldAnimate}\n />\n </>\n )}\n <Line\n type=\"monotone\"\n dataKey=\"value\"\n stroke={chartColor}\n strokeWidth={2}\n dot={false}\n isAnimationActive={shouldAnimate}\n />\n </LineChart>\n )}\n </ChartContainer>\n\n {/* Marker dot */}\n {showMarker && variant === 'line' && (\n <div\n className=\"absolute\"\n style={{\n right: 0,\n top: `${markerTop}%`,\n transform: 'translate(50%, -50%)',\n }}\n >\n <div\n className=\"size-[19px] rounded-full opacity-20\"\n style={{ backgroundColor: chartColor }}\n />\n <div\n className=\"absolute top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2 size-[10px] rounded-full bg-background border-2\"\n style={{ borderColor: chartColor }}\n />\n </div>\n )}\n </div>\n );\n}\n\nMetricMiniChart.displayName = 'MetricMiniChart';\n\n// ============================================\n// MetricChange - Change indicator component\n// ============================================\n\nconst metricChangeVariants = cva('inline-flex items-center gap-0.5', {\n variants: {\n variant: {\n default: '',\n badge:\n 'bg-background border border-border rounded-md shadow-xs px-1.5 py-0.5',\n },\n trend: {\n positive: '',\n negative: '',\n },\n },\n defaultVariants: {\n variant: 'default',\n trend: 'positive',\n },\n});\n\nexport interface MetricChangeProps\n extends React.HTMLAttributes<HTMLDivElement>,\n VariantProps<typeof metricChangeVariants> {\n /** Change value (e.g., \"100%\", \"+25%\") */\n value: string;\n /** Icon type ('none' to hide icon) */\n icon?: 'arrow' | 'trend' | 'arrow-right' | 'none';\n}\n\nfunction MetricChange({\n value,\n variant = 'default',\n trend = 'positive',\n icon = 'arrow',\n className,\n ...props\n}: MetricChangeProps) {\n const iconColor =\n trend === 'positive' ? 'var(--success)' : 'var(--destructive)';\n const textColor =\n variant === 'badge'\n ? 'text-secondary-foreground'\n : trend === 'positive'\n ? 'text-success'\n : 'text-destructive';\n\n const IconComponent =\n icon === 'none'\n ? null\n : icon === 'trend'\n ? TrendingUp\n : icon === 'arrow-right'\n ? ArrowUpRight\n : ArrowUp;\n\n const iconSize = variant === 'badge' ? 12 : 16;\n\n return (\n <div\n className={cn(metricChangeVariants({ variant, trend }), className)}\n {...props}\n >\n {IconComponent && (\n <IconComponent\n aria-hidden=\"true\"\n width={iconSize}\n height={iconSize}\n color={iconColor}\n className={cn(trend === 'negative' && 'rotate-180')}\n />\n )}\n <span className=\"sr-only\">\n {trend === 'positive' ? 'Increased' : 'Decreased'}\n </span>\n <span className={cn('text-sm font-medium', textColor)}>{value}</span>\n </div>\n );\n}\n\nMetricChange.displayName = 'MetricChange';\n\n// ============================================\n// MetricItem - Main component\n// ============================================\n\nconst metricItemVariants = cva(\n 'relative flex flex-col gap-2 p-5 bg-background rounded-xl border border-border shadow-xs transition-shadow duration-200 ease-out hover:shadow-sm motion-reduce:transition-none',\n {\n variants: {\n type: {\n simple: '',\n 'icon-01': '',\n 'icon-02': '',\n 'icon-03': '',\n 'icon-04': 'flex-row items-center',\n 'chart-01': '',\n 'chart-02': '',\n 'chart-03': '',\n 'chart-04': 'p-0 bg-transparent border-0 shadow-none',\n },\n breakpoint: {\n desktop: '',\n mobile: '',\n },\n },\n defaultVariants: {\n type: 'simple',\n breakpoint: 'desktop',\n },\n },\n);\n\nexport interface MetricItemProps\n extends React.HTMLAttributes<HTMLDivElement>,\n VariantProps<typeof metricItemVariants> {\n /** Title/label of the metric */\n title: string;\n /** Main value to display */\n value: string | number;\n /** Change indicator value */\n changeValue?: string;\n /** Change trend direction */\n changeTrend?: 'positive' | 'negative';\n /** Change icon type ('none' to hide icon) */\n changeIcon?: 'arrow' | 'trend' | 'arrow-right' | 'none';\n /** Comparison text (e.g., \"vs last month\") */\n comparisonText?: string;\n /** Subtitle/description text shown next to value (alternative to change indicator) */\n subtitle?: string;\n /** Show dropdown menu button */\n showDropdown?: boolean;\n /** Show action buttons */\n showActions?: boolean;\n /** Action button click handler */\n onViewReport?: () => void;\n /** Dropdown click handler */\n onDropdownClick?: () => void;\n /** Icon for icon variants */\n icon?: React.ReactNode;\n /** Icon background color */\n iconBgColor?: string;\n /** Icon color */\n iconColor?: string;\n /** Chart data for chart variants */\n chartData?: number[];\n /** Featured icon variant style */\n featuredIconVariant?: 'circle' | 'square' | 'modern';\n /** Custom content to render instead of chart (for chart-04 type) */\n children?: React.ReactNode;\n}\n\nconst MetricItem = React.memo(function MetricItem({\n title,\n value,\n changeValue,\n changeTrend = 'positive',\n changeIcon,\n comparisonText,\n subtitle,\n showDropdown = false,\n showActions = false,\n onViewReport,\n onDropdownClick,\n icon,\n iconBgColor,\n iconColor,\n chartData,\n featuredIconVariant = 'circle',\n type = 'simple',\n breakpoint = 'desktop',\n className,\n children,\n ...props\n}: MetricItemProps) {\n // Default icon for icon variants\n const defaultIcon = <TrendingUp width={24} height={24} />;\n const displayIcon = icon || defaultIcon;\n const displayValue = formatMetricValue(value);\n\n // Default icon colors based on type and variant\n const defaultIconBgColor =\n type === 'icon-01'\n ? featuredIconVariant === 'modern'\n ? 'var(--muted)' // for modern\n : 'var(--success-muted)' // for circle/square\n : type === 'icon-02' || type === 'icon-03' || type === 'icon-04'\n ? 'var(--muted)'\n : 'var(--success-muted)';\n\n const defaultIconColor =\n type === 'icon-01'\n ? featuredIconVariant === 'modern'\n ? 'var(--secondary-foreground)' // for modern\n : 'var(--success)' // for circle/square\n : type === 'icon-02'\n ? 'var(--secondary-foreground)'\n : 'var(--success)';\n\n const finalIconBgColor = iconBgColor || defaultIconBgColor;\n const finalIconColor = iconColor || defaultIconColor;\n\n // Chart-04 has a different structure\n if (type === 'chart-04') {\n return (\n <div\n data-slot=\"metric-item\"\n className={cn(metricItemVariants({ type, breakpoint }), className)}\n {...props}\n >\n <div className=\"flex flex-col gap-0.5 w-full\">\n {/* Header */}\n <div className=\"flex items-center px-5 pt-3 pb-2 w-full\">\n <p className=\"flex-1 text-sm font-semibold text-foreground\">\n {title}\n </p>\n </div>\n\n {/* Content card */}\n <div className=\"relative bg-background border border-border rounded-xl shadow-xs p-5 flex flex-col gap-5\">\n {/* Number and change */}\n <div className=\"flex flex-wrap items-center gap-3\">\n <p className=\"text-display-sm font-semibold text-foreground\">\n {displayValue}\n </p>\n {changeValue && (\n <div className=\"flex items-center gap-2\">\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n // chart-04 defaults to 'trend' icon for backward compatibility\n icon={changeIcon ?? 'trend'}\n />\n {comparisonText && (\n <span className=\"text-sm font-medium text-muted-foreground\">\n {comparisonText}\n </span>\n )}\n </div>\n )}\n </div>\n\n {/* Chart or custom content */}\n {children ? (\n children\n ) : chartData ? (\n <MetricMiniChart\n data={chartData}\n width={undefined}\n height={56}\n variant=\"line\"\n showMarker={false}\n trend={changeTrend}\n className=\"w-full\"\n />\n ) : null}\n\n {/* Dropdown */}\n {showDropdown && (\n <button\n type=\"button\"\n aria-label=\"More options\"\n className=\"absolute top-2 end-2 p-3 cursor-pointer rounded-sm focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 focus-visible:ring-offset-background transition-colors duration-150 ease-out hover:text-foreground\"\n onClick={onDropdownClick}\n >\n <MoreVertical\n width={20}\n height={20}\n className=\"text-muted-foreground\"\n />\n </button>\n )}\n </div>\n </div>\n </div>\n );\n }\n\n return (\n <div\n data-slot=\"metric-item\"\n className={cn(metricItemVariants({ type, breakpoint }), className)}\n {...props}\n >\n {/* Featured Icon (for icon-01 only - standalone icon above content) */}\n {type === 'icon-01' && (\n <div\n className={cn(\n 'flex items-center justify-center shrink-0 relative overflow-clip',\n featuredIconVariant === 'modern'\n ? 'rounded-[10px] border border-border shadow-xs'\n : featuredIconVariant === 'square'\n ? 'rounded-[10px] border border-border shadow-xs'\n : 'rounded-full',\n )}\n style={{\n width: 48,\n height: 48,\n backgroundColor: finalIconBgColor,\n color: finalIconColor,\n }}\n >\n {displayIcon}\n {/* Skeuomorphic inner shadow overlay for modern variant */}\n {featuredIconVariant === 'modern' && (\n <div\n className=\"absolute inset-0 pointer-events-none rounded-[10px]\"\n style={{\n boxShadow: 'var(--shadow-inset-ring)',\n }}\n />\n )}\n </div>\n )}\n\n {/* Icon-02 and Icon-03: Heading row with icon + title */}\n {(type === 'icon-02' || type === 'icon-03') && (\n <div className=\"flex items-center gap-3 w-full\">\n <div\n className={cn(\n 'flex items-center justify-center shrink-0',\n type === 'icon-02'\n ? 'rounded-full'\n : 'rounded-lg border border-border shadow-xs',\n )}\n style={{\n width: 48,\n height: 48,\n backgroundColor: finalIconBgColor,\n color: finalIconColor,\n }}\n >\n {icon || <Eye width={24} height={24} />}\n </div>\n <p className=\"flex-1 text-base font-semibold text-foreground\">\n {title}\n </p>\n </div>\n )}\n\n {/* Icon-04: Horizontal layout with featured icon + content */}\n {type === 'icon-04' && (\n <div\n className={cn(\n 'flex items-center justify-center shrink-0 rounded-md border border-border shadow-xs',\n )}\n style={{\n width: 40,\n height: 40,\n backgroundColor: finalIconBgColor,\n color: finalIconColor,\n }}\n >\n {icon || <TrendingUp width={20} height={20} />}\n </div>\n )}\n\n {/* Heading and number section */}\n {type !== 'icon-02' && type !== 'icon-03' && (\n <div\n className={cn(\n 'flex flex-col gap-2',\n type === 'icon-04' ? 'flex-1 min-w-0' : 'w-full',\n )}\n >\n {/* Title */}\n {type === 'chart-01' || type === 'chart-02' ? (\n <p className=\"text-base font-semibold text-foreground\">{title}</p>\n ) : type === 'icon-04' || type === 'icon-01' ? (\n <p className=\"text-sm font-semibold text-muted-foreground\">\n {title}\n </p>\n ) : (\n <p className=\"text-sm font-medium text-muted-foreground\">{title}</p>\n )}\n\n {/* Number and badge row */}\n {type === 'simple' || type === 'icon-01' || type === 'icon-04' ? (\n <div className=\"flex flex-wrap items-center justify-between gap-3 w-full\">\n <p className=\"text-display-sm font-semibold text-foreground\">\n {displayValue}\n </p>\n {/* Show inline change + comparison OR badge OR subtitle */}\n {changeValue && comparisonText ? (\n <div className=\"flex items-center gap-2\">\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n icon=\"arrow\"\n />\n <span className=\"text-sm font-medium text-muted-foreground\">\n {comparisonText}\n </span>\n </div>\n ) : changeValue ? (\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n // badge variant defaults to 'arrow-right' icon for backward compatibility\n icon={changeIcon ?? 'arrow-right'}\n variant=\"badge\"\n />\n ) : subtitle ? (\n <span className=\"text-sm font-medium text-muted-foreground\">\n {subtitle}\n </span>\n ) : null}\n </div>\n ) : null}\n </div>\n )}\n\n {/* Chart variants content */}\n {type === 'chart-01' && (\n <div className=\"flex items-end gap-4 w-full\">\n <div className=\"flex-1 flex flex-col gap-3\">\n <p className=\"text-display-sm font-semibold text-foreground\">\n {displayValue}\n </p>\n {(changeValue || comparisonText) && (\n <div className=\"flex items-center gap-2\">\n {changeValue && (\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n icon=\"arrow\"\n />\n )}\n {comparisonText && (\n <span className=\"text-sm font-medium text-muted-foreground truncate\">\n {comparisonText}\n </span>\n )}\n </div>\n )}\n </div>\n {chartData && (\n <MetricMiniChart\n data={chartData}\n width={112}\n height={56}\n variant=\"line\"\n trend={changeTrend}\n />\n )}\n </div>\n )}\n\n {type === 'chart-02' && (\n <div className=\"flex items-end gap-4 w-full\">\n <div className=\"flex-1 flex items-start gap-2\">\n <p className=\"text-display-md font-semibold text-foreground\">\n {displayValue}\n </p>\n {changeValue && (\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n icon=\"trend\"\n />\n )}\n </div>\n {chartData && (\n <MetricMiniChart\n data={chartData}\n width={128}\n height={56}\n variant=\"layers\"\n showMarker={false}\n trend={changeTrend}\n />\n )}\n </div>\n )}\n\n {type === 'chart-03' && (\n <>\n <div className=\"flex flex-col gap-2 w-full\">\n <p className=\"text-sm font-medium text-muted-foreground\">{title}</p>\n <div className=\"flex flex-wrap items-center justify-between gap-3 w-full\">\n <p className=\"text-display-sm font-semibold text-foreground\">\n {displayValue}\n </p>\n {(changeValue || comparisonText) && (\n <div className=\"flex items-center gap-2\">\n {changeValue && (\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n icon=\"trend\"\n />\n )}\n {comparisonText && (\n <span className=\"text-sm font-medium text-muted-foreground\">\n {comparisonText}\n </span>\n )}\n </div>\n )}\n </div>\n </div>\n {chartData && (\n <MetricMiniChart\n data={chartData}\n height={72}\n variant=\"area\"\n showMarker={false}\n trend={changeTrend}\n className=\"w-full\"\n />\n )}\n </>\n )}\n\n {/* Icon-02 and Icon-03 number section */}\n {(type === 'icon-02' || type === 'icon-03') && (\n <div className=\"flex items-end gap-4 w-full\">\n <div className=\"flex-1 flex flex-col gap-3\">\n <p className=\"text-display-md font-semibold text-foreground\">\n {displayValue}\n </p>\n {(changeValue || comparisonText) && (\n <div className=\"flex items-center gap-2\">\n {changeValue && (\n <MetricChange\n value={changeValue}\n trend={changeTrend}\n icon={type === 'icon-03' ? 'trend' : 'arrow'}\n />\n )}\n {comparisonText && (\n <span className=\"text-sm font-medium text-muted-foreground truncate\">\n {comparisonText}\n </span>\n )}\n </div>\n )}\n </div>\n {chartData && (\n <MetricMiniChart\n data={chartData}\n width={112}\n height={56}\n variant=\"line\"\n trend={changeTrend}\n />\n )}\n </div>\n )}\n\n {/* Dropdown button */}\n {showDropdown && (\n <button\n type=\"button\"\n aria-label=\"More options\"\n className=\"absolute top-2 end-2 cursor-pointer rounded-sm p-3 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 focus-visible:ring-offset-background transition-colors duration-150 ease-out hover:text-foreground\"\n onClick={onDropdownClick}\n >\n <MoreVertical\n width={20}\n height={20}\n className=\"text-muted-foreground\"\n />\n </button>\n )}\n\n {/* Action buttons */}\n {showActions && (\n <div className=\"flex items-center gap-2 pt-2\">\n <Button\n appearance=\"outline\"\n variant=\"secondary\"\n size=\"sm\"\n onClick={onViewReport}\n >\n View report\n </Button>\n </div>\n )}\n </div>\n );\n});\n\nMetricItem.displayName = 'MetricItem';\n\nexport {\n MetricChange,\n MetricItem,\n MetricMiniChart,\n metricChangeVariants,\n metricItemVariants,\n metricMiniChartVariants,\n};\n"],"mappings":"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"}
|