@tollerud/ui 1.0.8 → 1.1.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/README.md +4 -5
- package/dist/index.cjs +1181 -0
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +251 -1
- package/dist/index.d.ts +251 -1
- package/dist/index.js +1162 -3
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -2,12 +2,12 @@
|
|
|
2
2
|
import { clsx } from 'clsx';
|
|
3
3
|
import { twMerge } from 'tailwind-merge';
|
|
4
4
|
import * as React2 from 'react';
|
|
5
|
-
import { forwardRef, useState, useCallback, lazy, useRef, useEffect, useMemo, useId, Suspense } from 'react';
|
|
5
|
+
import { forwardRef, useState, useCallback, lazy, useRef, useEffect, useMemo, useId, Fragment as Fragment$1, createContext, useContext, Suspense } from 'react';
|
|
6
6
|
import { Slot } from '@radix-ui/react-slot';
|
|
7
7
|
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
8
8
|
import { motion } from 'framer-motion';
|
|
9
9
|
import * as DialogPrimitive from '@radix-ui/react-dialog';
|
|
10
|
-
import { X } from 'lucide-react';
|
|
10
|
+
import { X, ChevronRight, ChevronLeft, MoreHorizontal, Check, ChevronDown, EyeOff, Eye, Calendar, Upload, File } from 'lucide-react';
|
|
11
11
|
import * as TooltipPrimitive from '@radix-ui/react-tooltip';
|
|
12
12
|
import * as TabsPrimitive from '@radix-ui/react-tabs';
|
|
13
13
|
import * as ProgressPrimitive from '@radix-ui/react-progress';
|
|
@@ -2650,7 +2650,1166 @@ function MetricBadge({ label, value }) {
|
|
|
2650
2650
|
/* @__PURE__ */ jsx("span", { className: "float-right text-tollerud-text-primary font-mono", children: value })
|
|
2651
2651
|
] });
|
|
2652
2652
|
}
|
|
2653
|
+
var Divider = forwardRef(
|
|
2654
|
+
({ className, orientation = "horizontal", label, ...props }, ref) => {
|
|
2655
|
+
if (orientation === "vertical") {
|
|
2656
|
+
return /* @__PURE__ */ jsx(
|
|
2657
|
+
"div",
|
|
2658
|
+
{
|
|
2659
|
+
ref,
|
|
2660
|
+
role: "separator",
|
|
2661
|
+
"aria-orientation": "vertical",
|
|
2662
|
+
className: cn("w-px self-stretch bg-tollerud-border", className),
|
|
2663
|
+
...props
|
|
2664
|
+
}
|
|
2665
|
+
);
|
|
2666
|
+
}
|
|
2667
|
+
if (label) {
|
|
2668
|
+
return /* @__PURE__ */ jsxs(
|
|
2669
|
+
"div",
|
|
2670
|
+
{
|
|
2671
|
+
ref,
|
|
2672
|
+
role: "separator",
|
|
2673
|
+
"aria-orientation": "horizontal",
|
|
2674
|
+
className: cn("flex items-center gap-3 text-xs text-tollerud-text-muted", className),
|
|
2675
|
+
...props,
|
|
2676
|
+
children: [
|
|
2677
|
+
/* @__PURE__ */ jsx("span", { className: "h-px flex-1 bg-tollerud-border" }),
|
|
2678
|
+
/* @__PURE__ */ jsx("span", { children: label }),
|
|
2679
|
+
/* @__PURE__ */ jsx("span", { className: "h-px flex-1 bg-tollerud-border" })
|
|
2680
|
+
]
|
|
2681
|
+
}
|
|
2682
|
+
);
|
|
2683
|
+
}
|
|
2684
|
+
return /* @__PURE__ */ jsx(
|
|
2685
|
+
"div",
|
|
2686
|
+
{
|
|
2687
|
+
ref,
|
|
2688
|
+
role: "separator",
|
|
2689
|
+
"aria-orientation": "horizontal",
|
|
2690
|
+
className: cn("h-px w-full bg-tollerud-border", className),
|
|
2691
|
+
...props
|
|
2692
|
+
}
|
|
2693
|
+
);
|
|
2694
|
+
}
|
|
2695
|
+
);
|
|
2696
|
+
Divider.displayName = "Divider";
|
|
2697
|
+
var pillVariants = {
|
|
2698
|
+
outline: "bg-transparent border border-tollerud-border text-tollerud-text-secondary",
|
|
2699
|
+
solid: "bg-tollerud-surface-raised text-tollerud-text-primary",
|
|
2700
|
+
accent: "bg-tollerud-yellow/15 border border-tollerud-yellow/30 text-tollerud-yellow"
|
|
2701
|
+
};
|
|
2702
|
+
var Pill = forwardRef(
|
|
2703
|
+
({ className, variant = "outline", ...props }, ref) => {
|
|
2704
|
+
return /* @__PURE__ */ jsx(
|
|
2705
|
+
"span",
|
|
2706
|
+
{
|
|
2707
|
+
ref,
|
|
2708
|
+
className: cn(
|
|
2709
|
+
"inline-flex items-center gap-1 px-2.5 py-1 text-xs font-medium rounded-full leading-none",
|
|
2710
|
+
pillVariants[variant],
|
|
2711
|
+
className
|
|
2712
|
+
),
|
|
2713
|
+
...props
|
|
2714
|
+
}
|
|
2715
|
+
);
|
|
2716
|
+
}
|
|
2717
|
+
);
|
|
2718
|
+
Pill.displayName = "Pill";
|
|
2719
|
+
var avatarSizes = {
|
|
2720
|
+
sm: "h-6 w-6 text-[10px]",
|
|
2721
|
+
md: "h-8 w-8 text-xs",
|
|
2722
|
+
lg: "h-11 w-11 text-sm"
|
|
2723
|
+
};
|
|
2724
|
+
function initialsFrom(name) {
|
|
2725
|
+
const parts = name.trim().split(/\s+/).filter(Boolean);
|
|
2726
|
+
if (parts.length === 0) return "";
|
|
2727
|
+
if (parts.length === 1) return parts[0].slice(0, 2).toUpperCase();
|
|
2728
|
+
return (parts[0][0] + parts[parts.length - 1][0]).toUpperCase();
|
|
2729
|
+
}
|
|
2730
|
+
var Avatar = forwardRef(
|
|
2731
|
+
({ className, src, name, fallback, size = "md", ...props }, ref) => {
|
|
2732
|
+
const [errored, setErrored] = useState(false);
|
|
2733
|
+
const showImage = !!src && !errored;
|
|
2734
|
+
return /* @__PURE__ */ jsx(
|
|
2735
|
+
"span",
|
|
2736
|
+
{
|
|
2737
|
+
ref,
|
|
2738
|
+
className: cn(
|
|
2739
|
+
"relative inline-flex shrink-0 items-center justify-center overflow-hidden rounded-full select-none",
|
|
2740
|
+
"bg-tollerud-surface-raised text-tollerud-text-secondary font-medium",
|
|
2741
|
+
"ring-1 ring-tollerud-border",
|
|
2742
|
+
avatarSizes[size],
|
|
2743
|
+
className
|
|
2744
|
+
),
|
|
2745
|
+
...props,
|
|
2746
|
+
children: showImage ? (
|
|
2747
|
+
// eslint-disable-next-line @next/next/no-img-element
|
|
2748
|
+
/* @__PURE__ */ jsx(
|
|
2749
|
+
"img",
|
|
2750
|
+
{
|
|
2751
|
+
src,
|
|
2752
|
+
alt: name ?? "",
|
|
2753
|
+
className: "h-full w-full object-cover",
|
|
2754
|
+
onError: () => setErrored(true)
|
|
2755
|
+
}
|
|
2756
|
+
)
|
|
2757
|
+
) : /* @__PURE__ */ jsx("span", { "aria-hidden": !!name, children: fallback ?? (name ? initialsFrom(name) : null) })
|
|
2758
|
+
}
|
|
2759
|
+
);
|
|
2760
|
+
}
|
|
2761
|
+
);
|
|
2762
|
+
Avatar.displayName = "Avatar";
|
|
2763
|
+
var AvatarGroup = forwardRef(
|
|
2764
|
+
({ className, max, size = "md", children, ...props }, ref) => {
|
|
2765
|
+
const items = Array.isArray(children) ? children : [children];
|
|
2766
|
+
const visible = max ? items.slice(0, max) : items;
|
|
2767
|
+
const overflow = max ? items.length - max : 0;
|
|
2768
|
+
return /* @__PURE__ */ jsxs(
|
|
2769
|
+
"div",
|
|
2770
|
+
{
|
|
2771
|
+
ref,
|
|
2772
|
+
className: cn("flex items-center -space-x-2", className),
|
|
2773
|
+
...props,
|
|
2774
|
+
children: [
|
|
2775
|
+
visible.map((child, i) => /* @__PURE__ */ jsx("span", { className: "ring-2 ring-tollerud-surface rounded-full", children: child }, i)),
|
|
2776
|
+
overflow > 0 && /* @__PURE__ */ jsxs(
|
|
2777
|
+
"span",
|
|
2778
|
+
{
|
|
2779
|
+
className: cn(
|
|
2780
|
+
"relative inline-flex shrink-0 items-center justify-center rounded-full select-none",
|
|
2781
|
+
"bg-tollerud-surface-raised text-tollerud-text-muted font-medium",
|
|
2782
|
+
"ring-2 ring-tollerud-surface",
|
|
2783
|
+
avatarSizes[size]
|
|
2784
|
+
),
|
|
2785
|
+
children: [
|
|
2786
|
+
"+",
|
|
2787
|
+
overflow
|
|
2788
|
+
]
|
|
2789
|
+
}
|
|
2790
|
+
)
|
|
2791
|
+
]
|
|
2792
|
+
}
|
|
2793
|
+
);
|
|
2794
|
+
}
|
|
2795
|
+
);
|
|
2796
|
+
AvatarGroup.displayName = "AvatarGroup";
|
|
2797
|
+
var Breadcrumb = forwardRef(
|
|
2798
|
+
({ className, items, separator, ...props }, ref) => {
|
|
2799
|
+
return /* @__PURE__ */ jsx("nav", { ref, "aria-label": "Breadcrumb", className: cn("text-sm", className), ...props, children: /* @__PURE__ */ jsx("ol", { className: "flex items-center gap-1.5 flex-wrap", children: items.map((item, i) => {
|
|
2800
|
+
const isLast = i === items.length - 1;
|
|
2801
|
+
const content = !isLast && (item.href || item.onClick) ? /* @__PURE__ */ jsx(
|
|
2802
|
+
"a",
|
|
2803
|
+
{
|
|
2804
|
+
href: item.href,
|
|
2805
|
+
onClick: item.onClick,
|
|
2806
|
+
className: "text-tollerud-text-secondary hover:text-tollerud-text-primary transition-colors duration-[150ms]",
|
|
2807
|
+
children: item.label
|
|
2808
|
+
}
|
|
2809
|
+
) : /* @__PURE__ */ jsx(
|
|
2810
|
+
"span",
|
|
2811
|
+
{
|
|
2812
|
+
"aria-current": isLast ? "page" : void 0,
|
|
2813
|
+
className: isLast ? "text-tollerud-text-primary font-medium" : "text-tollerud-text-secondary",
|
|
2814
|
+
children: item.label
|
|
2815
|
+
}
|
|
2816
|
+
);
|
|
2817
|
+
return /* @__PURE__ */ jsxs(Fragment$1, { children: [
|
|
2818
|
+
/* @__PURE__ */ jsx("li", { className: "flex items-center gap-1.5", children: content }),
|
|
2819
|
+
!isLast && /* @__PURE__ */ jsx("li", { "aria-hidden": "true", className: "flex items-center text-tollerud-text-muted", children: separator ?? /* @__PURE__ */ jsx(ChevronRight, { size: 14 }) })
|
|
2820
|
+
] }, i);
|
|
2821
|
+
}) }) });
|
|
2822
|
+
}
|
|
2823
|
+
);
|
|
2824
|
+
Breadcrumb.displayName = "Breadcrumb";
|
|
2825
|
+
function getPageRange(page, pageCount, siblingCount) {
|
|
2826
|
+
const totalVisible = siblingCount * 2 + 5;
|
|
2827
|
+
if (pageCount <= totalVisible) {
|
|
2828
|
+
return Array.from({ length: pageCount }, (_, i) => i + 1);
|
|
2829
|
+
}
|
|
2830
|
+
const left = Math.max(page - siblingCount, 1);
|
|
2831
|
+
const right = Math.min(page + siblingCount, pageCount);
|
|
2832
|
+
const range = [1];
|
|
2833
|
+
if (left > 2) range.push("ellipsis");
|
|
2834
|
+
for (let p = left === 1 ? 2 : left; p <= (right === pageCount ? pageCount - 1 : right); p++) {
|
|
2835
|
+
range.push(p);
|
|
2836
|
+
}
|
|
2837
|
+
if (right < pageCount - 1) range.push("ellipsis");
|
|
2838
|
+
if (pageCount > 1) range.push(pageCount);
|
|
2839
|
+
return range;
|
|
2840
|
+
}
|
|
2841
|
+
var navButtonClasses = "inline-flex h-8 min-w-8 items-center justify-center rounded px-2 text-sm transition-colors duration-[150ms] disabled:opacity-40 disabled:pointer-events-none";
|
|
2842
|
+
var Pagination = forwardRef(
|
|
2843
|
+
({ className, page, pageCount, onChange, siblingCount = 1, ...props }, ref) => {
|
|
2844
|
+
const range = getPageRange(page, pageCount, siblingCount);
|
|
2845
|
+
return /* @__PURE__ */ jsxs("nav", { ref, "aria-label": "Pagination", className: cn("flex items-center gap-1", className), ...props, children: [
|
|
2846
|
+
/* @__PURE__ */ jsx(
|
|
2847
|
+
"button",
|
|
2848
|
+
{
|
|
2849
|
+
type: "button",
|
|
2850
|
+
"aria-label": "Previous page",
|
|
2851
|
+
disabled: page <= 1,
|
|
2852
|
+
onClick: () => onChange(page - 1),
|
|
2853
|
+
className: cn(navButtonClasses, "text-tollerud-text-secondary hover:bg-tollerud-surface-hover"),
|
|
2854
|
+
children: /* @__PURE__ */ jsx(ChevronLeft, { size: 16 })
|
|
2855
|
+
}
|
|
2856
|
+
),
|
|
2857
|
+
range.map(
|
|
2858
|
+
(item, i) => item === "ellipsis" ? /* @__PURE__ */ jsx("span", { className: "inline-flex h-8 w-8 items-center justify-center text-tollerud-text-muted", children: /* @__PURE__ */ jsx(MoreHorizontal, { size: 16 }) }, `e-${i}`) : /* @__PURE__ */ jsx(
|
|
2859
|
+
"button",
|
|
2860
|
+
{
|
|
2861
|
+
type: "button",
|
|
2862
|
+
"aria-current": item === page ? "page" : void 0,
|
|
2863
|
+
onClick: () => onChange(item),
|
|
2864
|
+
className: cn(
|
|
2865
|
+
navButtonClasses,
|
|
2866
|
+
item === page ? "bg-tollerud-yellow text-tollerud-noir-black font-medium" : "text-tollerud-text-secondary hover:bg-tollerud-surface-hover"
|
|
2867
|
+
),
|
|
2868
|
+
children: item
|
|
2869
|
+
},
|
|
2870
|
+
item
|
|
2871
|
+
)
|
|
2872
|
+
),
|
|
2873
|
+
/* @__PURE__ */ jsx(
|
|
2874
|
+
"button",
|
|
2875
|
+
{
|
|
2876
|
+
type: "button",
|
|
2877
|
+
"aria-label": "Next page",
|
|
2878
|
+
disabled: page >= pageCount,
|
|
2879
|
+
onClick: () => onChange(page + 1),
|
|
2880
|
+
className: cn(navButtonClasses, "text-tollerud-text-secondary hover:bg-tollerud-surface-hover"),
|
|
2881
|
+
children: /* @__PURE__ */ jsx(ChevronRight, { size: 16 })
|
|
2882
|
+
}
|
|
2883
|
+
)
|
|
2884
|
+
] });
|
|
2885
|
+
}
|
|
2886
|
+
);
|
|
2887
|
+
Pagination.displayName = "Pagination";
|
|
2888
|
+
var Segmented = forwardRef(
|
|
2889
|
+
({ className, options, value, onChange, size = "md", ...props }, ref) => {
|
|
2890
|
+
return /* @__PURE__ */ jsx(
|
|
2891
|
+
"div",
|
|
2892
|
+
{
|
|
2893
|
+
ref,
|
|
2894
|
+
role: "radiogroup",
|
|
2895
|
+
className: cn(
|
|
2896
|
+
"inline-flex items-center gap-0.5 rounded-lg p-1 bg-tollerud-surface-raised border border-tollerud-border",
|
|
2897
|
+
className
|
|
2898
|
+
),
|
|
2899
|
+
...props,
|
|
2900
|
+
children: options.map((opt) => {
|
|
2901
|
+
const active = opt.value === value;
|
|
2902
|
+
return /* @__PURE__ */ jsx(
|
|
2903
|
+
"button",
|
|
2904
|
+
{
|
|
2905
|
+
type: "button",
|
|
2906
|
+
role: "radio",
|
|
2907
|
+
"aria-checked": active,
|
|
2908
|
+
disabled: opt.disabled,
|
|
2909
|
+
onClick: () => !opt.disabled && onChange(opt.value),
|
|
2910
|
+
className: cn(
|
|
2911
|
+
"rounded-md font-medium transition-colors duration-[150ms]",
|
|
2912
|
+
size === "sm" ? "px-2.5 py-1 text-xs" : "px-3.5 py-1.5 text-sm",
|
|
2913
|
+
active ? "bg-tollerud-yellow text-tollerud-noir-black" : "text-tollerud-text-secondary hover:text-tollerud-text-primary",
|
|
2914
|
+
opt.disabled && "opacity-40 pointer-events-none"
|
|
2915
|
+
),
|
|
2916
|
+
children: opt.label
|
|
2917
|
+
},
|
|
2918
|
+
opt.value
|
|
2919
|
+
);
|
|
2920
|
+
})
|
|
2921
|
+
}
|
|
2922
|
+
);
|
|
2923
|
+
}
|
|
2924
|
+
);
|
|
2925
|
+
Segmented.displayName = "Segmented";
|
|
2926
|
+
var Stepper = forwardRef(
|
|
2927
|
+
({ className, steps, current, orientation = "horizontal", ...props }, ref) => {
|
|
2928
|
+
const vertical = orientation === "vertical";
|
|
2929
|
+
return /* @__PURE__ */ jsx(
|
|
2930
|
+
"ol",
|
|
2931
|
+
{
|
|
2932
|
+
ref,
|
|
2933
|
+
className: cn("flex", vertical ? "flex-col gap-0" : "items-start gap-0 w-full", className),
|
|
2934
|
+
...props,
|
|
2935
|
+
children: steps.map((step, i) => {
|
|
2936
|
+
const status = i < current ? "complete" : i === current ? "active" : "upcoming";
|
|
2937
|
+
const isLast = i === steps.length - 1;
|
|
2938
|
+
return /* @__PURE__ */ jsxs(
|
|
2939
|
+
"li",
|
|
2940
|
+
{
|
|
2941
|
+
className: cn(
|
|
2942
|
+
"flex",
|
|
2943
|
+
vertical ? "flex-row gap-3" : "flex-col flex-1 gap-2",
|
|
2944
|
+
!vertical && !isLast && "pr-2"
|
|
2945
|
+
),
|
|
2946
|
+
children: [
|
|
2947
|
+
/* @__PURE__ */ jsxs("div", { className: cn("flex items-center", vertical ? "flex-col" : "flex-row gap-2 w-full"), children: [
|
|
2948
|
+
/* @__PURE__ */ jsx(
|
|
2949
|
+
"span",
|
|
2950
|
+
{
|
|
2951
|
+
className: cn(
|
|
2952
|
+
"flex h-7 w-7 shrink-0 items-center justify-center rounded-full text-xs font-medium transition-colors duration-[150ms]",
|
|
2953
|
+
status === "complete" && "bg-tollerud-yellow text-tollerud-noir-black",
|
|
2954
|
+
status === "active" && "border-2 border-tollerud-yellow text-tollerud-yellow",
|
|
2955
|
+
status === "upcoming" && "border border-tollerud-border text-tollerud-text-muted"
|
|
2956
|
+
),
|
|
2957
|
+
children: status === "complete" ? /* @__PURE__ */ jsx(Check, { size: 14 }) : i + 1
|
|
2958
|
+
}
|
|
2959
|
+
),
|
|
2960
|
+
!isLast && /* @__PURE__ */ jsx(
|
|
2961
|
+
"span",
|
|
2962
|
+
{
|
|
2963
|
+
"aria-hidden": "true",
|
|
2964
|
+
className: cn(
|
|
2965
|
+
"bg-tollerud-border",
|
|
2966
|
+
vertical ? "w-px flex-1 my-1" : "h-px flex-1",
|
|
2967
|
+
status === "complete" && "bg-tollerud-yellow"
|
|
2968
|
+
)
|
|
2969
|
+
}
|
|
2970
|
+
)
|
|
2971
|
+
] }),
|
|
2972
|
+
/* @__PURE__ */ jsxs("div", { className: cn("flex flex-col", vertical && "pb-6"), children: [
|
|
2973
|
+
/* @__PURE__ */ jsx(
|
|
2974
|
+
"span",
|
|
2975
|
+
{
|
|
2976
|
+
className: cn(
|
|
2977
|
+
"text-sm font-medium",
|
|
2978
|
+
status === "upcoming" ? "text-tollerud-text-muted" : "text-tollerud-text-primary"
|
|
2979
|
+
),
|
|
2980
|
+
children: step.label
|
|
2981
|
+
}
|
|
2982
|
+
),
|
|
2983
|
+
step.description && /* @__PURE__ */ jsx("span", { className: "text-xs text-tollerud-text-muted", children: step.description })
|
|
2984
|
+
] })
|
|
2985
|
+
]
|
|
2986
|
+
},
|
|
2987
|
+
i
|
|
2988
|
+
);
|
|
2989
|
+
})
|
|
2990
|
+
}
|
|
2991
|
+
);
|
|
2992
|
+
}
|
|
2993
|
+
);
|
|
2994
|
+
Stepper.displayName = "Stepper";
|
|
2995
|
+
var Panel = forwardRef(
|
|
2996
|
+
({ className, title, description, actions, children, ...props }, ref) => {
|
|
2997
|
+
const hasHeader = title || description || actions;
|
|
2998
|
+
return /* @__PURE__ */ jsxs(
|
|
2999
|
+
"div",
|
|
3000
|
+
{
|
|
3001
|
+
ref,
|
|
3002
|
+
className: cn(
|
|
3003
|
+
"rounded-lg border border-tollerud-border bg-tollerud-surface overflow-hidden",
|
|
3004
|
+
className
|
|
3005
|
+
),
|
|
3006
|
+
...props,
|
|
3007
|
+
children: [
|
|
3008
|
+
hasHeader && /* @__PURE__ */ jsxs("div", { className: "flex items-start justify-between gap-4 px-5 py-4 border-b border-tollerud-border", children: [
|
|
3009
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-0.5", children: [
|
|
3010
|
+
title && /* @__PURE__ */ jsx("h3", { className: "text-sm font-medium text-tollerud-text-primary", children: title }),
|
|
3011
|
+
description && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-text-muted", children: description })
|
|
3012
|
+
] }),
|
|
3013
|
+
actions && /* @__PURE__ */ jsx("div", { className: "flex items-center gap-2 shrink-0", children: actions })
|
|
3014
|
+
] }),
|
|
3015
|
+
children && /* @__PURE__ */ jsx("div", { className: "px-5 py-4", children })
|
|
3016
|
+
]
|
|
3017
|
+
}
|
|
3018
|
+
);
|
|
3019
|
+
}
|
|
3020
|
+
);
|
|
3021
|
+
Panel.displayName = "Panel";
|
|
3022
|
+
var meterTones = {
|
|
3023
|
+
default: "bg-tollerud-yellow",
|
|
3024
|
+
success: "bg-tollerud-success",
|
|
3025
|
+
warning: "bg-tollerud-warning",
|
|
3026
|
+
error: "bg-tollerud-error"
|
|
3027
|
+
};
|
|
3028
|
+
var Meter = forwardRef(
|
|
3029
|
+
({ className, value, max = 100, label, showValue, tone = "default", ...props }, ref) => {
|
|
3030
|
+
const pct = Math.min(100, Math.max(0, value / max * 100));
|
|
3031
|
+
return /* @__PURE__ */ jsxs("div", { ref, className: cn("flex flex-col gap-1.5", className), ...props, children: [
|
|
3032
|
+
(label || showValue) && /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between text-xs", children: [
|
|
3033
|
+
label && /* @__PURE__ */ jsx("span", { className: "text-tollerud-text-secondary", children: label }),
|
|
3034
|
+
showValue && /* @__PURE__ */ jsxs("span", { className: "text-tollerud-text-muted tabular-nums", children: [
|
|
3035
|
+
Math.round(pct),
|
|
3036
|
+
"%"
|
|
3037
|
+
] })
|
|
3038
|
+
] }),
|
|
3039
|
+
/* @__PURE__ */ jsx(
|
|
3040
|
+
"div",
|
|
3041
|
+
{
|
|
3042
|
+
role: "meter",
|
|
3043
|
+
"aria-valuenow": value,
|
|
3044
|
+
"aria-valuemin": 0,
|
|
3045
|
+
"aria-valuemax": max,
|
|
3046
|
+
className: "h-1.5 w-full overflow-hidden rounded-full bg-tollerud-surface-raised",
|
|
3047
|
+
children: /* @__PURE__ */ jsx(
|
|
3048
|
+
"div",
|
|
3049
|
+
{
|
|
3050
|
+
className: cn("h-full rounded-full transition-[width] duration-300", meterTones[tone]),
|
|
3051
|
+
style: { width: `${pct}%` }
|
|
3052
|
+
}
|
|
3053
|
+
)
|
|
3054
|
+
}
|
|
3055
|
+
)
|
|
3056
|
+
] });
|
|
3057
|
+
}
|
|
3058
|
+
);
|
|
3059
|
+
Meter.displayName = "Meter";
|
|
3060
|
+
var FormRow = forwardRef(
|
|
3061
|
+
({ className, label, description, error, required, htmlFor, children, ...props }, ref) => {
|
|
3062
|
+
const autoId = useId();
|
|
3063
|
+
const descriptionId = description ? `${autoId}-description` : void 0;
|
|
3064
|
+
const errorId = error ? `${autoId}-error` : void 0;
|
|
3065
|
+
return /* @__PURE__ */ jsxs("div", { ref, className: cn("flex flex-col gap-1.5", className), ...props, children: [
|
|
3066
|
+
label && /* @__PURE__ */ jsxs("label", { htmlFor, className: "text-sm font-medium text-tollerud-text-primary", children: [
|
|
3067
|
+
label,
|
|
3068
|
+
required && /* @__PURE__ */ jsx("span", { className: "ml-0.5 text-tollerud-error", children: "*" })
|
|
3069
|
+
] }),
|
|
3070
|
+
description && /* @__PURE__ */ jsx("p", { id: descriptionId, className: "text-xs text-tollerud-text-muted", children: description }),
|
|
3071
|
+
/* @__PURE__ */ jsx("div", { "aria-describedby": [descriptionId, errorId].filter(Boolean).join(" ") || void 0, children }),
|
|
3072
|
+
error && /* @__PURE__ */ jsx("p", { id: errorId, className: "text-xs text-tollerud-error", children: error })
|
|
3073
|
+
] });
|
|
3074
|
+
}
|
|
3075
|
+
);
|
|
3076
|
+
FormRow.displayName = "FormRow";
|
|
3077
|
+
var PricingCard = forwardRef(
|
|
3078
|
+
({
|
|
3079
|
+
className,
|
|
3080
|
+
name,
|
|
3081
|
+
price,
|
|
3082
|
+
period,
|
|
3083
|
+
description,
|
|
3084
|
+
features = [],
|
|
3085
|
+
ctaLabel = "Get started",
|
|
3086
|
+
onCtaClick,
|
|
3087
|
+
featured,
|
|
3088
|
+
badge,
|
|
3089
|
+
...props
|
|
3090
|
+
}, ref) => {
|
|
3091
|
+
return /* @__PURE__ */ jsxs(
|
|
3092
|
+
"div",
|
|
3093
|
+
{
|
|
3094
|
+
ref,
|
|
3095
|
+
className: cn(
|
|
3096
|
+
"flex flex-col gap-5 rounded-xl border p-6",
|
|
3097
|
+
featured ? "border-tollerud-yellow bg-tollerud-yellow/[0.04] shadow-[0_0_0_1px_rgba(255,255,0,0.15)]" : "border-tollerud-border bg-tollerud-surface",
|
|
3098
|
+
className
|
|
3099
|
+
),
|
|
3100
|
+
...props,
|
|
3101
|
+
children: [
|
|
3102
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-1", children: [
|
|
3103
|
+
badge && /* @__PURE__ */ jsx("span", { className: "inline-flex w-fit items-center rounded-full bg-tollerud-yellow/15 px-2.5 py-0.5 text-xs font-medium text-tollerud-yellow", children: badge }),
|
|
3104
|
+
/* @__PURE__ */ jsx("h3", { className: "text-base font-medium text-tollerud-text-primary", children: name }),
|
|
3105
|
+
description && /* @__PURE__ */ jsx("p", { className: "text-sm text-tollerud-text-muted", children: description })
|
|
3106
|
+
] }),
|
|
3107
|
+
/* @__PURE__ */ jsxs("div", { className: "flex items-baseline gap-1", children: [
|
|
3108
|
+
/* @__PURE__ */ jsx("span", { className: "text-3xl font-semibold tracking-tight text-tollerud-text-primary", children: price }),
|
|
3109
|
+
period && /* @__PURE__ */ jsx("span", { className: "text-sm text-tollerud-text-muted", children: period })
|
|
3110
|
+
] }),
|
|
3111
|
+
features.length > 0 && /* @__PURE__ */ jsx("ul", { className: "flex flex-col gap-2.5", children: features.map((feature, i) => /* @__PURE__ */ jsxs("li", { className: "flex items-start gap-2.5 text-sm text-tollerud-text-secondary", children: [
|
|
3112
|
+
/* @__PURE__ */ jsx(Check, { size: 16, className: "mt-0.5 shrink-0 text-tollerud-yellow" }),
|
|
3113
|
+
/* @__PURE__ */ jsx("span", { children: feature })
|
|
3114
|
+
] }, i)) }),
|
|
3115
|
+
/* @__PURE__ */ jsx(Button, { variant: featured ? "primary" : "secondary", onClick: onCtaClick, className: "mt-auto w-full", children: ctaLabel })
|
|
3116
|
+
]
|
|
3117
|
+
}
|
|
3118
|
+
);
|
|
3119
|
+
}
|
|
3120
|
+
);
|
|
3121
|
+
PricingCard.displayName = "PricingCard";
|
|
3122
|
+
var AccordionContext = createContext(null);
|
|
3123
|
+
function useAccordionContext(component) {
|
|
3124
|
+
const ctx = useContext(AccordionContext);
|
|
3125
|
+
if (!ctx) throw new Error(`<${component}> must be used within <Accordion>`);
|
|
3126
|
+
return ctx;
|
|
3127
|
+
}
|
|
3128
|
+
var Accordion = forwardRef(
|
|
3129
|
+
({ className, multiple = false, defaultOpen, children, ...props }, ref) => {
|
|
3130
|
+
const [openItems, setOpenItems] = useState(() => {
|
|
3131
|
+
if (!defaultOpen) return /* @__PURE__ */ new Set();
|
|
3132
|
+
return new Set(Array.isArray(defaultOpen) ? defaultOpen : [defaultOpen]);
|
|
3133
|
+
});
|
|
3134
|
+
const toggle = (value) => {
|
|
3135
|
+
setOpenItems((prev) => {
|
|
3136
|
+
const next = multiple ? new Set(prev) : /* @__PURE__ */ new Set();
|
|
3137
|
+
if (prev.has(value)) {
|
|
3138
|
+
next.delete(value);
|
|
3139
|
+
} else {
|
|
3140
|
+
next.add(value);
|
|
3141
|
+
}
|
|
3142
|
+
return next;
|
|
3143
|
+
});
|
|
3144
|
+
};
|
|
3145
|
+
return /* @__PURE__ */ jsx(AccordionContext.Provider, { value: { openItems, toggle }, children: /* @__PURE__ */ jsx("div", { ref, className: cn("flex flex-col divide-y divide-tollerud-border rounded-lg border border-tollerud-border", className), ...props, children }) });
|
|
3146
|
+
}
|
|
3147
|
+
);
|
|
3148
|
+
Accordion.displayName = "Accordion";
|
|
3149
|
+
var AccordionItemContext = createContext(null);
|
|
3150
|
+
var AccordionItem = forwardRef(
|
|
3151
|
+
({ className, value, children, ...props }, ref) => {
|
|
3152
|
+
const { openItems } = useAccordionContext("AccordionItem");
|
|
3153
|
+
const autoId = useId();
|
|
3154
|
+
const open = openItems.has(value);
|
|
3155
|
+
return /* @__PURE__ */ jsx(
|
|
3156
|
+
AccordionItemContext.Provider,
|
|
3157
|
+
{
|
|
3158
|
+
value: { value, open, triggerId: `${autoId}-trigger`, contentId: `${autoId}-content` },
|
|
3159
|
+
children: /* @__PURE__ */ jsx("div", { ref, className: cn("first:rounded-t-lg last:rounded-b-lg", className), ...props, children })
|
|
3160
|
+
}
|
|
3161
|
+
);
|
|
3162
|
+
}
|
|
3163
|
+
);
|
|
3164
|
+
AccordionItem.displayName = "AccordionItem";
|
|
3165
|
+
function useAccordionItemContext(component) {
|
|
3166
|
+
const ctx = useContext(AccordionItemContext);
|
|
3167
|
+
if (!ctx) throw new Error(`<${component}> must be used within <AccordionItem>`);
|
|
3168
|
+
return ctx;
|
|
3169
|
+
}
|
|
3170
|
+
var AccordionTrigger = forwardRef(
|
|
3171
|
+
({ className, children, ...props }, ref) => {
|
|
3172
|
+
const { toggle } = useAccordionContext("AccordionTrigger");
|
|
3173
|
+
const { value, open, triggerId, contentId } = useAccordionItemContext("AccordionTrigger");
|
|
3174
|
+
return /* @__PURE__ */ jsxs(
|
|
3175
|
+
"button",
|
|
3176
|
+
{
|
|
3177
|
+
ref,
|
|
3178
|
+
id: triggerId,
|
|
3179
|
+
type: "button",
|
|
3180
|
+
"aria-expanded": open,
|
|
3181
|
+
"aria-controls": contentId,
|
|
3182
|
+
onClick: () => toggle(value),
|
|
3183
|
+
className: cn(
|
|
3184
|
+
"flex w-full items-center justify-between gap-4 px-4 py-3.5 text-left text-sm font-medium",
|
|
3185
|
+
"text-tollerud-text-primary hover:bg-tollerud-surface-hover transition-colors duration-[150ms]",
|
|
3186
|
+
className
|
|
3187
|
+
),
|
|
3188
|
+
...props,
|
|
3189
|
+
children: [
|
|
3190
|
+
children,
|
|
3191
|
+
/* @__PURE__ */ jsx(
|
|
3192
|
+
ChevronDown,
|
|
3193
|
+
{
|
|
3194
|
+
size: 16,
|
|
3195
|
+
className: cn("shrink-0 text-tollerud-text-muted transition-transform duration-[200ms]", open && "rotate-180")
|
|
3196
|
+
}
|
|
3197
|
+
)
|
|
3198
|
+
]
|
|
3199
|
+
}
|
|
3200
|
+
);
|
|
3201
|
+
}
|
|
3202
|
+
);
|
|
3203
|
+
AccordionTrigger.displayName = "AccordionTrigger";
|
|
3204
|
+
var AccordionContent = forwardRef(
|
|
3205
|
+
({ className, children, ...props }, ref) => {
|
|
3206
|
+
const { open, triggerId, contentId } = useAccordionItemContext("AccordionContent");
|
|
3207
|
+
return /* @__PURE__ */ jsx(
|
|
3208
|
+
"div",
|
|
3209
|
+
{
|
|
3210
|
+
ref,
|
|
3211
|
+
id: contentId,
|
|
3212
|
+
role: "region",
|
|
3213
|
+
"aria-labelledby": triggerId,
|
|
3214
|
+
hidden: !open,
|
|
3215
|
+
className: cn("px-4 pb-4 text-sm text-tollerud-text-secondary", className),
|
|
3216
|
+
...props,
|
|
3217
|
+
children
|
|
3218
|
+
}
|
|
3219
|
+
);
|
|
3220
|
+
}
|
|
3221
|
+
);
|
|
3222
|
+
AccordionContent.displayName = "AccordionContent";
|
|
3223
|
+
var Slider = forwardRef(
|
|
3224
|
+
({ className, label, showValue, id: idProp, value, defaultValue, min = 0, max = 100, onChange, ...props }, ref) => {
|
|
3225
|
+
const autoId = useId();
|
|
3226
|
+
const id = idProp ?? autoId;
|
|
3227
|
+
const current = value ?? defaultValue ?? min;
|
|
3228
|
+
return /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-1.5", children: [
|
|
3229
|
+
(label || showValue) && /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between text-xs", children: [
|
|
3230
|
+
label && /* @__PURE__ */ jsx("label", { htmlFor: id, className: "font-medium text-tollerud-text-muted", children: label }),
|
|
3231
|
+
showValue && /* @__PURE__ */ jsx("span", { className: "text-tollerud-text-secondary tabular-nums", children: current })
|
|
3232
|
+
] }),
|
|
3233
|
+
/* @__PURE__ */ jsx(
|
|
3234
|
+
"input",
|
|
3235
|
+
{
|
|
3236
|
+
ref,
|
|
3237
|
+
id,
|
|
3238
|
+
type: "range",
|
|
3239
|
+
min,
|
|
3240
|
+
max,
|
|
3241
|
+
value,
|
|
3242
|
+
defaultValue,
|
|
3243
|
+
onChange: (e) => onChange?.(Number(e.target.value)),
|
|
3244
|
+
className: cn(
|
|
3245
|
+
"h-1.5 w-full cursor-pointer appearance-none rounded-full bg-tollerud-surface-raised accent-tollerud-yellow",
|
|
3246
|
+
"[&::-webkit-slider-thumb]:appearance-none [&::-webkit-slider-thumb]:h-4 [&::-webkit-slider-thumb]:w-4",
|
|
3247
|
+
"[&::-webkit-slider-thumb]:rounded-full [&::-webkit-slider-thumb]:bg-tollerud-yellow [&::-webkit-slider-thumb]:cursor-pointer",
|
|
3248
|
+
"[&::-webkit-slider-thumb]:border-2 [&::-webkit-slider-thumb]:border-tollerud-noir-black",
|
|
3249
|
+
"[&::-moz-range-thumb]:h-4 [&::-moz-range-thumb]:w-4 [&::-moz-range-thumb]:rounded-full",
|
|
3250
|
+
"[&::-moz-range-thumb]:bg-tollerud-yellow [&::-moz-range-thumb]:border-2 [&::-moz-range-thumb]:border-tollerud-noir-black [&::-moz-range-thumb]:cursor-pointer",
|
|
3251
|
+
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-tollerud-yellow/50",
|
|
3252
|
+
"disabled:opacity-40 disabled:pointer-events-none",
|
|
3253
|
+
className
|
|
3254
|
+
),
|
|
3255
|
+
...props
|
|
3256
|
+
}
|
|
3257
|
+
)
|
|
3258
|
+
] });
|
|
3259
|
+
}
|
|
3260
|
+
);
|
|
3261
|
+
Slider.displayName = "Slider";
|
|
3262
|
+
var PasswordInput = forwardRef(
|
|
3263
|
+
({ className, label, error, id, ...props }, ref) => {
|
|
3264
|
+
const [visible, setVisible] = useState(false);
|
|
3265
|
+
return /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-1", children: [
|
|
3266
|
+
label && /* @__PURE__ */ jsx("label", { htmlFor: id, className: "text-xs font-medium text-tollerud-text-muted", children: label }),
|
|
3267
|
+
/* @__PURE__ */ jsxs("div", { className: "relative", children: [
|
|
3268
|
+
/* @__PURE__ */ jsx(
|
|
3269
|
+
"input",
|
|
3270
|
+
{
|
|
3271
|
+
ref,
|
|
3272
|
+
id,
|
|
3273
|
+
type: visible ? "text" : "password",
|
|
3274
|
+
className: cn(
|
|
3275
|
+
"w-full font-sans text-base px-3 py-2 pr-10 rounded",
|
|
3276
|
+
"bg-tollerud-surface-raised border",
|
|
3277
|
+
"text-tollerud-text-primary",
|
|
3278
|
+
"placeholder:text-tollerud-text-muted",
|
|
3279
|
+
"transition-[border-color] duration-[150ms]",
|
|
3280
|
+
"focus:outline-none focus:border-tollerud-yellow focus:shadow-[0_0_0_1px_#E8D500]",
|
|
3281
|
+
error ? "border-tollerud-error" : "border-tollerud-border",
|
|
3282
|
+
className
|
|
3283
|
+
),
|
|
3284
|
+
...props
|
|
3285
|
+
}
|
|
3286
|
+
),
|
|
3287
|
+
/* @__PURE__ */ jsx(
|
|
3288
|
+
"button",
|
|
3289
|
+
{
|
|
3290
|
+
type: "button",
|
|
3291
|
+
onClick: () => setVisible((v) => !v),
|
|
3292
|
+
"aria-label": visible ? "Hide password" : "Show password",
|
|
3293
|
+
"aria-pressed": visible,
|
|
3294
|
+
className: "absolute right-2.5 top-1/2 -translate-y-1/2 text-tollerud-text-muted hover:text-tollerud-text-secondary transition-colors duration-[150ms]",
|
|
3295
|
+
children: visible ? /* @__PURE__ */ jsx(EyeOff, { size: 16 }) : /* @__PURE__ */ jsx(Eye, { size: 16 })
|
|
3296
|
+
}
|
|
3297
|
+
)
|
|
3298
|
+
] }),
|
|
3299
|
+
error && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-error mt-0.5", children: error })
|
|
3300
|
+
] });
|
|
3301
|
+
}
|
|
3302
|
+
);
|
|
3303
|
+
PasswordInput.displayName = "PasswordInput";
|
|
3304
|
+
var defaultFilter = (option, query) => option.label.toLowerCase().includes(query.toLowerCase());
|
|
3305
|
+
function Combobox({
|
|
3306
|
+
options,
|
|
3307
|
+
value: valueProp,
|
|
3308
|
+
defaultValue,
|
|
3309
|
+
onChange,
|
|
3310
|
+
placeholder = "Search\u2026",
|
|
3311
|
+
label,
|
|
3312
|
+
error,
|
|
3313
|
+
filter = defaultFilter,
|
|
3314
|
+
className,
|
|
3315
|
+
disabled
|
|
3316
|
+
}) {
|
|
3317
|
+
const id = useId();
|
|
3318
|
+
const rootRef = useRef(null);
|
|
3319
|
+
const isControlled = valueProp !== void 0;
|
|
3320
|
+
const [internalValue, setInternalValue] = useState(defaultValue);
|
|
3321
|
+
const value = isControlled ? valueProp : internalValue;
|
|
3322
|
+
const [open, setOpen] = useState(false);
|
|
3323
|
+
const [query, setQuery] = useState("");
|
|
3324
|
+
const [activeIndex, setActiveIndex] = useState(0);
|
|
3325
|
+
const selected = options.find((o) => o.value === value);
|
|
3326
|
+
const filtered = useMemo(() => {
|
|
3327
|
+
if (!query) return options;
|
|
3328
|
+
return options.filter((o) => filter(o, query));
|
|
3329
|
+
}, [options, query, filter]);
|
|
3330
|
+
useEffect(() => {
|
|
3331
|
+
if (!open) return;
|
|
3332
|
+
function onClickOutside(e) {
|
|
3333
|
+
if (rootRef.current && !rootRef.current.contains(e.target)) {
|
|
3334
|
+
setOpen(false);
|
|
3335
|
+
setQuery("");
|
|
3336
|
+
}
|
|
3337
|
+
}
|
|
3338
|
+
function onResize() {
|
|
3339
|
+
setOpen(false);
|
|
3340
|
+
setQuery("");
|
|
3341
|
+
}
|
|
3342
|
+
document.addEventListener("mousedown", onClickOutside);
|
|
3343
|
+
window.addEventListener("resize", onResize);
|
|
3344
|
+
return () => {
|
|
3345
|
+
document.removeEventListener("mousedown", onClickOutside);
|
|
3346
|
+
window.removeEventListener("resize", onResize);
|
|
3347
|
+
};
|
|
3348
|
+
}, [open]);
|
|
3349
|
+
const commit = (option) => {
|
|
3350
|
+
if (option.disabled) return;
|
|
3351
|
+
if (!isControlled) setInternalValue(option.value);
|
|
3352
|
+
onChange?.(option.value);
|
|
3353
|
+
setOpen(false);
|
|
3354
|
+
setQuery("");
|
|
3355
|
+
};
|
|
3356
|
+
const onKeyDown = (e) => {
|
|
3357
|
+
if (e.key === "ArrowDown") {
|
|
3358
|
+
e.preventDefault();
|
|
3359
|
+
setOpen(true);
|
|
3360
|
+
setActiveIndex((i) => Math.min(i + 1, filtered.length - 1));
|
|
3361
|
+
} else if (e.key === "ArrowUp") {
|
|
3362
|
+
e.preventDefault();
|
|
3363
|
+
setActiveIndex((i) => Math.max(i - 1, 0));
|
|
3364
|
+
} else if (e.key === "Enter") {
|
|
3365
|
+
e.preventDefault();
|
|
3366
|
+
const opt = filtered[activeIndex];
|
|
3367
|
+
if (opt) commit(opt);
|
|
3368
|
+
} else if (e.key === "Escape") {
|
|
3369
|
+
setOpen(false);
|
|
3370
|
+
setQuery("");
|
|
3371
|
+
}
|
|
3372
|
+
};
|
|
3373
|
+
return /* @__PURE__ */ jsxs("div", { ref: rootRef, className: cn("relative flex flex-col gap-1", className), children: [
|
|
3374
|
+
label && /* @__PURE__ */ jsx("label", { htmlFor: id, className: "text-xs font-medium text-tollerud-text-muted", children: label }),
|
|
3375
|
+
/* @__PURE__ */ jsxs("div", { className: "relative", children: [
|
|
3376
|
+
/* @__PURE__ */ jsx(
|
|
3377
|
+
"input",
|
|
3378
|
+
{
|
|
3379
|
+
id,
|
|
3380
|
+
role: "combobox",
|
|
3381
|
+
"aria-expanded": open,
|
|
3382
|
+
"aria-autocomplete": "list",
|
|
3383
|
+
"aria-controls": `${id}-listbox`,
|
|
3384
|
+
disabled,
|
|
3385
|
+
value: open ? query : selected?.label ?? "",
|
|
3386
|
+
placeholder: selected ? selected.label : placeholder,
|
|
3387
|
+
onFocus: () => {
|
|
3388
|
+
setOpen(true);
|
|
3389
|
+
setActiveIndex(0);
|
|
3390
|
+
},
|
|
3391
|
+
onChange: (e) => {
|
|
3392
|
+
setQuery(e.target.value);
|
|
3393
|
+
setActiveIndex(0);
|
|
3394
|
+
if (!open) setOpen(true);
|
|
3395
|
+
},
|
|
3396
|
+
onKeyDown,
|
|
3397
|
+
className: cn(
|
|
3398
|
+
"w-full font-sans text-base px-3 py-2 pr-9 rounded",
|
|
3399
|
+
"bg-tollerud-surface-raised border",
|
|
3400
|
+
"text-tollerud-text-primary placeholder:text-tollerud-text-muted",
|
|
3401
|
+
"transition-[border-color] duration-[150ms]",
|
|
3402
|
+
"focus:outline-none focus:border-tollerud-yellow focus:shadow-[0_0_0_1px_#E8D500]",
|
|
3403
|
+
error ? "border-tollerud-error" : "border-tollerud-border",
|
|
3404
|
+
disabled && "opacity-50 pointer-events-none"
|
|
3405
|
+
)
|
|
3406
|
+
}
|
|
3407
|
+
),
|
|
3408
|
+
/* @__PURE__ */ jsx(
|
|
3409
|
+
ChevronDown,
|
|
3410
|
+
{
|
|
3411
|
+
size: 15,
|
|
3412
|
+
className: cn(
|
|
3413
|
+
"pointer-events-none absolute right-3 top-1/2 -translate-y-1/2 text-tollerud-text-muted transition-transform duration-[150ms]",
|
|
3414
|
+
open && "rotate-180"
|
|
3415
|
+
)
|
|
3416
|
+
}
|
|
3417
|
+
)
|
|
3418
|
+
] }),
|
|
3419
|
+
open && /* @__PURE__ */ jsxs(
|
|
3420
|
+
"ul",
|
|
3421
|
+
{
|
|
3422
|
+
id: `${id}-listbox`,
|
|
3423
|
+
role: "listbox",
|
|
3424
|
+
className: "absolute top-full z-20 mt-1 max-h-64 w-full overflow-auto rounded-lg border border-tollerud-border bg-tollerud-surface-overlay py-1 shadow-lg",
|
|
3425
|
+
children: [
|
|
3426
|
+
filtered.length === 0 && /* @__PURE__ */ jsx("li", { className: "px-3 py-2 text-sm text-tollerud-text-muted", children: "No results" }),
|
|
3427
|
+
filtered.map((option, i) => {
|
|
3428
|
+
const isSelected = option.value === value;
|
|
3429
|
+
return /* @__PURE__ */ jsxs(
|
|
3430
|
+
"li",
|
|
3431
|
+
{
|
|
3432
|
+
role: "option",
|
|
3433
|
+
"aria-selected": isSelected,
|
|
3434
|
+
onMouseDown: (e) => {
|
|
3435
|
+
e.preventDefault();
|
|
3436
|
+
commit(option);
|
|
3437
|
+
},
|
|
3438
|
+
onMouseEnter: () => setActiveIndex(i),
|
|
3439
|
+
className: cn(
|
|
3440
|
+
"flex items-center justify-between gap-2 px-3 py-2 text-sm cursor-pointer",
|
|
3441
|
+
i === activeIndex ? "bg-tollerud-surface-hover text-tollerud-text-primary" : "text-tollerud-text-secondary",
|
|
3442
|
+
option.disabled && "opacity-40 pointer-events-none"
|
|
3443
|
+
),
|
|
3444
|
+
children: [
|
|
3445
|
+
option.label,
|
|
3446
|
+
isSelected && /* @__PURE__ */ jsx(Check, { size: 14, className: "text-tollerud-yellow" })
|
|
3447
|
+
]
|
|
3448
|
+
},
|
|
3449
|
+
option.value
|
|
3450
|
+
);
|
|
3451
|
+
})
|
|
3452
|
+
]
|
|
3453
|
+
}
|
|
3454
|
+
),
|
|
3455
|
+
error && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-error mt-0.5", children: error })
|
|
3456
|
+
] });
|
|
3457
|
+
}
|
|
3458
|
+
Combobox.displayName = "Combobox";
|
|
3459
|
+
var defaultFormat = (date) => date.toLocaleDateString(void 0, { year: "numeric", month: "short", day: "numeric" });
|
|
3460
|
+
function isSameDay(a, b) {
|
|
3461
|
+
return a.getFullYear() === b.getFullYear() && a.getMonth() === b.getMonth() && a.getDate() === b.getDate();
|
|
3462
|
+
}
|
|
3463
|
+
function startOfMonth(date) {
|
|
3464
|
+
return new Date(date.getFullYear(), date.getMonth(), 1);
|
|
3465
|
+
}
|
|
3466
|
+
function buildCalendarGrid(monthDate) {
|
|
3467
|
+
const first = startOfMonth(monthDate);
|
|
3468
|
+
const startWeekday = first.getDay();
|
|
3469
|
+
const daysInMonth = new Date(monthDate.getFullYear(), monthDate.getMonth() + 1, 0).getDate();
|
|
3470
|
+
const cells = [];
|
|
3471
|
+
for (let i = 0; i < startWeekday; i++) cells.push(null);
|
|
3472
|
+
for (let d = 1; d <= daysInMonth; d++) cells.push(new Date(monthDate.getFullYear(), monthDate.getMonth(), d));
|
|
3473
|
+
return cells;
|
|
3474
|
+
}
|
|
3475
|
+
var WEEKDAYS = ["Su", "Mo", "Tu", "We", "Th", "Fr", "Sa"];
|
|
3476
|
+
function DatePicker({
|
|
3477
|
+
value: valueProp,
|
|
3478
|
+
defaultValue = null,
|
|
3479
|
+
onChange,
|
|
3480
|
+
label,
|
|
3481
|
+
error,
|
|
3482
|
+
placeholder = "Select a date",
|
|
3483
|
+
formatDate = defaultFormat,
|
|
3484
|
+
className,
|
|
3485
|
+
disabled
|
|
3486
|
+
}) {
|
|
3487
|
+
const id = useId();
|
|
3488
|
+
const rootRef = useRef(null);
|
|
3489
|
+
const isControlled = valueProp !== void 0;
|
|
3490
|
+
const [internalValue, setInternalValue] = useState(defaultValue);
|
|
3491
|
+
const value = isControlled ? valueProp ?? null : internalValue;
|
|
3492
|
+
const [open, setOpen] = useState(false);
|
|
3493
|
+
const [viewMonth, setViewMonth] = useState(() => startOfMonth(value ?? /* @__PURE__ */ new Date()));
|
|
3494
|
+
const cells = useMemo(() => buildCalendarGrid(viewMonth), [viewMonth]);
|
|
3495
|
+
useEffect(() => {
|
|
3496
|
+
if (!open) return;
|
|
3497
|
+
function onClickOutside(e) {
|
|
3498
|
+
if (rootRef.current && !rootRef.current.contains(e.target)) setOpen(false);
|
|
3499
|
+
}
|
|
3500
|
+
function onResize() {
|
|
3501
|
+
setOpen(false);
|
|
3502
|
+
}
|
|
3503
|
+
document.addEventListener("mousedown", onClickOutside);
|
|
3504
|
+
window.addEventListener("resize", onResize);
|
|
3505
|
+
return () => {
|
|
3506
|
+
document.removeEventListener("mousedown", onClickOutside);
|
|
3507
|
+
window.removeEventListener("resize", onResize);
|
|
3508
|
+
};
|
|
3509
|
+
}, [open]);
|
|
3510
|
+
const select = (date) => {
|
|
3511
|
+
if (!isControlled) setInternalValue(date);
|
|
3512
|
+
onChange?.(date);
|
|
3513
|
+
setOpen(false);
|
|
3514
|
+
};
|
|
3515
|
+
return /* @__PURE__ */ jsxs("div", { ref: rootRef, className: cn("relative flex flex-col gap-1", className), children: [
|
|
3516
|
+
label && /* @__PURE__ */ jsx("label", { htmlFor: id, className: "text-xs font-medium text-tollerud-text-muted", children: label }),
|
|
3517
|
+
/* @__PURE__ */ jsxs(
|
|
3518
|
+
"button",
|
|
3519
|
+
{
|
|
3520
|
+
id,
|
|
3521
|
+
type: "button",
|
|
3522
|
+
disabled,
|
|
3523
|
+
onClick: () => {
|
|
3524
|
+
setViewMonth(startOfMonth(value ?? /* @__PURE__ */ new Date()));
|
|
3525
|
+
setOpen((o) => !o);
|
|
3526
|
+
},
|
|
3527
|
+
"aria-haspopup": "dialog",
|
|
3528
|
+
"aria-expanded": open,
|
|
3529
|
+
className: cn(
|
|
3530
|
+
"flex w-full items-center justify-between gap-2 rounded px-3 py-2 text-left text-base",
|
|
3531
|
+
"bg-tollerud-surface-raised border",
|
|
3532
|
+
"transition-[border-color] duration-[150ms]",
|
|
3533
|
+
"focus:outline-none focus:border-tollerud-yellow focus:shadow-[0_0_0_1px_#E8D500]",
|
|
3534
|
+
error ? "border-tollerud-error" : "border-tollerud-border",
|
|
3535
|
+
value ? "text-tollerud-text-primary" : "text-tollerud-text-muted",
|
|
3536
|
+
disabled && "opacity-50 pointer-events-none"
|
|
3537
|
+
),
|
|
3538
|
+
children: [
|
|
3539
|
+
/* @__PURE__ */ jsx("span", { children: value ? formatDate(value) : placeholder }),
|
|
3540
|
+
/* @__PURE__ */ jsx(Calendar, { size: 15, className: "text-tollerud-text-muted" })
|
|
3541
|
+
]
|
|
3542
|
+
}
|
|
3543
|
+
),
|
|
3544
|
+
open && /* @__PURE__ */ jsxs(
|
|
3545
|
+
"div",
|
|
3546
|
+
{
|
|
3547
|
+
role: "dialog",
|
|
3548
|
+
"aria-label": "Choose date",
|
|
3549
|
+
className: "absolute top-full z-20 mt-1 w-72 rounded-lg border border-tollerud-border bg-tollerud-surface-overlay p-3 shadow-lg",
|
|
3550
|
+
children: [
|
|
3551
|
+
/* @__PURE__ */ jsxs("div", { className: "mb-2 flex items-center justify-between", children: [
|
|
3552
|
+
/* @__PURE__ */ jsx(
|
|
3553
|
+
"button",
|
|
3554
|
+
{
|
|
3555
|
+
type: "button",
|
|
3556
|
+
"aria-label": "Previous month",
|
|
3557
|
+
onClick: () => setViewMonth((m) => new Date(m.getFullYear(), m.getMonth() - 1, 1)),
|
|
3558
|
+
className: "rounded p-1 text-tollerud-text-secondary hover:bg-tollerud-surface-hover",
|
|
3559
|
+
children: /* @__PURE__ */ jsx(ChevronLeft, { size: 16 })
|
|
3560
|
+
}
|
|
3561
|
+
),
|
|
3562
|
+
/* @__PURE__ */ jsx("span", { className: "text-sm font-medium text-tollerud-text-primary", children: viewMonth.toLocaleDateString(void 0, { month: "long", year: "numeric" }) }),
|
|
3563
|
+
/* @__PURE__ */ jsx(
|
|
3564
|
+
"button",
|
|
3565
|
+
{
|
|
3566
|
+
type: "button",
|
|
3567
|
+
"aria-label": "Next month",
|
|
3568
|
+
onClick: () => setViewMonth((m) => new Date(m.getFullYear(), m.getMonth() + 1, 1)),
|
|
3569
|
+
className: "rounded p-1 text-tollerud-text-secondary hover:bg-tollerud-surface-hover",
|
|
3570
|
+
children: /* @__PURE__ */ jsx(ChevronRight, { size: 16 })
|
|
3571
|
+
}
|
|
3572
|
+
)
|
|
3573
|
+
] }),
|
|
3574
|
+
/* @__PURE__ */ jsxs("div", { className: "grid grid-cols-7 gap-1 text-center", children: [
|
|
3575
|
+
WEEKDAYS.map((d) => /* @__PURE__ */ jsx("span", { className: "text-[11px] font-medium text-tollerud-text-muted py-1", children: d }, d)),
|
|
3576
|
+
cells.map((date, i) => {
|
|
3577
|
+
if (!date) return /* @__PURE__ */ jsx("span", {}, i);
|
|
3578
|
+
const selected = value ? isSameDay(date, value) : false;
|
|
3579
|
+
const today = isSameDay(date, /* @__PURE__ */ new Date());
|
|
3580
|
+
return /* @__PURE__ */ jsx(
|
|
3581
|
+
"button",
|
|
3582
|
+
{
|
|
3583
|
+
type: "button",
|
|
3584
|
+
onClick: () => select(date),
|
|
3585
|
+
className: cn(
|
|
3586
|
+
"h-8 w-8 rounded-full text-sm transition-colors duration-[150ms]",
|
|
3587
|
+
selected ? "bg-tollerud-yellow text-tollerud-noir-black font-medium" : "text-tollerud-text-secondary hover:bg-tollerud-surface-hover",
|
|
3588
|
+
!selected && today && "ring-1 ring-tollerud-yellow/40"
|
|
3589
|
+
),
|
|
3590
|
+
children: date.getDate()
|
|
3591
|
+
},
|
|
3592
|
+
i
|
|
3593
|
+
);
|
|
3594
|
+
})
|
|
3595
|
+
] })
|
|
3596
|
+
]
|
|
3597
|
+
}
|
|
3598
|
+
),
|
|
3599
|
+
error && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-error mt-0.5", children: error })
|
|
3600
|
+
] });
|
|
3601
|
+
}
|
|
3602
|
+
DatePicker.displayName = "DatePicker";
|
|
3603
|
+
function formatBytes(bytes) {
|
|
3604
|
+
if (bytes < 1024) return `${bytes} B`;
|
|
3605
|
+
if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;
|
|
3606
|
+
return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
|
|
3607
|
+
}
|
|
3608
|
+
function FileUpload({
|
|
3609
|
+
label,
|
|
3610
|
+
description,
|
|
3611
|
+
error,
|
|
3612
|
+
accept,
|
|
3613
|
+
multiple,
|
|
3614
|
+
onFilesChange,
|
|
3615
|
+
className,
|
|
3616
|
+
disabled
|
|
3617
|
+
}) {
|
|
3618
|
+
const id = useId();
|
|
3619
|
+
const inputRef = useRef(null);
|
|
3620
|
+
const [files, setFiles] = useState([]);
|
|
3621
|
+
const [dragging, setDragging] = useState(false);
|
|
3622
|
+
const setAndNotify = (next) => {
|
|
3623
|
+
setFiles(next);
|
|
3624
|
+
onFilesChange?.(next);
|
|
3625
|
+
};
|
|
3626
|
+
const addFiles = (incoming) => {
|
|
3627
|
+
if (!incoming || incoming.length === 0) return;
|
|
3628
|
+
const incomingArr = Array.from(incoming);
|
|
3629
|
+
setAndNotify(multiple ? [...files, ...incomingArr] : [incomingArr[0]]);
|
|
3630
|
+
};
|
|
3631
|
+
const removeAt = (index) => {
|
|
3632
|
+
setAndNotify(files.filter((_, i) => i !== index));
|
|
3633
|
+
};
|
|
3634
|
+
const onDrop = (e) => {
|
|
3635
|
+
e.preventDefault();
|
|
3636
|
+
setDragging(false);
|
|
3637
|
+
if (disabled) return;
|
|
3638
|
+
addFiles(e.dataTransfer.files);
|
|
3639
|
+
};
|
|
3640
|
+
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col gap-1.5", className), children: [
|
|
3641
|
+
label && /* @__PURE__ */ jsx("label", { htmlFor: id, className: "text-xs font-medium text-tollerud-text-muted", children: label }),
|
|
3642
|
+
/* @__PURE__ */ jsxs(
|
|
3643
|
+
"div",
|
|
3644
|
+
{
|
|
3645
|
+
role: "button",
|
|
3646
|
+
tabIndex: disabled ? -1 : 0,
|
|
3647
|
+
"aria-disabled": disabled,
|
|
3648
|
+
onClick: () => !disabled && inputRef.current?.click(),
|
|
3649
|
+
onKeyDown: (e) => {
|
|
3650
|
+
if (!disabled && (e.key === "Enter" || e.key === " ")) {
|
|
3651
|
+
e.preventDefault();
|
|
3652
|
+
inputRef.current?.click();
|
|
3653
|
+
}
|
|
3654
|
+
},
|
|
3655
|
+
onDragOver: (e) => {
|
|
3656
|
+
e.preventDefault();
|
|
3657
|
+
if (!disabled) setDragging(true);
|
|
3658
|
+
},
|
|
3659
|
+
onDragLeave: () => setDragging(false),
|
|
3660
|
+
onDrop,
|
|
3661
|
+
className: cn(
|
|
3662
|
+
"flex flex-col items-center justify-center gap-2 rounded-lg border border-dashed px-6 py-8 text-center cursor-pointer transition-colors duration-[150ms]",
|
|
3663
|
+
dragging ? "border-tollerud-yellow bg-tollerud-yellow/[0.06]" : "border-tollerud-border bg-tollerud-surface-raised hover:border-tollerud-text-secondary",
|
|
3664
|
+
error && "border-tollerud-error",
|
|
3665
|
+
disabled && "opacity-50 pointer-events-none"
|
|
3666
|
+
),
|
|
3667
|
+
children: [
|
|
3668
|
+
/* @__PURE__ */ jsx(Upload, { size: 20, className: "text-tollerud-text-muted" }),
|
|
3669
|
+
/* @__PURE__ */ jsxs("div", { className: "text-sm text-tollerud-text-secondary", children: [
|
|
3670
|
+
/* @__PURE__ */ jsx("span", { className: "font-medium text-tollerud-yellow", children: "Click to upload" }),
|
|
3671
|
+
" or drag and drop"
|
|
3672
|
+
] }),
|
|
3673
|
+
description && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-text-muted", children: description }),
|
|
3674
|
+
/* @__PURE__ */ jsx(
|
|
3675
|
+
"input",
|
|
3676
|
+
{
|
|
3677
|
+
ref: inputRef,
|
|
3678
|
+
id,
|
|
3679
|
+
type: "file",
|
|
3680
|
+
accept,
|
|
3681
|
+
multiple,
|
|
3682
|
+
disabled,
|
|
3683
|
+
onChange: (e) => addFiles(e.target.files),
|
|
3684
|
+
className: "sr-only"
|
|
3685
|
+
}
|
|
3686
|
+
)
|
|
3687
|
+
]
|
|
3688
|
+
}
|
|
3689
|
+
),
|
|
3690
|
+
files.length > 0 && /* @__PURE__ */ jsx("ul", { className: "flex flex-col gap-1.5", children: files.map((file, i) => /* @__PURE__ */ jsxs(
|
|
3691
|
+
"li",
|
|
3692
|
+
{
|
|
3693
|
+
className: "flex items-center gap-2.5 rounded-md border border-tollerud-border bg-tollerud-surface-raised px-3 py-2 text-sm",
|
|
3694
|
+
children: [
|
|
3695
|
+
/* @__PURE__ */ jsx(File, { size: 15, className: "shrink-0 text-tollerud-text-muted" }),
|
|
3696
|
+
/* @__PURE__ */ jsx("span", { className: "flex-1 truncate text-tollerud-text-primary", children: file.name }),
|
|
3697
|
+
/* @__PURE__ */ jsx("span", { className: "shrink-0 text-xs text-tollerud-text-muted", children: formatBytes(file.size) }),
|
|
3698
|
+
/* @__PURE__ */ jsx(
|
|
3699
|
+
"button",
|
|
3700
|
+
{
|
|
3701
|
+
type: "button",
|
|
3702
|
+
"aria-label": `Remove ${file.name}`,
|
|
3703
|
+
onClick: () => removeAt(i),
|
|
3704
|
+
className: "shrink-0 text-tollerud-text-muted hover:text-tollerud-text-primary transition-colors duration-[150ms]",
|
|
3705
|
+
children: /* @__PURE__ */ jsx(X, { size: 14 })
|
|
3706
|
+
}
|
|
3707
|
+
)
|
|
3708
|
+
]
|
|
3709
|
+
},
|
|
3710
|
+
`${file.name}-${i}`
|
|
3711
|
+
)) }),
|
|
3712
|
+
error && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-error", children: error })
|
|
3713
|
+
] });
|
|
3714
|
+
}
|
|
3715
|
+
FileUpload.displayName = "FileUpload";
|
|
3716
|
+
function TagInput({
|
|
3717
|
+
value: valueProp,
|
|
3718
|
+
defaultValue = [],
|
|
3719
|
+
onChange,
|
|
3720
|
+
label,
|
|
3721
|
+
error,
|
|
3722
|
+
placeholder = "Add a tag\u2026",
|
|
3723
|
+
max,
|
|
3724
|
+
className,
|
|
3725
|
+
disabled
|
|
3726
|
+
}) {
|
|
3727
|
+
const id = useId();
|
|
3728
|
+
const isControlled = valueProp !== void 0;
|
|
3729
|
+
const [internalTags, setInternalTags] = useState(defaultValue);
|
|
3730
|
+
const tags = isControlled ? valueProp : internalTags;
|
|
3731
|
+
const [draft, setDraft] = useState("");
|
|
3732
|
+
const setAndNotify = (next) => {
|
|
3733
|
+
if (!isControlled) setInternalTags(next);
|
|
3734
|
+
onChange?.(next);
|
|
3735
|
+
};
|
|
3736
|
+
const addTag = (raw) => {
|
|
3737
|
+
const tag = raw.trim();
|
|
3738
|
+
if (!tag || tags.includes(tag)) return;
|
|
3739
|
+
if (max && tags.length >= max) return;
|
|
3740
|
+
setAndNotify([...tags, tag]);
|
|
3741
|
+
setDraft("");
|
|
3742
|
+
};
|
|
3743
|
+
const removeTag = (index) => {
|
|
3744
|
+
setAndNotify(tags.filter((_, i) => i !== index));
|
|
3745
|
+
};
|
|
3746
|
+
const onKeyDown = (e) => {
|
|
3747
|
+
if (e.key === "Enter" || e.key === ",") {
|
|
3748
|
+
e.preventDefault();
|
|
3749
|
+
addTag(draft);
|
|
3750
|
+
} else if (e.key === "Backspace" && draft === "" && tags.length > 0) {
|
|
3751
|
+
removeTag(tags.length - 1);
|
|
3752
|
+
}
|
|
3753
|
+
};
|
|
3754
|
+
const atMax = max ? tags.length >= max : false;
|
|
3755
|
+
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col gap-1", className), children: [
|
|
3756
|
+
label && /* @__PURE__ */ jsx("label", { htmlFor: id, className: "text-xs font-medium text-tollerud-text-muted", children: label }),
|
|
3757
|
+
/* @__PURE__ */ jsxs(
|
|
3758
|
+
"div",
|
|
3759
|
+
{
|
|
3760
|
+
className: cn(
|
|
3761
|
+
"flex flex-wrap items-center gap-1.5 rounded px-2.5 py-1.5",
|
|
3762
|
+
"bg-tollerud-surface-raised border",
|
|
3763
|
+
"transition-[border-color] duration-[150ms]",
|
|
3764
|
+
"focus-within:border-tollerud-yellow focus-within:shadow-[0_0_0_1px_#E8D500]",
|
|
3765
|
+
error ? "border-tollerud-error" : "border-tollerud-border",
|
|
3766
|
+
disabled && "opacity-50 pointer-events-none"
|
|
3767
|
+
),
|
|
3768
|
+
children: [
|
|
3769
|
+
tags.map((tag, i) => /* @__PURE__ */ jsxs(
|
|
3770
|
+
"span",
|
|
3771
|
+
{
|
|
3772
|
+
className: "inline-flex items-center gap-1 rounded-full bg-tollerud-surface-hover px-2.5 py-0.5 text-xs font-medium text-tollerud-text-primary",
|
|
3773
|
+
children: [
|
|
3774
|
+
tag,
|
|
3775
|
+
/* @__PURE__ */ jsx(
|
|
3776
|
+
"button",
|
|
3777
|
+
{
|
|
3778
|
+
type: "button",
|
|
3779
|
+
"aria-label": `Remove ${tag}`,
|
|
3780
|
+
onClick: () => removeTag(i),
|
|
3781
|
+
className: "text-tollerud-text-muted hover:text-tollerud-text-primary transition-colors duration-[150ms]",
|
|
3782
|
+
children: /* @__PURE__ */ jsx(X, { size: 12 })
|
|
3783
|
+
}
|
|
3784
|
+
)
|
|
3785
|
+
]
|
|
3786
|
+
},
|
|
3787
|
+
`${tag}-${i}`
|
|
3788
|
+
)),
|
|
3789
|
+
/* @__PURE__ */ jsx(
|
|
3790
|
+
"input",
|
|
3791
|
+
{
|
|
3792
|
+
id,
|
|
3793
|
+
value: draft,
|
|
3794
|
+
disabled: disabled || atMax,
|
|
3795
|
+
onChange: (e) => setDraft(e.target.value),
|
|
3796
|
+
onKeyDown,
|
|
3797
|
+
onBlur: () => addTag(draft),
|
|
3798
|
+
placeholder: atMax ? "" : placeholder,
|
|
3799
|
+
className: cn(
|
|
3800
|
+
"min-w-[6rem] flex-1 bg-transparent py-0.5 text-sm text-tollerud-text-primary",
|
|
3801
|
+
"placeholder:text-tollerud-text-muted focus:outline-none"
|
|
3802
|
+
)
|
|
3803
|
+
}
|
|
3804
|
+
)
|
|
3805
|
+
]
|
|
3806
|
+
}
|
|
3807
|
+
),
|
|
3808
|
+
error && /* @__PURE__ */ jsx("p", { className: "text-xs text-tollerud-error mt-0.5", children: error })
|
|
3809
|
+
] });
|
|
3810
|
+
}
|
|
3811
|
+
TagInput.displayName = "TagInput";
|
|
2653
3812
|
|
|
2654
|
-
export { ActionDiff, ActionRow, Alert, AlertInbox, ApprovalCard, BackupStatusPanel, Badge, BentoDashboard, Button, Card, Checkbox, CodeBlock, CommandMenu, Container, DataTable, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, DockerStackCard, DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuLabel, DropdownMenuSeparator, DropdownMenuTrigger, Empty, EmptyContent, EmptyDescription, EmptyHeader, EmptyIcon, EmptyTitle, Footer, GlowCard, HostCard, IncidentCard, Input, Kbd, LogViewer, NoirGlowBackground, Progress, Radio, RadioGroup, RollbackPlan, Select, ServiceHealthCard, Sheet, SheetClose, SheetContent, SheetDescription, SheetHeader, SheetTitle, SheetTrigger, Skeleton, StatCard, StatusDot, Switch, Tabs, TabsContent, TabsList, TabsTrigger, Textarea, Timeline, Toaster, Tooltip, TooltipContent, TooltipProvider, TooltipTrigger, buttonVariants, cn };
|
|
3813
|
+
export { Accordion, AccordionContent, AccordionItem, AccordionTrigger, ActionDiff, ActionRow, Alert, AlertInbox, ApprovalCard, Avatar, AvatarGroup, BackupStatusPanel, Badge, BentoDashboard, Breadcrumb, Button, Card, Checkbox, CodeBlock, Combobox, CommandMenu, Container, DataTable, DatePicker, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, Divider, DockerStackCard, DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuLabel, DropdownMenuSeparator, DropdownMenuTrigger, Empty, EmptyContent, EmptyDescription, EmptyHeader, EmptyIcon, EmptyTitle, FileUpload, Footer, FormRow, GlowCard, HostCard, IncidentCard, Input, Kbd, LogViewer, Meter, NoirGlowBackground, Pagination, Panel, PasswordInput, Pill, PricingCard, Progress, Radio, RadioGroup, RollbackPlan, Segmented, Select, ServiceHealthCard, Sheet, SheetClose, SheetContent, SheetDescription, SheetHeader, SheetTitle, SheetTrigger, Skeleton, Slider, StatCard, StatusDot, Stepper, Switch, Tabs, TabsContent, TabsList, TabsTrigger, TagInput, Textarea, Timeline, Toaster, Tooltip, TooltipContent, TooltipProvider, TooltipTrigger, buttonVariants, cn };
|
|
2655
3814
|
//# sourceMappingURL=index.js.map
|
|
2656
3815
|
//# sourceMappingURL=index.js.map
|