@trackunit/react-components 1.14.33 → 1.15.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/index.cjs.js +171 -171
- package/index.esm.js +171 -171
- package/package.json +5 -5
- package/src/components/KPICard/KPICard.d.ts +2 -2
- package/src/components/Menu/MoreMenu/MoreMenu.d.ts +3 -2
- package/src/components/PageHeader/types.d.ts +2 -2
- package/src/components/PreferenceCard/PreferenceCard.d.ts +1 -1
- package/src/components/Sidebar/Sidebar.d.ts +2 -1
- package/src/index.d.ts +47 -23
- package/src/components/Alert/index.d.ts +0 -1
- package/src/components/Badge/index.d.ts +0 -1
- package/src/components/Card/index.d.ts +0 -4
- package/src/components/Collapse/index.d.ts +0 -1
- package/src/components/CopyableText/index.d.ts +0 -1
- package/src/components/Heading/index.d.ts +0 -1
- package/src/components/Indicator/index.d.ts +0 -1
- package/src/components/Menu/index.d.ts +0 -5
- package/src/components/Notice/index.d.ts +0 -1
- package/src/components/Page/index.d.ts +0 -2
- package/src/components/PageHeader/components/index.d.ts +0 -3
- package/src/components/PageHeader/index.d.ts +0 -4
- package/src/components/Popover/index.d.ts +0 -5
- package/src/components/Prompt/index.d.ts +0 -1
- package/src/components/SectionHeader/index.d.ts +0 -1
- package/src/components/Skeleton/index.d.ts +0 -4
- package/src/components/SkeletonLines/index.d.ts +0 -2
- package/src/components/Spacer/index.d.ts +0 -1
- package/src/components/Spinner/index.d.ts +0 -1
- package/src/components/Tag/index.d.ts +0 -1
- package/src/components/Text/index.d.ts +0 -1
- package/src/components/Tooltip/index.d.ts +0 -1
- package/src/components/ValueBar/index.d.ts +0 -3
- package/src/components/buttons/index.d.ts +0 -4
package/index.cjs.js
CHANGED
|
@@ -905,16 +905,6 @@ const IconButton = ({ icon, size = "medium", square = true, loading = false, dis
|
|
|
905
905
|
};
|
|
906
906
|
IconButton.displayName = "IconButton";
|
|
907
907
|
|
|
908
|
-
/**
|
|
909
|
-
* The StarButton component is used for favorite actions or similar.
|
|
910
|
-
*
|
|
911
|
-
* @param {StarButtonProps} props - The props for the StarButton component
|
|
912
|
-
* @returns {ReactElement} StarButton component
|
|
913
|
-
*/
|
|
914
|
-
const StarButton = ({ starred, onClick }) => {
|
|
915
|
-
return (jsxRuntime.jsx("div", { "data-test-id": "starred-filter", onClick: onClick, children: jsxRuntime.jsx(Icon, { color: starred ? "primary" : "neutral", name: "Star", size: "medium" }) }));
|
|
916
|
-
};
|
|
917
|
-
|
|
918
908
|
const cvaAlert = cssClassVarianceUtilities.cvaMerge(["flex", "flex-col", "gap-3", "relative", "p-3", "rounded-lg", "@container"], {
|
|
919
909
|
variants: {
|
|
920
910
|
color: {
|
|
@@ -1416,6 +1406,16 @@ const BreadcrumbContainer = ({ "data-testid": dataTestId, breadcrumbItems, }) =>
|
|
|
1416
1406
|
return jsxRuntime.jsx(BreadcrumbForLargeScreen, { breadcrumbItems: breadcrumbItems, "data-testid": `largeScreen-${dataTestId}` });
|
|
1417
1407
|
};
|
|
1418
1408
|
|
|
1409
|
+
/**
|
|
1410
|
+
* The StarButton component is used for favorite actions or similar.
|
|
1411
|
+
*
|
|
1412
|
+
* @param {StarButtonProps} props - The props for the StarButton component
|
|
1413
|
+
* @returns {ReactElement} StarButton component
|
|
1414
|
+
*/
|
|
1415
|
+
const StarButton = ({ starred, onClick }) => {
|
|
1416
|
+
return (jsxRuntime.jsx("div", { "data-test-id": "starred-filter", onClick: onClick, children: jsxRuntime.jsx(Icon, { color: starred ? "primary" : "neutral", name: "Star", size: "medium" }) }));
|
|
1417
|
+
};
|
|
1418
|
+
|
|
1419
1419
|
const cvaCard = cssClassVarianceUtilities.cvaMerge([
|
|
1420
1420
|
"flex",
|
|
1421
1421
|
"border",
|
|
@@ -3955,16 +3955,6 @@ const PopoverContent = function PopoverContent({ className, "data-testid": dataT
|
|
|
3955
3955
|
}, ...context.getFloatingProps(props), children: typeof children === "function" ? children(() => context.setIsOpen(false)) : children }) })) : null }));
|
|
3956
3956
|
};
|
|
3957
3957
|
|
|
3958
|
-
/**
|
|
3959
|
-
* The PopoverTitle component.
|
|
3960
|
-
*
|
|
3961
|
-
* @param {PopoverTitleProps} props - The props for the PopoverTitle component
|
|
3962
|
-
* @returns {ReactElement} PopoverTitle component
|
|
3963
|
-
*/
|
|
3964
|
-
const PopoverTitle = ({ children, action, divider = false, className, "data-testid": dataTestId, }) => {
|
|
3965
|
-
return (jsxRuntime.jsxs("div", { className: cvaPopoverTitleContainer({ divider, className }), "data-testid": dataTestId, children: [jsxRuntime.jsx(Text, { className: cvaPopoverTitleText(), size: "small", subtle: true, type: "div", uppercase: true, weight: "bold", children: children }), action] }));
|
|
3966
|
-
};
|
|
3967
|
-
|
|
3968
3958
|
/**
|
|
3969
3959
|
* The PopoverTrigger component is used to trigger the popover.
|
|
3970
3960
|
*
|
|
@@ -4418,27 +4408,6 @@ const KPI = ({ title, value, unit, className, "data-testid": dataTestId, tooltip
|
|
|
4418
4408
|
return (jsxRuntime.jsx(Tooltip, { className: "min-w-8 shrink-0", "data-testid": dataTestId ? `${dataTestId}-tooltip` : undefined, disabled: tooltipLabel === undefined || tooltipLabel === "", label: tooltipLabel, placement: "bottom", children: jsxRuntime.jsxs("div", { className: cvaKPI({ variant, className }), "data-testid": dataTestId, style: style, ...rest, children: [jsxRuntime.jsx(Text, { className: tailwindMerge.twMerge("truncate", "whitespace-nowrap"), "data-testid": dataTestId ? `${dataTestId}-title` : undefined, size: isSmallVariant ? "small" : "medium", subtle: true, weight: isSmallVariant ? "normal" : "bold", children: title }), jsxRuntime.jsx("div", { className: tailwindMerge.twMerge("truncate", "whitespace-nowrap"), children: jsxRuntime.jsxs(Text, { className: "truncate whitespace-nowrap text-lg font-medium", "data-testid": dataTestId ? `${dataTestId}-value` : undefined, size: isSmallVariant ? "small" : "large", type: "div", weight: isSmallVariant ? "bold" : "thick", children: [value, " ", unit] }) })] }) }));
|
|
4419
4409
|
};
|
|
4420
4410
|
|
|
4421
|
-
/**
|
|
4422
|
-
* Display a single placeholder block for shape-based elements before data gets loaded to reduce load-time frustration.
|
|
4423
|
-
*
|
|
4424
|
-
* Fills the full height for images, badges, buttons, avatars, and other shape-based elements.
|
|
4425
|
-
* Uses numbers or CSS length values for height.
|
|
4426
|
-
*
|
|
4427
|
-
* For text content, use SkeletonLabel component instead.
|
|
4428
|
-
* For multiple text lines, use SkeletonLines component instead.
|
|
4429
|
-
*/
|
|
4430
|
-
const SkeletonBlock = react.memo((props) => {
|
|
4431
|
-
const { width = "100%", height = 16, flexibleWidth = false, className, "data-testid": dataTestId, children } = props;
|
|
4432
|
-
const widthValue = typeof width === "number" ? `${width}px` : width;
|
|
4433
|
-
const heightValue = typeof height === "number" ? `${height}px` : height;
|
|
4434
|
-
return (jsxRuntime.jsx("div", { "aria-label": "Loading", className: cvaSkeleton({ className }), "data-testid": dataTestId, role: "status", style: {
|
|
4435
|
-
width: flexibleWidth ? "100%" : widthValue,
|
|
4436
|
-
maxWidth: flexibleWidth ? widthValue : undefined,
|
|
4437
|
-
height: heightValue,
|
|
4438
|
-
}, children: children }));
|
|
4439
|
-
});
|
|
4440
|
-
SkeletonBlock.displayName = "SkeletonBlock";
|
|
4441
|
-
|
|
4442
4411
|
/**
|
|
4443
4412
|
* Generates a random width percentage string for skeleton loading components.
|
|
4444
4413
|
*
|
|
@@ -4452,136 +4421,6 @@ const getResponsiveRandomWidthPercentage = ({ min, max }) => {
|
|
|
4452
4421
|
return `${randomWidth}%`;
|
|
4453
4422
|
};
|
|
4454
4423
|
|
|
4455
|
-
/**
|
|
4456
|
-
* Preset configurations for common skeleton patterns.
|
|
4457
|
-
*/
|
|
4458
|
-
const PRESET_CONFIGURATIONS = {
|
|
4459
|
-
"short-paragraph": [
|
|
4460
|
-
{ textSize: "text-base", width: "100%" },
|
|
4461
|
-
{ textSize: "text-base", width: "100%" },
|
|
4462
|
-
{ textSize: "text-base", width: "60%" },
|
|
4463
|
-
],
|
|
4464
|
-
paragraph: [
|
|
4465
|
-
{ textSize: "text-base", width: "100%" },
|
|
4466
|
-
{ textSize: "text-base", width: "100%" },
|
|
4467
|
-
{ textSize: "text-base", width: "95%" },
|
|
4468
|
-
{ textSize: "text-base", width: "90%" },
|
|
4469
|
-
{ textSize: "text-base", width: "65%" },
|
|
4470
|
-
],
|
|
4471
|
-
"long-paragraph": [
|
|
4472
|
-
{ textSize: "text-base", width: "100%" },
|
|
4473
|
-
{ textSize: "text-base", width: "100%" },
|
|
4474
|
-
{ textSize: "text-base", width: "98%" },
|
|
4475
|
-
{ textSize: "text-base", width: "95%" },
|
|
4476
|
-
{ textSize: "text-base", width: "92%" },
|
|
4477
|
-
{ textSize: "text-base", width: "88%" },
|
|
4478
|
-
{ textSize: "text-base", width: "85%" },
|
|
4479
|
-
{ textSize: "text-base", width: "60%" },
|
|
4480
|
-
],
|
|
4481
|
-
"title-paragraph": [
|
|
4482
|
-
{ textSize: "text-2xl", width: "65%" },
|
|
4483
|
-
{ textSize: "text-base", width: "100%" },
|
|
4484
|
-
{ textSize: "text-base", width: "95%" },
|
|
4485
|
-
{ textSize: "text-base", width: "70%" },
|
|
4486
|
-
],
|
|
4487
|
-
"heading-text": [
|
|
4488
|
-
{ textSize: "text-xl", width: "60%" },
|
|
4489
|
-
{ textSize: "text-base", width: "100%" },
|
|
4490
|
-
{ textSize: "text-base", width: "100%" },
|
|
4491
|
-
{ textSize: "text-base", width: "90%" },
|
|
4492
|
-
{ textSize: "text-base", width: "65%" },
|
|
4493
|
-
],
|
|
4494
|
-
article: [
|
|
4495
|
-
{ textSize: "text-3xl", width: "70%" },
|
|
4496
|
-
{ textSize: "text-sm", width: "40%" },
|
|
4497
|
-
{ textSize: "text-base", width: "100%" },
|
|
4498
|
-
{ textSize: "text-base", width: "100%" },
|
|
4499
|
-
{ textSize: "text-base", width: "95%" },
|
|
4500
|
-
{ textSize: "text-base", width: "90%" },
|
|
4501
|
-
{ textSize: "text-base", width: "65%" },
|
|
4502
|
-
],
|
|
4503
|
-
};
|
|
4504
|
-
|
|
4505
|
-
const cvaSkeletonContainer = cssClassVarianceUtilities.cvaMerge(["flex", "flex-col"]);
|
|
4506
|
-
cssClassVarianceUtilities.cvaMerge([
|
|
4507
|
-
"relative",
|
|
4508
|
-
"overflow-hidden",
|
|
4509
|
-
"rounded-lg",
|
|
4510
|
-
// Gradient background
|
|
4511
|
-
"bg-gradient-to-r",
|
|
4512
|
-
"from-gray-200/80",
|
|
4513
|
-
"via-gray-300/60",
|
|
4514
|
-
"to-gray-200/80",
|
|
4515
|
-
// Pulse animation
|
|
4516
|
-
"animate-pulse",
|
|
4517
|
-
// Shimmer overlay
|
|
4518
|
-
"before:absolute",
|
|
4519
|
-
"before:inset-0",
|
|
4520
|
-
"before:bg-gradient-to-r",
|
|
4521
|
-
"before:from-transparent",
|
|
4522
|
-
"before:via-white/50",
|
|
4523
|
-
"before:to-transparent",
|
|
4524
|
-
"before:opacity-0",
|
|
4525
|
-
"before:animate-pulse",
|
|
4526
|
-
// Smooth transitions for accessibility
|
|
4527
|
-
"transition-all",
|
|
4528
|
-
"duration-300",
|
|
4529
|
-
"ease-in-out",
|
|
4530
|
-
]);
|
|
4531
|
-
|
|
4532
|
-
/**
|
|
4533
|
-
* Display multiple placeholder lines before data gets loaded to reduce load-time frustration.
|
|
4534
|
-
*
|
|
4535
|
-
* Supports three modes:
|
|
4536
|
-
* - **Uniform mode** (default): Display identical lines using `count` prop
|
|
4537
|
-
* - **Custom mode**: Display customized lines with per-line configuration using `variant="custom"` and `lines` prop
|
|
4538
|
-
* - **Preset mode**: Display common patterns using `variant="preset"` and `preset` name
|
|
4539
|
-
*
|
|
4540
|
-
* Built on top of the [SkeletonLabel](?path=/docs/components-loading-states-skeletonlabel--docs) component for text-specific margins and sizing.
|
|
4541
|
-
*
|
|
4542
|
-
* @example
|
|
4543
|
-
* // Uniform lines (simple mode)
|
|
4544
|
-
* <SkeletonLines count={3} textSize="text-base" variant="uniform" />
|
|
4545
|
-
* @example
|
|
4546
|
-
* // Custom lines (advanced mode)
|
|
4547
|
-
* <SkeletonLines
|
|
4548
|
-
* variant="custom"
|
|
4549
|
-
* lines={[
|
|
4550
|
-
* { textSize: "text-lg", width: "100%" },
|
|
4551
|
-
* { textSize: "text-base", width: "95%" },
|
|
4552
|
-
* { textSize: "text-base", width: "70%" }
|
|
4553
|
-
* ]}
|
|
4554
|
-
* />
|
|
4555
|
-
* @example
|
|
4556
|
-
* // Preset lines (quick patterns)
|
|
4557
|
-
* <SkeletonLines variant="preset" preset="title-paragraph" />
|
|
4558
|
-
*/
|
|
4559
|
-
const SkeletonLines = react.memo((props) => {
|
|
4560
|
-
const { className, "data-testid": dataTestId } = props;
|
|
4561
|
-
// Generate line configs based on variant
|
|
4562
|
-
let lineConfigs;
|
|
4563
|
-
if (props.variant === "preset") {
|
|
4564
|
-
// TypeScript now knows props is PresetSkeletonLinesProps
|
|
4565
|
-
lineConfigs = PRESET_CONFIGURATIONS[props.preset];
|
|
4566
|
-
}
|
|
4567
|
-
else if (props.variant === "custom") {
|
|
4568
|
-
// TypeScript now knows props is CustomSkeletonLinesProps
|
|
4569
|
-
lineConfigs = props.lines;
|
|
4570
|
-
}
|
|
4571
|
-
else {
|
|
4572
|
-
// TypeScript now knows props is UniformSkeletonLinesProps
|
|
4573
|
-
lineConfigs = Array.from({ length: props.count }, () => ({
|
|
4574
|
-
textSize: props.textSize,
|
|
4575
|
-
width: props.width,
|
|
4576
|
-
flexibleWidth: props.flexibleWidth,
|
|
4577
|
-
className: props.lineClassName,
|
|
4578
|
-
}));
|
|
4579
|
-
}
|
|
4580
|
-
const lineCount = lineConfigs.length;
|
|
4581
|
-
return (jsxRuntime.jsx("div", { "aria-label": `Loading ${lineCount} ${lineCount === 1 ? "item" : "items"}`, className: cvaSkeletonContainer({ className }), "data-testid": dataTestId, "data-variant": props.variant, role: "status", ...(props.variant === "preset" && { "data-preset": props.preset }), children: lineConfigs.map((config, index) => (jsxRuntime.jsx(SkeletonLabel, { className: config.className, "data-testid": dataTestId ? `${dataTestId}-${index}` : undefined, flexibleWidth: config.flexibleWidth ?? true, textSize: config.textSize ?? "text-base", width: config.width ?? "100%" }, index))) }));
|
|
4582
|
-
});
|
|
4583
|
-
SkeletonLines.displayName = "SkeletonLines";
|
|
4584
|
-
|
|
4585
4424
|
/**
|
|
4586
4425
|
* Skeleton loading indicator that mimics the KPI component structure.
|
|
4587
4426
|
* Uses the same layout, spacing, and visual hierarchy as KPI.
|
|
@@ -4828,6 +4667,27 @@ const KPICard = ({ isActive = false, onClick, className, "data-testid": dataTest
|
|
|
4828
4667
|
jsxRuntime.jsxs("div", { className: "flex items-center gap-1 truncate", "data-testid": dataTestId ? `${dataTestId}-notice` : undefined, children: [notice.iconName ? (jsxRuntime.jsx(Icon, { color: notice.iconColor, "data-testid": dataTestId ? `${dataTestId}-notice-icon` : undefined, name: notice.iconName, size: "small" })) : null, jsxRuntime.jsx(Text, { className: "truncate text-neutral-900", "data-testid": dataTestId ? `${dataTestId}-notice-label` : undefined, size: "small", children: notice.label })] })) : null, children] }) }));
|
|
4829
4668
|
};
|
|
4830
4669
|
|
|
4670
|
+
/**
|
|
4671
|
+
* Display a single placeholder block for shape-based elements before data gets loaded to reduce load-time frustration.
|
|
4672
|
+
*
|
|
4673
|
+
* Fills the full height for images, badges, buttons, avatars, and other shape-based elements.
|
|
4674
|
+
* Uses numbers or CSS length values for height.
|
|
4675
|
+
*
|
|
4676
|
+
* For text content, use SkeletonLabel component instead.
|
|
4677
|
+
* For multiple text lines, use SkeletonLines component instead.
|
|
4678
|
+
*/
|
|
4679
|
+
const SkeletonBlock = react.memo((props) => {
|
|
4680
|
+
const { width = "100%", height = 16, flexibleWidth = false, className, "data-testid": dataTestId, children } = props;
|
|
4681
|
+
const widthValue = typeof width === "number" ? `${width}px` : width;
|
|
4682
|
+
const heightValue = typeof height === "number" ? `${height}px` : height;
|
|
4683
|
+
return (jsxRuntime.jsx("div", { "aria-label": "Loading", className: cvaSkeleton({ className }), "data-testid": dataTestId, role: "status", style: {
|
|
4684
|
+
width: flexibleWidth ? "100%" : widthValue,
|
|
4685
|
+
maxWidth: flexibleWidth ? widthValue : undefined,
|
|
4686
|
+
height: heightValue,
|
|
4687
|
+
}, children: children }));
|
|
4688
|
+
});
|
|
4689
|
+
SkeletonBlock.displayName = "SkeletonBlock";
|
|
4690
|
+
|
|
4831
4691
|
/**
|
|
4832
4692
|
* Skeleton loading indicator that mimics the KPICard component structure.
|
|
4833
4693
|
* Uses the same layout, spacing, and visual hierarchy as KPICard.
|
|
@@ -5875,6 +5735,136 @@ const PageContent = ({ className, children, "data-testid": dataTestId, layout, }
|
|
|
5875
5735
|
return (jsxRuntime.jsx("div", { className: cvaPageContent({ className, layout }), "data-testid": dataTestId ? dataTestId : "page-content", children: children }));
|
|
5876
5736
|
};
|
|
5877
5737
|
|
|
5738
|
+
/**
|
|
5739
|
+
* Preset configurations for common skeleton patterns.
|
|
5740
|
+
*/
|
|
5741
|
+
const PRESET_CONFIGURATIONS = {
|
|
5742
|
+
"short-paragraph": [
|
|
5743
|
+
{ textSize: "text-base", width: "100%" },
|
|
5744
|
+
{ textSize: "text-base", width: "100%" },
|
|
5745
|
+
{ textSize: "text-base", width: "60%" },
|
|
5746
|
+
],
|
|
5747
|
+
paragraph: [
|
|
5748
|
+
{ textSize: "text-base", width: "100%" },
|
|
5749
|
+
{ textSize: "text-base", width: "100%" },
|
|
5750
|
+
{ textSize: "text-base", width: "95%" },
|
|
5751
|
+
{ textSize: "text-base", width: "90%" },
|
|
5752
|
+
{ textSize: "text-base", width: "65%" },
|
|
5753
|
+
],
|
|
5754
|
+
"long-paragraph": [
|
|
5755
|
+
{ textSize: "text-base", width: "100%" },
|
|
5756
|
+
{ textSize: "text-base", width: "100%" },
|
|
5757
|
+
{ textSize: "text-base", width: "98%" },
|
|
5758
|
+
{ textSize: "text-base", width: "95%" },
|
|
5759
|
+
{ textSize: "text-base", width: "92%" },
|
|
5760
|
+
{ textSize: "text-base", width: "88%" },
|
|
5761
|
+
{ textSize: "text-base", width: "85%" },
|
|
5762
|
+
{ textSize: "text-base", width: "60%" },
|
|
5763
|
+
],
|
|
5764
|
+
"title-paragraph": [
|
|
5765
|
+
{ textSize: "text-2xl", width: "65%" },
|
|
5766
|
+
{ textSize: "text-base", width: "100%" },
|
|
5767
|
+
{ textSize: "text-base", width: "95%" },
|
|
5768
|
+
{ textSize: "text-base", width: "70%" },
|
|
5769
|
+
],
|
|
5770
|
+
"heading-text": [
|
|
5771
|
+
{ textSize: "text-xl", width: "60%" },
|
|
5772
|
+
{ textSize: "text-base", width: "100%" },
|
|
5773
|
+
{ textSize: "text-base", width: "100%" },
|
|
5774
|
+
{ textSize: "text-base", width: "90%" },
|
|
5775
|
+
{ textSize: "text-base", width: "65%" },
|
|
5776
|
+
],
|
|
5777
|
+
article: [
|
|
5778
|
+
{ textSize: "text-3xl", width: "70%" },
|
|
5779
|
+
{ textSize: "text-sm", width: "40%" },
|
|
5780
|
+
{ textSize: "text-base", width: "100%" },
|
|
5781
|
+
{ textSize: "text-base", width: "100%" },
|
|
5782
|
+
{ textSize: "text-base", width: "95%" },
|
|
5783
|
+
{ textSize: "text-base", width: "90%" },
|
|
5784
|
+
{ textSize: "text-base", width: "65%" },
|
|
5785
|
+
],
|
|
5786
|
+
};
|
|
5787
|
+
|
|
5788
|
+
const cvaSkeletonContainer = cssClassVarianceUtilities.cvaMerge(["flex", "flex-col"]);
|
|
5789
|
+
cssClassVarianceUtilities.cvaMerge([
|
|
5790
|
+
"relative",
|
|
5791
|
+
"overflow-hidden",
|
|
5792
|
+
"rounded-lg",
|
|
5793
|
+
// Gradient background
|
|
5794
|
+
"bg-gradient-to-r",
|
|
5795
|
+
"from-gray-200/80",
|
|
5796
|
+
"via-gray-300/60",
|
|
5797
|
+
"to-gray-200/80",
|
|
5798
|
+
// Pulse animation
|
|
5799
|
+
"animate-pulse",
|
|
5800
|
+
// Shimmer overlay
|
|
5801
|
+
"before:absolute",
|
|
5802
|
+
"before:inset-0",
|
|
5803
|
+
"before:bg-gradient-to-r",
|
|
5804
|
+
"before:from-transparent",
|
|
5805
|
+
"before:via-white/50",
|
|
5806
|
+
"before:to-transparent",
|
|
5807
|
+
"before:opacity-0",
|
|
5808
|
+
"before:animate-pulse",
|
|
5809
|
+
// Smooth transitions for accessibility
|
|
5810
|
+
"transition-all",
|
|
5811
|
+
"duration-300",
|
|
5812
|
+
"ease-in-out",
|
|
5813
|
+
]);
|
|
5814
|
+
|
|
5815
|
+
/**
|
|
5816
|
+
* Display multiple placeholder lines before data gets loaded to reduce load-time frustration.
|
|
5817
|
+
*
|
|
5818
|
+
* Supports three modes:
|
|
5819
|
+
* - **Uniform mode** (default): Display identical lines using `count` prop
|
|
5820
|
+
* - **Custom mode**: Display customized lines with per-line configuration using `variant="custom"` and `lines` prop
|
|
5821
|
+
* - **Preset mode**: Display common patterns using `variant="preset"` and `preset` name
|
|
5822
|
+
*
|
|
5823
|
+
* Built on top of the [SkeletonLabel](?path=/docs/components-loading-states-skeletonlabel--docs) component for text-specific margins and sizing.
|
|
5824
|
+
*
|
|
5825
|
+
* @example
|
|
5826
|
+
* // Uniform lines (simple mode)
|
|
5827
|
+
* <SkeletonLines count={3} textSize="text-base" variant="uniform" />
|
|
5828
|
+
* @example
|
|
5829
|
+
* // Custom lines (advanced mode)
|
|
5830
|
+
* <SkeletonLines
|
|
5831
|
+
* variant="custom"
|
|
5832
|
+
* lines={[
|
|
5833
|
+
* { textSize: "text-lg", width: "100%" },
|
|
5834
|
+
* { textSize: "text-base", width: "95%" },
|
|
5835
|
+
* { textSize: "text-base", width: "70%" }
|
|
5836
|
+
* ]}
|
|
5837
|
+
* />
|
|
5838
|
+
* @example
|
|
5839
|
+
* // Preset lines (quick patterns)
|
|
5840
|
+
* <SkeletonLines variant="preset" preset="title-paragraph" />
|
|
5841
|
+
*/
|
|
5842
|
+
const SkeletonLines = react.memo((props) => {
|
|
5843
|
+
const { className, "data-testid": dataTestId } = props;
|
|
5844
|
+
// Generate line configs based on variant
|
|
5845
|
+
let lineConfigs;
|
|
5846
|
+
if (props.variant === "preset") {
|
|
5847
|
+
// TypeScript now knows props is PresetSkeletonLinesProps
|
|
5848
|
+
lineConfigs = PRESET_CONFIGURATIONS[props.preset];
|
|
5849
|
+
}
|
|
5850
|
+
else if (props.variant === "custom") {
|
|
5851
|
+
// TypeScript now knows props is CustomSkeletonLinesProps
|
|
5852
|
+
lineConfigs = props.lines;
|
|
5853
|
+
}
|
|
5854
|
+
else {
|
|
5855
|
+
// TypeScript now knows props is UniformSkeletonLinesProps
|
|
5856
|
+
lineConfigs = Array.from({ length: props.count }, () => ({
|
|
5857
|
+
textSize: props.textSize,
|
|
5858
|
+
width: props.width,
|
|
5859
|
+
flexibleWidth: props.flexibleWidth,
|
|
5860
|
+
className: props.lineClassName,
|
|
5861
|
+
}));
|
|
5862
|
+
}
|
|
5863
|
+
const lineCount = lineConfigs.length;
|
|
5864
|
+
return (jsxRuntime.jsx("div", { "aria-label": `Loading ${lineCount} ${lineCount === 1 ? "item" : "items"}`, className: cvaSkeletonContainer({ className }), "data-testid": dataTestId, "data-variant": props.variant, role: "status", ...(props.variant === "preset" && { "data-preset": props.preset }), children: lineConfigs.map((config, index) => (jsxRuntime.jsx(SkeletonLabel, { className: config.className, "data-testid": dataTestId ? `${dataTestId}-${index}` : undefined, flexibleWidth: config.flexibleWidth ?? true, textSize: config.textSize ?? "text-base", width: config.width ?? "100%" }, index))) }));
|
|
5865
|
+
});
|
|
5866
|
+
SkeletonLines.displayName = "SkeletonLines";
|
|
5867
|
+
|
|
5878
5868
|
const LoadingContent = () => (jsxRuntime.jsx("div", { className: "flex flex-row items-center", "data-testid": "kpi-card-loading-content", children: jsxRuntime.jsx("div", { className: "w-full", children: jsxRuntime.jsx(SkeletonLines, { lines: [
|
|
5879
5869
|
{ textSize: "text-xs", width: 50 },
|
|
5880
5870
|
{ textSize: "text-lg", width: 40 },
|
|
@@ -6199,6 +6189,16 @@ const Polygon = ({ points, size, color = "black", opaque = true, className, "dat
|
|
|
6199
6189
|
};
|
|
6200
6190
|
const normalize = ({ value, min, max, size }) => ((value - min) / (max - min)) * size;
|
|
6201
6191
|
|
|
6192
|
+
/**
|
|
6193
|
+
* The PopoverTitle component.
|
|
6194
|
+
*
|
|
6195
|
+
* @param {PopoverTitleProps} props - The props for the PopoverTitle component
|
|
6196
|
+
* @returns {ReactElement} PopoverTitle component
|
|
6197
|
+
*/
|
|
6198
|
+
const PopoverTitle = ({ children, action, divider = false, className, "data-testid": dataTestId, }) => {
|
|
6199
|
+
return (jsxRuntime.jsxs("div", { className: cvaPopoverTitleContainer({ divider, className }), "data-testid": dataTestId, children: [jsxRuntime.jsx(Text, { className: cvaPopoverTitleText(), size: "small", subtle: true, type: "div", uppercase: true, weight: "bold", children: children }), action] }));
|
|
6200
|
+
};
|
|
6201
|
+
|
|
6202
6202
|
const cvaPreferenceCard = cssClassVarianceUtilities.cvaMerge([
|
|
6203
6203
|
"rounded-lg",
|
|
6204
6204
|
"border",
|
package/index.esm.js
CHANGED
|
@@ -903,16 +903,6 @@ const IconButton = ({ icon, size = "medium", square = true, loading = false, dis
|
|
|
903
903
|
};
|
|
904
904
|
IconButton.displayName = "IconButton";
|
|
905
905
|
|
|
906
|
-
/**
|
|
907
|
-
* The StarButton component is used for favorite actions or similar.
|
|
908
|
-
*
|
|
909
|
-
* @param {StarButtonProps} props - The props for the StarButton component
|
|
910
|
-
* @returns {ReactElement} StarButton component
|
|
911
|
-
*/
|
|
912
|
-
const StarButton = ({ starred, onClick }) => {
|
|
913
|
-
return (jsx("div", { "data-test-id": "starred-filter", onClick: onClick, children: jsx(Icon, { color: starred ? "primary" : "neutral", name: "Star", size: "medium" }) }));
|
|
914
|
-
};
|
|
915
|
-
|
|
916
906
|
const cvaAlert = cvaMerge(["flex", "flex-col", "gap-3", "relative", "p-3", "rounded-lg", "@container"], {
|
|
917
907
|
variants: {
|
|
918
908
|
color: {
|
|
@@ -1414,6 +1404,16 @@ const BreadcrumbContainer = ({ "data-testid": dataTestId, breadcrumbItems, }) =>
|
|
|
1414
1404
|
return jsx(BreadcrumbForLargeScreen, { breadcrumbItems: breadcrumbItems, "data-testid": `largeScreen-${dataTestId}` });
|
|
1415
1405
|
};
|
|
1416
1406
|
|
|
1407
|
+
/**
|
|
1408
|
+
* The StarButton component is used for favorite actions or similar.
|
|
1409
|
+
*
|
|
1410
|
+
* @param {StarButtonProps} props - The props for the StarButton component
|
|
1411
|
+
* @returns {ReactElement} StarButton component
|
|
1412
|
+
*/
|
|
1413
|
+
const StarButton = ({ starred, onClick }) => {
|
|
1414
|
+
return (jsx("div", { "data-test-id": "starred-filter", onClick: onClick, children: jsx(Icon, { color: starred ? "primary" : "neutral", name: "Star", size: "medium" }) }));
|
|
1415
|
+
};
|
|
1416
|
+
|
|
1417
1417
|
const cvaCard = cvaMerge([
|
|
1418
1418
|
"flex",
|
|
1419
1419
|
"border",
|
|
@@ -3953,16 +3953,6 @@ const PopoverContent = function PopoverContent({ className, "data-testid": dataT
|
|
|
3953
3953
|
}, ...context.getFloatingProps(props), children: typeof children === "function" ? children(() => context.setIsOpen(false)) : children }) })) : null }));
|
|
3954
3954
|
};
|
|
3955
3955
|
|
|
3956
|
-
/**
|
|
3957
|
-
* The PopoverTitle component.
|
|
3958
|
-
*
|
|
3959
|
-
* @param {PopoverTitleProps} props - The props for the PopoverTitle component
|
|
3960
|
-
* @returns {ReactElement} PopoverTitle component
|
|
3961
|
-
*/
|
|
3962
|
-
const PopoverTitle = ({ children, action, divider = false, className, "data-testid": dataTestId, }) => {
|
|
3963
|
-
return (jsxs("div", { className: cvaPopoverTitleContainer({ divider, className }), "data-testid": dataTestId, children: [jsx(Text, { className: cvaPopoverTitleText(), size: "small", subtle: true, type: "div", uppercase: true, weight: "bold", children: children }), action] }));
|
|
3964
|
-
};
|
|
3965
|
-
|
|
3966
3956
|
/**
|
|
3967
3957
|
* The PopoverTrigger component is used to trigger the popover.
|
|
3968
3958
|
*
|
|
@@ -4416,27 +4406,6 @@ const KPI = ({ title, value, unit, className, "data-testid": dataTestId, tooltip
|
|
|
4416
4406
|
return (jsx(Tooltip, { className: "min-w-8 shrink-0", "data-testid": dataTestId ? `${dataTestId}-tooltip` : undefined, disabled: tooltipLabel === undefined || tooltipLabel === "", label: tooltipLabel, placement: "bottom", children: jsxs("div", { className: cvaKPI({ variant, className }), "data-testid": dataTestId, style: style, ...rest, children: [jsx(Text, { className: twMerge("truncate", "whitespace-nowrap"), "data-testid": dataTestId ? `${dataTestId}-title` : undefined, size: isSmallVariant ? "small" : "medium", subtle: true, weight: isSmallVariant ? "normal" : "bold", children: title }), jsx("div", { className: twMerge("truncate", "whitespace-nowrap"), children: jsxs(Text, { className: "truncate whitespace-nowrap text-lg font-medium", "data-testid": dataTestId ? `${dataTestId}-value` : undefined, size: isSmallVariant ? "small" : "large", type: "div", weight: isSmallVariant ? "bold" : "thick", children: [value, " ", unit] }) })] }) }));
|
|
4417
4407
|
};
|
|
4418
4408
|
|
|
4419
|
-
/**
|
|
4420
|
-
* Display a single placeholder block for shape-based elements before data gets loaded to reduce load-time frustration.
|
|
4421
|
-
*
|
|
4422
|
-
* Fills the full height for images, badges, buttons, avatars, and other shape-based elements.
|
|
4423
|
-
* Uses numbers or CSS length values for height.
|
|
4424
|
-
*
|
|
4425
|
-
* For text content, use SkeletonLabel component instead.
|
|
4426
|
-
* For multiple text lines, use SkeletonLines component instead.
|
|
4427
|
-
*/
|
|
4428
|
-
const SkeletonBlock = memo((props) => {
|
|
4429
|
-
const { width = "100%", height = 16, flexibleWidth = false, className, "data-testid": dataTestId, children } = props;
|
|
4430
|
-
const widthValue = typeof width === "number" ? `${width}px` : width;
|
|
4431
|
-
const heightValue = typeof height === "number" ? `${height}px` : height;
|
|
4432
|
-
return (jsx("div", { "aria-label": "Loading", className: cvaSkeleton({ className }), "data-testid": dataTestId, role: "status", style: {
|
|
4433
|
-
width: flexibleWidth ? "100%" : widthValue,
|
|
4434
|
-
maxWidth: flexibleWidth ? widthValue : undefined,
|
|
4435
|
-
height: heightValue,
|
|
4436
|
-
}, children: children }));
|
|
4437
|
-
});
|
|
4438
|
-
SkeletonBlock.displayName = "SkeletonBlock";
|
|
4439
|
-
|
|
4440
4409
|
/**
|
|
4441
4410
|
* Generates a random width percentage string for skeleton loading components.
|
|
4442
4411
|
*
|
|
@@ -4450,136 +4419,6 @@ const getResponsiveRandomWidthPercentage = ({ min, max }) => {
|
|
|
4450
4419
|
return `${randomWidth}%`;
|
|
4451
4420
|
};
|
|
4452
4421
|
|
|
4453
|
-
/**
|
|
4454
|
-
* Preset configurations for common skeleton patterns.
|
|
4455
|
-
*/
|
|
4456
|
-
const PRESET_CONFIGURATIONS = {
|
|
4457
|
-
"short-paragraph": [
|
|
4458
|
-
{ textSize: "text-base", width: "100%" },
|
|
4459
|
-
{ textSize: "text-base", width: "100%" },
|
|
4460
|
-
{ textSize: "text-base", width: "60%" },
|
|
4461
|
-
],
|
|
4462
|
-
paragraph: [
|
|
4463
|
-
{ textSize: "text-base", width: "100%" },
|
|
4464
|
-
{ textSize: "text-base", width: "100%" },
|
|
4465
|
-
{ textSize: "text-base", width: "95%" },
|
|
4466
|
-
{ textSize: "text-base", width: "90%" },
|
|
4467
|
-
{ textSize: "text-base", width: "65%" },
|
|
4468
|
-
],
|
|
4469
|
-
"long-paragraph": [
|
|
4470
|
-
{ textSize: "text-base", width: "100%" },
|
|
4471
|
-
{ textSize: "text-base", width: "100%" },
|
|
4472
|
-
{ textSize: "text-base", width: "98%" },
|
|
4473
|
-
{ textSize: "text-base", width: "95%" },
|
|
4474
|
-
{ textSize: "text-base", width: "92%" },
|
|
4475
|
-
{ textSize: "text-base", width: "88%" },
|
|
4476
|
-
{ textSize: "text-base", width: "85%" },
|
|
4477
|
-
{ textSize: "text-base", width: "60%" },
|
|
4478
|
-
],
|
|
4479
|
-
"title-paragraph": [
|
|
4480
|
-
{ textSize: "text-2xl", width: "65%" },
|
|
4481
|
-
{ textSize: "text-base", width: "100%" },
|
|
4482
|
-
{ textSize: "text-base", width: "95%" },
|
|
4483
|
-
{ textSize: "text-base", width: "70%" },
|
|
4484
|
-
],
|
|
4485
|
-
"heading-text": [
|
|
4486
|
-
{ textSize: "text-xl", width: "60%" },
|
|
4487
|
-
{ textSize: "text-base", width: "100%" },
|
|
4488
|
-
{ textSize: "text-base", width: "100%" },
|
|
4489
|
-
{ textSize: "text-base", width: "90%" },
|
|
4490
|
-
{ textSize: "text-base", width: "65%" },
|
|
4491
|
-
],
|
|
4492
|
-
article: [
|
|
4493
|
-
{ textSize: "text-3xl", width: "70%" },
|
|
4494
|
-
{ textSize: "text-sm", width: "40%" },
|
|
4495
|
-
{ textSize: "text-base", width: "100%" },
|
|
4496
|
-
{ textSize: "text-base", width: "100%" },
|
|
4497
|
-
{ textSize: "text-base", width: "95%" },
|
|
4498
|
-
{ textSize: "text-base", width: "90%" },
|
|
4499
|
-
{ textSize: "text-base", width: "65%" },
|
|
4500
|
-
],
|
|
4501
|
-
};
|
|
4502
|
-
|
|
4503
|
-
const cvaSkeletonContainer = cvaMerge(["flex", "flex-col"]);
|
|
4504
|
-
cvaMerge([
|
|
4505
|
-
"relative",
|
|
4506
|
-
"overflow-hidden",
|
|
4507
|
-
"rounded-lg",
|
|
4508
|
-
// Gradient background
|
|
4509
|
-
"bg-gradient-to-r",
|
|
4510
|
-
"from-gray-200/80",
|
|
4511
|
-
"via-gray-300/60",
|
|
4512
|
-
"to-gray-200/80",
|
|
4513
|
-
// Pulse animation
|
|
4514
|
-
"animate-pulse",
|
|
4515
|
-
// Shimmer overlay
|
|
4516
|
-
"before:absolute",
|
|
4517
|
-
"before:inset-0",
|
|
4518
|
-
"before:bg-gradient-to-r",
|
|
4519
|
-
"before:from-transparent",
|
|
4520
|
-
"before:via-white/50",
|
|
4521
|
-
"before:to-transparent",
|
|
4522
|
-
"before:opacity-0",
|
|
4523
|
-
"before:animate-pulse",
|
|
4524
|
-
// Smooth transitions for accessibility
|
|
4525
|
-
"transition-all",
|
|
4526
|
-
"duration-300",
|
|
4527
|
-
"ease-in-out",
|
|
4528
|
-
]);
|
|
4529
|
-
|
|
4530
|
-
/**
|
|
4531
|
-
* Display multiple placeholder lines before data gets loaded to reduce load-time frustration.
|
|
4532
|
-
*
|
|
4533
|
-
* Supports three modes:
|
|
4534
|
-
* - **Uniform mode** (default): Display identical lines using `count` prop
|
|
4535
|
-
* - **Custom mode**: Display customized lines with per-line configuration using `variant="custom"` and `lines` prop
|
|
4536
|
-
* - **Preset mode**: Display common patterns using `variant="preset"` and `preset` name
|
|
4537
|
-
*
|
|
4538
|
-
* Built on top of the [SkeletonLabel](?path=/docs/components-loading-states-skeletonlabel--docs) component for text-specific margins and sizing.
|
|
4539
|
-
*
|
|
4540
|
-
* @example
|
|
4541
|
-
* // Uniform lines (simple mode)
|
|
4542
|
-
* <SkeletonLines count={3} textSize="text-base" variant="uniform" />
|
|
4543
|
-
* @example
|
|
4544
|
-
* // Custom lines (advanced mode)
|
|
4545
|
-
* <SkeletonLines
|
|
4546
|
-
* variant="custom"
|
|
4547
|
-
* lines={[
|
|
4548
|
-
* { textSize: "text-lg", width: "100%" },
|
|
4549
|
-
* { textSize: "text-base", width: "95%" },
|
|
4550
|
-
* { textSize: "text-base", width: "70%" }
|
|
4551
|
-
* ]}
|
|
4552
|
-
* />
|
|
4553
|
-
* @example
|
|
4554
|
-
* // Preset lines (quick patterns)
|
|
4555
|
-
* <SkeletonLines variant="preset" preset="title-paragraph" />
|
|
4556
|
-
*/
|
|
4557
|
-
const SkeletonLines = memo((props) => {
|
|
4558
|
-
const { className, "data-testid": dataTestId } = props;
|
|
4559
|
-
// Generate line configs based on variant
|
|
4560
|
-
let lineConfigs;
|
|
4561
|
-
if (props.variant === "preset") {
|
|
4562
|
-
// TypeScript now knows props is PresetSkeletonLinesProps
|
|
4563
|
-
lineConfigs = PRESET_CONFIGURATIONS[props.preset];
|
|
4564
|
-
}
|
|
4565
|
-
else if (props.variant === "custom") {
|
|
4566
|
-
// TypeScript now knows props is CustomSkeletonLinesProps
|
|
4567
|
-
lineConfigs = props.lines;
|
|
4568
|
-
}
|
|
4569
|
-
else {
|
|
4570
|
-
// TypeScript now knows props is UniformSkeletonLinesProps
|
|
4571
|
-
lineConfigs = Array.from({ length: props.count }, () => ({
|
|
4572
|
-
textSize: props.textSize,
|
|
4573
|
-
width: props.width,
|
|
4574
|
-
flexibleWidth: props.flexibleWidth,
|
|
4575
|
-
className: props.lineClassName,
|
|
4576
|
-
}));
|
|
4577
|
-
}
|
|
4578
|
-
const lineCount = lineConfigs.length;
|
|
4579
|
-
return (jsx("div", { "aria-label": `Loading ${lineCount} ${lineCount === 1 ? "item" : "items"}`, className: cvaSkeletonContainer({ className }), "data-testid": dataTestId, "data-variant": props.variant, role: "status", ...(props.variant === "preset" && { "data-preset": props.preset }), children: lineConfigs.map((config, index) => (jsx(SkeletonLabel, { className: config.className, "data-testid": dataTestId ? `${dataTestId}-${index}` : undefined, flexibleWidth: config.flexibleWidth ?? true, textSize: config.textSize ?? "text-base", width: config.width ?? "100%" }, index))) }));
|
|
4580
|
-
});
|
|
4581
|
-
SkeletonLines.displayName = "SkeletonLines";
|
|
4582
|
-
|
|
4583
4422
|
/**
|
|
4584
4423
|
* Skeleton loading indicator that mimics the KPI component structure.
|
|
4585
4424
|
* Uses the same layout, spacing, and visual hierarchy as KPI.
|
|
@@ -4826,6 +4665,27 @@ const KPICard = ({ isActive = false, onClick, className, "data-testid": dataTest
|
|
|
4826
4665
|
jsxs("div", { className: "flex items-center gap-1 truncate", "data-testid": dataTestId ? `${dataTestId}-notice` : undefined, children: [notice.iconName ? (jsx(Icon, { color: notice.iconColor, "data-testid": dataTestId ? `${dataTestId}-notice-icon` : undefined, name: notice.iconName, size: "small" })) : null, jsx(Text, { className: "truncate text-neutral-900", "data-testid": dataTestId ? `${dataTestId}-notice-label` : undefined, size: "small", children: notice.label })] })) : null, children] }) }));
|
|
4827
4666
|
};
|
|
4828
4667
|
|
|
4668
|
+
/**
|
|
4669
|
+
* Display a single placeholder block for shape-based elements before data gets loaded to reduce load-time frustration.
|
|
4670
|
+
*
|
|
4671
|
+
* Fills the full height for images, badges, buttons, avatars, and other shape-based elements.
|
|
4672
|
+
* Uses numbers or CSS length values for height.
|
|
4673
|
+
*
|
|
4674
|
+
* For text content, use SkeletonLabel component instead.
|
|
4675
|
+
* For multiple text lines, use SkeletonLines component instead.
|
|
4676
|
+
*/
|
|
4677
|
+
const SkeletonBlock = memo((props) => {
|
|
4678
|
+
const { width = "100%", height = 16, flexibleWidth = false, className, "data-testid": dataTestId, children } = props;
|
|
4679
|
+
const widthValue = typeof width === "number" ? `${width}px` : width;
|
|
4680
|
+
const heightValue = typeof height === "number" ? `${height}px` : height;
|
|
4681
|
+
return (jsx("div", { "aria-label": "Loading", className: cvaSkeleton({ className }), "data-testid": dataTestId, role: "status", style: {
|
|
4682
|
+
width: flexibleWidth ? "100%" : widthValue,
|
|
4683
|
+
maxWidth: flexibleWidth ? widthValue : undefined,
|
|
4684
|
+
height: heightValue,
|
|
4685
|
+
}, children: children }));
|
|
4686
|
+
});
|
|
4687
|
+
SkeletonBlock.displayName = "SkeletonBlock";
|
|
4688
|
+
|
|
4829
4689
|
/**
|
|
4830
4690
|
* Skeleton loading indicator that mimics the KPICard component structure.
|
|
4831
4691
|
* Uses the same layout, spacing, and visual hierarchy as KPICard.
|
|
@@ -5873,6 +5733,136 @@ const PageContent = ({ className, children, "data-testid": dataTestId, layout, }
|
|
|
5873
5733
|
return (jsx("div", { className: cvaPageContent({ className, layout }), "data-testid": dataTestId ? dataTestId : "page-content", children: children }));
|
|
5874
5734
|
};
|
|
5875
5735
|
|
|
5736
|
+
/**
|
|
5737
|
+
* Preset configurations for common skeleton patterns.
|
|
5738
|
+
*/
|
|
5739
|
+
const PRESET_CONFIGURATIONS = {
|
|
5740
|
+
"short-paragraph": [
|
|
5741
|
+
{ textSize: "text-base", width: "100%" },
|
|
5742
|
+
{ textSize: "text-base", width: "100%" },
|
|
5743
|
+
{ textSize: "text-base", width: "60%" },
|
|
5744
|
+
],
|
|
5745
|
+
paragraph: [
|
|
5746
|
+
{ textSize: "text-base", width: "100%" },
|
|
5747
|
+
{ textSize: "text-base", width: "100%" },
|
|
5748
|
+
{ textSize: "text-base", width: "95%" },
|
|
5749
|
+
{ textSize: "text-base", width: "90%" },
|
|
5750
|
+
{ textSize: "text-base", width: "65%" },
|
|
5751
|
+
],
|
|
5752
|
+
"long-paragraph": [
|
|
5753
|
+
{ textSize: "text-base", width: "100%" },
|
|
5754
|
+
{ textSize: "text-base", width: "100%" },
|
|
5755
|
+
{ textSize: "text-base", width: "98%" },
|
|
5756
|
+
{ textSize: "text-base", width: "95%" },
|
|
5757
|
+
{ textSize: "text-base", width: "92%" },
|
|
5758
|
+
{ textSize: "text-base", width: "88%" },
|
|
5759
|
+
{ textSize: "text-base", width: "85%" },
|
|
5760
|
+
{ textSize: "text-base", width: "60%" },
|
|
5761
|
+
],
|
|
5762
|
+
"title-paragraph": [
|
|
5763
|
+
{ textSize: "text-2xl", width: "65%" },
|
|
5764
|
+
{ textSize: "text-base", width: "100%" },
|
|
5765
|
+
{ textSize: "text-base", width: "95%" },
|
|
5766
|
+
{ textSize: "text-base", width: "70%" },
|
|
5767
|
+
],
|
|
5768
|
+
"heading-text": [
|
|
5769
|
+
{ textSize: "text-xl", width: "60%" },
|
|
5770
|
+
{ textSize: "text-base", width: "100%" },
|
|
5771
|
+
{ textSize: "text-base", width: "100%" },
|
|
5772
|
+
{ textSize: "text-base", width: "90%" },
|
|
5773
|
+
{ textSize: "text-base", width: "65%" },
|
|
5774
|
+
],
|
|
5775
|
+
article: [
|
|
5776
|
+
{ textSize: "text-3xl", width: "70%" },
|
|
5777
|
+
{ textSize: "text-sm", width: "40%" },
|
|
5778
|
+
{ textSize: "text-base", width: "100%" },
|
|
5779
|
+
{ textSize: "text-base", width: "100%" },
|
|
5780
|
+
{ textSize: "text-base", width: "95%" },
|
|
5781
|
+
{ textSize: "text-base", width: "90%" },
|
|
5782
|
+
{ textSize: "text-base", width: "65%" },
|
|
5783
|
+
],
|
|
5784
|
+
};
|
|
5785
|
+
|
|
5786
|
+
const cvaSkeletonContainer = cvaMerge(["flex", "flex-col"]);
|
|
5787
|
+
cvaMerge([
|
|
5788
|
+
"relative",
|
|
5789
|
+
"overflow-hidden",
|
|
5790
|
+
"rounded-lg",
|
|
5791
|
+
// Gradient background
|
|
5792
|
+
"bg-gradient-to-r",
|
|
5793
|
+
"from-gray-200/80",
|
|
5794
|
+
"via-gray-300/60",
|
|
5795
|
+
"to-gray-200/80",
|
|
5796
|
+
// Pulse animation
|
|
5797
|
+
"animate-pulse",
|
|
5798
|
+
// Shimmer overlay
|
|
5799
|
+
"before:absolute",
|
|
5800
|
+
"before:inset-0",
|
|
5801
|
+
"before:bg-gradient-to-r",
|
|
5802
|
+
"before:from-transparent",
|
|
5803
|
+
"before:via-white/50",
|
|
5804
|
+
"before:to-transparent",
|
|
5805
|
+
"before:opacity-0",
|
|
5806
|
+
"before:animate-pulse",
|
|
5807
|
+
// Smooth transitions for accessibility
|
|
5808
|
+
"transition-all",
|
|
5809
|
+
"duration-300",
|
|
5810
|
+
"ease-in-out",
|
|
5811
|
+
]);
|
|
5812
|
+
|
|
5813
|
+
/**
|
|
5814
|
+
* Display multiple placeholder lines before data gets loaded to reduce load-time frustration.
|
|
5815
|
+
*
|
|
5816
|
+
* Supports three modes:
|
|
5817
|
+
* - **Uniform mode** (default): Display identical lines using `count` prop
|
|
5818
|
+
* - **Custom mode**: Display customized lines with per-line configuration using `variant="custom"` and `lines` prop
|
|
5819
|
+
* - **Preset mode**: Display common patterns using `variant="preset"` and `preset` name
|
|
5820
|
+
*
|
|
5821
|
+
* Built on top of the [SkeletonLabel](?path=/docs/components-loading-states-skeletonlabel--docs) component for text-specific margins and sizing.
|
|
5822
|
+
*
|
|
5823
|
+
* @example
|
|
5824
|
+
* // Uniform lines (simple mode)
|
|
5825
|
+
* <SkeletonLines count={3} textSize="text-base" variant="uniform" />
|
|
5826
|
+
* @example
|
|
5827
|
+
* // Custom lines (advanced mode)
|
|
5828
|
+
* <SkeletonLines
|
|
5829
|
+
* variant="custom"
|
|
5830
|
+
* lines={[
|
|
5831
|
+
* { textSize: "text-lg", width: "100%" },
|
|
5832
|
+
* { textSize: "text-base", width: "95%" },
|
|
5833
|
+
* { textSize: "text-base", width: "70%" }
|
|
5834
|
+
* ]}
|
|
5835
|
+
* />
|
|
5836
|
+
* @example
|
|
5837
|
+
* // Preset lines (quick patterns)
|
|
5838
|
+
* <SkeletonLines variant="preset" preset="title-paragraph" />
|
|
5839
|
+
*/
|
|
5840
|
+
const SkeletonLines = memo((props) => {
|
|
5841
|
+
const { className, "data-testid": dataTestId } = props;
|
|
5842
|
+
// Generate line configs based on variant
|
|
5843
|
+
let lineConfigs;
|
|
5844
|
+
if (props.variant === "preset") {
|
|
5845
|
+
// TypeScript now knows props is PresetSkeletonLinesProps
|
|
5846
|
+
lineConfigs = PRESET_CONFIGURATIONS[props.preset];
|
|
5847
|
+
}
|
|
5848
|
+
else if (props.variant === "custom") {
|
|
5849
|
+
// TypeScript now knows props is CustomSkeletonLinesProps
|
|
5850
|
+
lineConfigs = props.lines;
|
|
5851
|
+
}
|
|
5852
|
+
else {
|
|
5853
|
+
// TypeScript now knows props is UniformSkeletonLinesProps
|
|
5854
|
+
lineConfigs = Array.from({ length: props.count }, () => ({
|
|
5855
|
+
textSize: props.textSize,
|
|
5856
|
+
width: props.width,
|
|
5857
|
+
flexibleWidth: props.flexibleWidth,
|
|
5858
|
+
className: props.lineClassName,
|
|
5859
|
+
}));
|
|
5860
|
+
}
|
|
5861
|
+
const lineCount = lineConfigs.length;
|
|
5862
|
+
return (jsx("div", { "aria-label": `Loading ${lineCount} ${lineCount === 1 ? "item" : "items"}`, className: cvaSkeletonContainer({ className }), "data-testid": dataTestId, "data-variant": props.variant, role: "status", ...(props.variant === "preset" && { "data-preset": props.preset }), children: lineConfigs.map((config, index) => (jsx(SkeletonLabel, { className: config.className, "data-testid": dataTestId ? `${dataTestId}-${index}` : undefined, flexibleWidth: config.flexibleWidth ?? true, textSize: config.textSize ?? "text-base", width: config.width ?? "100%" }, index))) }));
|
|
5863
|
+
});
|
|
5864
|
+
SkeletonLines.displayName = "SkeletonLines";
|
|
5865
|
+
|
|
5876
5866
|
const LoadingContent = () => (jsx("div", { className: "flex flex-row items-center", "data-testid": "kpi-card-loading-content", children: jsx("div", { className: "w-full", children: jsx(SkeletonLines, { lines: [
|
|
5877
5867
|
{ textSize: "text-xs", width: 50 },
|
|
5878
5868
|
{ textSize: "text-lg", width: 40 },
|
|
@@ -6197,6 +6187,16 @@ const Polygon = ({ points, size, color = "black", opaque = true, className, "dat
|
|
|
6197
6187
|
};
|
|
6198
6188
|
const normalize = ({ value, min, max, size }) => ((value - min) / (max - min)) * size;
|
|
6199
6189
|
|
|
6190
|
+
/**
|
|
6191
|
+
* The PopoverTitle component.
|
|
6192
|
+
*
|
|
6193
|
+
* @param {PopoverTitleProps} props - The props for the PopoverTitle component
|
|
6194
|
+
* @returns {ReactElement} PopoverTitle component
|
|
6195
|
+
*/
|
|
6196
|
+
const PopoverTitle = ({ children, action, divider = false, className, "data-testid": dataTestId, }) => {
|
|
6197
|
+
return (jsxs("div", { className: cvaPopoverTitleContainer({ divider, className }), "data-testid": dataTestId, children: [jsx(Text, { className: cvaPopoverTitleText(), size: "small", subtle: true, type: "div", uppercase: true, weight: "bold", children: children }), action] }));
|
|
6198
|
+
};
|
|
6199
|
+
|
|
6200
6200
|
const cvaPreferenceCard = cvaMerge([
|
|
6201
6201
|
"rounded-lg",
|
|
6202
6202
|
"border",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@trackunit/react-components",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.15.0",
|
|
4
4
|
"repository": "https://github.com/Trackunit/manager",
|
|
5
5
|
"license": "SEE LICENSE IN LICENSE.txt",
|
|
6
6
|
"engines": {
|
|
@@ -14,10 +14,10 @@
|
|
|
14
14
|
"@floating-ui/react": "^0.26.25",
|
|
15
15
|
"string-ts": "^2.0.0",
|
|
16
16
|
"tailwind-merge": "^2.0.0",
|
|
17
|
-
"@trackunit/ui-design-tokens": "1.
|
|
18
|
-
"@trackunit/css-class-variance-utilities": "1.
|
|
19
|
-
"@trackunit/shared-utils": "1.
|
|
20
|
-
"@trackunit/ui-icons": "1.
|
|
17
|
+
"@trackunit/ui-design-tokens": "1.11.0",
|
|
18
|
+
"@trackunit/css-class-variance-utilities": "1.11.0",
|
|
19
|
+
"@trackunit/shared-utils": "1.13.0",
|
|
20
|
+
"@trackunit/ui-icons": "1.11.0",
|
|
21
21
|
"@tanstack/react-router": "1.114.29",
|
|
22
22
|
"es-toolkit": "^1.39.10",
|
|
23
23
|
"@tanstack/react-virtual": "3.13.12",
|
|
@@ -3,8 +3,8 @@ import { IconName } from "@trackunit/ui-icons";
|
|
|
3
3
|
import { ReactElement, ReactNode } from "react";
|
|
4
4
|
import { IconColors } from "../Icon/Icon";
|
|
5
5
|
import { KPIProps } from "../KPI/KPI";
|
|
6
|
-
import { NoticeProps } from "../Notice";
|
|
7
|
-
import { ValueBarProps } from "../ValueBar";
|
|
6
|
+
import { NoticeProps } from "../Notice/Notice";
|
|
7
|
+
import { ValueBarProps } from "../ValueBar/ValueBar";
|
|
8
8
|
import { TrendIndicatorProps } from "./components/TrendIndicator/TrendIndicator";
|
|
9
9
|
export interface KPICardProps extends MappedOmit<KPIProps, "variant"> {
|
|
10
10
|
/**
|
|
@@ -2,8 +2,9 @@ import { MakePropertyOptional, MappedOmit } from "@trackunit/shared-utils";
|
|
|
2
2
|
import { ReactElement, ReactNode } from "react";
|
|
3
3
|
import { CommonProps } from "../../../common/CommonProps";
|
|
4
4
|
import { IconProps } from "../../Icon/Icon";
|
|
5
|
-
import { PopoverContentChildren
|
|
6
|
-
import {
|
|
5
|
+
import { PopoverContentChildren } from "../../Popover/PopoverContent";
|
|
6
|
+
import { PopoverProps } from "../../Popover/PopoverTypes";
|
|
7
|
+
import { IconButtonProps } from "../../buttons/IconButton/IconButton";
|
|
7
8
|
export type MenuPlacement = "above" | "below";
|
|
8
9
|
type FilteredIconProps = MakePropertyOptional<MappedOmit<IconProps, "onClick">, "name">;
|
|
9
10
|
type FilteredIconButtonProps = Omit<IconButtonProps, "icon" | "onClick">;
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { IconName } from "@trackunit/ui-icons";
|
|
2
2
|
import { MouseEvent, ReactElement, ReactNode } from "react";
|
|
3
3
|
import { CommonProps } from "../../common/CommonProps";
|
|
4
|
-
import { ButtonVariant } from "../buttons";
|
|
4
|
+
import { ButtonVariant } from "../buttons/shared/ButtonProps";
|
|
5
5
|
import { TabListProps } from "../Tabs/TabList";
|
|
6
|
-
import { TagColors } from "../Tag";
|
|
6
|
+
import { TagColors } from "../Tag/Tag";
|
|
7
7
|
export type PageHeaderKpiMetricsType = {
|
|
8
8
|
header: string;
|
|
9
9
|
value: string | number;
|
|
@@ -3,7 +3,7 @@ import { MappedOmit } from "@trackunit/shared-utils";
|
|
|
3
3
|
import { IconName } from "@trackunit/ui-icons";
|
|
4
4
|
import { ReactElement, ReactNode } from "react";
|
|
5
5
|
import { CommonProps } from "../../common/CommonProps";
|
|
6
|
-
import { TagProps } from "../Tag";
|
|
6
|
+
import { TagProps } from "../Tag/Tag";
|
|
7
7
|
import { cvaPreferenceCard } from "./PreferenceCard.variants";
|
|
8
8
|
/**
|
|
9
9
|
* Grid layout configuration for the PreferenceCard content area.
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { ComponentProps, ReactElement } from "react";
|
|
2
2
|
import { CommonProps } from "../../common/CommonProps";
|
|
3
|
-
import { MenuList
|
|
3
|
+
import { MenuList } from "../Menu/MenuList/MenuList";
|
|
4
|
+
import { MoreMenu } from "../Menu/MoreMenu/MoreMenu";
|
|
4
5
|
export interface SidebarItemProps extends CommonProps {
|
|
5
6
|
/**
|
|
6
7
|
* The id prop is used to identify the sidebar item in the dom.
|
package/src/index.d.ts
CHANGED
|
@@ -5,16 +5,22 @@ export * from "./common/PackageNameStoryComponent";
|
|
|
5
5
|
export * from "./common/Size";
|
|
6
6
|
export * from "./common/StorybookProps";
|
|
7
7
|
export * from "./common/Styleable";
|
|
8
|
-
export * from "./components/Alert";
|
|
9
|
-
export * from "./components/Badge";
|
|
8
|
+
export * from "./components/Alert/Alert";
|
|
9
|
+
export * from "./components/Badge/Badge";
|
|
10
10
|
export * from "./components/Breadcrumb/Breadcrumb";
|
|
11
|
-
export * from "./components/buttons";
|
|
11
|
+
export * from "./components/buttons/Button/Button";
|
|
12
|
+
export * from "./components/buttons/IconButton/IconButton";
|
|
12
13
|
export * from "./components/buttons/shared/Button.variants";
|
|
13
|
-
export * from "./components/
|
|
14
|
+
export * from "./components/buttons/shared/ButtonProps";
|
|
15
|
+
export * from "./components/buttons/StarButton/StarButton";
|
|
16
|
+
export * from "./components/Card/Card";
|
|
17
|
+
export * from "./components/Card/CardBody";
|
|
18
|
+
export * from "./components/Card/CardFooter";
|
|
19
|
+
export * from "./components/Card/CardHeader";
|
|
14
20
|
export * from "./components/Clickable/Clickable.variants";
|
|
15
|
-
export * from "./components/Collapse";
|
|
21
|
+
export * from "./components/Collapse/Collapse";
|
|
16
22
|
export * from "./components/CompletionStatusIndicator/CompletionStatusIndicator";
|
|
17
|
-
export * from "./components/CopyableText";
|
|
23
|
+
export * from "./components/CopyableText/CopyableText";
|
|
18
24
|
export * from "./components/DetailsList/DetailsList";
|
|
19
25
|
export * from "./components/EmptyState/EmptyState";
|
|
20
26
|
export * from "./components/EmptyState/EmptyState.variants";
|
|
@@ -24,11 +30,11 @@ export { createGrid } from "./components/GridAreas/createGrid";
|
|
|
24
30
|
export { GridAreas, type GridAreasProps } from "./components/GridAreas/GridAreas";
|
|
25
31
|
export type { GridAreasResult, GridConfig, SlotProps } from "./components/GridAreas/types";
|
|
26
32
|
export { useGridAreas } from "./components/GridAreas/useGridAreas";
|
|
27
|
-
export * from "./components/Heading";
|
|
33
|
+
export * from "./components/Heading/Heading";
|
|
28
34
|
export * from "./components/Highlight/Highlight";
|
|
29
35
|
export * from "./components/HorizontalOverflowScroller/HorizontalOverflowScroller";
|
|
30
36
|
export * from "./components/Icon/Icon";
|
|
31
|
-
export * from "./components/Indicator";
|
|
37
|
+
export * from "./components/Indicator/Indicator";
|
|
32
38
|
export * from "./components/Indicator/Indicator.variants";
|
|
33
39
|
export * from "./components/InteractableItem/InteractableItem.variants";
|
|
34
40
|
export * from "./components/KPI/KPI";
|
|
@@ -42,38 +48,56 @@ export * from "./components/List/List.variants";
|
|
|
42
48
|
export * from "./components/List/useList";
|
|
43
49
|
export * from "./components/ListItem/ListItem";
|
|
44
50
|
export * from "./components/ListItem/useListItemHeight";
|
|
45
|
-
export * from "./components/Menu";
|
|
51
|
+
export * from "./components/Menu/MenuDivider/MenuDivider";
|
|
52
|
+
export * from "./components/Menu/MenuItem/MenuItem";
|
|
46
53
|
export * from "./components/Menu/MenuItem/MenuItem.variants";
|
|
54
|
+
export * from "./components/Menu/MenuList/MenuList";
|
|
47
55
|
export * from "./components/Menu/MenuList/MenuList.variants";
|
|
48
|
-
export * from "./components/
|
|
49
|
-
export * from "./components/
|
|
50
|
-
export * from "./components/
|
|
56
|
+
export * from "./components/Menu/MoreMenu/MoreMenu";
|
|
57
|
+
export * from "./components/Notice/Notice";
|
|
58
|
+
export * from "./components/Page/Page";
|
|
59
|
+
export * from "./components/Page/PageContent";
|
|
60
|
+
export * from "./components/PageHeader/components/PageHeaderKpiMetrics";
|
|
61
|
+
export * from "./components/PageHeader/components/PageHeaderSecondaryActions";
|
|
62
|
+
export * from "./components/PageHeader/components/PageHeaderTitle";
|
|
63
|
+
export * from "./components/PageHeader/PageHeader";
|
|
64
|
+
export * from "./components/PageHeader/PageHeader.variants";
|
|
65
|
+
export * from "./components/PageHeader/types";
|
|
51
66
|
export * from "./components/Pagination/Pagination";
|
|
52
67
|
export * from "./components/Polygon/Polygon";
|
|
53
|
-
export * from "./components/Popover";
|
|
54
68
|
export * from "./components/Popover/Popover";
|
|
69
|
+
export * from "./components/Popover/PopoverContent";
|
|
70
|
+
export * from "./components/Popover/PopoverTitle";
|
|
71
|
+
export * from "./components/Popover/PopoverTrigger";
|
|
72
|
+
export * from "./components/Popover/PopoverTypes";
|
|
55
73
|
export * from "./components/Portal/Portal";
|
|
56
74
|
export * from "./components/PreferenceCard/PreferenceCard";
|
|
57
75
|
export * from "./components/PreferenceCard/PreferenceCard.variants";
|
|
58
76
|
export * from "./components/PreferenceCard/PreferenceCardSkeleton";
|
|
59
|
-
export * from "./components/Prompt";
|
|
60
|
-
export * from "./components/SectionHeader";
|
|
77
|
+
export * from "./components/Prompt/Prompt";
|
|
78
|
+
export * from "./components/SectionHeader/SectionHeader";
|
|
61
79
|
export * from "./components/Sidebar/Sidebar";
|
|
62
80
|
export * from "./components/Sidebar/useOverflowItems";
|
|
63
|
-
export
|
|
64
|
-
export
|
|
65
|
-
export
|
|
66
|
-
export
|
|
81
|
+
export { SkeletonBlock } from "./components/Skeleton/SkeletonBlock";
|
|
82
|
+
export type { SkeletonBlockProps } from "./components/Skeleton/SkeletonBlock";
|
|
83
|
+
export { SkeletonLabel } from "./components/Skeleton/SkeletonLabel";
|
|
84
|
+
export type { SkeletonLabelProps } from "./components/Skeleton/SkeletonLabel";
|
|
85
|
+
export * from "./components/SkeletonLines/skeleton-utils";
|
|
86
|
+
export * from "./components/SkeletonLines/SkeletonLines";
|
|
87
|
+
export * from "./components/Spacer/Spacer";
|
|
88
|
+
export * from "./components/Spinner/Spinner";
|
|
67
89
|
export * from "./components/Tabs/Tab";
|
|
68
90
|
export * from "./components/Tabs/TabContent";
|
|
69
91
|
export * from "./components/Tabs/TabList";
|
|
70
92
|
export * from "./components/Tabs/Tabs";
|
|
71
|
-
export * from "./components/Tag";
|
|
72
|
-
export * from "./components/Text";
|
|
93
|
+
export * from "./components/Tag/Tag";
|
|
94
|
+
export * from "./components/Text/Text";
|
|
73
95
|
export * from "./components/ToggleGroup/ToggleGroup";
|
|
74
96
|
export * from "./components/ToggleGroup/ToggleGroup.variants";
|
|
75
|
-
export * from "./components/Tooltip";
|
|
76
|
-
export * from "./components/ValueBar";
|
|
97
|
+
export * from "./components/Tooltip/Tooltip";
|
|
98
|
+
export * from "./components/ValueBar/ValueBar";
|
|
99
|
+
export { getValueBarColorByValue } from "./components/ValueBar/ValueBarHelper";
|
|
100
|
+
export * from "./components/ValueBar/ValueBarTypes";
|
|
77
101
|
export * from "./components/ZStack/ZStack";
|
|
78
102
|
export * from "./components/ZStack/ZStack.variants";
|
|
79
103
|
export * from "./hooks/encoding/useCustomEncoding";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Alert";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Badge";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Collapse";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./CopyableText";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Heading";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Indicator";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Notice";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Prompt";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./SectionHeader";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Spacer";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Spinner";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Tag";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Text";
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from "./Tooltip";
|