@almadar/ui 4.19.3 → 4.21.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/avl/index.cjs +52 -22
- package/dist/avl/index.js +52 -22
- package/dist/components/index.cjs +52 -21
- package/dist/components/index.js +52 -21
- package/dist/components/molecules/StatDisplay.d.ts +9 -1
- package/dist/components/molecules/Tabs.d.ts +4 -2
- package/dist/providers/index.cjs +52 -21
- package/dist/providers/index.js +52 -21
- package/dist/runtime/index.cjs +52 -22
- package/dist/runtime/index.js +52 -22
- package/package.json +1 -1
package/dist/components/index.js
CHANGED
|
@@ -2972,7 +2972,7 @@ var init_RangeSlider = __esm({
|
|
|
2972
2972
|
action,
|
|
2973
2973
|
actionPayload,
|
|
2974
2974
|
onChange,
|
|
2975
|
-
formatValue:
|
|
2975
|
+
formatValue: formatValue4,
|
|
2976
2976
|
...props
|
|
2977
2977
|
}, ref) => {
|
|
2978
2978
|
const [isDragging, setIsDragging] = useState(false);
|
|
@@ -2981,7 +2981,7 @@ var init_RangeSlider = __esm({
|
|
|
2981
2981
|
const eventBus = useSafeEventBus();
|
|
2982
2982
|
const percentage = max !== min ? (value - min) / (max - min) * 100 : 0;
|
|
2983
2983
|
const bufferedPercentage = buffered !== void 0 ? Math.min(buffered, 100) : void 0;
|
|
2984
|
-
const displayValue =
|
|
2984
|
+
const displayValue = formatValue4 ? formatValue4(value) : String(value);
|
|
2985
2985
|
const handleChange = useCallback(
|
|
2986
2986
|
(e) => {
|
|
2987
2987
|
const newValue = Number(e.target.value);
|
|
@@ -15516,6 +15516,7 @@ var init_Tabs = __esm({
|
|
|
15516
15516
|
defaultActiveTab,
|
|
15517
15517
|
activeTab: controlledActiveTab,
|
|
15518
15518
|
onTabChange,
|
|
15519
|
+
tabChangeEvent,
|
|
15519
15520
|
variant = "default",
|
|
15520
15521
|
orientation = "horizontal",
|
|
15521
15522
|
className
|
|
@@ -15538,6 +15539,9 @@ var init_Tabs = __esm({
|
|
|
15538
15539
|
setInternalActiveTab(tabId);
|
|
15539
15540
|
}
|
|
15540
15541
|
onTabChange?.(tabId);
|
|
15542
|
+
if (tabChangeEvent) {
|
|
15543
|
+
eventBus.emit(`UI:${tabChangeEvent}`, { tabId });
|
|
15544
|
+
}
|
|
15541
15545
|
if (tabEvent) {
|
|
15542
15546
|
eventBus.emit(`UI:${tabEvent}`, { tabId });
|
|
15543
15547
|
}
|
|
@@ -15618,7 +15622,7 @@ var init_Tabs = __esm({
|
|
|
15618
15622
|
isActive ? variant === "pills" ? "text-primary-foreground font-bold" : "text-foreground font-bold" : "text-muted-foreground hover:text-foreground"
|
|
15619
15623
|
),
|
|
15620
15624
|
children: [
|
|
15621
|
-
item.icon && /* @__PURE__ */ jsx(Icon, { icon: item.icon, size: "sm" }),
|
|
15625
|
+
item.icon && (typeof item.icon === "string" ? /* @__PURE__ */ jsx(Icon, { name: item.icon, size: "sm" }) : /* @__PURE__ */ jsx(Icon, { icon: item.icon, size: "sm" })),
|
|
15622
15626
|
/* @__PURE__ */ jsx(Typography, { variant: "small", weight: isActive ? "semibold" : "normal", className: "!text-inherit", children: item.label }),
|
|
15623
15627
|
item.badge !== void 0 && /* @__PURE__ */ jsx(Badge, { variant: "default", size: "sm", children: item.badge })
|
|
15624
15628
|
]
|
|
@@ -23097,25 +23101,24 @@ var init_Lightbox = __esm({
|
|
|
23097
23101
|
Lightbox.displayName = "Lightbox";
|
|
23098
23102
|
}
|
|
23099
23103
|
});
|
|
23100
|
-
function
|
|
23104
|
+
function formatNumber(value, format) {
|
|
23101
23105
|
if (value == null) return "0";
|
|
23102
23106
|
const v = typeof value === "number" ? value : value;
|
|
23103
|
-
let formatted;
|
|
23104
23107
|
switch (format) {
|
|
23105
23108
|
case "currency":
|
|
23106
|
-
|
|
23107
|
-
break;
|
|
23109
|
+
return typeof v === "number" ? `$${v.toFixed(2)}` : String(v);
|
|
23108
23110
|
case "percent":
|
|
23109
|
-
|
|
23110
|
-
break;
|
|
23111
|
+
return typeof v === "number" ? `${Math.round(v)}%` : String(v);
|
|
23111
23112
|
case "number":
|
|
23112
|
-
|
|
23113
|
-
break;
|
|
23113
|
+
return typeof v === "number" ? v.toLocaleString() : String(v);
|
|
23114
23114
|
default:
|
|
23115
|
-
|
|
23115
|
+
return String(v);
|
|
23116
23116
|
}
|
|
23117
|
-
|
|
23118
|
-
|
|
23117
|
+
}
|
|
23118
|
+
function composeDisplayValue(value, format, max, prefix, suffix) {
|
|
23119
|
+
const formatted = formatNumber(value, format);
|
|
23120
|
+
const withMax = max != null && max > 0 ? `${formatted} / ${max}` : formatted;
|
|
23121
|
+
return `${prefix ?? ""}${withMax}${suffix ?? ""}`;
|
|
23119
23122
|
}
|
|
23120
23123
|
var variantColor, StatDisplay;
|
|
23121
23124
|
var init_StatDisplay = __esm({
|
|
@@ -23139,6 +23142,10 @@ var init_StatDisplay = __esm({
|
|
|
23139
23142
|
label,
|
|
23140
23143
|
value,
|
|
23141
23144
|
max,
|
|
23145
|
+
target,
|
|
23146
|
+
trend,
|
|
23147
|
+
prefix,
|
|
23148
|
+
suffix,
|
|
23142
23149
|
icon: iconProp,
|
|
23143
23150
|
iconBg = "bg-muted",
|
|
23144
23151
|
iconColor = "text-foreground",
|
|
@@ -23154,7 +23161,13 @@ var init_StatDisplay = __esm({
|
|
|
23154
23161
|
const iconSizes2 = { sm: "h-4 w-4", md: "h-5 w-5", lg: "h-6 w-6" };
|
|
23155
23162
|
const valueSizes = { sm: "text-lg", md: "text-2xl", lg: "text-3xl" };
|
|
23156
23163
|
const padSizes = { sm: "p-3", md: "p-4", lg: "p-6" };
|
|
23157
|
-
const displayValue =
|
|
23164
|
+
const displayValue = composeDisplayValue(value, format, max, prefix, suffix);
|
|
23165
|
+
const numericValue = typeof value === "number" ? value : Number(value);
|
|
23166
|
+
const showTarget = typeof target === "number" && target > 0 && Number.isFinite(numericValue);
|
|
23167
|
+
const targetPct = showTarget ? Math.max(0, Math.min(100, numericValue / target * 100)) : 0;
|
|
23168
|
+
const showTrend = typeof trend === "number" && trend !== 0 && Number.isFinite(trend);
|
|
23169
|
+
const trendUp = showTrend && trend > 0;
|
|
23170
|
+
const trendLabel = showTrend ? `${trendUp ? "\u2191" : "\u2193"} ${Math.abs(trend)}` : "";
|
|
23158
23171
|
if (error) {
|
|
23159
23172
|
return /* @__PURE__ */ jsx(Card, { className: cn(padSizes[size], className), children: /* @__PURE__ */ jsx(Typography, { variant: "small", color: "error", children: error.message }) });
|
|
23160
23173
|
}
|
|
@@ -23169,13 +23182,31 @@ var init_StatDisplay = __esm({
|
|
|
23169
23182
|
ResolvedIcon && /* @__PURE__ */ jsx(ResolvedIcon, { className: cn(iconSizes2[size], iconColor) }),
|
|
23170
23183
|
typeof iconProp !== "string" && iconProp,
|
|
23171
23184
|
/* @__PURE__ */ jsx(Typography, { variant: "caption", color: "secondary", children: label }),
|
|
23172
|
-
/* @__PURE__ */ jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue })
|
|
23185
|
+
/* @__PURE__ */ jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue }),
|
|
23186
|
+
showTrend && /* @__PURE__ */ jsx(Typography, { variant: "caption", className: cn("font-semibold", trendUp ? "text-success" : "text-error"), children: trendLabel })
|
|
23173
23187
|
] });
|
|
23174
23188
|
}
|
|
23175
23189
|
return /* @__PURE__ */ jsx(Card, { className: cn(padSizes[size], className), children: /* @__PURE__ */ jsxs(HStack, { align: "start", justify: "between", children: [
|
|
23176
|
-
/* @__PURE__ */ jsxs(VStack, { gap: "none", className: "space-y-1", children: [
|
|
23190
|
+
/* @__PURE__ */ jsxs(VStack, { gap: "none", className: "space-y-1 flex-1", children: [
|
|
23177
23191
|
/* @__PURE__ */ jsx(Typography, { variant: "overline", color: "secondary", children: label }),
|
|
23178
|
-
/* @__PURE__ */
|
|
23192
|
+
/* @__PURE__ */ jsxs(HStack, { gap: "sm", align: "end", children: [
|
|
23193
|
+
/* @__PURE__ */ jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue }),
|
|
23194
|
+
showTrend && /* @__PURE__ */ jsx(
|
|
23195
|
+
Typography,
|
|
23196
|
+
{
|
|
23197
|
+
variant: "caption",
|
|
23198
|
+
className: cn("font-semibold pb-1", trendUp ? "text-success" : "text-error"),
|
|
23199
|
+
children: trendLabel
|
|
23200
|
+
}
|
|
23201
|
+
)
|
|
23202
|
+
] }),
|
|
23203
|
+
showTarget && /* @__PURE__ */ jsx(Box, { className: "mt-2 h-1.5 w-full bg-muted rounded-full overflow-hidden", children: /* @__PURE__ */ jsx(
|
|
23204
|
+
Box,
|
|
23205
|
+
{
|
|
23206
|
+
className: cn("h-full rounded-full transition-all", `bg-${variant === "default" ? "primary" : variant}`),
|
|
23207
|
+
style: { width: `${targetPct}%` }
|
|
23208
|
+
}
|
|
23209
|
+
) })
|
|
23179
23210
|
] }),
|
|
23180
23211
|
(ResolvedIcon || typeof iconProp !== "string" && iconProp) && /* @__PURE__ */ jsx(Box, { className: cn("p-3 rounded-md", iconBg), children: ResolvedIcon ? /* @__PURE__ */ jsx(ResolvedIcon, { className: cn(iconSizes2[size], iconColor) }) : iconProp })
|
|
23181
23212
|
] }) });
|
|
@@ -29431,7 +29462,7 @@ function getStatusStyle(fieldName, value) {
|
|
|
29431
29462
|
if (val.includes("low")) return STATUS_STYLES2.low;
|
|
29432
29463
|
return STATUS_STYLES2.default;
|
|
29433
29464
|
}
|
|
29434
|
-
function
|
|
29465
|
+
function formatValue3(value, fieldName) {
|
|
29435
29466
|
if (typeof value === "number") {
|
|
29436
29467
|
if (fieldName.toLowerCase().includes("progress") || fieldName.toLowerCase().includes("percent")) {
|
|
29437
29468
|
return `${value}%`;
|
|
@@ -29807,7 +29838,7 @@ var init_List = __esm({
|
|
|
29807
29838
|
className: "flex items-center gap-2 text-muted-foreground group-hover:text-foreground transition-colors",
|
|
29808
29839
|
children: [
|
|
29809
29840
|
/* @__PURE__ */ jsx(Calendar, { className: "w-3.5 h-3.5" }),
|
|
29810
|
-
/* @__PURE__ */ jsx(Typography, { as: "span", children:
|
|
29841
|
+
/* @__PURE__ */ jsx(Typography, { as: "span", children: formatValue3(value, field) })
|
|
29811
29842
|
]
|
|
29812
29843
|
},
|
|
29813
29844
|
field
|
|
@@ -29826,7 +29857,7 @@ var init_List = __esm({
|
|
|
29826
29857
|
formatFieldLabel2(field),
|
|
29827
29858
|
":"
|
|
29828
29859
|
] }),
|
|
29829
|
-
/* @__PURE__ */ jsx(Typography, { as: "span", className: "text-foreground", children:
|
|
29860
|
+
/* @__PURE__ */ jsx(Typography, { as: "span", className: "text-foreground", children: formatValue3(value, field) })
|
|
29830
29861
|
]
|
|
29831
29862
|
},
|
|
29832
29863
|
field
|
|
@@ -11,8 +11,16 @@ export interface StatDisplayProps {
|
|
|
11
11
|
label: string;
|
|
12
12
|
/** Primary value (number or formatted string) */
|
|
13
13
|
value: number | string;
|
|
14
|
-
/**
|
|
14
|
+
/** Optional denominator. >0 renders "value / max"; 0 or omitted hides the divider. */
|
|
15
15
|
max?: number;
|
|
16
|
+
/** Optional progress target. >0 renders a progress bar at value/target. */
|
|
17
|
+
target?: number;
|
|
18
|
+
/** Signed delta vs previous period. >0 renders ↑ green, <0 renders ↓ red, 0 hides. */
|
|
19
|
+
trend?: number;
|
|
20
|
+
/** Prefix prepended to the formatted value (e.g. "≈ "). */
|
|
21
|
+
prefix?: string;
|
|
22
|
+
/** Suffix appended to the formatted value (e.g. " /mo", " ms"). */
|
|
23
|
+
suffix?: string;
|
|
16
24
|
/** Lucide icon name or React node */
|
|
17
25
|
icon?: React.ReactNode;
|
|
18
26
|
/** Icon background color class */
|
|
@@ -13,8 +13,8 @@ export interface TabItem {
|
|
|
13
13
|
label: string;
|
|
14
14
|
/** Tab content - optional for event-driven tabs */
|
|
15
15
|
content?: React.ReactNode;
|
|
16
|
-
/** Tab icon */
|
|
17
|
-
icon?: LucideIcon;
|
|
16
|
+
/** Tab icon — pass either a Lucide component or its registry name (e.g. "file-text") */
|
|
17
|
+
icon?: LucideIcon | string;
|
|
18
18
|
/** Tab badge */
|
|
19
19
|
badge?: string | number;
|
|
20
20
|
/** Disable tab */
|
|
@@ -35,6 +35,8 @@ export interface TabsProps {
|
|
|
35
35
|
activeTab?: string;
|
|
36
36
|
/** Callback when tab changes */
|
|
37
37
|
onTabChange?: (tabId: string) => void;
|
|
38
|
+
/** Declarative tab change event — emits UI:{tabChangeEvent} with { tabId } */
|
|
39
|
+
tabChangeEvent?: string;
|
|
38
40
|
/** Tab variant */
|
|
39
41
|
variant?: 'default' | 'pills' | 'underline';
|
|
40
42
|
/** Tab orientation */
|
package/dist/providers/index.cjs
CHANGED
|
@@ -3539,7 +3539,7 @@ var init_RangeSlider = __esm({
|
|
|
3539
3539
|
action,
|
|
3540
3540
|
actionPayload,
|
|
3541
3541
|
onChange,
|
|
3542
|
-
formatValue:
|
|
3542
|
+
formatValue: formatValue4,
|
|
3543
3543
|
...props
|
|
3544
3544
|
}, ref) => {
|
|
3545
3545
|
const [isDragging, setIsDragging] = React115.useState(false);
|
|
@@ -3548,7 +3548,7 @@ var init_RangeSlider = __esm({
|
|
|
3548
3548
|
const eventBus = useSafeEventBus();
|
|
3549
3549
|
const percentage = max !== min ? (value - min) / (max - min) * 100 : 0;
|
|
3550
3550
|
const bufferedPercentage = buffered !== void 0 ? Math.min(buffered, 100) : void 0;
|
|
3551
|
-
const displayValue =
|
|
3551
|
+
const displayValue = formatValue4 ? formatValue4(value) : String(value);
|
|
3552
3552
|
const handleChange = React115.useCallback(
|
|
3553
3553
|
(e) => {
|
|
3554
3554
|
const newValue = Number(e.target.value);
|
|
@@ -17069,6 +17069,7 @@ var init_Tabs = __esm({
|
|
|
17069
17069
|
defaultActiveTab,
|
|
17070
17070
|
activeTab: controlledActiveTab,
|
|
17071
17071
|
onTabChange,
|
|
17072
|
+
tabChangeEvent,
|
|
17072
17073
|
variant = "default",
|
|
17073
17074
|
orientation = "horizontal",
|
|
17074
17075
|
className
|
|
@@ -17091,6 +17092,9 @@ var init_Tabs = __esm({
|
|
|
17091
17092
|
setInternalActiveTab(tabId);
|
|
17092
17093
|
}
|
|
17093
17094
|
onTabChange?.(tabId);
|
|
17095
|
+
if (tabChangeEvent) {
|
|
17096
|
+
eventBus.emit(`UI:${tabChangeEvent}`, { tabId });
|
|
17097
|
+
}
|
|
17094
17098
|
if (tabEvent) {
|
|
17095
17099
|
eventBus.emit(`UI:${tabEvent}`, { tabId });
|
|
17096
17100
|
}
|
|
@@ -17171,7 +17175,7 @@ var init_Tabs = __esm({
|
|
|
17171
17175
|
isActive ? variant === "pills" ? "text-primary-foreground font-bold" : "text-foreground font-bold" : "text-muted-foreground hover:text-foreground"
|
|
17172
17176
|
),
|
|
17173
17177
|
children: [
|
|
17174
|
-
item.icon && /* @__PURE__ */ jsxRuntime.jsx(Icon, { icon: item.icon, size: "sm" }),
|
|
17178
|
+
item.icon && (typeof item.icon === "string" ? /* @__PURE__ */ jsxRuntime.jsx(Icon, { name: item.icon, size: "sm" }) : /* @__PURE__ */ jsxRuntime.jsx(Icon, { icon: item.icon, size: "sm" })),
|
|
17175
17179
|
/* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "small", weight: isActive ? "semibold" : "normal", className: "!text-inherit", children: item.label }),
|
|
17176
17180
|
item.badge !== void 0 && /* @__PURE__ */ jsxRuntime.jsx(Badge, { variant: "default", size: "sm", children: item.badge })
|
|
17177
17181
|
]
|
|
@@ -24195,25 +24199,24 @@ var init_Lightbox = __esm({
|
|
|
24195
24199
|
Lightbox.displayName = "Lightbox";
|
|
24196
24200
|
}
|
|
24197
24201
|
});
|
|
24198
|
-
function
|
|
24202
|
+
function formatNumber(value, format) {
|
|
24199
24203
|
if (value == null) return "0";
|
|
24200
24204
|
const v = typeof value === "number" ? value : value;
|
|
24201
|
-
let formatted;
|
|
24202
24205
|
switch (format) {
|
|
24203
24206
|
case "currency":
|
|
24204
|
-
|
|
24205
|
-
break;
|
|
24207
|
+
return typeof v === "number" ? `$${v.toFixed(2)}` : String(v);
|
|
24206
24208
|
case "percent":
|
|
24207
|
-
|
|
24208
|
-
break;
|
|
24209
|
+
return typeof v === "number" ? `${Math.round(v)}%` : String(v);
|
|
24209
24210
|
case "number":
|
|
24210
|
-
|
|
24211
|
-
break;
|
|
24211
|
+
return typeof v === "number" ? v.toLocaleString() : String(v);
|
|
24212
24212
|
default:
|
|
24213
|
-
|
|
24213
|
+
return String(v);
|
|
24214
24214
|
}
|
|
24215
|
-
|
|
24216
|
-
|
|
24215
|
+
}
|
|
24216
|
+
function composeDisplayValue(value, format, max, prefix, suffix) {
|
|
24217
|
+
const formatted = formatNumber(value, format);
|
|
24218
|
+
const withMax = max != null && max > 0 ? `${formatted} / ${max}` : formatted;
|
|
24219
|
+
return `${prefix ?? ""}${withMax}${suffix ?? ""}`;
|
|
24217
24220
|
}
|
|
24218
24221
|
var variantColor, StatDisplay;
|
|
24219
24222
|
var init_StatDisplay = __esm({
|
|
@@ -24237,6 +24240,10 @@ var init_StatDisplay = __esm({
|
|
|
24237
24240
|
label,
|
|
24238
24241
|
value,
|
|
24239
24242
|
max,
|
|
24243
|
+
target,
|
|
24244
|
+
trend,
|
|
24245
|
+
prefix,
|
|
24246
|
+
suffix,
|
|
24240
24247
|
icon: iconProp,
|
|
24241
24248
|
iconBg = "bg-muted",
|
|
24242
24249
|
iconColor = "text-foreground",
|
|
@@ -24252,7 +24259,13 @@ var init_StatDisplay = __esm({
|
|
|
24252
24259
|
const iconSizes2 = { sm: "h-4 w-4", md: "h-5 w-5", lg: "h-6 w-6" };
|
|
24253
24260
|
const valueSizes = { sm: "text-lg", md: "text-2xl", lg: "text-3xl" };
|
|
24254
24261
|
const padSizes = { sm: "p-3", md: "p-4", lg: "p-6" };
|
|
24255
|
-
const displayValue =
|
|
24262
|
+
const displayValue = composeDisplayValue(value, format, max, prefix, suffix);
|
|
24263
|
+
const numericValue = typeof value === "number" ? value : Number(value);
|
|
24264
|
+
const showTarget = typeof target === "number" && target > 0 && Number.isFinite(numericValue);
|
|
24265
|
+
const targetPct = showTarget ? Math.max(0, Math.min(100, numericValue / target * 100)) : 0;
|
|
24266
|
+
const showTrend = typeof trend === "number" && trend !== 0 && Number.isFinite(trend);
|
|
24267
|
+
const trendUp = showTrend && trend > 0;
|
|
24268
|
+
const trendLabel = showTrend ? `${trendUp ? "\u2191" : "\u2193"} ${Math.abs(trend)}` : "";
|
|
24256
24269
|
if (error) {
|
|
24257
24270
|
return /* @__PURE__ */ jsxRuntime.jsx(Card, { className: cn(padSizes[size], className), children: /* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "small", color: "error", children: error.message }) });
|
|
24258
24271
|
}
|
|
@@ -24267,13 +24280,31 @@ var init_StatDisplay = __esm({
|
|
|
24267
24280
|
ResolvedIcon && /* @__PURE__ */ jsxRuntime.jsx(ResolvedIcon, { className: cn(iconSizes2[size], iconColor) }),
|
|
24268
24281
|
typeof iconProp !== "string" && iconProp,
|
|
24269
24282
|
/* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "caption", color: "secondary", children: label }),
|
|
24270
|
-
/* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue })
|
|
24283
|
+
/* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue }),
|
|
24284
|
+
showTrend && /* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "caption", className: cn("font-semibold", trendUp ? "text-success" : "text-error"), children: trendLabel })
|
|
24271
24285
|
] });
|
|
24272
24286
|
}
|
|
24273
24287
|
return /* @__PURE__ */ jsxRuntime.jsx(Card, { className: cn(padSizes[size], className), children: /* @__PURE__ */ jsxRuntime.jsxs(HStack, { align: "start", justify: "between", children: [
|
|
24274
|
-
/* @__PURE__ */ jsxRuntime.jsxs(VStack, { gap: "none", className: "space-y-1", children: [
|
|
24288
|
+
/* @__PURE__ */ jsxRuntime.jsxs(VStack, { gap: "none", className: "space-y-1 flex-1", children: [
|
|
24275
24289
|
/* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "overline", color: "secondary", children: label }),
|
|
24276
|
-
/* @__PURE__ */ jsxRuntime.
|
|
24290
|
+
/* @__PURE__ */ jsxRuntime.jsxs(HStack, { gap: "sm", align: "end", children: [
|
|
24291
|
+
/* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue }),
|
|
24292
|
+
showTrend && /* @__PURE__ */ jsxRuntime.jsx(
|
|
24293
|
+
Typography,
|
|
24294
|
+
{
|
|
24295
|
+
variant: "caption",
|
|
24296
|
+
className: cn("font-semibold pb-1", trendUp ? "text-success" : "text-error"),
|
|
24297
|
+
children: trendLabel
|
|
24298
|
+
}
|
|
24299
|
+
)
|
|
24300
|
+
] }),
|
|
24301
|
+
showTarget && /* @__PURE__ */ jsxRuntime.jsx(Box, { className: "mt-2 h-1.5 w-full bg-muted rounded-full overflow-hidden", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
24302
|
+
Box,
|
|
24303
|
+
{
|
|
24304
|
+
className: cn("h-full rounded-full transition-all", `bg-${variant === "default" ? "primary" : variant}`),
|
|
24305
|
+
style: { width: `${targetPct}%` }
|
|
24306
|
+
}
|
|
24307
|
+
) })
|
|
24277
24308
|
] }),
|
|
24278
24309
|
(ResolvedIcon || typeof iconProp !== "string" && iconProp) && /* @__PURE__ */ jsxRuntime.jsx(Box, { className: cn("p-3 rounded-md", iconBg), children: ResolvedIcon ? /* @__PURE__ */ jsxRuntime.jsx(ResolvedIcon, { className: cn(iconSizes2[size], iconColor) }) : iconProp })
|
|
24279
24310
|
] }) });
|
|
@@ -30434,7 +30465,7 @@ function getStatusStyle(fieldName, value) {
|
|
|
30434
30465
|
if (val.includes("low")) return STATUS_STYLES2.low;
|
|
30435
30466
|
return STATUS_STYLES2.default;
|
|
30436
30467
|
}
|
|
30437
|
-
function
|
|
30468
|
+
function formatValue3(value, fieldName) {
|
|
30438
30469
|
if (typeof value === "number") {
|
|
30439
30470
|
if (fieldName.toLowerCase().includes("progress") || fieldName.toLowerCase().includes("percent")) {
|
|
30440
30471
|
return `${value}%`;
|
|
@@ -30810,7 +30841,7 @@ var init_List = __esm({
|
|
|
30810
30841
|
className: "flex items-center gap-2 text-muted-foreground group-hover:text-foreground transition-colors",
|
|
30811
30842
|
children: [
|
|
30812
30843
|
/* @__PURE__ */ jsxRuntime.jsx(LucideIcons.Calendar, { className: "w-3.5 h-3.5" }),
|
|
30813
|
-
/* @__PURE__ */ jsxRuntime.jsx(Typography, { as: "span", children:
|
|
30844
|
+
/* @__PURE__ */ jsxRuntime.jsx(Typography, { as: "span", children: formatValue3(value, field) })
|
|
30814
30845
|
]
|
|
30815
30846
|
},
|
|
30816
30847
|
field
|
|
@@ -30829,7 +30860,7 @@ var init_List = __esm({
|
|
|
30829
30860
|
formatFieldLabel2(field),
|
|
30830
30861
|
":"
|
|
30831
30862
|
] }),
|
|
30832
|
-
/* @__PURE__ */ jsxRuntime.jsx(Typography, { as: "span", className: "text-foreground", children:
|
|
30863
|
+
/* @__PURE__ */ jsxRuntime.jsx(Typography, { as: "span", className: "text-foreground", children: formatValue3(value, field) })
|
|
30833
30864
|
]
|
|
30834
30865
|
},
|
|
30835
30866
|
field
|
package/dist/providers/index.js
CHANGED
|
@@ -3494,7 +3494,7 @@ var init_RangeSlider = __esm({
|
|
|
3494
3494
|
action,
|
|
3495
3495
|
actionPayload,
|
|
3496
3496
|
onChange,
|
|
3497
|
-
formatValue:
|
|
3497
|
+
formatValue: formatValue4,
|
|
3498
3498
|
...props
|
|
3499
3499
|
}, ref) => {
|
|
3500
3500
|
const [isDragging, setIsDragging] = useState(false);
|
|
@@ -3503,7 +3503,7 @@ var init_RangeSlider = __esm({
|
|
|
3503
3503
|
const eventBus = useSafeEventBus();
|
|
3504
3504
|
const percentage = max !== min ? (value - min) / (max - min) * 100 : 0;
|
|
3505
3505
|
const bufferedPercentage = buffered !== void 0 ? Math.min(buffered, 100) : void 0;
|
|
3506
|
-
const displayValue =
|
|
3506
|
+
const displayValue = formatValue4 ? formatValue4(value) : String(value);
|
|
3507
3507
|
const handleChange = useCallback(
|
|
3508
3508
|
(e) => {
|
|
3509
3509
|
const newValue = Number(e.target.value);
|
|
@@ -17024,6 +17024,7 @@ var init_Tabs = __esm({
|
|
|
17024
17024
|
defaultActiveTab,
|
|
17025
17025
|
activeTab: controlledActiveTab,
|
|
17026
17026
|
onTabChange,
|
|
17027
|
+
tabChangeEvent,
|
|
17027
17028
|
variant = "default",
|
|
17028
17029
|
orientation = "horizontal",
|
|
17029
17030
|
className
|
|
@@ -17046,6 +17047,9 @@ var init_Tabs = __esm({
|
|
|
17046
17047
|
setInternalActiveTab(tabId);
|
|
17047
17048
|
}
|
|
17048
17049
|
onTabChange?.(tabId);
|
|
17050
|
+
if (tabChangeEvent) {
|
|
17051
|
+
eventBus.emit(`UI:${tabChangeEvent}`, { tabId });
|
|
17052
|
+
}
|
|
17049
17053
|
if (tabEvent) {
|
|
17050
17054
|
eventBus.emit(`UI:${tabEvent}`, { tabId });
|
|
17051
17055
|
}
|
|
@@ -17126,7 +17130,7 @@ var init_Tabs = __esm({
|
|
|
17126
17130
|
isActive ? variant === "pills" ? "text-primary-foreground font-bold" : "text-foreground font-bold" : "text-muted-foreground hover:text-foreground"
|
|
17127
17131
|
),
|
|
17128
17132
|
children: [
|
|
17129
|
-
item.icon && /* @__PURE__ */ jsx(Icon, { icon: item.icon, size: "sm" }),
|
|
17133
|
+
item.icon && (typeof item.icon === "string" ? /* @__PURE__ */ jsx(Icon, { name: item.icon, size: "sm" }) : /* @__PURE__ */ jsx(Icon, { icon: item.icon, size: "sm" })),
|
|
17130
17134
|
/* @__PURE__ */ jsx(Typography, { variant: "small", weight: isActive ? "semibold" : "normal", className: "!text-inherit", children: item.label }),
|
|
17131
17135
|
item.badge !== void 0 && /* @__PURE__ */ jsx(Badge, { variant: "default", size: "sm", children: item.badge })
|
|
17132
17136
|
]
|
|
@@ -24150,25 +24154,24 @@ var init_Lightbox = __esm({
|
|
|
24150
24154
|
Lightbox.displayName = "Lightbox";
|
|
24151
24155
|
}
|
|
24152
24156
|
});
|
|
24153
|
-
function
|
|
24157
|
+
function formatNumber(value, format) {
|
|
24154
24158
|
if (value == null) return "0";
|
|
24155
24159
|
const v = typeof value === "number" ? value : value;
|
|
24156
|
-
let formatted;
|
|
24157
24160
|
switch (format) {
|
|
24158
24161
|
case "currency":
|
|
24159
|
-
|
|
24160
|
-
break;
|
|
24162
|
+
return typeof v === "number" ? `$${v.toFixed(2)}` : String(v);
|
|
24161
24163
|
case "percent":
|
|
24162
|
-
|
|
24163
|
-
break;
|
|
24164
|
+
return typeof v === "number" ? `${Math.round(v)}%` : String(v);
|
|
24164
24165
|
case "number":
|
|
24165
|
-
|
|
24166
|
-
break;
|
|
24166
|
+
return typeof v === "number" ? v.toLocaleString() : String(v);
|
|
24167
24167
|
default:
|
|
24168
|
-
|
|
24168
|
+
return String(v);
|
|
24169
24169
|
}
|
|
24170
|
-
|
|
24171
|
-
|
|
24170
|
+
}
|
|
24171
|
+
function composeDisplayValue(value, format, max, prefix, suffix) {
|
|
24172
|
+
const formatted = formatNumber(value, format);
|
|
24173
|
+
const withMax = max != null && max > 0 ? `${formatted} / ${max}` : formatted;
|
|
24174
|
+
return `${prefix ?? ""}${withMax}${suffix ?? ""}`;
|
|
24172
24175
|
}
|
|
24173
24176
|
var variantColor, StatDisplay;
|
|
24174
24177
|
var init_StatDisplay = __esm({
|
|
@@ -24192,6 +24195,10 @@ var init_StatDisplay = __esm({
|
|
|
24192
24195
|
label,
|
|
24193
24196
|
value,
|
|
24194
24197
|
max,
|
|
24198
|
+
target,
|
|
24199
|
+
trend,
|
|
24200
|
+
prefix,
|
|
24201
|
+
suffix,
|
|
24195
24202
|
icon: iconProp,
|
|
24196
24203
|
iconBg = "bg-muted",
|
|
24197
24204
|
iconColor = "text-foreground",
|
|
@@ -24207,7 +24214,13 @@ var init_StatDisplay = __esm({
|
|
|
24207
24214
|
const iconSizes2 = { sm: "h-4 w-4", md: "h-5 w-5", lg: "h-6 w-6" };
|
|
24208
24215
|
const valueSizes = { sm: "text-lg", md: "text-2xl", lg: "text-3xl" };
|
|
24209
24216
|
const padSizes = { sm: "p-3", md: "p-4", lg: "p-6" };
|
|
24210
|
-
const displayValue =
|
|
24217
|
+
const displayValue = composeDisplayValue(value, format, max, prefix, suffix);
|
|
24218
|
+
const numericValue = typeof value === "number" ? value : Number(value);
|
|
24219
|
+
const showTarget = typeof target === "number" && target > 0 && Number.isFinite(numericValue);
|
|
24220
|
+
const targetPct = showTarget ? Math.max(0, Math.min(100, numericValue / target * 100)) : 0;
|
|
24221
|
+
const showTrend = typeof trend === "number" && trend !== 0 && Number.isFinite(trend);
|
|
24222
|
+
const trendUp = showTrend && trend > 0;
|
|
24223
|
+
const trendLabel = showTrend ? `${trendUp ? "\u2191" : "\u2193"} ${Math.abs(trend)}` : "";
|
|
24211
24224
|
if (error) {
|
|
24212
24225
|
return /* @__PURE__ */ jsx(Card, { className: cn(padSizes[size], className), children: /* @__PURE__ */ jsx(Typography, { variant: "small", color: "error", children: error.message }) });
|
|
24213
24226
|
}
|
|
@@ -24222,13 +24235,31 @@ var init_StatDisplay = __esm({
|
|
|
24222
24235
|
ResolvedIcon && /* @__PURE__ */ jsx(ResolvedIcon, { className: cn(iconSizes2[size], iconColor) }),
|
|
24223
24236
|
typeof iconProp !== "string" && iconProp,
|
|
24224
24237
|
/* @__PURE__ */ jsx(Typography, { variant: "caption", color: "secondary", children: label }),
|
|
24225
|
-
/* @__PURE__ */ jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue })
|
|
24238
|
+
/* @__PURE__ */ jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue }),
|
|
24239
|
+
showTrend && /* @__PURE__ */ jsx(Typography, { variant: "caption", className: cn("font-semibold", trendUp ? "text-success" : "text-error"), children: trendLabel })
|
|
24226
24240
|
] });
|
|
24227
24241
|
}
|
|
24228
24242
|
return /* @__PURE__ */ jsx(Card, { className: cn(padSizes[size], className), children: /* @__PURE__ */ jsxs(HStack, { align: "start", justify: "between", children: [
|
|
24229
|
-
/* @__PURE__ */ jsxs(VStack, { gap: "none", className: "space-y-1", children: [
|
|
24243
|
+
/* @__PURE__ */ jsxs(VStack, { gap: "none", className: "space-y-1 flex-1", children: [
|
|
24230
24244
|
/* @__PURE__ */ jsx(Typography, { variant: "overline", color: "secondary", children: label }),
|
|
24231
|
-
/* @__PURE__ */
|
|
24245
|
+
/* @__PURE__ */ jsxs(HStack, { gap: "sm", align: "end", children: [
|
|
24246
|
+
/* @__PURE__ */ jsx(Typography, { variant: "h4", className: cn("font-bold", valueSizes[size], variantColor[variant]), children: displayValue }),
|
|
24247
|
+
showTrend && /* @__PURE__ */ jsx(
|
|
24248
|
+
Typography,
|
|
24249
|
+
{
|
|
24250
|
+
variant: "caption",
|
|
24251
|
+
className: cn("font-semibold pb-1", trendUp ? "text-success" : "text-error"),
|
|
24252
|
+
children: trendLabel
|
|
24253
|
+
}
|
|
24254
|
+
)
|
|
24255
|
+
] }),
|
|
24256
|
+
showTarget && /* @__PURE__ */ jsx(Box, { className: "mt-2 h-1.5 w-full bg-muted rounded-full overflow-hidden", children: /* @__PURE__ */ jsx(
|
|
24257
|
+
Box,
|
|
24258
|
+
{
|
|
24259
|
+
className: cn("h-full rounded-full transition-all", `bg-${variant === "default" ? "primary" : variant}`),
|
|
24260
|
+
style: { width: `${targetPct}%` }
|
|
24261
|
+
}
|
|
24262
|
+
) })
|
|
24232
24263
|
] }),
|
|
24233
24264
|
(ResolvedIcon || typeof iconProp !== "string" && iconProp) && /* @__PURE__ */ jsx(Box, { className: cn("p-3 rounded-md", iconBg), children: ResolvedIcon ? /* @__PURE__ */ jsx(ResolvedIcon, { className: cn(iconSizes2[size], iconColor) }) : iconProp })
|
|
24234
24265
|
] }) });
|
|
@@ -30389,7 +30420,7 @@ function getStatusStyle(fieldName, value) {
|
|
|
30389
30420
|
if (val.includes("low")) return STATUS_STYLES2.low;
|
|
30390
30421
|
return STATUS_STYLES2.default;
|
|
30391
30422
|
}
|
|
30392
|
-
function
|
|
30423
|
+
function formatValue3(value, fieldName) {
|
|
30393
30424
|
if (typeof value === "number") {
|
|
30394
30425
|
if (fieldName.toLowerCase().includes("progress") || fieldName.toLowerCase().includes("percent")) {
|
|
30395
30426
|
return `${value}%`;
|
|
@@ -30765,7 +30796,7 @@ var init_List = __esm({
|
|
|
30765
30796
|
className: "flex items-center gap-2 text-muted-foreground group-hover:text-foreground transition-colors",
|
|
30766
30797
|
children: [
|
|
30767
30798
|
/* @__PURE__ */ jsx(Calendar, { className: "w-3.5 h-3.5" }),
|
|
30768
|
-
/* @__PURE__ */ jsx(Typography, { as: "span", children:
|
|
30799
|
+
/* @__PURE__ */ jsx(Typography, { as: "span", children: formatValue3(value, field) })
|
|
30769
30800
|
]
|
|
30770
30801
|
},
|
|
30771
30802
|
field
|
|
@@ -30784,7 +30815,7 @@ var init_List = __esm({
|
|
|
30784
30815
|
formatFieldLabel2(field),
|
|
30785
30816
|
":"
|
|
30786
30817
|
] }),
|
|
30787
|
-
/* @__PURE__ */ jsx(Typography, { as: "span", className: "text-foreground", children:
|
|
30818
|
+
/* @__PURE__ */ jsx(Typography, { as: "span", className: "text-foreground", children: formatValue3(value, field) })
|
|
30788
30819
|
]
|
|
30789
30820
|
},
|
|
30790
30821
|
field
|