@olundot/ui 0.17.1 → 0.18.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -189,7 +189,7 @@ import { Slot } from "radix-ui";
189
189
  import { jsx, jsxs } from "react/jsx-runtime";
190
190
  var buttonVariants = cva(
191
191
  [
192
- "inline-flex cursor-pointer items-center justify-center whitespace-nowrap rounded-[var(--radius-sm)] border font-medium",
192
+ "inline-flex cursor-pointer items-center justify-center whitespace-nowrap rounded-[var(--radius-md)] border font-medium",
193
193
  "transition-[background-color,border-color,color,box-shadow,transform] motion-reduce:transition-none",
194
194
  "focus-visible:outline-none focus-visible:border-[var(--focus-ring)] focus-visible:shadow-[0_0_0_2px_var(--focus-ring)]",
195
195
  "active:scale-[0.98] disabled:active:scale-100 aria-disabled:active:scale-100",
@@ -201,10 +201,12 @@ var buttonVariants = cva(
201
201
  variants: {
202
202
  variant: {
203
203
  primary: "border-[var(--primary)] bg-[var(--primary)] text-[var(--primary-fg)] hover:bg-[var(--primary-hover)] hover:border-[var(--primary-hover)]",
204
+ /** @deprecated Use `secondary` — the single supporting-action family (#58). Removed in the next breaking release. */
204
205
  outline: "border-[var(--border)] bg-transparent text-foreground hover:border-[var(--border-strong)] hover:bg-[var(--action-hover)]",
205
206
  ghost: "border-transparent bg-transparent text-text-secondary hover:bg-[var(--action-hover)] hover:text-foreground",
206
207
  danger: "border-[var(--error)] bg-[var(--error)] text-[var(--error-contrast)] hover:bg-[var(--error-hover)] hover:border-[var(--error-hover)]",
207
208
  emergency: "border-[var(--error)] bg-[var(--error)] text-[var(--error-contrast)] hover:bg-[var(--error-hover)] hover:border-[var(--error-hover)]",
209
+ /** @deprecated Use `secondary` (identical styling, #58). Removed in the next breaking release. */
208
210
  subtle: "border-[var(--border-subtle)] bg-[var(--bg-surface)] text-foreground hover:border-[var(--border)] hover:bg-[var(--action-hover)]",
209
211
  default: "border-[var(--primary)] bg-[var(--primary)] text-[var(--primary-fg)] hover:bg-[var(--primary-hover)] hover:border-[var(--primary-hover)]",
210
212
  destructive: "border-[var(--error)] bg-[var(--error)] text-[var(--error-contrast)] hover:bg-[var(--error-hover)] hover:border-[var(--error-hover)]",
@@ -214,8 +216,11 @@ var buttonVariants = cva(
214
216
  size: {
215
217
  // Cross-control height map: Button sm/md/lg match field controls sm/md/lg (30/32/36px).
216
218
  // Height comes from h-* alone — no vertical padding (py-12 inside h-32 left a 6px content box).
217
- xs: "h-[28px] gap-[6px] px-pad-compact-x text-[12px] [&_svg]:size-[14px] [&_svg]:stroke-[1.75]",
218
- sm: "h-[30px] gap-[6px] px-pad-compact-x text-body-sm [&_svg]:size-[16px]",
219
+ // xs/sm: invisible ::before stretches the hit area to 44px tall (#69), vertically only so
220
+ // side-by-side buttons never overlap. Its inset is measured from the padding box, inside
221
+ // the 1px border every variant carries: inset = (44 - (height - 2 × 1px)) / 2.
222
+ xs: "relative h-[28px] gap-[6px] px-pad-compact-x text-[12px] before:absolute before:inset-x-0 before:-inset-y-[9px] before:content-[''] [&_svg]:size-[14px] [&_svg]:stroke-[1.75]",
223
+ sm: "relative h-[30px] gap-[6px] px-pad-compact-x text-body-sm before:absolute before:inset-x-0 before:-inset-y-[8px] before:content-[''] [&_svg]:size-[16px]",
219
224
  md: "h-[32px] gap-[6px] px-pad-default-x text-body-sm [&_svg]:size-[16px]",
220
225
  lg: "h-[36px] gap-[var(--space-2)] px-pad-default-x text-[15px] [&_svg]:size-[18px]",
221
226
  xl: "h-[40px] gap-[var(--space-2)] px-5 text-[15px] [&_svg]:size-[18px]",
@@ -230,6 +235,7 @@ var buttonVariants = cva(
230
235
  }
231
236
  }
232
237
  );
238
+ var footerButtonHitAreaClassName = "relative before:absolute before:inset-x-0 before:-inset-y-[5px] before:content-['']";
233
239
  var Button = React.forwardRef(
234
240
  ({
235
241
  asChild = false,
@@ -325,7 +331,7 @@ var CopyButton = React2.forwardRef(
325
331
  onCopied,
326
332
  size = "sm",
327
333
  value,
328
- variant = "outline",
334
+ variant = "secondary",
329
335
  ...props
330
336
  }, ref) => {
331
337
  const [copied, setCopied] = React2.useState(false);
@@ -611,7 +617,7 @@ var fileUploadZoneVariants = cva3(
611
617
  variants: {
612
618
  size: {
613
619
  default: "gap-[var(--space-2)] rounded-[var(--radius-md)] px-[var(--space-6)] py-[var(--space-10)]",
614
- compact: "gap-[var(--space-1)] rounded-[var(--radius-sm)] px-[var(--space-4)] py-[20px]"
620
+ compact: "gap-[var(--space-1)] rounded-[var(--radius-md)] px-[var(--space-4)] py-[20px]"
615
621
  },
616
622
  surface: surfaceClassNames
617
623
  },
@@ -1046,7 +1052,7 @@ function DismissButton({
1046
1052
  marginTop: -1,
1047
1053
  alignItems: "center",
1048
1054
  justifyContent: "center",
1049
- borderRadius: "var(--radius-sm)",
1055
+ borderRadius: "var(--radius-md)",
1050
1056
  border: 0,
1051
1057
  background: hover ? "var(--action-hover)" : "transparent",
1052
1058
  color: hover ? strong ? fg : "var(--text-primary)" : strong ? "color-mix(in srgb, " + fg + " 70%, transparent)" : "var(--text-tertiary)",
@@ -1532,7 +1538,7 @@ var Select = React7.forwardRef(
1532
1538
  "data-slot": "select-content",
1533
1539
  position: "popper",
1534
1540
  sideOffset: 4,
1535
- className: "z-[var(--z-popover)] max-h-[var(--radix-select-content-available-height)] min-w-[var(--radix-select-trigger-width)] overflow-hidden rounded-[var(--radius-md)] border border-[var(--border)] bg-[var(--bg-surface)] text-foreground shadow-[var(--shadow-4)]",
1541
+ className: "z-[var(--z-popover)] max-h-[var(--radix-select-content-available-height)] min-w-[var(--radix-select-trigger-width)] overflow-hidden rounded-[var(--radius-md)] border border-[var(--border)] bg-[var(--bg-surface)] text-foreground shadow-[var(--shadow-16)]",
1536
1542
  children: [
1537
1543
  /* @__PURE__ */ jsx7(
1538
1544
  SelectPrimitive.ScrollUpButton,
@@ -2823,7 +2829,7 @@ var WizardLayout = React16.forwardRef(
2823
2829
  type: "button",
2824
2830
  "data-slot": "wizard-layout-step-button",
2825
2831
  "data-step-state": step.resolvedState,
2826
- className: "flex cursor-pointer flex-col items-center gap-[var(--space-2)] rounded-[var(--radius-sm)] focus-visible:outline-none focus-visible:ring-[1px] focus-visible:ring-[var(--focus-ring)]",
2832
+ className: "flex cursor-pointer flex-col items-center gap-[var(--space-2)] rounded-[var(--radius-md)] focus-visible:outline-none focus-visible:ring-[1px] focus-visible:ring-[var(--focus-ring)]",
2827
2833
  onClick: () => onStepChange(index),
2828
2834
  children: [
2829
2835
  /* @__PURE__ */ jsx17(
@@ -2952,7 +2958,7 @@ var tabsListVariants = cva8(
2952
2958
  {
2953
2959
  variant: "line",
2954
2960
  orientation: "horizontal",
2955
- className: "border-b border-[var(--border-subtle)] gap-[var(--space-6)] overflow-x-auto overflow-y-hidden mb-[var(--space-6)]"
2961
+ className: "border-b border-[var(--border-subtle)] gap-[var(--space-6)] overflow-x-auto overflow-y-hidden"
2956
2962
  },
2957
2963
  {
2958
2964
  variant: "line",
@@ -2962,7 +2968,7 @@ var tabsListVariants = cva8(
2962
2968
  {
2963
2969
  variant: "contained",
2964
2970
  orientation: "horizontal",
2965
- className: "gap-[var(--space-1)] overflow-x-auto overflow-y-hidden mb-[var(--space-6)]"
2971
+ className: "gap-[var(--space-1)] overflow-x-auto overflow-y-hidden"
2966
2972
  },
2967
2973
  {
2968
2974
  variant: "contained",
@@ -3225,31 +3231,41 @@ var DetailLayout = React18.forwardRef(
3225
3231
  ...props,
3226
3232
  children: [
3227
3233
  /* @__PURE__ */ jsx19("div", { "data-slot": "detail-layout-header", className: "min-w-0", children: header }),
3228
- tabs ? /* @__PURE__ */ jsx19(Tabs, { tabs, activeKey: activeTab, onChange: onTabChange, baseId, children: hasExplicitTabsContent ? /* @__PURE__ */ jsx19(
3229
- DetailLayoutBody,
3234
+ tabs ? /* @__PURE__ */ jsx19(
3235
+ Tabs,
3230
3236
  {
3231
- aside,
3232
- bodyClassName,
3233
- contentClassName,
3234
- asideClassName,
3235
- stickyAside,
3236
- stickyAsideTopClassName,
3237
- children: appendFooterToActiveTabsContent(children, activeTab, footer)
3238
- }
3239
- ) : tabs.map((tab) => /* @__PURE__ */ jsx19(
3240
- TabsContent,
3241
- {
3242
- tabKey: tab.key,
3237
+ tabs,
3238
+ activeKey: activeTab,
3239
+ onChange: onTabChange,
3243
3240
  baseId,
3244
- forceMount: true,
3245
- hidden: tab.key !== activeTab,
3246
- children: tab.key === activeTab ? /* @__PURE__ */ jsxs18(Fragment6, { children: [
3247
- body,
3248
- footer ? /* @__PURE__ */ jsx19("div", { "data-slot": "detail-layout-footer", className: "min-w-0", children: footer }) : null
3249
- ] }) : null
3250
- },
3251
- tab.key
3252
- )) }) : /* @__PURE__ */ jsxs18(Fragment6, { children: [
3241
+ className: "flex flex-col gap-[var(--space-6)]",
3242
+ children: hasExplicitTabsContent ? /* @__PURE__ */ jsx19(
3243
+ DetailLayoutBody,
3244
+ {
3245
+ aside,
3246
+ bodyClassName,
3247
+ contentClassName,
3248
+ asideClassName,
3249
+ stickyAside,
3250
+ stickyAsideTopClassName,
3251
+ children: appendFooterToActiveTabsContent(children, activeTab, footer)
3252
+ }
3253
+ ) : tabs.map((tab) => /* @__PURE__ */ jsx19(
3254
+ TabsContent,
3255
+ {
3256
+ tabKey: tab.key,
3257
+ baseId,
3258
+ forceMount: true,
3259
+ hidden: tab.key !== activeTab,
3260
+ children: tab.key === activeTab ? /* @__PURE__ */ jsxs18(Fragment6, { children: [
3261
+ body,
3262
+ footer ? /* @__PURE__ */ jsx19("div", { "data-slot": "detail-layout-footer", className: "min-w-0", children: footer }) : null
3263
+ ] }) : null
3264
+ },
3265
+ tab.key
3266
+ ))
3267
+ }
3268
+ ) : /* @__PURE__ */ jsxs18(Fragment6, { children: [
3253
3269
  body,
3254
3270
  footer ? /* @__PURE__ */ jsx19("div", { "data-slot": "detail-layout-footer", className: "min-w-0", children: footer }) : null
3255
3271
  ] })
@@ -3420,18 +3436,286 @@ var FormLayout = React19.forwardRef(
3420
3436
  FormLayout.displayName = "FormLayout";
3421
3437
 
3422
3438
  // src/components/ui/form-modal.tsx
3423
- import * as React21 from "react";
3439
+ import * as React22 from "react";
3424
3440
 
3425
3441
  // src/components/ui/dialog.tsx
3426
- import * as React20 from "react";
3442
+ import * as React21 from "react";
3427
3443
  import { Dialog as DialogPrimitive } from "radix-ui";
3428
3444
  import { X } from "lucide-react";
3445
+
3446
+ // src/components/ui/sheet.tsx
3447
+ import { XIcon as XIcon2 } from "lucide-react";
3448
+ import { Dialog as SheetPrimitive } from "radix-ui";
3449
+
3450
+ // src/lib/use-return-focus.ts
3451
+ import * as React20 from "react";
3452
+ function useReturnFocus() {
3453
+ const returnTo = React20.useRef(null);
3454
+ const onOpenAutoFocus = React20.useCallback(() => {
3455
+ const active = document.activeElement;
3456
+ returnTo.current = active instanceof HTMLElement && active !== document.body ? active : null;
3457
+ }, []);
3458
+ const onCloseAutoFocus = React20.useCallback((event) => {
3459
+ const target = returnTo.current;
3460
+ returnTo.current = null;
3461
+ if (!target?.isConnected) return;
3462
+ event.preventDefault();
3463
+ target.focus();
3464
+ }, []);
3465
+ return { onOpenAutoFocus, onCloseAutoFocus };
3466
+ }
3467
+
3468
+ // src/components/ui/sheet.tsx
3429
3469
  import { jsx as jsx21, jsxs as jsxs20 } from "react/jsx-runtime";
3470
+ var defaultSheetMotionConfig = {
3471
+ type: "slide",
3472
+ duration: 300,
3473
+ easing: "decel"
3474
+ };
3475
+ var sheetMotionEasingValue = {
3476
+ standard: "var(--ease-standard)",
3477
+ // decel/sharp have no canonical --ease-* token; these compat beziers are frozen
3478
+ // specifically to back this public `easing` prop (see tokens/compat.css).
3479
+ decel: "var(--easing-decel)",
3480
+ accel: "var(--ease-in)",
3481
+ sharp: "var(--easing-sharp)",
3482
+ bounce: "var(--ease-out)"
3483
+ };
3484
+ function resolveSheetMotionConfig(motion) {
3485
+ if (motion === false) return false;
3486
+ return {
3487
+ ...defaultSheetMotionConfig,
3488
+ ...motion
3489
+ };
3490
+ }
3491
+ function formatSheetMotionDuration(duration) {
3492
+ return typeof duration === "number" ? `${duration}ms` : duration;
3493
+ }
3494
+ function getSheetMotionStyle(motionConfig, style) {
3495
+ if (!motionConfig) return style;
3496
+ return {
3497
+ ...style,
3498
+ "--sheet-motion-duration": formatSheetMotionDuration(motionConfig.duration),
3499
+ "--sheet-motion-easing": sheetMotionEasingValue[motionConfig.easing]
3500
+ };
3501
+ }
3502
+ function getDefaultSheetMotionStyle(style) {
3503
+ return getSheetMotionStyle(defaultSheetMotionConfig, style);
3504
+ }
3505
+ function Sheet({ ...props }) {
3506
+ return /* @__PURE__ */ jsx21(SheetPrimitive.Root, { "data-slot": "sheet", ...props });
3507
+ }
3508
+ function SheetTrigger({
3509
+ ...props
3510
+ }) {
3511
+ return /* @__PURE__ */ jsx21(SheetPrimitive.Trigger, { "data-slot": "sheet-trigger", ...props });
3512
+ }
3513
+ function SheetClose({
3514
+ ...props
3515
+ }) {
3516
+ return /* @__PURE__ */ jsx21(SheetPrimitive.Close, { "data-slot": "sheet-close", ...props });
3517
+ }
3518
+ function SheetPortal({
3519
+ ...props
3520
+ }) {
3521
+ return /* @__PURE__ */ jsx21(SheetPrimitive.Portal, { "data-slot": "sheet-portal", ...props });
3522
+ }
3523
+ function SheetOverlay({
3524
+ className,
3525
+ motion,
3526
+ style,
3527
+ ...props
3528
+ }) {
3529
+ const motionConfig = resolveSheetMotionConfig(motion);
3530
+ return /* @__PURE__ */ jsx21(
3531
+ SheetPrimitive.Overlay,
3532
+ {
3533
+ "data-slot": "sheet-overlay",
3534
+ className: cn(
3535
+ "fixed inset-0 z-[var(--z-overlay)] bg-[var(--scrim)]",
3536
+ motionConfig && cn(
3537
+ "transition-opacity motion-reduce:transition-none",
3538
+ "duration-[var(--sheet-motion-duration)]",
3539
+ "data-[state=closed]:opacity-0 data-[state=open]:opacity-100",
3540
+ "data-[state=open]:animate-[olun-sheet-fade-in_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]",
3541
+ "data-[state=closed]:animate-[olun-sheet-fade-out_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]",
3542
+ "motion-reduce:animate-none"
3543
+ ),
3544
+ className
3545
+ ),
3546
+ style: getSheetMotionStyle(motionConfig, style),
3547
+ ...props
3548
+ }
3549
+ );
3550
+ }
3551
+ function SheetContent({
3552
+ className,
3553
+ children,
3554
+ side = "right",
3555
+ mobileSide,
3556
+ motion,
3557
+ showCloseButton = false,
3558
+ style,
3559
+ onOpenAutoFocus,
3560
+ onCloseAutoFocus,
3561
+ ...props
3562
+ }) {
3563
+ const motionConfig = resolveSheetMotionConfig(motion);
3564
+ const hasSlideMotion = motionConfig && motionConfig.type === "slide";
3565
+ const returnFocus = useReturnFocus();
3566
+ const handleOpenAutoFocus = (event) => {
3567
+ returnFocus.onOpenAutoFocus();
3568
+ onOpenAutoFocus?.(event);
3569
+ };
3570
+ const handleCloseAutoFocus = (event) => {
3571
+ onCloseAutoFocus?.(event);
3572
+ if (!event.defaultPrevented) returnFocus.onCloseAutoFocus(event);
3573
+ };
3574
+ return /* @__PURE__ */ jsxs20(SheetPortal, { children: [
3575
+ /* @__PURE__ */ jsx21(SheetOverlay, { motion: motionConfig }),
3576
+ /* @__PURE__ */ jsxs20(
3577
+ SheetPrimitive.Content,
3578
+ {
3579
+ "data-slot": "sheet-content",
3580
+ className: cn(
3581
+ "fixed z-[var(--z-modal)] flex flex-col gap-4 border-[var(--border)] bg-[var(--bg-surface)] shadow-[var(--shadow-16)]",
3582
+ motionConfig && cn(
3583
+ "motion-reduce:animate-none",
3584
+ motionConfig.type === "fade" && "data-[state=open]:animate-[olun-sheet-fade-in_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-fade-out_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3585
+ ),
3586
+ side === "right" && cn(
3587
+ "inset-y-0 right-0 h-full w-3/4 border-l sm:max-w-sm",
3588
+ hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3589
+ ),
3590
+ side === "left" && cn(
3591
+ "inset-y-0 left-0 h-full w-3/4 border-r sm:max-w-sm",
3592
+ hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3593
+ ),
3594
+ side === "top" && cn(
3595
+ "inset-x-0 top-0 h-auto border-b",
3596
+ hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3597
+ ),
3598
+ side === "bottom" && cn(
3599
+ "inset-x-0 bottom-0 h-auto border-t",
3600
+ hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3601
+ ),
3602
+ mobileSide === "right" && cn(
3603
+ "max-[899px]:inset-y-0 max-[899px]:right-0 max-[899px]:left-auto max-[899px]:h-full max-[899px]:w-3/4 max-[899px]:border-l max-[899px]:border-t-0 max-[899px]:rounded-none",
3604
+ hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3605
+ ),
3606
+ mobileSide === "left" && cn(
3607
+ "max-[899px]:inset-y-0 max-[899px]:left-0 max-[899px]:right-auto max-[899px]:h-full max-[899px]:w-3/4 max-[899px]:border-r max-[899px]:border-t-0 max-[899px]:rounded-none",
3608
+ hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3609
+ ),
3610
+ mobileSide === "top" && cn(
3611
+ // `max-w-none!` overrides the side variant's `sm:max-w-sm` cap (see mobileSide bottom).
3612
+ "max-[899px]:inset-x-0 max-[899px]:top-0 max-[899px]:bottom-auto max-[899px]:h-auto max-[899px]:w-full max-[899px]:max-w-none! max-[899px]:border-b max-[899px]:border-l-0 max-[899px]:rounded-none",
3613
+ hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3614
+ ),
3615
+ mobileSide === "bottom" && cn(
3616
+ // `max-w-none!` overrides the side variant's `sm:max-w-sm` cap so the bottom sheet
3617
+ // spans the full viewport width across the whole < 900px band (not capped to 24rem).
3618
+ "max-[899px]:inset-x-0 max-[899px]:bottom-0 max-[899px]:top-auto max-[899px]:h-auto max-[899px]:w-full max-[899px]:max-w-none! max-[899px]:border-t max-[899px]:border-l-0 max-[899px]:rounded-none",
3619
+ hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3620
+ ),
3621
+ className
3622
+ ),
3623
+ style: getSheetMotionStyle(motionConfig, style),
3624
+ onOpenAutoFocus: handleOpenAutoFocus,
3625
+ onCloseAutoFocus: handleCloseAutoFocus,
3626
+ ...props,
3627
+ children: [
3628
+ children,
3629
+ showCloseButton && /* @__PURE__ */ jsxs20(SheetPrimitive.Close, { className: "absolute top-4 right-4 cursor-pointer rounded-[var(--radius-md)] opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:ring-2 focus:ring-ring focus:ring-offset-2 focus:outline-hidden disabled:pointer-events-none data-[state=open]:bg-secondary", children: [
3630
+ /* @__PURE__ */ jsx21(XIcon2, { className: "size-[16px]" }),
3631
+ /* @__PURE__ */ jsx21("span", { className: "sr-only", children: "Close" })
3632
+ ] })
3633
+ ]
3634
+ }
3635
+ )
3636
+ ] });
3637
+ }
3638
+ function SheetBody({ className, ...props }) {
3639
+ return /* @__PURE__ */ jsx21(
3640
+ "div",
3641
+ {
3642
+ "data-slot": "sheet-body",
3643
+ className: cn("flex-1 overflow-y-auto p-4", className),
3644
+ ...props
3645
+ }
3646
+ );
3647
+ }
3648
+ function SheetHeader({ className, ...props }) {
3649
+ return /* @__PURE__ */ jsx21(
3650
+ "div",
3651
+ {
3652
+ "data-slot": "sheet-header",
3653
+ className: cn("flex flex-col gap-1.5 p-4", className),
3654
+ ...props
3655
+ }
3656
+ );
3657
+ }
3658
+ function SheetFooter({ className, ...props }) {
3659
+ return /* @__PURE__ */ jsx21(
3660
+ "div",
3661
+ {
3662
+ "data-slot": "sheet-footer",
3663
+ className: cn("mt-auto flex flex-col gap-2 p-4", className),
3664
+ ...props
3665
+ }
3666
+ );
3667
+ }
3668
+ function SheetTitle({
3669
+ className,
3670
+ ...props
3671
+ }) {
3672
+ return /* @__PURE__ */ jsx21(
3673
+ SheetPrimitive.Title,
3674
+ {
3675
+ "data-slot": "sheet-title",
3676
+ className: cn("font-semibold text-foreground", className),
3677
+ ...props
3678
+ }
3679
+ );
3680
+ }
3681
+ function SheetDescription({
3682
+ className,
3683
+ ...props
3684
+ }) {
3685
+ return /* @__PURE__ */ jsx21(
3686
+ SheetPrimitive.Description,
3687
+ {
3688
+ "data-slot": "sheet-description",
3689
+ className: cn("text-sm text-muted-foreground", className),
3690
+ ...props
3691
+ }
3692
+ );
3693
+ }
3694
+
3695
+ // src/components/ui/dialog.tsx
3696
+ import { jsx as jsx22, jsxs as jsxs21 } from "react/jsx-runtime";
3697
+ var dialogMobileSheetClassName = cn(
3698
+ // `!` on the box geometry so consumer width/offset classes (unprefixed or `sm:`) never keep
3699
+ // the centered card inside the < 900px band.
3700
+ "max-[899px]:inset-x-0! max-[899px]:top-auto! max-[899px]:bottom-0! max-[899px]:translate-x-0! max-[899px]:translate-y-0!",
3701
+ "max-[899px]:w-full! max-[899px]:max-w-none!",
3702
+ "max-[899px]:max-h-[85dvh] max-[899px]:overflow-y-auto",
3703
+ "max-[899px]:rounded-b-none max-[899px]:border-x-0",
3704
+ // Home-indicator clearance without touching the consumer's padding (DialogFooter's edge bleed
3705
+ // depends on it): a transparent bottom border as tall as the safe area, painted by the surface.
3706
+ "max-[899px]:border-b-[length:env(safe-area-inset-bottom)] max-[899px]:border-b-transparent",
3707
+ // motion-safe gate (not a motion-reduce override): a later-sorted variant would out-rank it.
3708
+ "max-[899px]:motion-safe:data-[state=open]:animate-[olun-sheet-in-from-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]",
3709
+ "max-[899px]:motion-safe:data-[state=closed]:animate-[olun-sheet-out-to-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
3710
+ );
3711
+ function dialogMobileSheetStyle(style) {
3712
+ return getDefaultSheetMotionStyle(style);
3713
+ }
3430
3714
  var Dialog = DialogPrimitive.Root;
3431
3715
  var DialogTrigger = DialogPrimitive.Trigger;
3432
3716
  var DialogPortal = DialogPrimitive.Portal;
3433
3717
  var DialogClose = DialogPrimitive.Close;
3434
- var DialogOverlay = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx21(
3718
+ var DialogOverlay = React21.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx22(
3435
3719
  DialogPrimitive.Overlay,
3436
3720
  {
3437
3721
  ref,
@@ -3448,9 +3732,9 @@ var DialogOverlay = React20.forwardRef(({ className, ...props }, ref) => /* @__P
3448
3732
  }
3449
3733
  ));
3450
3734
  DialogOverlay.displayName = DialogPrimitive.Overlay.displayName;
3451
- var DialogContent = React20.forwardRef(({ className, children, showCloseButton = false, ...props }, ref) => /* @__PURE__ */ jsxs20(DialogPortal, { children: [
3452
- /* @__PURE__ */ jsx21(DialogOverlay, {}),
3453
- /* @__PURE__ */ jsxs20(
3735
+ var DialogContent = React21.forwardRef(({ className, children, showCloseButton = false, mobilePresentation = "center", ...props }, ref) => /* @__PURE__ */ jsxs21(DialogPortal, { children: [
3736
+ /* @__PURE__ */ jsx22(DialogOverlay, {}),
3737
+ /* @__PURE__ */ jsxs21(
3454
3738
  DialogPrimitive.Content,
3455
3739
  {
3456
3740
  ref,
@@ -3472,24 +3756,26 @@ var DialogContent = React20.forwardRef(({ className, children, showCloseButton =
3472
3756
  "data-[state=closed]:slide-out-to-left-1/2 data-[state=closed]:slide-out-to-top-[48%]",
3473
3757
  "data-[state=open]:slide-in-from-left-1/2 data-[state=open]:slide-in-from-top-[48%]",
3474
3758
  "motion-reduce:animate-none",
3759
+ mobilePresentation === "sheet" && dialogMobileSheetClassName,
3475
3760
  className
3476
3761
  ),
3477
3762
  ...props,
3763
+ ...mobilePresentation === "sheet" && { style: dialogMobileSheetStyle(props.style) },
3478
3764
  children: [
3479
3765
  children,
3480
- showCloseButton ? /* @__PURE__ */ jsx21(
3766
+ showCloseButton ? /* @__PURE__ */ jsx22(
3481
3767
  DialogPrimitive.Close,
3482
3768
  {
3483
3769
  className: cn(
3484
3770
  "absolute right-4 top-4 inline-flex size-[32px] cursor-pointer items-center justify-center",
3485
- "rounded-sm text-text-secondary",
3771
+ "rounded-[var(--radius-md)] text-text-secondary",
3486
3772
  "transition-colors motion-reduce:transition-none",
3487
3773
  "hover:bg-accent hover:text-accent-foreground",
3488
3774
  "focus-visible:outline-none focus-visible:shadow-focus-ring",
3489
3775
  "disabled:pointer-events-none disabled:text-text-disabled"
3490
3776
  ),
3491
3777
  "aria-label": "\uB2EB\uAE30",
3492
- children: /* @__PURE__ */ jsx21(X, { className: "size-[16px]" })
3778
+ children: /* @__PURE__ */ jsx22(X, { className: "size-[16px]" })
3493
3779
  }
3494
3780
  ) : null
3495
3781
  ]
@@ -3500,7 +3786,7 @@ DialogContent.displayName = DialogPrimitive.Content.displayName;
3500
3786
  var DialogHeader = ({
3501
3787
  className,
3502
3788
  ...props
3503
- }) => /* @__PURE__ */ jsx21(
3789
+ }) => /* @__PURE__ */ jsx22(
3504
3790
  "div",
3505
3791
  {
3506
3792
  className: cn(
@@ -3515,7 +3801,7 @@ DialogHeader.displayName = "DialogHeader";
3515
3801
  var DialogFooter = ({
3516
3802
  className,
3517
3803
  ...props
3518
- }) => /* @__PURE__ */ jsx21(
3804
+ }) => /* @__PURE__ */ jsx22(
3519
3805
  "div",
3520
3806
  {
3521
3807
  className: cn(
@@ -3531,7 +3817,7 @@ var DialogFooter = ({
3531
3817
  }
3532
3818
  );
3533
3819
  DialogFooter.displayName = "DialogFooter";
3534
- var DialogTitle = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx21(
3820
+ var DialogTitle = React21.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx22(
3535
3821
  DialogPrimitive.Title,
3536
3822
  {
3537
3823
  ref,
@@ -3543,7 +3829,7 @@ var DialogTitle = React20.forwardRef(({ className, ...props }, ref) => /* @__PUR
3543
3829
  }
3544
3830
  ));
3545
3831
  DialogTitle.displayName = DialogPrimitive.Title.displayName;
3546
- var DialogDescription = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx21(
3832
+ var DialogDescription = React21.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx22(
3547
3833
  DialogPrimitive.Description,
3548
3834
  {
3549
3835
  ref,
@@ -3552,7 +3838,7 @@ var DialogDescription = React20.forwardRef(({ className, ...props }, ref) => /*
3552
3838
  }
3553
3839
  ));
3554
3840
  DialogDescription.displayName = DialogPrimitive.Description.displayName;
3555
- var DialogEyebrow = React20.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx21(
3841
+ var DialogEyebrow = React21.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx22(
3556
3842
  "p",
3557
3843
  {
3558
3844
  ref,
@@ -3567,7 +3853,7 @@ DialogEyebrow.displayName = "DialogEyebrow";
3567
3853
  var DialogRawContent = DialogPrimitive.Content;
3568
3854
 
3569
3855
  // src/components/ui/form-modal.tsx
3570
- import { jsx as jsx22, jsxs as jsxs21 } from "react/jsx-runtime";
3856
+ import { jsx as jsx23, jsxs as jsxs22 } from "react/jsx-runtime";
3571
3857
  var formModalContentClassName = cn(
3572
3858
  "w-[calc(100vw-2rem)]",
3573
3859
  "max-w-[560px]",
@@ -3608,12 +3894,14 @@ function FormModal({
3608
3894
  cancelLabel = "\uCDE8\uC18C",
3609
3895
  wide = false,
3610
3896
  loading = false,
3611
- status
3897
+ status,
3898
+ mobilePresentation = "center"
3612
3899
  }) {
3613
- const [pending, setPending] = React21.useState(false);
3614
- const busyRef = React21.useRef(false);
3900
+ const [pending, setPending] = React22.useState(false);
3901
+ const busyRef = React22.useRef(false);
3615
3902
  const isBusy = loading || pending;
3616
- const handleOpenChange = React21.useCallback(
3903
+ const returnFocus = useReturnFocus();
3904
+ const handleOpenChange = React22.useCallback(
3617
3905
  (nextOpen) => {
3618
3906
  if (!nextOpen && isBusy) {
3619
3907
  return;
@@ -3622,7 +3910,7 @@ function FormModal({
3622
3910
  },
3623
3911
  [isBusy, onOpenChange]
3624
3912
  );
3625
- const handleSubmit = React21.useCallback(
3913
+ const handleSubmit = React22.useCallback(
3626
3914
  async (event) => {
3627
3915
  event.preventDefault();
3628
3916
  if (busyRef.current || loading) {
@@ -3640,37 +3928,41 @@ function FormModal({
3640
3928
  },
3641
3929
  [loading, onOpenChange, onSubmit]
3642
3930
  );
3643
- return /* @__PURE__ */ jsx22(Dialog, { open, onOpenChange: handleOpenChange, children: /* @__PURE__ */ jsx22(
3931
+ return /* @__PURE__ */ jsx23(Dialog, { open, onOpenChange: handleOpenChange, children: /* @__PURE__ */ jsx23(
3644
3932
  DialogContent,
3645
3933
  {
3646
3934
  "data-slot": "form-modal-content",
3935
+ mobilePresentation,
3936
+ ...returnFocus,
3647
3937
  className: cn(
3648
3938
  formModalContentClassName,
3649
3939
  wide && formModalWideContentClassName
3650
3940
  ),
3651
- children: /* @__PURE__ */ jsxs21("form", { "data-slot": "form-modal-form", onSubmit: handleSubmit, children: [
3652
- /* @__PURE__ */ jsxs21("div", { "data-slot": "form-modal-header", className: formModalHeaderClassName, children: [
3653
- /* @__PURE__ */ jsx22(DialogTitle, { className: formModalTitleClassName, children: title }),
3654
- description ? /* @__PURE__ */ jsx22(DialogDescription, { className: formModalDescriptionClassName, children: description }) : null,
3655
- status ? /* @__PURE__ */ jsx22("div", { "data-slot": "form-modal-status", children: status }) : null
3941
+ children: /* @__PURE__ */ jsxs22("form", { "data-slot": "form-modal-form", onSubmit: handleSubmit, children: [
3942
+ /* @__PURE__ */ jsxs22("div", { "data-slot": "form-modal-header", className: formModalHeaderClassName, children: [
3943
+ /* @__PURE__ */ jsx23(DialogTitle, { className: formModalTitleClassName, children: title }),
3944
+ description ? /* @__PURE__ */ jsx23(DialogDescription, { className: formModalDescriptionClassName, children: description }) : null,
3945
+ status ? /* @__PURE__ */ jsx23("div", { "data-slot": "form-modal-status", children: status }) : null
3656
3946
  ] }),
3657
- /* @__PURE__ */ jsx22("div", { "data-slot": "form-modal-body", className: formModalBodyClassName, children }),
3658
- /* @__PURE__ */ jsxs21(
3947
+ /* @__PURE__ */ jsx23("div", { "data-slot": "form-modal-body", className: formModalBodyClassName, children }),
3948
+ /* @__PURE__ */ jsxs22(
3659
3949
  "div",
3660
3950
  {
3661
3951
  "data-slot": "form-modal-footer",
3662
3952
  className: formModalFooterClassName,
3663
3953
  children: [
3664
- /* @__PURE__ */ jsx22(
3954
+ /* @__PURE__ */ jsx23(
3665
3955
  Button,
3666
3956
  {
3667
3957
  variant: "secondary",
3958
+ size: "lg",
3959
+ className: footerButtonHitAreaClassName,
3668
3960
  disabled: isBusy,
3669
3961
  onClick: () => handleOpenChange(false),
3670
3962
  children: cancelLabel
3671
3963
  }
3672
3964
  ),
3673
- /* @__PURE__ */ jsx22(Button, { type: "submit", loading: isBusy, children: submitLabel })
3965
+ /* @__PURE__ */ jsx23(Button, { type: "submit", size: "lg", className: footerButtonHitAreaClassName, loading: isBusy, children: submitLabel })
3674
3966
  ]
3675
3967
  }
3676
3968
  )
@@ -3680,7 +3972,7 @@ function FormModal({
3680
3972
  }
3681
3973
 
3682
3974
  // src/components/ui/info-modal.tsx
3683
- import { jsx as jsx23, jsxs as jsxs22 } from "react/jsx-runtime";
3975
+ import { jsx as jsx24, jsxs as jsxs23 } from "react/jsx-runtime";
3684
3976
  var infoModalContentClassName = cn(
3685
3977
  "w-[calc(100vw-2rem)]",
3686
3978
  "max-w-[420px]",
@@ -3719,20 +4011,24 @@ function InfoModal({
3719
4011
  children,
3720
4012
  closeLabel = "\uB2EB\uAE30",
3721
4013
  width = "default",
3722
- footer
4014
+ footer,
4015
+ mobilePresentation = "center"
3723
4016
  }) {
3724
- return /* @__PURE__ */ jsx23(Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxs22(
4017
+ const returnFocus = useReturnFocus();
4018
+ return /* @__PURE__ */ jsx24(Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxs23(
3725
4019
  DialogContent,
3726
4020
  {
3727
4021
  "data-slot": "info-modal-content",
4022
+ mobilePresentation,
4023
+ ...returnFocus,
3728
4024
  className: cn(
3729
4025
  infoModalContentClassName,
3730
4026
  width === "wide" && infoModalWideContentClassName
3731
4027
  ),
3732
4028
  children: [
3733
- /* @__PURE__ */ jsxs22("div", { "data-slot": "info-modal-header", className: infoModalHeaderClassName, children: [
3734
- /* @__PURE__ */ jsx23(DialogTitle, { "data-slot": "info-modal-title", className: infoModalTitleClassName, children: title }),
3735
- description ? /* @__PURE__ */ jsx23(
4029
+ /* @__PURE__ */ jsxs23("div", { "data-slot": "info-modal-header", className: infoModalHeaderClassName, children: [
4030
+ /* @__PURE__ */ jsx24(DialogTitle, { "data-slot": "info-modal-title", className: infoModalTitleClassName, children: title }),
4031
+ description ? /* @__PURE__ */ jsx24(
3736
4032
  DialogDescription,
3737
4033
  {
3738
4034
  "data-slot": "info-modal-description",
@@ -3741,13 +4037,14 @@ function InfoModal({
3741
4037
  }
3742
4038
  ) : null
3743
4039
  ] }),
3744
- /* @__PURE__ */ jsx23("div", { "data-slot": "info-modal-body", className: infoModalBodyClassName, children }),
3745
- /* @__PURE__ */ jsx23("div", { "data-slot": "info-modal-footer", className: infoModalFooterClassName, children: footer ?? /* @__PURE__ */ jsx23(
4040
+ /* @__PURE__ */ jsx24("div", { "data-slot": "info-modal-body", className: infoModalBodyClassName, children }),
4041
+ /* @__PURE__ */ jsx24("div", { "data-slot": "info-modal-footer", className: infoModalFooterClassName, children: footer ?? /* @__PURE__ */ jsx24(
3746
4042
  Button,
3747
4043
  {
3748
4044
  "data-slot": "info-modal-close-button",
3749
4045
  variant: "secondary",
3750
- size: "sm",
4046
+ size: "lg",
4047
+ className: footerButtonHitAreaClassName,
3751
4048
  onClick: () => onOpenChange(false),
3752
4049
  children: closeLabel
3753
4050
  }
@@ -3758,15 +4055,15 @@ function InfoModal({
3758
4055
  }
3759
4056
 
3760
4057
  // src/components/ui/filter-toolbar.tsx
3761
- import * as React25 from "react";
4058
+ import * as React26 from "react";
3762
4059
  import { SlidersHorizontal } from "lucide-react";
3763
4060
 
3764
4061
  // src/components/ui/chip.tsx
3765
- import * as React22 from "react";
4062
+ import * as React23 from "react";
3766
4063
  import { cva as cva9 } from "class-variance-authority";
3767
4064
  import { X as X2 } from "lucide-react";
3768
4065
  import { Slot as Slot2 } from "radix-ui";
3769
- import { jsx as jsx24, jsxs as jsxs23 } from "react/jsx-runtime";
4066
+ import { jsx as jsx25, jsxs as jsxs24 } from "react/jsx-runtime";
3770
4067
  var chipVariants = cva9(
3771
4068
  [
3772
4069
  "inline-flex w-fit shrink-0 items-center justify-center whitespace-nowrap",
@@ -3858,7 +4155,7 @@ var chipCountVariants = cva9(
3858
4155
  }
3859
4156
  }
3860
4157
  );
3861
- var Chip = React22.forwardRef(
4158
+ var Chip = React23.forwardRef(
3862
4159
  ({
3863
4160
  className,
3864
4161
  variant = "filter",
@@ -3883,7 +4180,7 @@ var Chip = React22.forwardRef(
3883
4180
  value: _value,
3884
4181
  ...spanProps
3885
4182
  } = props;
3886
- return /* @__PURE__ */ jsxs23(
4183
+ return /* @__PURE__ */ jsxs24(
3887
4184
  "span",
3888
4185
  {
3889
4186
  "data-slot": "chip",
@@ -3892,8 +4189,8 @@ var Chip = React22.forwardRef(
3892
4189
  className: cn(chipVariants({ variant, tone, size, pressed, className })),
3893
4190
  ...spanProps,
3894
4191
  children: [
3895
- /* @__PURE__ */ jsx24("span", { children }),
3896
- count !== void 0 ? /* @__PURE__ */ jsx24(
4192
+ /* @__PURE__ */ jsx25("span", { children }),
4193
+ count !== void 0 ? /* @__PURE__ */ jsx25(
3897
4194
  "span",
3898
4195
  {
3899
4196
  "aria-hidden": "true",
@@ -3903,7 +4200,7 @@ var Chip = React22.forwardRef(
3903
4200
  children: count
3904
4201
  }
3905
4202
  ) : null,
3906
- /* @__PURE__ */ jsx24(
4203
+ /* @__PURE__ */ jsx25(
3907
4204
  "button",
3908
4205
  {
3909
4206
  ref,
@@ -3913,7 +4210,7 @@ var Chip = React22.forwardRef(
3913
4210
  disabled,
3914
4211
  onClick,
3915
4212
  className: "inline-flex size-[var(--space-4)] items-center justify-center rounded-[var(--radius-full)] text-text-tertiary focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[var(--focus-ring)]",
3916
- children: /* @__PURE__ */ jsx24(X2, { "aria-hidden": "true", size: 14, strokeWidth: 2.25 })
4213
+ children: /* @__PURE__ */ jsx25(X2, { "aria-hidden": "true", size: 14, strokeWidth: 2.25 })
3917
4214
  }
3918
4215
  )
3919
4216
  ]
@@ -3921,7 +4218,7 @@ var Chip = React22.forwardRef(
3921
4218
  );
3922
4219
  }
3923
4220
  const Comp = asChild ? Slot2.Root : "button";
3924
- return /* @__PURE__ */ jsxs23(
4221
+ return /* @__PURE__ */ jsxs24(
3925
4222
  Comp,
3926
4223
  {
3927
4224
  ref,
@@ -3936,7 +4233,7 @@ var Chip = React22.forwardRef(
3936
4233
  ...props,
3937
4234
  children: [
3938
4235
  children,
3939
- count !== void 0 ? /* @__PURE__ */ jsx24(
4236
+ count !== void 0 ? /* @__PURE__ */ jsx25(
3940
4237
  "span",
3941
4238
  {
3942
4239
  "aria-hidden": "true",
@@ -3954,13 +4251,13 @@ var Chip = React22.forwardRef(
3954
4251
  Chip.displayName = "Chip";
3955
4252
 
3956
4253
  // src/components/ui/icon-button.tsx
3957
- import * as React23 from "react";
4254
+ import * as React24 from "react";
3958
4255
  import { cva as cva10 } from "class-variance-authority";
3959
- import { jsx as jsx25, jsxs as jsxs24 } from "react/jsx-runtime";
4256
+ import { jsx as jsx26, jsxs as jsxs25 } from "react/jsx-runtime";
3960
4257
  var iconButtonVariants = cva10(
3961
4258
  [
3962
4259
  "olun-icon-button relative inline-flex cursor-pointer shrink-0 items-center justify-center before:absolute before:content-['']",
3963
- "rounded-[var(--radius-sm)] border font-medium",
4260
+ "rounded-[var(--radius-md)] border font-medium",
3964
4261
  "transition-colors motion-reduce:transition-none",
3965
4262
  "focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[var(--focus-ring)]",
3966
4263
  "disabled:cursor-not-allowed disabled:bg-[var(--action-disabled-bg)] disabled:text-text-disabled",
@@ -3999,6 +4296,9 @@ var iconButtonVariants = cva10(
3999
4296
  className: "border-[var(--error)] bg-[var(--error-bg)] text-[var(--error)]"
4000
4297
  }
4001
4298
  ],
4299
+ // ghost is the intended default, not a fallback: ghost is reserved for icon-only
4300
+ // actions repeated in rows or chrome (toolbars, headers, table rows), and
4301
+ // IconButton is its canonical entry point (#58). Text actions use Button.
4002
4302
  defaultVariants: {
4003
4303
  variant: "ghost",
4004
4304
  size: "md",
@@ -4037,7 +4337,7 @@ var iconStrokeWidth = {
4037
4337
  md: 2.25,
4038
4338
  lg: 1.75
4039
4339
  };
4040
- var IconButton = React23.forwardRef(
4340
+ var IconButton = React24.forwardRef(
4041
4341
  ({
4042
4342
  className,
4043
4343
  variant = "ghost",
@@ -4046,343 +4346,128 @@ var IconButton = React23.forwardRef(
4046
4346
  icon: Icon,
4047
4347
  badge,
4048
4348
  badgeTone = "info",
4049
- type,
4050
- title,
4051
- "aria-label": ariaLabel,
4052
- "aria-labelledby": ariaLabelledBy,
4053
- ...props
4054
- }, ref) => {
4055
- const resolvedSize = size ?? "md";
4056
- const isToggle = pressed !== void 0;
4057
- const isPressed = pressed === true;
4058
- const hoverTitle = title ?? (typeof ariaLabel === "string" ? ariaLabel : void 0);
4059
- return /* @__PURE__ */ jsxs24(
4060
- "button",
4061
- {
4062
- ref,
4063
- ...props,
4064
- "data-slot": "icon-button",
4065
- "data-variant": variant,
4066
- "data-size": resolvedSize,
4067
- "data-pressed": isToggle ? String(isPressed) : void 0,
4068
- "aria-label": ariaLabel,
4069
- "aria-labelledby": ariaLabelledBy,
4070
- "aria-pressed": isToggle ? isPressed : void 0,
4071
- title: hoverTitle,
4072
- className: cn(
4073
- iconButtonVariants({ variant, size, pressed: isPressed, className })
4074
- ),
4075
- type: type ?? "button",
4076
- children: [
4077
- /* @__PURE__ */ jsx25(
4078
- Icon,
4079
- {
4080
- "aria-hidden": "true",
4081
- "data-slot": "icon-button-icon",
4082
- size: iconSize2[resolvedSize],
4083
- strokeWidth: iconStrokeWidth[resolvedSize]
4084
- }
4085
- ),
4086
- badge !== void 0 ? /* @__PURE__ */ jsx25(
4087
- "span",
4088
- {
4089
- "aria-hidden": "true",
4090
- "data-slot": "icon-button-badge",
4091
- "data-badge-tone": badgeTone,
4092
- className: iconButtonBadgeVariants({ tone: badgeTone }),
4093
- children: badge
4094
- }
4095
- ) : null
4096
- ]
4097
- }
4098
- );
4099
- }
4100
- );
4101
- IconButton.displayName = "IconButton";
4102
-
4103
- // src/components/ui/popover.tsx
4104
- import * as React24 from "react";
4105
- import { Popover as PopoverPrimitive } from "radix-ui";
4106
- import { jsx as jsx26, jsxs as jsxs25 } from "react/jsx-runtime";
4107
- function Popover({ modal = false, ...props }) {
4108
- return /* @__PURE__ */ jsx26(PopoverPrimitive.Root, { modal, ...props });
4109
- }
4110
- var popoverArrowClassName = "fill-[var(--bg-surface)] stroke-[var(--border)] [&>polygon]:[vector-effect:non-scaling-stroke]";
4111
- var PopoverTrigger = PopoverPrimitive.Trigger;
4112
- var PopoverAnchor = PopoverPrimitive.Anchor;
4113
- var PopoverClose = PopoverPrimitive.Close;
4114
- var PopoverContent = React24.forwardRef(({ className, align = "center", sideOffset = 8, collisionPadding = 8, showArrow = false, children, ...props }, ref) => /* @__PURE__ */ jsx26(PopoverPrimitive.Portal, { children: /* @__PURE__ */ jsxs25(
4115
- PopoverPrimitive.Content,
4116
- {
4117
- ref,
4118
- align,
4119
- sideOffset,
4120
- collisionPadding,
4121
- "data-slot": "popover-content",
4122
- className: cn(
4123
- "z-[var(--z-popover)] w-[260px] outline-none",
4124
- "rounded-[var(--radius-md)] border border-[var(--border)]",
4125
- "bg-[var(--bg-surface)] p-[var(--space-4)] text-foreground",
4126
- "shadow-[var(--shadow-4)]",
4127
- "data-[state=open]:animate-in data-[state=closed]:animate-out",
4128
- "data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0",
4129
- "data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95",
4130
- "data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2",
4131
- "data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2",
4132
- "motion-reduce:animate-none",
4133
- className
4134
- ),
4135
- ...props,
4136
- children: [
4137
- children,
4138
- showArrow ? /* @__PURE__ */ jsx26(
4139
- PopoverPrimitive.Arrow,
4140
- {
4141
- "data-slot": "popover-arrow",
4142
- className: popoverArrowClassName,
4143
- width: 11,
4144
- height: 5
4145
- }
4146
- ) : null
4147
- ]
4148
- }
4149
- ) }));
4150
- PopoverContent.displayName = PopoverPrimitive.Content.displayName;
4151
- var PopoverArrow = React24.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx26(
4152
- PopoverPrimitive.Arrow,
4153
- {
4154
- ref,
4155
- "data-slot": "popover-arrow",
4156
- className: cn(popoverArrowClassName, className),
4157
- width: 11,
4158
- height: 5,
4159
- ...props
4160
- }
4161
- ));
4162
- PopoverArrow.displayName = PopoverPrimitive.Arrow.displayName;
4163
-
4164
- // src/components/ui/sheet-drawer.tsx
4165
- import { Maximize2Icon, Minimize2Icon, XIcon as XIcon3 } from "lucide-react";
4166
-
4167
- // src/components/ui/sheet.tsx
4168
- import { XIcon as XIcon2 } from "lucide-react";
4169
- import { Dialog as SheetPrimitive } from "radix-ui";
4170
- import { jsx as jsx27, jsxs as jsxs26 } from "react/jsx-runtime";
4171
- var defaultSheetMotionConfig = {
4172
- type: "slide",
4173
- duration: 300,
4174
- easing: "decel"
4175
- };
4176
- var sheetMotionEasingValue = {
4177
- standard: "var(--ease-standard)",
4178
- // decel/sharp have no canonical --ease-* token; these compat beziers are frozen
4179
- // specifically to back this public `easing` prop (see tokens/compat.css).
4180
- decel: "var(--easing-decel)",
4181
- accel: "var(--ease-in)",
4182
- sharp: "var(--easing-sharp)",
4183
- bounce: "var(--ease-out)"
4184
- };
4185
- function resolveSheetMotionConfig(motion) {
4186
- if (motion === false) return false;
4187
- return {
4188
- ...defaultSheetMotionConfig,
4189
- ...motion
4190
- };
4191
- }
4192
- function formatSheetMotionDuration(duration) {
4193
- return typeof duration === "number" ? `${duration}ms` : duration;
4194
- }
4195
- function getSheetMotionStyle(motionConfig, style) {
4196
- if (!motionConfig) return style;
4197
- return {
4198
- ...style,
4199
- "--sheet-motion-duration": formatSheetMotionDuration(motionConfig.duration),
4200
- "--sheet-motion-easing": sheetMotionEasingValue[motionConfig.easing]
4201
- };
4202
- }
4203
- function Sheet({ ...props }) {
4204
- return /* @__PURE__ */ jsx27(SheetPrimitive.Root, { "data-slot": "sheet", ...props });
4205
- }
4206
- function SheetTrigger({
4207
- ...props
4208
- }) {
4209
- return /* @__PURE__ */ jsx27(SheetPrimitive.Trigger, { "data-slot": "sheet-trigger", ...props });
4210
- }
4211
- function SheetClose({
4212
- ...props
4213
- }) {
4214
- return /* @__PURE__ */ jsx27(SheetPrimitive.Close, { "data-slot": "sheet-close", ...props });
4215
- }
4216
- function SheetPortal({
4217
- ...props
4218
- }) {
4219
- return /* @__PURE__ */ jsx27(SheetPrimitive.Portal, { "data-slot": "sheet-portal", ...props });
4220
- }
4221
- function SheetOverlay({
4222
- className,
4223
- motion,
4224
- style,
4225
- ...props
4226
- }) {
4227
- const motionConfig = resolveSheetMotionConfig(motion);
4228
- return /* @__PURE__ */ jsx27(
4229
- SheetPrimitive.Overlay,
4230
- {
4231
- "data-slot": "sheet-overlay",
4232
- className: cn(
4233
- "fixed inset-0 z-[var(--z-overlay)] bg-[var(--scrim)]",
4234
- motionConfig && cn(
4235
- "transition-opacity motion-reduce:transition-none",
4236
- "duration-[var(--sheet-motion-duration)]",
4237
- "data-[state=closed]:opacity-0 data-[state=open]:opacity-100",
4238
- "data-[state=open]:animate-[olun-sheet-fade-in_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]",
4239
- "data-[state=closed]:animate-[olun-sheet-fade-out_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]",
4240
- "motion-reduce:animate-none"
4241
- ),
4242
- className
4243
- ),
4244
- style: getSheetMotionStyle(motionConfig, style),
4245
- ...props
4246
- }
4247
- );
4248
- }
4249
- function SheetContent({
4250
- className,
4251
- children,
4252
- side = "right",
4253
- mobileSide,
4254
- motion,
4255
- showCloseButton = false,
4256
- style,
4257
- ...props
4258
- }) {
4259
- const motionConfig = resolveSheetMotionConfig(motion);
4260
- const hasSlideMotion = motionConfig && motionConfig.type === "slide";
4261
- return /* @__PURE__ */ jsxs26(SheetPortal, { children: [
4262
- /* @__PURE__ */ jsx27(SheetOverlay, { motion: motionConfig }),
4263
- /* @__PURE__ */ jsxs26(
4264
- SheetPrimitive.Content,
4265
- {
4266
- "data-slot": "sheet-content",
4267
- className: cn(
4268
- "fixed z-[var(--z-modal)] flex flex-col gap-4 border-[var(--border)] bg-[var(--bg-surface)] shadow-[var(--shadow-4)]",
4269
- motionConfig && cn(
4270
- "motion-reduce:animate-none",
4271
- motionConfig.type === "fade" && "data-[state=open]:animate-[olun-sheet-fade-in_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-fade-out_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4272
- ),
4273
- side === "right" && cn(
4274
- "inset-y-0 right-0 h-full w-3/4 border-l sm:max-w-sm",
4275
- hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4276
- ),
4277
- side === "left" && cn(
4278
- "inset-y-0 left-0 h-full w-3/4 border-r sm:max-w-sm",
4279
- hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4280
- ),
4281
- side === "top" && cn(
4282
- "inset-x-0 top-0 h-auto border-b",
4283
- hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4284
- ),
4285
- side === "bottom" && cn(
4286
- "inset-x-0 bottom-0 h-auto border-t",
4287
- hasSlideMotion && "data-[state=open]:animate-[olun-sheet-in-from-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] data-[state=closed]:animate-[olun-sheet-out-to-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4288
- ),
4289
- mobileSide === "right" && cn(
4290
- "max-[899px]:inset-y-0 max-[899px]:right-0 max-[899px]:left-auto max-[899px]:h-full max-[899px]:w-3/4 max-[899px]:border-l max-[899px]:border-t-0 max-[899px]:rounded-none",
4291
- hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-right_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4292
- ),
4293
- mobileSide === "left" && cn(
4294
- "max-[899px]:inset-y-0 max-[899px]:left-0 max-[899px]:right-auto max-[899px]:h-full max-[899px]:w-3/4 max-[899px]:border-r max-[899px]:border-t-0 max-[899px]:rounded-none",
4295
- hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-left_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4296
- ),
4297
- mobileSide === "top" && cn(
4298
- // `max-w-none!` overrides the side variant's `sm:max-w-sm` cap (see mobileSide bottom).
4299
- "max-[899px]:inset-x-0 max-[899px]:top-0 max-[899px]:bottom-auto max-[899px]:h-auto max-[899px]:w-full max-[899px]:max-w-none! max-[899px]:border-b max-[899px]:border-l-0 max-[899px]:rounded-none",
4300
- hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-top_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4301
- ),
4302
- mobileSide === "bottom" && cn(
4303
- // `max-w-none!` overrides the side variant's `sm:max-w-sm` cap so the bottom sheet
4304
- // spans the full viewport width across the whole < 900px band (not capped to 24rem).
4305
- "max-[899px]:inset-x-0 max-[899px]:bottom-0 max-[899px]:top-auto max-[899px]:h-auto max-[899px]:w-full max-[899px]:max-w-none! max-[899px]:border-t max-[899px]:border-l-0 max-[899px]:rounded-none",
4306
- hasSlideMotion && "max-[899px]:data-[state=open]:animate-[olun-sheet-in-from-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both] max-[899px]:data-[state=closed]:animate-[olun-sheet-out-to-bottom_var(--sheet-motion-duration)_var(--sheet-motion-easing)_both]"
4307
- ),
4308
- className
4309
- ),
4310
- style: getSheetMotionStyle(motionConfig, style),
4311
- ...props,
4312
- children: [
4313
- children,
4314
- showCloseButton && /* @__PURE__ */ jsxs26(SheetPrimitive.Close, { className: "absolute top-4 right-4 cursor-pointer rounded-xs opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:ring-2 focus:ring-ring focus:ring-offset-2 focus:outline-hidden disabled:pointer-events-none data-[state=open]:bg-secondary", children: [
4315
- /* @__PURE__ */ jsx27(XIcon2, { className: "size-[16px]" }),
4316
- /* @__PURE__ */ jsx27("span", { className: "sr-only", children: "Close" })
4317
- ] })
4318
- ]
4319
- }
4320
- )
4321
- ] });
4322
- }
4323
- function SheetBody({ className, ...props }) {
4324
- return /* @__PURE__ */ jsx27(
4325
- "div",
4326
- {
4327
- "data-slot": "sheet-body",
4328
- className: cn("flex-1 overflow-y-auto p-4", className),
4329
- ...props
4330
- }
4331
- );
4332
- }
4333
- function SheetHeader({ className, ...props }) {
4334
- return /* @__PURE__ */ jsx27(
4335
- "div",
4336
- {
4337
- "data-slot": "sheet-header",
4338
- className: cn("flex flex-col gap-1.5 p-4", className),
4339
- ...props
4340
- }
4341
- );
4342
- }
4343
- function SheetFooter({ className, ...props }) {
4344
- return /* @__PURE__ */ jsx27(
4345
- "div",
4346
- {
4347
- "data-slot": "sheet-footer",
4348
- className: cn("mt-auto flex flex-col gap-2 p-4", className),
4349
- ...props
4350
- }
4351
- );
4352
- }
4353
- function SheetTitle({
4354
- className,
4355
- ...props
4356
- }) {
4357
- return /* @__PURE__ */ jsx27(
4358
- SheetPrimitive.Title,
4359
- {
4360
- "data-slot": "sheet-title",
4361
- className: cn("font-semibold text-foreground", className),
4362
- ...props
4363
- }
4364
- );
4365
- }
4366
- function SheetDescription({
4367
- className,
4368
- ...props
4369
- }) {
4370
- return /* @__PURE__ */ jsx27(
4371
- SheetPrimitive.Description,
4372
- {
4373
- "data-slot": "sheet-description",
4374
- className: cn("text-sm text-muted-foreground", className),
4375
- ...props
4376
- }
4377
- );
4349
+ type,
4350
+ title,
4351
+ "aria-label": ariaLabel,
4352
+ "aria-labelledby": ariaLabelledBy,
4353
+ ...props
4354
+ }, ref) => {
4355
+ const resolvedSize = size ?? "md";
4356
+ const isToggle = pressed !== void 0;
4357
+ const isPressed = pressed === true;
4358
+ const hoverTitle = title ?? (typeof ariaLabel === "string" ? ariaLabel : void 0);
4359
+ return /* @__PURE__ */ jsxs25(
4360
+ "button",
4361
+ {
4362
+ ref,
4363
+ ...props,
4364
+ "data-slot": "icon-button",
4365
+ "data-variant": variant,
4366
+ "data-size": resolvedSize,
4367
+ "data-pressed": isToggle ? String(isPressed) : void 0,
4368
+ "aria-label": ariaLabel,
4369
+ "aria-labelledby": ariaLabelledBy,
4370
+ "aria-pressed": isToggle ? isPressed : void 0,
4371
+ title: hoverTitle,
4372
+ className: cn(
4373
+ iconButtonVariants({ variant, size, pressed: isPressed, className })
4374
+ ),
4375
+ type: type ?? "button",
4376
+ children: [
4377
+ /* @__PURE__ */ jsx26(
4378
+ Icon,
4379
+ {
4380
+ "aria-hidden": "true",
4381
+ "data-slot": "icon-button-icon",
4382
+ size: iconSize2[resolvedSize],
4383
+ strokeWidth: iconStrokeWidth[resolvedSize]
4384
+ }
4385
+ ),
4386
+ badge !== void 0 ? /* @__PURE__ */ jsx26(
4387
+ "span",
4388
+ {
4389
+ "aria-hidden": "true",
4390
+ "data-slot": "icon-button-badge",
4391
+ "data-badge-tone": badgeTone,
4392
+ className: iconButtonBadgeVariants({ tone: badgeTone }),
4393
+ children: badge
4394
+ }
4395
+ ) : null
4396
+ ]
4397
+ }
4398
+ );
4399
+ }
4400
+ );
4401
+ IconButton.displayName = "IconButton";
4402
+
4403
+ // src/components/ui/popover.tsx
4404
+ import * as React25 from "react";
4405
+ import { Popover as PopoverPrimitive } from "radix-ui";
4406
+ import { jsx as jsx27, jsxs as jsxs26 } from "react/jsx-runtime";
4407
+ function Popover({ modal = false, ...props }) {
4408
+ return /* @__PURE__ */ jsx27(PopoverPrimitive.Root, { modal, ...props });
4378
4409
  }
4410
+ var popoverArrowClassName = "fill-[var(--bg-surface)] stroke-[var(--border)] [&>polygon]:[vector-effect:non-scaling-stroke]";
4411
+ var PopoverTrigger = PopoverPrimitive.Trigger;
4412
+ var PopoverAnchor = PopoverPrimitive.Anchor;
4413
+ var PopoverClose = PopoverPrimitive.Close;
4414
+ var PopoverContent = React25.forwardRef(({ className, align = "center", sideOffset = 8, collisionPadding = 8, showArrow = false, children, ...props }, ref) => /* @__PURE__ */ jsx27(PopoverPrimitive.Portal, { children: /* @__PURE__ */ jsxs26(
4415
+ PopoverPrimitive.Content,
4416
+ {
4417
+ ref,
4418
+ align,
4419
+ sideOffset,
4420
+ collisionPadding,
4421
+ "data-slot": "popover-content",
4422
+ className: cn(
4423
+ "z-[var(--z-popover)] w-[260px] outline-none",
4424
+ "rounded-[var(--radius-md)] border border-[var(--border)]",
4425
+ "bg-[var(--bg-surface)] p-[var(--space-4)] text-foreground",
4426
+ "shadow-[var(--shadow-16)]",
4427
+ "data-[state=open]:animate-in data-[state=closed]:animate-out",
4428
+ "data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0",
4429
+ "data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95",
4430
+ "data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2",
4431
+ "data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2",
4432
+ "motion-reduce:animate-none",
4433
+ className
4434
+ ),
4435
+ ...props,
4436
+ children: [
4437
+ children,
4438
+ showArrow ? /* @__PURE__ */ jsx27(
4439
+ PopoverPrimitive.Arrow,
4440
+ {
4441
+ "data-slot": "popover-arrow",
4442
+ className: popoverArrowClassName,
4443
+ width: 11,
4444
+ height: 5
4445
+ }
4446
+ ) : null
4447
+ ]
4448
+ }
4449
+ ) }));
4450
+ PopoverContent.displayName = PopoverPrimitive.Content.displayName;
4451
+ var PopoverArrow = React25.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx27(
4452
+ PopoverPrimitive.Arrow,
4453
+ {
4454
+ ref,
4455
+ "data-slot": "popover-arrow",
4456
+ className: cn(popoverArrowClassName, className),
4457
+ width: 11,
4458
+ height: 5,
4459
+ ...props
4460
+ }
4461
+ ));
4462
+ PopoverArrow.displayName = PopoverPrimitive.Arrow.displayName;
4379
4463
 
4380
4464
  // src/components/ui/sheet-drawer.tsx
4465
+ import { Maximize2Icon, Minimize2Icon, XIcon as XIcon3 } from "lucide-react";
4381
4466
  import { jsx as jsx28, jsxs as jsxs27 } from "react/jsx-runtime";
4382
4467
  var sheetDrawerContentClassName = cn(
4383
4468
  "gap-0 p-0",
4384
4469
  "bg-[var(--bg-surface)] text-foreground",
4385
- "border-[var(--border)] shadow-[var(--shadow-4)]",
4470
+ "border-[var(--border)] shadow-[var(--shadow-16)]",
4386
4471
  "min-[900px]:w-[480px] min-[900px]:max-w-[480px]",
4387
4472
  "max-[899px]:h-[min(85dvh,720px)] max-[899px]:max-h-[85dvh] max-[899px]:w-full max-[899px]:max-w-none",
4388
4473
  "max-[899px]:rounded-t-[var(--radius-lg)]"
@@ -4402,7 +4487,7 @@ var sheetDrawerTitleClassName = "text-[18px] font-bold leading-snug text-foregro
4402
4487
  var sheetDrawerDescriptionClassName = "break-keep text-[14px] leading-normal text-text-secondary";
4403
4488
  var sheetDrawerCloseButtonClassName = cn(
4404
4489
  "flex size-[32px] shrink-0 cursor-pointer items-center justify-center",
4405
- "rounded-[var(--radius-sm)] text-text-tertiary transition-colors",
4490
+ "rounded-[var(--radius-md)] text-text-tertiary transition-colors",
4406
4491
  "hover:bg-[var(--action-hover)] hover:text-foreground",
4407
4492
  "focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[var(--focus-ring)] focus-visible:ring-offset-2"
4408
4493
  );
@@ -4411,7 +4496,7 @@ var sheetDrawerHeaderActionsClassName = cn(
4411
4496
  );
4412
4497
  var sheetDrawerExpandButtonClassName = cn(
4413
4498
  "inline-flex cursor-pointer items-center justify-center gap-[var(--space-1)]",
4414
- "rounded-[var(--radius-sm)] text-text-tertiary transition-colors",
4499
+ "rounded-[var(--radius-md)] text-text-tertiary transition-colors",
4415
4500
  "hover:bg-[var(--action-hover)] hover:text-foreground",
4416
4501
  "focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[var(--focus-ring)] focus-visible:ring-offset-2",
4417
4502
  "h-[32px] px-[var(--space-2)]"
@@ -4554,7 +4639,7 @@ var collapsibleClassNames = {
4554
4639
  trigger: "hidden"
4555
4640
  }
4556
4641
  };
4557
- var FilterToolbar = React25.forwardRef(
4642
+ var FilterToolbar = React26.forwardRef(
4558
4643
  ({
4559
4644
  className,
4560
4645
  search,
@@ -4569,15 +4654,15 @@ var FilterToolbar = React25.forwardRef(
4569
4654
  actions,
4570
4655
  ...props
4571
4656
  }, ref) => {
4572
- const [rootElement, setRootElement] = React25.useState(
4657
+ const [rootElement, setRootElement] = React26.useState(
4573
4658
  null
4574
4659
  );
4575
- const [containerWidth, setContainerWidth] = React25.useState(
4660
+ const [containerWidth, setContainerWidth] = React26.useState(
4576
4661
  null
4577
4662
  );
4578
- const [overlayOpen, setOverlayOpen] = React25.useState(false);
4579
- const triggerRef = React25.useRef(null);
4580
- const setRootRefs = React25.useCallback(
4663
+ const [overlayOpen, setOverlayOpen] = React26.useState(false);
4664
+ const triggerRef = React26.useRef(null);
4665
+ const setRootRefs = React26.useCallback(
4581
4666
  (element) => {
4582
4667
  setRootElement(element);
4583
4668
  if (typeof ref === "function") ref(element);
@@ -4585,7 +4670,7 @@ var FilterToolbar = React25.forwardRef(
4585
4670
  },
4586
4671
  [ref]
4587
4672
  );
4588
- React25.useEffect(() => {
4673
+ React26.useEffect(() => {
4589
4674
  if (!rootElement) return;
4590
4675
  const updateWidth = () => {
4591
4676
  setContainerWidth(rootElement.getBoundingClientRect().width);
@@ -4596,7 +4681,7 @@ var FilterToolbar = React25.forwardRef(
4596
4681
  observer.observe(rootElement);
4597
4682
  return () => observer.disconnect();
4598
4683
  }, [rootElement]);
4599
- const handleOverlayOpenChange = React25.useCallback((open) => {
4684
+ const handleOverlayOpenChange = React26.useCallback((open) => {
4600
4685
  setOverlayOpen(open);
4601
4686
  if (!open) queueMicrotask(() => triggerRef.current?.focus());
4602
4687
  }, []);
@@ -4795,12 +4880,12 @@ var FilterToolbar = React25.forwardRef(
4795
4880
  FilterToolbar.displayName = "FilterToolbar";
4796
4881
 
4797
4882
  // src/components/ui/data-table.tsx
4798
- import * as React27 from "react";
4883
+ import * as React28 from "react";
4799
4884
  import { ChevronDown as ChevronDown3, ChevronUp as ChevronUp2, ChevronsUpDown } from "lucide-react";
4800
4885
  import { cva as cva12 } from "class-variance-authority";
4801
4886
 
4802
4887
  // src/components/ui/checkbox.tsx
4803
- import * as React26 from "react";
4888
+ import * as React27 from "react";
4804
4889
  import { cva as cva11 } from "class-variance-authority";
4805
4890
  import { Check as Check3, Minus } from "lucide-react";
4806
4891
  import { Checkbox as CheckboxPrimitive } from "radix-ui";
@@ -4860,7 +4945,7 @@ var checkboxGroupItemVariants = cva11(
4860
4945
  {
4861
4946
  variants: {
4862
4947
  appearance: {
4863
- plain: "inline-flex items-start gap-[var(--space-3)] rounded-[var(--radius-sm)] px-pad-compact-x py-pad-compact-y",
4948
+ plain: "inline-flex items-start gap-[var(--space-3)] rounded-[var(--radius-md)] px-pad-compact-x py-pad-compact-y",
4864
4949
  card: [
4865
4950
  "flex min-h-[calc(var(--space-12)+var(--space-2))] items-start gap-[var(--space-3)]",
4866
4951
  "rounded-[var(--radius-md)] border border-[var(--border-subtle)] bg-[var(--bg-surface)]",
@@ -4907,11 +4992,11 @@ var checkboxGroupBoxVariants = cva11(
4907
4992
  }
4908
4993
  }
4909
4994
  );
4910
- var CheckboxGroupContext = React26.createContext(null);
4995
+ var CheckboxGroupContext = React27.createContext(null);
4911
4996
  function getLabel(children, label) {
4912
4997
  return children ?? label;
4913
4998
  }
4914
- var Checkbox = React26.forwardRef(
4999
+ var Checkbox = React27.forwardRef(
4915
5000
  ({
4916
5001
  className,
4917
5002
  size = "md",
@@ -4929,8 +5014,8 @@ var Checkbox = React26.forwardRef(
4929
5014
  onCheckedChange,
4930
5015
  ...props
4931
5016
  }, ref) => {
4932
- const group = React26.useContext(CheckboxGroupContext);
4933
- const generatedId = React26.useId();
5017
+ const group = React27.useContext(CheckboxGroupContext);
5018
+ const generatedId = React27.useId();
4934
5019
  const checkboxId = id ?? generatedId;
4935
5020
  const labelContent = getLabel(children, label);
4936
5021
  const isGrouped = Boolean(group && value != null);
@@ -5196,7 +5281,7 @@ function getRenderedCell(row, column) {
5196
5281
  if (value === null || value === void 0) {
5197
5282
  return null;
5198
5283
  }
5199
- if (React27.isValidElement(value)) {
5284
+ if (React28.isValidElement(value)) {
5200
5285
  return value;
5201
5286
  }
5202
5287
  return String(value);
@@ -5292,8 +5377,9 @@ function MobileSortControls({
5292
5377
  type: "button",
5293
5378
  "data-slot": "data-table-mobile-sort-button",
5294
5379
  size: "xs",
5295
- variant: active ? "secondary" : "outline",
5380
+ variant: "secondary",
5296
5381
  "aria-pressed": active,
5382
+ className: active ? "border-[var(--border-strong)] bg-[var(--action-selected)] hover:border-[var(--border-strong)] hover:bg-[var(--action-selected)]" : void 0,
5297
5383
  onClick: () => onSortChange?.(column.key, nextSort),
5298
5384
  children: /* @__PURE__ */ jsxs30("span", { className: "inline-flex min-w-0 items-center gap-[var(--space-1)]", children: [
5299
5385
  /* @__PURE__ */ jsx31("span", { className: "truncate", children: column.header }),
@@ -5558,9 +5644,9 @@ function DataTableMobileCardView({
5558
5644
  }
5559
5645
  );
5560
5646
  }
5561
- var MemoDataTableRow = React27.memo(DataTableRowView);
5562
- var MemoDataTableMobileCard = React27.memo(DataTableMobileCardView);
5563
- var useIsomorphicLayoutEffect = typeof window === "undefined" ? React27.useEffect : React27.useLayoutEffect;
5647
+ var MemoDataTableRow = React28.memo(DataTableRowView);
5648
+ var MemoDataTableMobileCard = React28.memo(DataTableMobileCardView);
5649
+ var useIsomorphicLayoutEffect = typeof window === "undefined" ? React28.useEffect : React28.useLayoutEffect;
5564
5650
  var VIRTUAL_DEFAULT_OVERSCAN = 8;
5565
5651
  var VIRTUAL_INITIAL_ROWS = 24;
5566
5652
  var VIRTUAL_FALLBACK_SIZE = { desktop: 48, mobile: 120 };
@@ -5583,16 +5669,16 @@ function useVirtualWindow({
5583
5669
  desktopListRef,
5584
5670
  mobileListRef
5585
5671
  }) {
5586
- const [win, setWin] = React27.useState({
5672
+ const [win, setWin] = React28.useState({
5587
5673
  layout: null,
5588
5674
  start: 0,
5589
5675
  end: VIRTUAL_INITIAL_ROWS,
5590
5676
  size: 0
5591
5677
  });
5592
- const measuredSize = React27.useRef({ desktop: 0, mobile: 0 });
5593
- const update = React27.useRef(() => void 0);
5594
- const reported = React27.useRef("");
5595
- const latest = React27.useRef({ count, layout: "desktop" });
5678
+ const measuredSize = React28.useRef({ desktop: 0, mobile: 0 });
5679
+ const update = React28.useRef(() => void 0);
5680
+ const reported = React28.useRef("");
5681
+ const latest = React28.useRef({ count, layout: "desktop" });
5596
5682
  update.current = () => {
5597
5683
  if (!enabled) {
5598
5684
  return;
@@ -5639,7 +5725,7 @@ function useVirtualWindow({
5639
5725
  useIsomorphicLayoutEffect(() => {
5640
5726
  update.current();
5641
5727
  });
5642
- React27.useEffect(() => {
5728
+ React28.useEffect(() => {
5643
5729
  if (!enabled) {
5644
5730
  return;
5645
5731
  }
@@ -5661,7 +5747,7 @@ function useVirtualWindow({
5661
5747
  window.cancelAnimationFrame(frame);
5662
5748
  };
5663
5749
  }, [enabled]);
5664
- const scrollToIndex = React27.useCallback(
5750
+ const scrollToIndex = React28.useCallback(
5665
5751
  (index) => {
5666
5752
  const { count: rowCount, layout } = latest.current;
5667
5753
  const list = (layout === "desktop" ? desktopListRef : mobileListRef).current;
@@ -5718,10 +5804,10 @@ function DataTableInner({
5718
5804
  }, ref) {
5719
5805
  const virtualOptions = virtual ? virtual === true ? {} : virtual : null;
5720
5806
  const isVirtual = virtualOptions !== null;
5721
- const desktopRef = React27.useRef(null);
5722
- const headerRef = React27.useRef(null);
5723
- const desktopListRef = React27.useRef(null);
5724
- const mobileListRef = React27.useRef(null);
5807
+ const desktopRef = React28.useRef(null);
5808
+ const headerRef = React28.useRef(null);
5809
+ const desktopListRef = React28.useRef(null);
5810
+ const mobileListRef = React28.useRef(null);
5725
5811
  const { win: virtualWindow, scrollToIndex } = useVirtualWindow({
5726
5812
  enabled: isVirtual,
5727
5813
  count: data.length,
@@ -5732,7 +5818,7 @@ function DataTableInner({
5732
5818
  desktopListRef,
5733
5819
  mobileListRef
5734
5820
  });
5735
- React27.useImperativeHandle(virtualOptions?.handleRef, () => ({ scrollToIndex }), [scrollToIndex]);
5821
+ React28.useImperativeHandle(virtualOptions?.handleRef, () => ({ scrollToIndex }), [scrollToIndex]);
5736
5822
  const resolvedSelectedIds = selectedIds ?? /* @__PURE__ */ new Set();
5737
5823
  const rowIds = data.map((row) => getRowId(row, keyField));
5738
5824
  const selectedCount = rowIds.filter((id) => resolvedSelectedIds.has(id)).length;
@@ -5767,19 +5853,19 @@ function DataTableInner({
5767
5853
  window.location.assign(href);
5768
5854
  }
5769
5855
  };
5770
- const latestHandlers = React27.useRef({ toggleRow, activateRow, onRowContextMenu });
5856
+ const latestHandlers = React28.useRef({ toggleRow, activateRow, onRowContextMenu });
5771
5857
  useIsomorphicLayoutEffect(() => {
5772
5858
  latestHandlers.current = { toggleRow, activateRow, onRowContextMenu };
5773
5859
  });
5774
- const stableToggleRow = React27.useCallback(
5860
+ const stableToggleRow = React28.useCallback(
5775
5861
  (id, checked) => latestHandlers.current.toggleRow(id, checked),
5776
5862
  []
5777
5863
  );
5778
- const stableActivateRow = React27.useCallback(
5864
+ const stableActivateRow = React28.useCallback(
5779
5865
  (row, href, event) => latestHandlers.current.activateRow(row, href, event),
5780
5866
  []
5781
5867
  );
5782
- const stableRowContextMenu = React27.useCallback(
5868
+ const stableRowContextMenu = React28.useCallback(
5783
5869
  (rowId, event) => latestHandlers.current.onRowContextMenu?.(rowId, event),
5784
5870
  []
5785
5871
  );
@@ -6002,7 +6088,7 @@ function DataTableInner({
6002
6088
  }
6003
6089
  );
6004
6090
  }
6005
- var DataTable = React27.forwardRef(DataTableInner);
6091
+ var DataTable = React28.forwardRef(DataTableInner);
6006
6092
  DataTable.displayName = "DataTable";
6007
6093
 
6008
6094
  // src/components/ui/dropdown-menu.tsx
@@ -6043,7 +6129,7 @@ function DropdownMenuContent({
6043
6129
  className: cn(
6044
6130
  "z-[var(--z-popover)] max-h-(--radix-dropdown-menu-content-available-height) min-w-[8rem]",
6045
6131
  "origin-(--radix-dropdown-menu-content-transform-origin) overflow-x-hidden overflow-y-auto",
6046
- "rounded-sm border border-[var(--border)] bg-[var(--bg-surface)] p-[var(--space-1)] text-text-primary shadow-2",
6132
+ "rounded-[var(--radius-lg)] border border-[var(--border)] bg-[var(--bg-surface)] p-[var(--space-1)] text-text-primary shadow-[var(--shadow-16)]",
6047
6133
  "data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2",
6048
6134
  "data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2",
6049
6135
  "data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=closed]:zoom-out-95",
@@ -6242,7 +6328,7 @@ function DropdownMenuSubContent({
6242
6328
  "data-slot": "dropdown-menu-sub-content",
6243
6329
  className: cn(
6244
6330
  "z-[var(--z-popover)] min-w-[8rem] origin-(--radix-dropdown-menu-content-transform-origin) overflow-hidden",
6245
- "rounded-sm border border-[var(--border)] bg-[var(--bg-surface)] p-[var(--space-1)] text-text-primary shadow-2",
6331
+ "rounded-[var(--radius-lg)] border border-[var(--border)] bg-[var(--bg-surface)] p-[var(--space-1)] text-text-primary shadow-[var(--shadow-16)]",
6246
6332
  "data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2",
6247
6333
  "data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2",
6248
6334
  "data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=closed]:zoom-out-95",
@@ -6287,7 +6373,7 @@ function ContextMenu({
6287
6373
  }
6288
6374
 
6289
6375
  // src/components/ui/bulk-action-bar.tsx
6290
- import * as React28 from "react";
6376
+ import * as React29 from "react";
6291
6377
  import { X as X3 } from "lucide-react";
6292
6378
  import { jsx as jsx34, jsxs as jsxs33 } from "react/jsx-runtime";
6293
6379
  function ActionButton({ action }) {
@@ -6314,7 +6400,7 @@ function ActionButton({ action }) {
6314
6400
  gap: 6,
6315
6401
  height: 30,
6316
6402
  padding: "0 10px",
6317
- borderRadius: "var(--radius-sm)",
6403
+ borderRadius: "var(--radius-md)",
6318
6404
  fontFamily: "var(--font-sans)",
6319
6405
  fontSize: 13,
6320
6406
  fontWeight: 500,
@@ -6371,7 +6457,7 @@ function ClearButton({ onClear }) {
6371
6457
  flexShrink: 0,
6372
6458
  alignItems: "center",
6373
6459
  justifyContent: "center",
6374
- borderRadius: "var(--radius-sm)"
6460
+ borderRadius: "var(--radius-md)"
6375
6461
  },
6376
6462
  children: /* @__PURE__ */ jsx34(X3, { size: 16, strokeWidth: 1.75, "aria-hidden": "true" })
6377
6463
  }
@@ -6428,10 +6514,10 @@ var idleLineStyle = {
6428
6514
  fontVariantNumeric: "tabular-nums",
6429
6515
  color: "var(--text-secondary)"
6430
6516
  };
6431
- var useIsomorphicLayoutEffect2 = typeof window === "undefined" ? React28.useEffect : React28.useLayoutEffect;
6517
+ var useIsomorphicLayoutEffect2 = typeof window === "undefined" ? React29.useEffect : React29.useLayoutEffect;
6432
6518
  function useCompactSummary(slot, enabled) {
6433
- const [fullWidth, setFullWidth] = React28.useState(null);
6434
- const measure = React28.useCallback(() => {
6519
+ const [fullWidth, setFullWidth] = React29.useState(null);
6520
+ const measure = React29.useCallback(() => {
6435
6521
  if (!slot) return;
6436
6522
  setFullWidth((prev) => {
6437
6523
  if (prev === null) return slot.scrollWidth > slot.clientWidth ? slot.scrollWidth : null;
@@ -6441,7 +6527,7 @@ function useCompactSummary(slot, enabled) {
6441
6527
  useIsomorphicLayoutEffect2(() => {
6442
6528
  if (enabled) measure();
6443
6529
  });
6444
- React28.useEffect(() => {
6530
+ React29.useEffect(() => {
6445
6531
  if (!enabled || !slot || typeof ResizeObserver === "undefined") return;
6446
6532
  const observer = new ResizeObserver(measure);
6447
6533
  observer.observe(slot);
@@ -6478,7 +6564,7 @@ function BulkActionBar({
6478
6564
  children: trailing
6479
6565
  }
6480
6566
  ) : null;
6481
- const [summaryElement, setSummaryElement] = React28.useState(null);
6567
+ const [summaryElement, setSummaryElement] = React29.useState(null);
6482
6568
  const compact = useCompactSummary(
6483
6569
  summaryElement,
6484
6570
  inline && compactSummary !== void 0 && compactSummary !== null
@@ -6667,8 +6753,23 @@ function BulkActionBar({
6667
6753
  style: { ...floatingStyle, ...style },
6668
6754
  ...props,
6669
6755
  children: [
6670
- countLabel,
6671
- summarySlot,
6756
+ /* @__PURE__ */ jsxs33(
6757
+ "div",
6758
+ {
6759
+ role: "status",
6760
+ "data-slot": "bulk-action-bar-state",
6761
+ style: {
6762
+ display: "flex",
6763
+ minWidth: 0,
6764
+ alignItems: "center",
6765
+ gap: "var(--space-2)"
6766
+ },
6767
+ children: [
6768
+ countLabel,
6769
+ summarySlot
6770
+ ]
6771
+ }
6772
+ ),
6672
6773
  count > 0 && actions.length > 0 ? /* @__PURE__ */ jsx34(Divider, {}) : null,
6673
6774
  actionGroup,
6674
6775
  /* @__PURE__ */ jsx34(Divider, {}),
@@ -6680,7 +6781,7 @@ function BulkActionBar({
6680
6781
  }
6681
6782
 
6682
6783
  // src/components/ui/confirm-dialog.tsx
6683
- import * as React29 from "react";
6784
+ import * as React30 from "react";
6684
6785
  import { Fragment as Fragment8, jsx as jsx35, jsxs as jsxs34 } from "react/jsx-runtime";
6685
6786
  var confirmDialogContentClassName = cn(
6686
6787
  "fixed left-1/2 top-1/2 z-[var(--z-modal)]",
@@ -6710,12 +6811,14 @@ function ConfirmDialog({
6710
6811
  onConfirm,
6711
6812
  loading = false,
6712
6813
  children,
6713
- confirmDisabled = false
6814
+ confirmDisabled = false,
6815
+ mobilePresentation = "center"
6714
6816
  }) {
6715
- const [pending, setPending] = React29.useState(false);
6716
- const busyRef = React29.useRef(false);
6817
+ const [pending, setPending] = React30.useState(false);
6818
+ const busyRef = React30.useRef(false);
6717
6819
  const isBusy = loading || pending;
6718
- const handleOpenChange = React29.useCallback(
6820
+ const returnFocus = useReturnFocus();
6821
+ const handleOpenChange = React30.useCallback(
6719
6822
  (nextOpen) => {
6720
6823
  if (!nextOpen && isBusy) {
6721
6824
  return;
@@ -6724,7 +6827,7 @@ function ConfirmDialog({
6724
6827
  },
6725
6828
  [isBusy, onOpenChange]
6726
6829
  );
6727
- const handleConfirm = React29.useCallback(async () => {
6830
+ const handleConfirm = React30.useCallback(async () => {
6728
6831
  if (busyRef.current || loading || confirmDisabled) {
6729
6832
  return;
6730
6833
  }
@@ -6764,11 +6867,23 @@ function ConfirmDialog({
6764
6867
  "data-slot": "dialog-footer",
6765
6868
  className: confirmDialogFooterClassName,
6766
6869
  children: [
6767
- /* @__PURE__ */ jsx35(Button, { variant: "secondary", disabled: isBusy, onClick: () => handleOpenChange(false), children: cancelLabel }),
6870
+ /* @__PURE__ */ jsx35(
6871
+ Button,
6872
+ {
6873
+ variant: "secondary",
6874
+ size: "lg",
6875
+ className: footerButtonHitAreaClassName,
6876
+ disabled: isBusy,
6877
+ onClick: () => handleOpenChange(false),
6878
+ children: cancelLabel
6879
+ }
6880
+ ),
6768
6881
  /* @__PURE__ */ jsx35(
6769
6882
  Button,
6770
6883
  {
6771
6884
  variant: tone === "destructive" ? "destructive" : "primary",
6885
+ size: "lg",
6886
+ className: footerButtonHitAreaClassName,
6772
6887
  loading: isBusy,
6773
6888
  disabled: confirmDisabled,
6774
6889
  onClick: handleConfirm,
@@ -6781,7 +6896,20 @@ function ConfirmDialog({
6781
6896
  ] });
6782
6897
  return /* @__PURE__ */ jsx35(Dialog, { open, onOpenChange: handleOpenChange, children: /* @__PURE__ */ jsxs34(DialogPortal, { children: [
6783
6898
  /* @__PURE__ */ jsx35(DialogOverlay, {}),
6784
- /* @__PURE__ */ jsx35(DialogRawContent, { role: "alertdialog", "data-slot": "dialog-content", className: confirmDialogContentClassName, children: dialogBody })
6899
+ /* @__PURE__ */ jsx35(
6900
+ DialogRawContent,
6901
+ {
6902
+ role: "alertdialog",
6903
+ "data-slot": "dialog-content",
6904
+ className: cn(
6905
+ confirmDialogContentClassName,
6906
+ mobilePresentation === "sheet" && dialogMobileSheetClassName
6907
+ ),
6908
+ style: mobilePresentation === "sheet" ? dialogMobileSheetStyle() : void 0,
6909
+ ...returnFocus,
6910
+ children: dialogBody
6911
+ }
6912
+ )
6785
6913
  ] }) });
6786
6914
  }
6787
6915
 
@@ -6880,9 +7008,100 @@ function AvatarFallback({
6880
7008
  );
6881
7009
  }
6882
7010
 
6883
- // src/components/ui/badge.tsx
6884
- import * as React30 from "react";
7011
+ // src/components/ui/action-sheet.tsx
7012
+ import * as React31 from "react";
7013
+ import { X as X4 } from "lucide-react";
6885
7014
  import { jsx as jsx38, jsxs as jsxs35 } from "react/jsx-runtime";
7015
+ var actionSheetContentClassName = cn(
7016
+ "gap-0 max-h-[85dvh] rounded-t-[var(--radius-lg)]",
7017
+ "pb-[env(safe-area-inset-bottom)]"
7018
+ );
7019
+ var actionSheetHeaderClassName = cn(
7020
+ "flex items-start gap-[var(--space-3)] px-[var(--space-4)] pt-[var(--space-4)] pb-[var(--space-3)]"
7021
+ );
7022
+ var actionSheetTitleClassName = cn(
7023
+ "break-keep text-[15px] font-semibold leading-snug text-foreground"
7024
+ );
7025
+ var actionSheetDescriptionClassName = cn(
7026
+ "mt-[var(--space-1)] break-keep text-[13px] leading-normal text-text-secondary"
7027
+ );
7028
+ var actionSheetListClassName = "min-h-0 overflow-y-auto";
7029
+ var actionSheetItemClassName = cn(
7030
+ "flex min-h-12 w-full cursor-pointer items-center gap-[var(--space-3)] px-[var(--space-4)] text-left",
7031
+ "border-t border-[var(--border-subtle)] text-[13px] font-medium text-text-primary",
7032
+ "transition-colors motion-reduce:transition-none hover:bg-[var(--action-hover)]",
7033
+ "focus-visible:outline-2 focus-visible:-outline-offset-2 focus-visible:outline-[var(--focus-ring)]",
7034
+ "enabled:data-[destructive]:text-[var(--semantic-error-fg)]",
7035
+ "disabled:cursor-not-allowed disabled:bg-[var(--action-disabled-bg)] disabled:text-text-disabled"
7036
+ );
7037
+ function ActionSheet({
7038
+ open,
7039
+ onOpenChange,
7040
+ title,
7041
+ description,
7042
+ items,
7043
+ closeLabel = "\uB2EB\uAE30"
7044
+ }) {
7045
+ const pendingRef = React31.useRef(null);
7046
+ const returnFocus = useReturnFocus();
7047
+ const handleOpenChange = (nextOpen) => {
7048
+ pendingRef.current = null;
7049
+ onOpenChange(nextOpen);
7050
+ };
7051
+ const handleSelect = (item) => {
7052
+ onOpenChange(false);
7053
+ pendingRef.current = item;
7054
+ };
7055
+ const handleCloseAutoFocus = (event) => {
7056
+ returnFocus.onCloseAutoFocus(event);
7057
+ const item = pendingRef.current;
7058
+ pendingRef.current = null;
7059
+ item?.onSelect();
7060
+ };
7061
+ return /* @__PURE__ */ jsx38(Sheet, { open, onOpenChange: handleOpenChange, children: /* @__PURE__ */ jsxs35(
7062
+ SheetContent,
7063
+ {
7064
+ side: "bottom",
7065
+ "data-slot": "action-sheet-content",
7066
+ className: actionSheetContentClassName,
7067
+ onOpenAutoFocus: returnFocus.onOpenAutoFocus,
7068
+ onCloseAutoFocus: handleCloseAutoFocus,
7069
+ ...description ? {} : { "aria-describedby": void 0 },
7070
+ children: [
7071
+ /* @__PURE__ */ jsxs35("div", { "data-slot": "action-sheet-header", className: actionSheetHeaderClassName, children: [
7072
+ /* @__PURE__ */ jsxs35("div", { className: "min-w-0 flex-1", children: [
7073
+ /* @__PURE__ */ jsx38(SheetTitle, { className: actionSheetTitleClassName, children: title }),
7074
+ description ? /* @__PURE__ */ jsx38(SheetDescription, { className: actionSheetDescriptionClassName, children: description }) : null
7075
+ ] }),
7076
+ /* @__PURE__ */ jsx38(SheetClose, { asChild: true, children: /* @__PURE__ */ jsx38(IconButton, { size: "sm", icon: X4, "aria-label": closeLabel }) })
7077
+ ] }),
7078
+ /* @__PURE__ */ jsx38("div", { "data-slot": "action-sheet-list", className: actionSheetListClassName, children: items.map((item) => {
7079
+ const Icon = item.icon;
7080
+ return /* @__PURE__ */ jsxs35(
7081
+ "button",
7082
+ {
7083
+ type: "button",
7084
+ "data-slot": "action-sheet-item",
7085
+ "data-destructive": item.destructive ? "" : void 0,
7086
+ className: actionSheetItemClassName,
7087
+ disabled: item.disabled,
7088
+ onClick: () => handleSelect(item),
7089
+ children: [
7090
+ Icon ? /* @__PURE__ */ jsx38(Icon, { "aria-hidden": true, size: 17, strokeWidth: 1.75, className: "shrink-0" }) : null,
7091
+ /* @__PURE__ */ jsx38("span", { className: "min-w-0 flex-1 break-keep", children: item.label })
7092
+ ]
7093
+ },
7094
+ item.id
7095
+ );
7096
+ }) })
7097
+ ]
7098
+ }
7099
+ ) });
7100
+ }
7101
+
7102
+ // src/components/ui/badge.tsx
7103
+ import * as React32 from "react";
7104
+ import { jsx as jsx39, jsxs as jsxs36 } from "react/jsx-runtime";
6886
7105
  var DOT = {
6887
7106
  error: "var(--semantic-error-fg)",
6888
7107
  warning: "var(--semantic-warning-fg)",
@@ -6891,8 +7110,8 @@ var DOT = {
6891
7110
  neutral: "var(--text-tertiary)",
6892
7111
  brand: "var(--accent-pop)"
6893
7112
  };
6894
- var Badge = React30.forwardRef(
6895
- ({ tone = "neutral", className, children, ...props }, ref) => /* @__PURE__ */ jsxs35(
7113
+ var Badge = React32.forwardRef(
7114
+ ({ tone = "neutral", className, children, ...props }, ref) => /* @__PURE__ */ jsxs36(
6896
7115
  "span",
6897
7116
  {
6898
7117
  ref,
@@ -6906,7 +7125,7 @@ var Badge = React30.forwardRef(
6906
7125
  ),
6907
7126
  ...props,
6908
7127
  children: [
6909
- /* @__PURE__ */ jsx38(
7128
+ /* @__PURE__ */ jsx39(
6910
7129
  "span",
6911
7130
  {
6912
7131
  "aria-hidden": "true",
@@ -6923,8 +7142,8 @@ var Badge = React30.forwardRef(
6923
7142
  Badge.displayName = "Badge";
6924
7143
 
6925
7144
  // src/components/ui/two-tier-badge.tsx
6926
- import * as React31 from "react";
6927
- import { jsx as jsx39, jsxs as jsxs36 } from "react/jsx-runtime";
7145
+ import * as React33 from "react";
7146
+ import { jsx as jsx40, jsxs as jsxs37 } from "react/jsx-runtime";
6928
7147
  var FG = {
6929
7148
  neutral: "var(--text-secondary)",
6930
7149
  info: "var(--semantic-info-fg)",
@@ -6945,7 +7164,7 @@ var SEGMENT = {
6945
7164
  md: "gap-[7px] py-[var(--space-1)] px-[var(--space-3)] text-[14px]"
6946
7165
  };
6947
7166
  var DOT2 = { xs: 5, sm: 6, md: 7 };
6948
- var TwoTierBadge = React31.forwardRef(
7167
+ var TwoTierBadge = React33.forwardRef(
6949
7168
  ({ primary, secondary, tone = "neutral", emphasis = "subtle", size = "sm", showDot = false, className, style, ...props }, ref) => {
6950
7169
  const strong = emphasis === "strong";
6951
7170
  const fg = FG[tone];
@@ -6954,7 +7173,7 @@ var TwoTierBadge = React31.forwardRef(
6954
7173
  const frame = strong ? tinted : "var(--border-subtle)";
6955
7174
  const divider = strong ? tinted : "var(--border)";
6956
7175
  const dotSize = DOT2[size];
6957
- return /* @__PURE__ */ jsxs36(
7176
+ return /* @__PURE__ */ jsxs37(
6958
7177
  "span",
6959
7178
  {
6960
7179
  ref,
@@ -6968,14 +7187,14 @@ var TwoTierBadge = React31.forwardRef(
6968
7187
  style: { fontFamily: "var(--font-sans)", borderColor: frame, background: "transparent", ...style },
6969
7188
  ...props,
6970
7189
  children: [
6971
- /* @__PURE__ */ jsxs36(
7190
+ /* @__PURE__ */ jsxs37(
6972
7191
  "span",
6973
7192
  {
6974
7193
  "data-slot": "two-tier-badge-primary",
6975
7194
  className: cn("inline-flex items-center whitespace-nowrap font-semibold", SEGMENT[size]),
6976
7195
  style: { color: fg, background: strong ? BG[tone] : "transparent" },
6977
7196
  children: [
6978
- showDot ? /* @__PURE__ */ jsx39(
7197
+ showDot ? /* @__PURE__ */ jsx40(
6979
7198
  "span",
6980
7199
  {
6981
7200
  "aria-hidden": "true",
@@ -6990,11 +7209,11 @@ var TwoTierBadge = React31.forwardRef(
6990
7209
  }
6991
7210
  }
6992
7211
  ) : null,
6993
- /* @__PURE__ */ jsx39("span", { children: primary })
7212
+ /* @__PURE__ */ jsx40("span", { children: primary })
6994
7213
  ]
6995
7214
  }
6996
7215
  ),
6997
- secondary != null ? /* @__PURE__ */ jsx39(
7216
+ secondary != null ? /* @__PURE__ */ jsx40(
6998
7217
  "span",
6999
7218
  {
7000
7219
  "data-slot": "two-tier-badge-secondary",
@@ -7015,8 +7234,8 @@ var TwoTierBadge = React31.forwardRef(
7015
7234
  TwoTierBadge.displayName = "TwoTierBadge";
7016
7235
 
7017
7236
  // src/components/ui/status-badge.tsx
7018
- import * as React32 from "react";
7019
- import { jsx as jsx40, jsxs as jsxs37 } from "react/jsx-runtime";
7237
+ import * as React34 from "react";
7238
+ import { jsx as jsx41, jsxs as jsxs38 } from "react/jsx-runtime";
7020
7239
  var ROLE = {
7021
7240
  error: "error",
7022
7241
  warning: "warning",
@@ -7045,13 +7264,13 @@ var SIZE = {
7045
7264
  sm: { cls: "gap-[6px] py-[var(--space-1)] px-[var(--space-2)] text-[12px]", dot: 6 },
7046
7265
  md: { cls: "gap-[var(--space-2)] py-[var(--space-1)] px-[14px] text-[14px]", dot: 7 }
7047
7266
  };
7048
- var StatusBadge = React32.forwardRef(
7267
+ var StatusBadge = React34.forwardRef(
7049
7268
  ({ status = "active", emphasis = "subtle", size = "sm", showDot = true, pulse = true, className, children, style, ...props }, ref) => {
7050
7269
  const role = ROLE[status];
7051
7270
  const fg = FG2[role];
7052
7271
  const strong = emphasis === "strong";
7053
7272
  const ringDot = role === "neutral";
7054
- return /* @__PURE__ */ jsxs37(
7273
+ return /* @__PURE__ */ jsxs38(
7055
7274
  "span",
7056
7275
  {
7057
7276
  ref,
@@ -7069,7 +7288,7 @@ var StatusBadge = React32.forwardRef(
7069
7288
  },
7070
7289
  ...props,
7071
7290
  children: [
7072
- showDot ? /* @__PURE__ */ jsx40(
7291
+ showDot ? /* @__PURE__ */ jsx41(
7073
7292
  "span",
7074
7293
  {
7075
7294
  "aria-hidden": "true",
@@ -7087,7 +7306,7 @@ var StatusBadge = React32.forwardRef(
7087
7306
  }
7088
7307
  ) : null,
7089
7308
  children,
7090
- /* @__PURE__ */ jsx40("style", { children: "@keyframes olun-status-pulse{0%,100%{opacity:1}50%{opacity:.4}}@media (prefers-reduced-motion: reduce){[data-slot=status-badge-dot]{animation:none!important}}" })
7309
+ /* @__PURE__ */ jsx41("style", { children: "@keyframes olun-status-pulse{0%,100%{opacity:1}50%{opacity:.4}}@media (prefers-reduced-motion: reduce){[data-slot=status-badge-dot]{animation:none!important}}" })
7091
7310
  ]
7092
7311
  }
7093
7312
  );
@@ -7096,9 +7315,9 @@ var StatusBadge = React32.forwardRef(
7096
7315
  StatusBadge.displayName = "StatusBadge";
7097
7316
 
7098
7317
  // src/components/ui/notification-badge.tsx
7099
- import * as React33 from "react";
7318
+ import * as React35 from "react";
7100
7319
  import { cva as cva13 } from "class-variance-authority";
7101
- import { jsx as jsx41 } from "react/jsx-runtime";
7320
+ import { jsx as jsx42 } from "react/jsx-runtime";
7102
7321
  var notificationBadgeVariants = cva13(
7103
7322
  [
7104
7323
  "inline-flex shrink-0 items-center justify-center rounded-[var(--radius-full)]",
@@ -7129,7 +7348,7 @@ function formatNotificationCount(count, max) {
7129
7348
  }
7130
7349
  return String(count);
7131
7350
  }
7132
- var NotificationBadge = React33.forwardRef(
7351
+ var NotificationBadge = React35.forwardRef(
7133
7352
  ({
7134
7353
  className,
7135
7354
  count,
@@ -7144,7 +7363,7 @@ var NotificationBadge = React33.forwardRef(
7144
7363
  }
7145
7364
  const normalizedMax = Math.max(1, Math.floor(max));
7146
7365
  const label = ariaLabel ?? (count > normalizedMax ? `\uC77D\uC9C0 \uC54A\uC740 \uC54C\uB9BC ${normalizedMax}\uAC1C \uC774\uC0C1` : `\uC77D\uC9C0 \uC54A\uC740 \uC54C\uB9BC ${count}\uAC1C`);
7147
- return /* @__PURE__ */ jsx41(
7366
+ return /* @__PURE__ */ jsx42(
7148
7367
  "span",
7149
7368
  {
7150
7369
  ref,
@@ -7162,9 +7381,9 @@ var NotificationBadge = React33.forwardRef(
7162
7381
  NotificationBadge.displayName = "NotificationBadge";
7163
7382
 
7164
7383
  // src/components/ui/empty-state.tsx
7165
- import * as React34 from "react";
7384
+ import * as React36 from "react";
7166
7385
  import { cva as cva14 } from "class-variance-authority";
7167
- import { jsx as jsx42, jsxs as jsxs38 } from "react/jsx-runtime";
7386
+ import { jsx as jsx43, jsxs as jsxs39 } from "react/jsx-runtime";
7168
7387
  var emptyStateBaseVariants = cva14(
7169
7388
  [
7170
7389
  "flex flex-col items-center justify-center text-center",
@@ -7236,7 +7455,7 @@ var iconSize3 = {
7236
7455
  md: 20,
7237
7456
  lg: 24
7238
7457
  };
7239
- var EmptyState = React34.forwardRef(
7458
+ var EmptyState = React36.forwardRef(
7240
7459
  ({
7241
7460
  className,
7242
7461
  size = "md",
@@ -7251,7 +7470,7 @@ var EmptyState = React34.forwardRef(
7251
7470
  ...props
7252
7471
  }, ref) => {
7253
7472
  const resolvedSize = size ?? "md";
7254
- return /* @__PURE__ */ jsxs38(
7473
+ return /* @__PURE__ */ jsxs39(
7255
7474
  "div",
7256
7475
  {
7257
7476
  ref,
@@ -7260,17 +7479,17 @@ var EmptyState = React34.forwardRef(
7260
7479
  className: cn(emptyStateVariants({ size, tone, surface, bordered, className })),
7261
7480
  ...props,
7262
7481
  children: [
7263
- Icon ? /* @__PURE__ */ jsx42(
7482
+ Icon ? /* @__PURE__ */ jsx43(
7264
7483
  "span",
7265
7484
  {
7266
7485
  "aria-hidden": "true",
7267
7486
  "data-slot": "empty-state-icon",
7268
7487
  className: emptyStateIconVariants({ size: resolvedSize }),
7269
- children: /* @__PURE__ */ jsx42(Icon, { size: iconSize3[resolvedSize], strokeWidth: 1.75 })
7488
+ children: /* @__PURE__ */ jsx43(Icon, { size: iconSize3[resolvedSize], strokeWidth: 1.75 })
7270
7489
  }
7271
7490
  ) : null,
7272
- /* @__PURE__ */ jsxs38("div", { className: "flex max-w-[420px] flex-col items-center gap-[var(--space-2)]", children: [
7273
- /* @__PURE__ */ jsx42(
7491
+ /* @__PURE__ */ jsxs39("div", { className: "flex max-w-[420px] flex-col items-center gap-[var(--space-2)]", children: [
7492
+ /* @__PURE__ */ jsx43(
7274
7493
  "h2",
7275
7494
  {
7276
7495
  "data-slot": "empty-state-title",
@@ -7278,7 +7497,7 @@ var EmptyState = React34.forwardRef(
7278
7497
  children: title
7279
7498
  }
7280
7499
  ),
7281
- description ? /* @__PURE__ */ jsx42(
7500
+ description ? /* @__PURE__ */ jsx43(
7282
7501
  "p",
7283
7502
  {
7284
7503
  "data-slot": "empty-state-description",
@@ -7286,7 +7505,7 @@ var EmptyState = React34.forwardRef(
7286
7505
  children: description
7287
7506
  }
7288
7507
  ) : null,
7289
- hint ? /* @__PURE__ */ jsx42(
7508
+ hint ? /* @__PURE__ */ jsx43(
7290
7509
  "p",
7291
7510
  {
7292
7511
  "data-slot": "empty-state-hint",
@@ -7295,7 +7514,7 @@ var EmptyState = React34.forwardRef(
7295
7514
  }
7296
7515
  ) : null
7297
7516
  ] }),
7298
- action ? /* @__PURE__ */ jsx42("div", { "data-slot": "empty-state-action", className: "mt-[var(--space-2)]", children: action }) : null
7517
+ action ? /* @__PURE__ */ jsx43("div", { "data-slot": "empty-state-action", className: "mt-[var(--space-2)]", children: action }) : null
7299
7518
  ]
7300
7519
  }
7301
7520
  );
@@ -7304,10 +7523,10 @@ var EmptyState = React34.forwardRef(
7304
7523
  EmptyState.displayName = "EmptyState";
7305
7524
 
7306
7525
  // src/components/ui/error-state.tsx
7307
- import * as React35 from "react";
7526
+ import * as React37 from "react";
7308
7527
  import { AlertTriangle } from "lucide-react";
7309
7528
  import { cva as cva15 } from "class-variance-authority";
7310
- import { jsx as jsx43, jsxs as jsxs39 } from "react/jsx-runtime";
7529
+ import { jsx as jsx44, jsxs as jsxs40 } from "react/jsx-runtime";
7311
7530
  var errorStateVariants = cva15(
7312
7531
  [
7313
7532
  "flex flex-col items-center justify-center text-center",
@@ -7329,7 +7548,7 @@ var errorStateVariants = cva15(
7329
7548
  }
7330
7549
  }
7331
7550
  );
7332
- var ErrorState = React35.forwardRef(
7551
+ var ErrorState = React37.forwardRef(
7333
7552
  ({
7334
7553
  className,
7335
7554
  size = "md",
@@ -7340,7 +7559,7 @@ var ErrorState = React35.forwardRef(
7340
7559
  onRetry,
7341
7560
  retryLabel = "\uB2E4\uC2DC \uC2DC\uB3C4",
7342
7561
  ...props
7343
- }, ref) => /* @__PURE__ */ jsxs39(
7562
+ }, ref) => /* @__PURE__ */ jsxs40(
7344
7563
  "div",
7345
7564
  {
7346
7565
  ref,
@@ -7349,17 +7568,17 @@ var ErrorState = React35.forwardRef(
7349
7568
  className: cn(errorStateVariants({ size, surface, className })),
7350
7569
  ...props,
7351
7570
  children: [
7352
- /* @__PURE__ */ jsx43(
7571
+ /* @__PURE__ */ jsx44(
7353
7572
  "span",
7354
7573
  {
7355
7574
  "aria-hidden": "true",
7356
7575
  "data-slot": "error-state-icon",
7357
7576
  className: "inline-flex size-[48px] items-center justify-center rounded-[var(--radius-full)] bg-[var(--error-bg)] text-[var(--error)]",
7358
- children: /* @__PURE__ */ jsx43(AlertTriangle, { size: 24, strokeWidth: 1.75 })
7577
+ children: /* @__PURE__ */ jsx44(AlertTriangle, { size: 24, strokeWidth: 1.75 })
7359
7578
  }
7360
7579
  ),
7361
- /* @__PURE__ */ jsxs39("div", { className: "flex max-w-[420px] flex-col items-center gap-[var(--space-2)]", children: [
7362
- /* @__PURE__ */ jsx43(
7580
+ /* @__PURE__ */ jsxs40("div", { className: "flex max-w-[420px] flex-col items-center gap-[var(--space-2)]", children: [
7581
+ /* @__PURE__ */ jsx44(
7363
7582
  "h2",
7364
7583
  {
7365
7584
  "data-slot": "error-state-title",
@@ -7367,7 +7586,7 @@ var ErrorState = React35.forwardRef(
7367
7586
  children: title
7368
7587
  }
7369
7588
  ),
7370
- /* @__PURE__ */ jsx43(
7589
+ /* @__PURE__ */ jsx44(
7371
7590
  "p",
7372
7591
  {
7373
7592
  "data-slot": "error-state-message",
@@ -7375,7 +7594,7 @@ var ErrorState = React35.forwardRef(
7375
7594
  children: message
7376
7595
  }
7377
7596
  ),
7378
- errorCode ? /* @__PURE__ */ jsx43(
7597
+ errorCode ? /* @__PURE__ */ jsx44(
7379
7598
  "p",
7380
7599
  {
7381
7600
  "data-slot": "error-state-code",
@@ -7384,7 +7603,7 @@ var ErrorState = React35.forwardRef(
7384
7603
  }
7385
7604
  ) : null
7386
7605
  ] }),
7387
- onRetry ? /* @__PURE__ */ jsx43(Button, { size: "sm", variant: "outline", onClick: onRetry, children: retryLabel }) : null
7606
+ onRetry ? /* @__PURE__ */ jsx44(Button, { size: "sm", variant: "secondary", onClick: onRetry, children: retryLabel }) : null
7388
7607
  ]
7389
7608
  }
7390
7609
  )
@@ -7392,9 +7611,9 @@ var ErrorState = React35.forwardRef(
7392
7611
  ErrorState.displayName = "ErrorState";
7393
7612
 
7394
7613
  // src/components/ui/skeleton.tsx
7395
- import * as React36 from "react";
7614
+ import * as React38 from "react";
7396
7615
  import { cva as cva16 } from "class-variance-authority";
7397
- import { jsx as jsx44 } from "react/jsx-runtime";
7616
+ import { jsx as jsx45 } from "react/jsx-runtime";
7398
7617
  var skeletonVariants = cva16(
7399
7618
  [
7400
7619
  // bg-inset: light #F1F2F4 reads on white surfaces (bg-raised was white = invisible);
@@ -7438,8 +7657,8 @@ var spinnerVariants = cva16(
7438
7657
  }
7439
7658
  }
7440
7659
  );
7441
- var Skeleton = React36.forwardRef(
7442
- ({ className, shape, style, ...props }, ref) => /* @__PURE__ */ jsx44(
7660
+ var Skeleton = React38.forwardRef(
7661
+ ({ className, shape, style, ...props }, ref) => /* @__PURE__ */ jsx45(
7443
7662
  "div",
7444
7663
  {
7445
7664
  ref,
@@ -7452,15 +7671,15 @@ var Skeleton = React36.forwardRef(
7452
7671
  );
7453
7672
  Skeleton.displayName = "Skeleton";
7454
7673
  var defaultTextWidths = ["92%", "84%", "68%", "76%"];
7455
- var SkeletonText = React36.forwardRef(
7456
- ({ className, lines = 3, widths = defaultTextWidths, ...props }, ref) => /* @__PURE__ */ jsx44(
7674
+ var SkeletonText = React38.forwardRef(
7675
+ ({ className, lines = 3, widths = defaultTextWidths, ...props }, ref) => /* @__PURE__ */ jsx45(
7457
7676
  "div",
7458
7677
  {
7459
7678
  ref,
7460
7679
  "data-slot": "skeleton-text",
7461
7680
  className: cn("flex flex-col gap-[var(--space-2)]", className),
7462
7681
  ...props,
7463
- children: Array.from({ length: lines }, (_, index) => /* @__PURE__ */ jsx44(
7682
+ children: Array.from({ length: lines }, (_, index) => /* @__PURE__ */ jsx45(
7464
7683
  Skeleton,
7465
7684
  {
7466
7685
  shape: "text",
@@ -7472,7 +7691,7 @@ var SkeletonText = React36.forwardRef(
7472
7691
  )
7473
7692
  );
7474
7693
  SkeletonText.displayName = "SkeletonText";
7475
- var SkeletonRow = React36.forwardRef(
7694
+ var SkeletonRow = React38.forwardRef(
7476
7695
  ({
7477
7696
  className,
7478
7697
  columns,
@@ -7483,7 +7702,7 @@ var SkeletonRow = React36.forwardRef(
7483
7702
  }, ref) => {
7484
7703
  const rowCount = Math.max(5, count);
7485
7704
  const gridTemplateColumns = columns.map((column) => column.width ?? "1fr").join(" ");
7486
- return /* @__PURE__ */ jsx44(
7705
+ return /* @__PURE__ */ jsx45(
7487
7706
  "div",
7488
7707
  {
7489
7708
  ref,
@@ -7497,7 +7716,7 @@ var SkeletonRow = React36.forwardRef(
7497
7716
  className
7498
7717
  ),
7499
7718
  ...props,
7500
- children: Array.from({ length: rowCount }, (_, rowIndex) => /* @__PURE__ */ jsx44(
7719
+ children: Array.from({ length: rowCount }, (_, rowIndex) => /* @__PURE__ */ jsx45(
7501
7720
  "div",
7502
7721
  {
7503
7722
  "data-slot": "skeleton-row",
@@ -7505,11 +7724,11 @@ var SkeletonRow = React36.forwardRef(
7505
7724
  "grid min-h-[48px] items-center border-t border-[var(--border-subtle)] first:border-t-0"
7506
7725
  ),
7507
7726
  style: { gridTemplateColumns },
7508
- children: columns.map((column, columnIndex) => /* @__PURE__ */ jsx44(
7727
+ children: columns.map((column, columnIndex) => /* @__PURE__ */ jsx45(
7509
7728
  "div",
7510
7729
  {
7511
7730
  className: "px-[var(--space-4)] py-[var(--space-2)]",
7512
- children: /* @__PURE__ */ jsx44(
7731
+ children: /* @__PURE__ */ jsx45(
7513
7732
  Skeleton,
7514
7733
  {
7515
7734
  shape: "text",
@@ -7529,8 +7748,8 @@ var SkeletonRow = React36.forwardRef(
7529
7748
  }
7530
7749
  );
7531
7750
  SkeletonRow.displayName = "SkeletonRow";
7532
- var Spinner = React36.forwardRef(
7533
- ({ className, size, label = "\uB85C\uB529 \uC911", ...props }, ref) => /* @__PURE__ */ jsx44(
7751
+ var Spinner = React38.forwardRef(
7752
+ ({ className, size, label = "\uB85C\uB529 \uC911", ...props }, ref) => /* @__PURE__ */ jsx45(
7534
7753
  "span",
7535
7754
  {
7536
7755
  ref,
@@ -7545,12 +7764,12 @@ var Spinner = React36.forwardRef(
7545
7764
  Spinner.displayName = "Spinner";
7546
7765
 
7547
7766
  // src/components/ui/pagination.tsx
7548
- import * as React37 from "react";
7767
+ import * as React39 from "react";
7549
7768
  import { ChevronsLeft, ChevronLeft, ChevronRight as ChevronRight2, ChevronsRight } from "lucide-react";
7550
7769
  import { cva as cva17 } from "class-variance-authority";
7551
7770
 
7552
7771
  // src/components/ui/page-size-select.tsx
7553
- import { jsx as jsx45, jsxs as jsxs40 } from "react/jsx-runtime";
7772
+ import { jsx as jsx46, jsxs as jsxs41 } from "react/jsx-runtime";
7554
7773
  var DEFAULT_OPTIONS = [10, 20, 50, 100];
7555
7774
  function PageSizeSelect({
7556
7775
  value,
@@ -7569,7 +7788,7 @@ function PageSizeSelect({
7569
7788
  label: `${opt}${unit}`
7570
7789
  }));
7571
7790
  const selectSize = size === "compact" ? "sm" : "md";
7572
- return /* @__PURE__ */ jsxs40(
7791
+ return /* @__PURE__ */ jsxs41(
7573
7792
  "div",
7574
7793
  {
7575
7794
  "data-slot": "page-size-select",
@@ -7578,8 +7797,8 @@ function PageSizeSelect({
7578
7797
  className
7579
7798
  ),
7580
7799
  children: [
7581
- label != null ? /* @__PURE__ */ jsx45("span", { children: label }) : null,
7582
- /* @__PURE__ */ jsx45(
7800
+ label != null ? /* @__PURE__ */ jsx46("span", { children: label }) : null,
7801
+ /* @__PURE__ */ jsx46(
7583
7802
  Select,
7584
7803
  {
7585
7804
  id,
@@ -7601,7 +7820,7 @@ function PageSizeSelect({
7601
7820
  }
7602
7821
 
7603
7822
  // src/components/ui/pagination.tsx
7604
- import { jsx as jsx46, jsxs as jsxs41 } from "react/jsx-runtime";
7823
+ import { jsx as jsx47, jsxs as jsxs42 } from "react/jsx-runtime";
7605
7824
  var paginationVariants = cva17(
7606
7825
  [
7607
7826
  "flex w-full flex-col gap-[var(--space-3)]",
@@ -7622,7 +7841,7 @@ var paginationVariants = cva17(
7622
7841
  );
7623
7842
  var paginationControlVariants = cva17(
7624
7843
  [
7625
- "inline-flex shrink-0 items-center justify-center rounded-[var(--radius-sm)] border",
7844
+ "inline-flex shrink-0 items-center justify-center rounded-[var(--radius-md)] border",
7626
7845
  "border-transparent bg-transparent font-medium text-text-secondary",
7627
7846
  "transition-colors motion-reduce:transition-none",
7628
7847
  "hover:border-[var(--border-strong)] hover:bg-[var(--action-hover)] hover:text-foreground",
@@ -7674,7 +7893,7 @@ function NavigationButton({
7674
7893
  icon: Icon,
7675
7894
  onPageChange
7676
7895
  }) {
7677
- return /* @__PURE__ */ jsx46(
7896
+ return /* @__PURE__ */ jsx47(
7678
7897
  "button",
7679
7898
  {
7680
7899
  "aria-label": label,
@@ -7682,11 +7901,11 @@ function NavigationButton({
7682
7901
  className: paginationControlVariants({ size }),
7683
7902
  type: "button",
7684
7903
  onClick: () => onPageChange?.(page),
7685
- children: /* @__PURE__ */ jsx46(Icon, { "aria-hidden": "true", "data-slot": "pagination-icon" })
7904
+ children: /* @__PURE__ */ jsx47(Icon, { "aria-hidden": "true", "data-slot": "pagination-icon" })
7686
7905
  }
7687
7906
  );
7688
7907
  }
7689
- var Pagination = React37.forwardRef(
7908
+ var Pagination = React39.forwardRef(
7690
7909
  ({
7691
7910
  className,
7692
7911
  size = "standard",
@@ -7711,7 +7930,7 @@ var Pagination = React37.forwardRef(
7711
7930
  const items = getPaginationItems(currentPage, pageCount);
7712
7931
  const isFirstPage = currentPage === 1;
7713
7932
  const isLastPage = currentPage === pageCount;
7714
- return /* @__PURE__ */ jsxs41(
7933
+ return /* @__PURE__ */ jsxs42(
7715
7934
  "nav",
7716
7935
  {
7717
7936
  ref,
@@ -7721,9 +7940,9 @@ var Pagination = React37.forwardRef(
7721
7940
  className: cn(paginationVariants({ size: resolvedSize, className })),
7722
7941
  ...props,
7723
7942
  children: [
7724
- /* @__PURE__ */ jsxs41("div", { className: "flex flex-wrap items-center gap-[var(--space-3)]", children: [
7725
- /* @__PURE__ */ jsx46("span", { "data-slot": "pagination-total", className: "font-medium text-text-secondary", children: totalLabel(total) }),
7726
- showPageSize ? /* @__PURE__ */ jsx46("div", { "data-slot": "pagination-size", children: /* @__PURE__ */ jsx46(
7943
+ /* @__PURE__ */ jsxs42("div", { className: "flex flex-wrap items-center gap-[var(--space-3)]", children: [
7944
+ /* @__PURE__ */ jsx47("span", { "data-slot": "pagination-total", className: "font-medium text-text-secondary", children: totalLabel(total) }),
7945
+ showPageSize ? /* @__PURE__ */ jsx47("div", { "data-slot": "pagination-size", children: /* @__PURE__ */ jsx47(
7727
7946
  PageSizeSelect,
7728
7947
  {
7729
7948
  label: pageSizeLabel,
@@ -7735,13 +7954,13 @@ var Pagination = React37.forwardRef(
7735
7954
  }
7736
7955
  ) }) : null
7737
7956
  ] }),
7738
- /* @__PURE__ */ jsxs41(
7957
+ /* @__PURE__ */ jsxs42(
7739
7958
  "div",
7740
7959
  {
7741
7960
  "data-slot": "pagination-list",
7742
7961
  className: "flex items-center justify-center gap-[var(--space-1)]",
7743
7962
  children: [
7744
- /* @__PURE__ */ jsx46(
7963
+ /* @__PURE__ */ jsx47(
7745
7964
  NavigationButton,
7746
7965
  {
7747
7966
  label: "\uCCAB \uD398\uC774\uC9C0",
@@ -7752,7 +7971,7 @@ var Pagination = React37.forwardRef(
7752
7971
  onPageChange
7753
7972
  }
7754
7973
  ),
7755
- /* @__PURE__ */ jsx46(
7974
+ /* @__PURE__ */ jsx47(
7756
7975
  NavigationButton,
7757
7976
  {
7758
7977
  label: "\uC774\uC804 \uD398\uC774\uC9C0",
@@ -7764,7 +7983,7 @@ var Pagination = React37.forwardRef(
7764
7983
  }
7765
7984
  ),
7766
7985
  items.map(
7767
- (item, index) => item === "ellipsis" ? /* @__PURE__ */ jsx46(
7986
+ (item, index) => item === "ellipsis" ? /* @__PURE__ */ jsx47(
7768
7987
  "span",
7769
7988
  {
7770
7989
  "data-slot": "pagination-ellipsis",
@@ -7776,7 +7995,7 @@ var Pagination = React37.forwardRef(
7776
7995
  children: "..."
7777
7996
  },
7778
7997
  `ellipsis-${index}`
7779
- ) : /* @__PURE__ */ jsx46(
7998
+ ) : /* @__PURE__ */ jsx47(
7780
7999
  "button",
7781
8000
  {
7782
8001
  "aria-label": `${item} \uD398\uC774\uC9C0`,
@@ -7790,7 +8009,7 @@ var Pagination = React37.forwardRef(
7790
8009
  item
7791
8010
  )
7792
8011
  ),
7793
- /* @__PURE__ */ jsx46(
8012
+ /* @__PURE__ */ jsx47(
7794
8013
  NavigationButton,
7795
8014
  {
7796
8015
  label: "\uB2E4\uC74C \uD398\uC774\uC9C0",
@@ -7801,7 +8020,7 @@ var Pagination = React37.forwardRef(
7801
8020
  onPageChange
7802
8021
  }
7803
8022
  ),
7804
- /* @__PURE__ */ jsx46(
8023
+ /* @__PURE__ */ jsx47(
7805
8024
  NavigationButton,
7806
8025
  {
7807
8026
  label: "\uB9C8\uC9C0\uB9C9 \uD398\uC774\uC9C0",
@@ -7824,17 +8043,17 @@ Pagination.displayName = "Pagination";
7824
8043
 
7825
8044
  // src/components/ui/mode-toggle.tsx
7826
8045
  import { cva as cva18 } from "class-variance-authority";
7827
- import { jsx as jsx47, jsxs as jsxs42 } from "react/jsx-runtime";
8046
+ import { jsx as jsx48, jsxs as jsxs43 } from "react/jsx-runtime";
7828
8047
  var modeToggleVariants = cva18(
7829
8048
  [
7830
- "inline-flex items-center rounded-[var(--radius-sm)] border border-[var(--border-subtle)]",
8049
+ "inline-flex items-center rounded-[var(--radius-md)] border border-[var(--border-subtle)]",
7831
8050
  "bg-[var(--bg-inset)] p-[2px]"
7832
8051
  ].join(" ")
7833
8052
  );
7834
8053
  var modeToggleItemVariants = cva18(
7835
8054
  [
7836
8055
  "inline-flex min-h-[28px] cursor-pointer items-center justify-center gap-[var(--space-1)]",
7837
- "rounded-[calc(var(--radius-sm)_-_2px)] px-[var(--space-3)] py-[var(--space-1)]",
8056
+ "rounded-[calc(var(--radius-md)_-_2px)] px-[var(--space-3)] py-[var(--space-1)]",
7838
8057
  "font-[family-name:var(--font-display)] text-xs font-medium leading-none",
7839
8058
  "text-text-secondary transition-[background-color,color,box-shadow]",
7840
8059
  "duration-[var(--dur-fast)] ease-[var(--ease-standard)]",
@@ -7854,7 +8073,7 @@ function ModeToggle({
7854
8073
  onChange,
7855
8074
  ...props
7856
8075
  }) {
7857
- return /* @__PURE__ */ jsx47(
8076
+ return /* @__PURE__ */ jsx48(
7858
8077
  "div",
7859
8078
  {
7860
8079
  role: "group",
@@ -7864,7 +8083,7 @@ function ModeToggle({
7864
8083
  children: options.map((option) => {
7865
8084
  const Icon = option.icon;
7866
8085
  const isActive = option.value === value;
7867
- return /* @__PURE__ */ jsxs42(
8086
+ return /* @__PURE__ */ jsxs43(
7868
8087
  "button",
7869
8088
  {
7870
8089
  type: "button",
@@ -7880,8 +8099,8 @@ function ModeToggle({
7880
8099
  }
7881
8100
  },
7882
8101
  children: [
7883
- Icon ? /* @__PURE__ */ jsx47(Icon, { "aria-hidden": "true", "data-slot": "mode-toggle-icon" }) : null,
7884
- /* @__PURE__ */ jsx47("span", { children: option.label })
8102
+ Icon ? /* @__PURE__ */ jsx48(Icon, { "aria-hidden": "true", "data-slot": "mode-toggle-icon" }) : null,
8103
+ /* @__PURE__ */ jsx48("span", { children: option.label })
7885
8104
  ]
7886
8105
  },
7887
8106
  option.value
@@ -7892,9 +8111,9 @@ function ModeToggle({
7892
8111
  }
7893
8112
 
7894
8113
  // src/components/ui/action-footer.tsx
7895
- import * as React38 from "react";
8114
+ import * as React40 from "react";
7896
8115
  import { cva as cva19 } from "class-variance-authority";
7897
- import { jsx as jsx48, jsxs as jsxs43 } from "react/jsx-runtime";
8116
+ import { jsx as jsx49, jsxs as jsxs44 } from "react/jsx-runtime";
7898
8117
  var actionFooterVariants = cva19(
7899
8118
  [
7900
8119
  "flex flex-wrap items-center gap-[var(--space-4)] border-t border-[var(--border-subtle)]",
@@ -7965,11 +8184,12 @@ function getStatusLabel(status) {
7965
8184
  }
7966
8185
  }
7967
8186
  function renderAction(action) {
7968
- return /* @__PURE__ */ jsx48(
8187
+ return /* @__PURE__ */ jsx49(
7969
8188
  Button,
7970
8189
  {
7971
8190
  variant: action.variant,
7972
- size: "md",
8191
+ size: "lg",
8192
+ className: footerButtonHitAreaClassName,
7973
8193
  disabled: action.disabled,
7974
8194
  loading: action.loading,
7975
8195
  leadingIcon: action.leadingIcon,
@@ -7979,7 +8199,7 @@ function renderAction(action) {
7979
8199
  action.id ?? action.label
7980
8200
  );
7981
8201
  }
7982
- var ActionFooter = React38.forwardRef(
8202
+ var ActionFooter = React40.forwardRef(
7983
8203
  ({
7984
8204
  className,
7985
8205
  status,
@@ -7996,7 +8216,7 @@ var ActionFooter = React38.forwardRef(
7996
8216
  const mainActions = sortMainActions(
7997
8217
  visibleActions.filter((action) => !destructiveVariants.has(action.variant ?? "default"))
7998
8218
  );
7999
- return /* @__PURE__ */ jsxs43(
8219
+ return /* @__PURE__ */ jsxs44(
8000
8220
  "div",
8001
8221
  {
8002
8222
  ref,
@@ -8005,7 +8225,7 @@ var ActionFooter = React38.forwardRef(
8005
8225
  className: cn(actionFooterVariants({ position, surface, className })),
8006
8226
  ...props,
8007
8227
  children: [
8008
- destructiveActions.length > 0 ? /* @__PURE__ */ jsx48(
8228
+ destructiveActions.length > 0 ? /* @__PURE__ */ jsx49(
8009
8229
  "div",
8010
8230
  {
8011
8231
  "data-slot": "action-footer-destructive-actions",
@@ -8013,7 +8233,7 @@ var ActionFooter = React38.forwardRef(
8013
8233
  children: destructiveActions.map(renderAction)
8014
8234
  }
8015
8235
  ) : null,
8016
- status ? /* @__PURE__ */ jsxs43(
8236
+ status ? /* @__PURE__ */ jsxs44(
8017
8237
  "div",
8018
8238
  {
8019
8239
  "data-slot": "action-footer-status",
@@ -8021,7 +8241,7 @@ var ActionFooter = React38.forwardRef(
8021
8241
  "aria-live": "polite",
8022
8242
  className: cn(actionFooterStatusVariants({ kind: status.kind })),
8023
8243
  children: [
8024
- /* @__PURE__ */ jsx48(
8244
+ /* @__PURE__ */ jsx49(
8025
8245
  "span",
8026
8246
  {
8027
8247
  "aria-hidden": "true",
@@ -8029,11 +8249,11 @@ var ActionFooter = React38.forwardRef(
8029
8249
  className: "size-[6px] shrink-0 rounded-[var(--radius-full)]"
8030
8250
  }
8031
8251
  ),
8032
- /* @__PURE__ */ jsx48("span", { className: "truncate", children: getStatusLabel(status) })
8252
+ /* @__PURE__ */ jsx49("span", { className: "truncate", children: getStatusLabel(status) })
8033
8253
  ]
8034
8254
  }
8035
8255
  ) : null,
8036
- /* @__PURE__ */ jsx48(
8256
+ /* @__PURE__ */ jsx49(
8037
8257
  "div",
8038
8258
  {
8039
8259
  "data-slot": "action-footer-main-actions",
@@ -8049,9 +8269,9 @@ var ActionFooter = React38.forwardRef(
8049
8269
  ActionFooter.displayName = "ActionFooter";
8050
8270
 
8051
8271
  // src/components/ui/toast.tsx
8052
- import * as React39 from "react";
8272
+ import * as React41 from "react";
8053
8273
  import { cva as cva20 } from "class-variance-authority";
8054
- import { jsx as jsx49, jsxs as jsxs44 } from "react/jsx-runtime";
8274
+ import { jsx as jsx50, jsxs as jsxs45 } from "react/jsx-runtime";
8055
8275
  var DOT3 = {
8056
8276
  default: "var(--neutral)",
8057
8277
  success: "var(--success)",
@@ -8064,7 +8284,7 @@ var toastVariants = cva20(
8064
8284
  "flex min-w-[280px] max-w-[420px] items-center",
8065
8285
  "gap-[11px] rounded-[10px] border border-[var(--border)]",
8066
8286
  "px-[14px] py-[11px]",
8067
- "shadow-[var(--shadow-4)]",
8287
+ "shadow-[var(--shadow-8)]",
8068
8288
  "pointer-events-auto",
8069
8289
  "motion-reduce:animate-none"
8070
8290
  ].join(" "),
@@ -8169,7 +8389,7 @@ var toast = {
8169
8389
  }
8170
8390
  };
8171
8391
  var Toast = toast;
8172
- var ToastRoot = React39.forwardRef(
8392
+ var ToastRoot = React41.forwardRef(
8173
8393
  ({
8174
8394
  className,
8175
8395
  id,
@@ -8186,10 +8406,10 @@ var ToastRoot = React39.forwardRef(
8186
8406
  ...props
8187
8407
  }, ref) => {
8188
8408
  const durationMs = getToastDuration({ message, variant, duration });
8189
- const onCloseRef = React39.useRef(onClose);
8409
+ const onCloseRef = React41.useRef(onClose);
8190
8410
  onCloseRef.current = onClose;
8191
- const timerRef = React39.useRef(null);
8192
- React39.useEffect(() => {
8411
+ const timerRef = React41.useRef(null);
8412
+ React41.useEffect(() => {
8193
8413
  if (!onCloseRef.current) return void 0;
8194
8414
  const timer = createToastTimer(durationMs, () => onCloseRef.current?.());
8195
8415
  timerRef.current = timer;
@@ -8198,7 +8418,7 @@ var ToastRoot = React39.forwardRef(
8198
8418
  timerRef.current = null;
8199
8419
  };
8200
8420
  }, [durationMs]);
8201
- return /* @__PURE__ */ jsxs44(
8421
+ return /* @__PURE__ */ jsxs45(
8202
8422
  "div",
8203
8423
  {
8204
8424
  ref,
@@ -8226,7 +8446,7 @@ var ToastRoot = React39.forwardRef(
8226
8446
  },
8227
8447
  ...props,
8228
8448
  children: [
8229
- /* @__PURE__ */ jsx49(
8449
+ /* @__PURE__ */ jsx50(
8230
8450
  "span",
8231
8451
  {
8232
8452
  "aria-hidden": "true",
@@ -8235,8 +8455,8 @@ var ToastRoot = React39.forwardRef(
8235
8455
  style: { background: DOT3[variant] ?? DOT3.default }
8236
8456
  }
8237
8457
  ),
8238
- /* @__PURE__ */ jsxs44("div", { "data-slot": "toast-body", className: "min-w-0 flex-1", children: [
8239
- /* @__PURE__ */ jsx49(
8458
+ /* @__PURE__ */ jsxs45("div", { "data-slot": "toast-body", className: "min-w-0 flex-1", children: [
8459
+ /* @__PURE__ */ jsx50(
8240
8460
  "div",
8241
8461
  {
8242
8462
  "data-slot": "toast-message",
@@ -8244,7 +8464,7 @@ var ToastRoot = React39.forwardRef(
8244
8464
  children: message
8245
8465
  }
8246
8466
  ),
8247
- description ? /* @__PURE__ */ jsx49(
8467
+ description ? /* @__PURE__ */ jsx50(
8248
8468
  "div",
8249
8469
  {
8250
8470
  "data-slot": "toast-description",
@@ -8253,25 +8473,25 @@ var ToastRoot = React39.forwardRef(
8253
8473
  }
8254
8474
  ) : null
8255
8475
  ] }),
8256
- /* @__PURE__ */ jsxs44("div", { "data-slot": "toast-actions", className: "flex shrink-0 items-center gap-[2px]", children: [
8257
- action ? /* @__PURE__ */ jsx49(
8476
+ /* @__PURE__ */ jsxs45("div", { "data-slot": "toast-actions", className: "flex shrink-0 items-center gap-[2px]", children: [
8477
+ action ? /* @__PURE__ */ jsx50(
8258
8478
  Button,
8259
8479
  {
8260
8480
  "data-slot": "toast-action",
8261
8481
  size: "xs",
8262
- variant: "outline",
8482
+ variant: "secondary",
8263
8483
  onClick: action.onClick,
8264
8484
  children: action.label
8265
8485
  }
8266
8486
  ) : null,
8267
- /* @__PURE__ */ jsx49(
8487
+ /* @__PURE__ */ jsx50(
8268
8488
  "button",
8269
8489
  {
8270
8490
  type: "button",
8271
8491
  "aria-label": "\uC54C\uB9BC \uB2EB\uAE30",
8272
8492
  "data-slot": "toast-close",
8273
8493
  className: cn(
8274
- "inline-flex size-[28px] shrink-0 cursor-pointer items-center justify-center rounded-[var(--radius-sm)]",
8494
+ "inline-flex size-[28px] shrink-0 cursor-pointer items-center justify-center rounded-[var(--radius-md)]",
8275
8495
  "text-current opacity-70 transition-opacity hover:opacity-100",
8276
8496
  "focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[var(--focus-ring)]"
8277
8497
  ),
@@ -8286,7 +8506,7 @@ var ToastRoot = React39.forwardRef(
8286
8506
  }
8287
8507
  );
8288
8508
  ToastRoot.displayName = "ToastRoot";
8289
- var ToastViewport = React39.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx49(
8509
+ var ToastViewport = React41.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ jsx50(
8290
8510
  "ol",
8291
8511
  {
8292
8512
  ref,
@@ -8297,24 +8517,24 @@ var ToastViewport = React39.forwardRef(({ className, ...props }, ref) => /* @__P
8297
8517
  ));
8298
8518
  ToastViewport.displayName = "ToastViewport";
8299
8519
  function ToastProvider({ children, maxToasts = 3, className, ...props }) {
8300
- const [items, setItems] = React39.useState([]);
8301
- React39.useEffect(
8520
+ const [items, setItems] = React41.useState([]);
8521
+ React41.useEffect(
8302
8522
  () => toast.subscribe((nextItems) => {
8303
8523
  setItems(limitToasts(nextItems, maxToasts));
8304
8524
  }),
8305
8525
  [maxToasts]
8306
8526
  );
8307
- return /* @__PURE__ */ jsxs44("div", { "data-slot": "toast-provider", className, ...props, children: [
8527
+ return /* @__PURE__ */ jsxs45("div", { "data-slot": "toast-provider", className, ...props, children: [
8308
8528
  children,
8309
- /* @__PURE__ */ jsx49(ToastViewport, { children: items.map((item) => /* @__PURE__ */ jsx49("li", { children: /* @__PURE__ */ jsx49(ToastRoot, { ...item, onClose: () => toast.dismiss(item.id) }) }, item.id)) })
8529
+ /* @__PURE__ */ jsx50(ToastViewport, { children: items.map((item) => /* @__PURE__ */ jsx50("li", { children: /* @__PURE__ */ jsx50(ToastRoot, { ...item, onClose: () => toast.dismiss(item.id) }) }, item.id)) })
8310
8530
  ] });
8311
8531
  }
8312
8532
 
8313
8533
  // src/components/ui/otp-field.tsx
8314
- import * as React40 from "react";
8534
+ import * as React42 from "react";
8315
8535
  import { cva as cva21 } from "class-variance-authority";
8316
8536
  import { AlertCircle as AlertCircle4 } from "lucide-react";
8317
- import { Fragment as Fragment9, jsx as jsx50, jsxs as jsxs45 } from "react/jsx-runtime";
8537
+ import { Fragment as Fragment9, jsx as jsx51, jsxs as jsxs46 } from "react/jsx-runtime";
8318
8538
  var otpFieldVariants = cva21("flex w-full min-w-0 flex-col gap-[var(--space-3)]", {
8319
8539
  variants: {
8320
8540
  size: {
@@ -8441,7 +8661,7 @@ function fillDigitsFromIndex(slots, index, inserted, length) {
8441
8661
  focusIndex: Math.min(cursor, length - 1)
8442
8662
  };
8443
8663
  }
8444
- var OTPField = React40.forwardRef(
8664
+ var OTPField = React42.forwardRef(
8445
8665
  ({
8446
8666
  className,
8447
8667
  defaultValue,
@@ -8463,24 +8683,24 @@ var OTPField = React40.forwardRef(
8463
8683
  required,
8464
8684
  ...props
8465
8685
  }, ref) => {
8466
- const generatedId = React40.useId();
8686
+ const generatedId = React42.useId();
8467
8687
  const fieldId = id ?? generatedId;
8468
8688
  const labelId = `${fieldId}-label`;
8469
8689
  const helperId = helperText ? `${fieldId}-helper` : void 0;
8470
8690
  const errorId = errorText ? `${fieldId}-error` : void 0;
8471
8691
  const resolvedState = invalid || errorText ? "error" : "default";
8472
8692
  const isControlled = value !== void 0;
8473
- const [uncontrolledSlots, setUncontrolledSlots] = React40.useState(
8693
+ const [uncontrolledSlots, setUncontrolledSlots] = React42.useState(
8474
8694
  () => toDigitsArray(onlyDigits(defaultValue, length), length)
8475
8695
  );
8476
- const resolvedSlots = React40.useMemo(
8696
+ const resolvedSlots = React42.useMemo(
8477
8697
  () => isControlled ? toDigitsArray(onlyDigits(value, length), length) : uncontrolledSlots,
8478
8698
  [isControlled, length, uncontrolledSlots, value]
8479
8699
  );
8480
8700
  const resolvedValue = joinDigits(resolvedSlots).slice(0, length);
8481
- const cellsRef = React40.useRef([]);
8701
+ const cellsRef = React42.useRef([]);
8482
8702
  const groupDescribedBy = [helperId, errorId].filter(Boolean).join(" ") || void 0;
8483
- const setResolvedValue = React40.useCallback(
8703
+ const setResolvedValue = React42.useCallback(
8484
8704
  (nextSlots, focusIndex) => {
8485
8705
  const normalizedSlots = nextSlots.slice(0, length);
8486
8706
  const normalizedValue = joinDigits(normalizedSlots).slice(0, length);
@@ -8499,7 +8719,7 @@ var OTPField = React40.forwardRef(
8499
8719
  },
8500
8720
  [disabled, isControlled, length, onComplete, onValueChange]
8501
8721
  );
8502
- return /* @__PURE__ */ jsxs45(
8722
+ return /* @__PURE__ */ jsxs46(
8503
8723
  "fieldset",
8504
8724
  {
8505
8725
  ref,
@@ -8512,7 +8732,7 @@ var OTPField = React40.forwardRef(
8512
8732
  className: cn(otpFieldVariants({ size, className })),
8513
8733
  ...props,
8514
8734
  children: [
8515
- /* @__PURE__ */ jsxs45(
8735
+ /* @__PURE__ */ jsxs46(
8516
8736
  "legend",
8517
8737
  {
8518
8738
  id: labelId,
@@ -8520,11 +8740,11 @@ var OTPField = React40.forwardRef(
8520
8740
  className: "text-sm font-medium leading-snug text-foreground",
8521
8741
  children: [
8522
8742
  label,
8523
- required ? /* @__PURE__ */ jsx50("span", { "aria-hidden": "true", className: "ml-1 font-bold text-[var(--error)]", children: "*" }) : null
8743
+ required ? /* @__PURE__ */ jsx51("span", { "aria-hidden": "true", className: "ml-1 font-bold text-[var(--error)]", children: "*" }) : null
8524
8744
  ]
8525
8745
  }
8526
8746
  ),
8527
- /* @__PURE__ */ jsx50(
8747
+ /* @__PURE__ */ jsx51(
8528
8748
  "div",
8529
8749
  {
8530
8750
  "data-slot": "otp-field-group",
@@ -8534,7 +8754,7 @@ var OTPField = React40.forwardRef(
8534
8754
  children: Array.from({ length }, (_, index) => {
8535
8755
  const digit = resolvedSlots[index] ?? "";
8536
8756
  const inputId = `${fieldId}-cell-${index + 1}`;
8537
- return /* @__PURE__ */ jsx50(
8757
+ return /* @__PURE__ */ jsx51(
8538
8758
  "input",
8539
8759
  {
8540
8760
  ref: (node) => {
@@ -8629,15 +8849,15 @@ var OTPField = React40.forwardRef(
8629
8849
  })
8630
8850
  }
8631
8851
  ),
8632
- helperText || errorText ? /* @__PURE__ */ jsx50(
8852
+ helperText || errorText ? /* @__PURE__ */ jsx51(
8633
8853
  "p",
8634
8854
  {
8635
8855
  id: errorText ? errorId : helperId,
8636
8856
  "data-slot": "otp-field-message",
8637
8857
  "data-kind": errorText ? "error" : "helper",
8638
8858
  className: otpFieldMessageVariants({ state: resolvedState }),
8639
- children: errorText ? /* @__PURE__ */ jsxs45(Fragment9, { children: [
8640
- /* @__PURE__ */ jsx50(
8859
+ children: errorText ? /* @__PURE__ */ jsxs46(Fragment9, { children: [
8860
+ /* @__PURE__ */ jsx51(
8641
8861
  AlertCircle4,
8642
8862
  {
8643
8863
  "aria-hidden": "true",
@@ -8645,11 +8865,11 @@ var OTPField = React40.forwardRef(
8645
8865
  strokeWidth: 2
8646
8866
  }
8647
8867
  ),
8648
- /* @__PURE__ */ jsx50("span", { children: errorText })
8649
- ] }) : /* @__PURE__ */ jsx50("span", { children: helperText })
8868
+ /* @__PURE__ */ jsx51("span", { children: errorText })
8869
+ ] }) : /* @__PURE__ */ jsx51("span", { children: helperText })
8650
8870
  }
8651
8871
  ) : null,
8652
- name ? /* @__PURE__ */ jsx50(
8872
+ name ? /* @__PURE__ */ jsx51(
8653
8873
  "input",
8654
8874
  {
8655
8875
  "aria-hidden": "true",
@@ -8670,10 +8890,10 @@ var OTPField = React40.forwardRef(
8670
8890
  OTPField.displayName = "OTPField";
8671
8891
 
8672
8892
  // src/components/ui/search-field.tsx
8673
- import * as React41 from "react";
8674
- import { Search, X as X4 } from "lucide-react";
8893
+ import * as React43 from "react";
8894
+ import { Search, X as X5 } from "lucide-react";
8675
8895
  import { cva as cva22 } from "class-variance-authority";
8676
- import { jsx as jsx51, jsxs as jsxs46 } from "react/jsx-runtime";
8896
+ import { jsx as jsx52, jsxs as jsxs47 } from "react/jsx-runtime";
8677
8897
  var searchFieldVariants = cva22("relative flex w-full items-center", {
8678
8898
  variants: {
8679
8899
  size: {
@@ -8738,7 +8958,7 @@ var iconSize4 = {
8738
8958
  function hasVisibleValue(value) {
8739
8959
  return typeof value === "string" ? value.length > 0 : value !== void 0;
8740
8960
  }
8741
- var SearchField = React41.forwardRef(
8961
+ var SearchField = React43.forwardRef(
8742
8962
  ({
8743
8963
  className,
8744
8964
  inputMode = "search",
@@ -8754,12 +8974,12 @@ var SearchField = React41.forwardRef(
8754
8974
  ...props
8755
8975
  }, ref) => {
8756
8976
  const resolvedSize = size ?? "md";
8757
- const inputRef = React41.useRef(null);
8758
- const [hasText, setHasText] = React41.useState(
8977
+ const inputRef = React43.useRef(null);
8978
+ const [hasText, setHasText] = React43.useState(
8759
8979
  () => hasVisibleValue(value ?? defaultValue)
8760
8980
  );
8761
- React41.useImperativeHandle(ref, () => inputRef.current);
8762
- React41.useEffect(() => {
8981
+ React43.useImperativeHandle(ref, () => inputRef.current);
8982
+ React43.useEffect(() => {
8763
8983
  if (value !== void 0) {
8764
8984
  setHasText(hasVisibleValue(value));
8765
8985
  }
@@ -8772,14 +8992,14 @@ var SearchField = React41.forwardRef(
8772
8992
  }
8773
8993
  onClear?.();
8774
8994
  };
8775
- return /* @__PURE__ */ jsxs46(
8995
+ return /* @__PURE__ */ jsxs47(
8776
8996
  "div",
8777
8997
  {
8778
8998
  "data-slot": "search-field",
8779
8999
  "data-size": resolvedSize,
8780
9000
  className: cn(searchFieldVariants({ size, className })),
8781
9001
  children: [
8782
- /* @__PURE__ */ jsx51(
9002
+ /* @__PURE__ */ jsx52(
8783
9003
  Search,
8784
9004
  {
8785
9005
  "aria-hidden": "true",
@@ -8789,7 +9009,7 @@ var SearchField = React41.forwardRef(
8789
9009
  strokeWidth: resolvedSize === "sm" ? 2 : 1.75
8790
9010
  }
8791
9011
  ),
8792
- /* @__PURE__ */ jsx51(
9012
+ /* @__PURE__ */ jsx52(
8793
9013
  "input",
8794
9014
  {
8795
9015
  ref: inputRef,
@@ -8810,7 +9030,7 @@ var SearchField = React41.forwardRef(
8810
9030
  ...props
8811
9031
  }
8812
9032
  ),
8813
- showClear ? /* @__PURE__ */ jsx51(
9033
+ showClear ? /* @__PURE__ */ jsx52(
8814
9034
  "button",
8815
9035
  {
8816
9036
  type: "button",
@@ -8818,7 +9038,7 @@ var SearchField = React41.forwardRef(
8818
9038
  "data-slot": "search-field-clear",
8819
9039
  className: "absolute right-[8px] top-1/2 inline-flex size-[var(--space-4)] -translate-y-1/2 cursor-pointer items-center justify-center rounded-[var(--radius-full)] text-text-tertiary transition-colors hover:text-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-[var(--focus-ring)]",
8820
9040
  onClick: clearInput,
8821
- children: /* @__PURE__ */ jsx51(X4, { "aria-hidden": "true", size: 16, strokeWidth: 1.75 })
9041
+ children: /* @__PURE__ */ jsx52(X5, { "aria-hidden": "true", size: 16, strokeWidth: 1.75 })
8822
9042
  }
8823
9043
  ) : null
8824
9044
  ]
@@ -8829,9 +9049,9 @@ var SearchField = React41.forwardRef(
8829
9049
  SearchField.displayName = "SearchField";
8830
9050
 
8831
9051
  // src/components/ui/checkbox-group.tsx
8832
- import * as React42 from "react";
9052
+ import * as React44 from "react";
8833
9053
  import { cva as cva23 } from "class-variance-authority";
8834
- import { jsx as jsx52 } from "react/jsx-runtime";
9054
+ import { jsx as jsx53 } from "react/jsx-runtime";
8835
9055
  var checkboxGroupVariants = cva23("gap-[var(--space-2)]", {
8836
9056
  variants: {
8837
9057
  appearance: {
@@ -8857,7 +9077,7 @@ var checkboxGroupVariants = cva23("gap-[var(--space-2)]", {
8857
9077
  function toSelectionSet(value) {
8858
9078
  return new Set(value ?? []);
8859
9079
  }
8860
- var CheckboxGroup = React42.forwardRef(
9080
+ var CheckboxGroup = React44.forwardRef(
8861
9081
  ({
8862
9082
  className,
8863
9083
  children,
@@ -8873,14 +9093,14 @@ var CheckboxGroup = React42.forwardRef(
8873
9093
  ...props
8874
9094
  }, ref) => {
8875
9095
  const isControlled = value != null;
8876
- const [uncontrolledValue, setUncontrolledValue] = React42.useState(
9096
+ const [uncontrolledValue, setUncontrolledValue] = React44.useState(
8877
9097
  () => toSelectionSet(defaultValue)
8878
9098
  );
8879
- const selectedValues = React42.useMemo(
9099
+ const selectedValues = React44.useMemo(
8880
9100
  () => isControlled ? toSelectionSet(value) : uncontrolledValue,
8881
9101
  [isControlled, uncontrolledValue, value]
8882
9102
  );
8883
- const toggleValue = React42.useCallback(
9103
+ const toggleValue = React44.useCallback(
8884
9104
  (itemValue, checked) => {
8885
9105
  const nextValues = new Set(selectedValues);
8886
9106
  if (checked) {
@@ -8896,7 +9116,7 @@ var CheckboxGroup = React42.forwardRef(
8896
9116
  },
8897
9117
  [isControlled, onValueChange, selectedValues]
8898
9118
  );
8899
- const contextValue = React42.useMemo(
9119
+ const contextValue = React44.useMemo(
8900
9120
  () => ({
8901
9121
  appearance,
8902
9122
  density,
@@ -8907,7 +9127,7 @@ var CheckboxGroup = React42.forwardRef(
8907
9127
  }),
8908
9128
  [appearance, density, disabled, name, selectedValues, toggleValue]
8909
9129
  );
8910
- return /* @__PURE__ */ jsx52(CheckboxGroupContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsx52(
9130
+ return /* @__PURE__ */ jsx53(CheckboxGroupContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsx53(
8911
9131
  "div",
8912
9132
  {
8913
9133
  ref,
@@ -8931,11 +9151,11 @@ var CheckboxGroup = React42.forwardRef(
8931
9151
  CheckboxGroup.displayName = "CheckboxGroup";
8932
9152
 
8933
9153
  // src/components/ui/radio-group.tsx
8934
- import * as React43 from "react";
9154
+ import * as React45 from "react";
8935
9155
  import { cva as cva24 } from "class-variance-authority";
8936
9156
  import { Circle } from "lucide-react";
8937
9157
  import { RadioGroup as RadioGroupPrimitive } from "radix-ui";
8938
- import { jsx as jsx53, jsxs as jsxs47 } from "react/jsx-runtime";
9158
+ import { jsx as jsx54, jsxs as jsxs48 } from "react/jsx-runtime";
8939
9159
  var radioGroupVariants = cva24("gap-[var(--space-2)]", {
8940
9160
  variants: {
8941
9161
  appearance: {
@@ -8970,7 +9190,7 @@ var radioVariants = cva24(
8970
9190
  {
8971
9191
  variants: {
8972
9192
  appearance: {
8973
- plain: "inline-flex items-start gap-[var(--space-3)] rounded-[var(--radius-sm)] px-pad-compact-x py-pad-compact-y",
9193
+ plain: "inline-flex items-start gap-[var(--space-3)] rounded-[var(--radius-md)] px-pad-compact-x py-pad-compact-y",
8974
9194
  card: [
8975
9195
  "flex min-h-[calc(var(--space-12)+var(--space-2))] items-start gap-[var(--space-3)]",
8976
9196
  "rounded-[var(--radius-md)] border border-[var(--border-subtle)] bg-[var(--bg-surface)]",
@@ -9024,11 +9244,11 @@ var radioControlVariants = cva24(
9024
9244
  }
9025
9245
  }
9026
9246
  );
9027
- var RadioGroupContext = React43.createContext({
9247
+ var RadioGroupContext = React45.createContext({
9028
9248
  appearance: "plain",
9029
9249
  density: "comfortable"
9030
9250
  });
9031
- var RadioGroup = React43.forwardRef(
9251
+ var RadioGroup = React45.forwardRef(
9032
9252
  ({
9033
9253
  className,
9034
9254
  children,
@@ -9039,11 +9259,11 @@ var RadioGroup = React43.forwardRef(
9039
9259
  required,
9040
9260
  ...props
9041
9261
  }, ref) => {
9042
- const contextValue = React43.useMemo(
9262
+ const contextValue = React45.useMemo(
9043
9263
  () => ({ appearance, density }),
9044
9264
  [appearance, density]
9045
9265
  );
9046
- return /* @__PURE__ */ jsx53(RadioGroupContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsx53(
9266
+ return /* @__PURE__ */ jsx54(RadioGroupContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsx54(
9047
9267
  RadioGroupPrimitive.Root,
9048
9268
  {
9049
9269
  ref,
@@ -9066,13 +9286,13 @@ var RadioGroup = React43.forwardRef(
9066
9286
  }
9067
9287
  );
9068
9288
  RadioGroup.displayName = "RadioGroup";
9069
- var Radio = React43.forwardRef(({ className, children, description, id, ...props }, ref) => {
9070
- const { appearance, density } = React43.useContext(RadioGroupContext);
9071
- const generatedId = React43.useId();
9289
+ var Radio = React45.forwardRef(({ className, children, description, id, ...props }, ref) => {
9290
+ const { appearance, density } = React45.useContext(RadioGroupContext);
9291
+ const generatedId = React45.useId();
9072
9292
  const radioId = id ?? generatedId;
9073
9293
  const labelId = `${radioId}-label`;
9074
9294
  const descriptionId = description ? `${radioId}-description` : void 0;
9075
- return /* @__PURE__ */ jsxs47(
9295
+ return /* @__PURE__ */ jsxs48(
9076
9296
  RadioGroupPrimitive.Item,
9077
9297
  {
9078
9298
  ref,
@@ -9083,24 +9303,24 @@ var Radio = React43.forwardRef(({ className, children, description, id, ...props
9083
9303
  className: cn(radioVariants({ appearance, density }), className),
9084
9304
  ...props,
9085
9305
  children: [
9086
- /* @__PURE__ */ jsx53(
9306
+ /* @__PURE__ */ jsx54(
9087
9307
  "span",
9088
9308
  {
9089
9309
  "aria-hidden": "true",
9090
9310
  "data-slot": "radio-control",
9091
9311
  className: radioControlVariants({ appearance }),
9092
- children: /* @__PURE__ */ jsx53(
9312
+ children: /* @__PURE__ */ jsx54(
9093
9313
  RadioGroupPrimitive.Indicator,
9094
9314
  {
9095
9315
  "data-slot": "radio-indicator",
9096
9316
  className: "flex items-center justify-center",
9097
- children: /* @__PURE__ */ jsx53(Circle, { "aria-hidden": "true", size: 8, fill: "currentColor" })
9317
+ children: /* @__PURE__ */ jsx54(Circle, { "aria-hidden": "true", size: 8, fill: "currentColor" })
9098
9318
  }
9099
9319
  )
9100
9320
  }
9101
9321
  ),
9102
- /* @__PURE__ */ jsxs47("span", { className: "flex min-w-0 flex-col gap-[var(--space-1)]", children: [
9103
- /* @__PURE__ */ jsx53(
9322
+ /* @__PURE__ */ jsxs48("span", { className: "flex min-w-0 flex-col gap-[var(--space-1)]", children: [
9323
+ /* @__PURE__ */ jsx54(
9104
9324
  "span",
9105
9325
  {
9106
9326
  id: labelId,
@@ -9112,7 +9332,7 @@ var Radio = React43.forwardRef(({ className, children, description, id, ...props
9112
9332
  children
9113
9333
  }
9114
9334
  ),
9115
- description ? /* @__PURE__ */ jsx53(
9335
+ description ? /* @__PURE__ */ jsx54(
9116
9336
  "span",
9117
9337
  {
9118
9338
  id: descriptionId,
@@ -9130,20 +9350,20 @@ Radio.displayName = "Radio";
9130
9350
 
9131
9351
  // src/components/ui/scroll-area.tsx
9132
9352
  import { ScrollArea as ScrollAreaPrimitive } from "radix-ui";
9133
- import { jsx as jsx54, jsxs as jsxs48 } from "react/jsx-runtime";
9353
+ import { jsx as jsx55, jsxs as jsxs49 } from "react/jsx-runtime";
9134
9354
  function ScrollArea({
9135
9355
  className,
9136
9356
  children,
9137
9357
  ...props
9138
9358
  }) {
9139
- return /* @__PURE__ */ jsxs48(
9359
+ return /* @__PURE__ */ jsxs49(
9140
9360
  ScrollAreaPrimitive.Root,
9141
9361
  {
9142
9362
  "data-slot": "scroll-area",
9143
9363
  className: cn("relative", className),
9144
9364
  ...props,
9145
9365
  children: [
9146
- /* @__PURE__ */ jsx54(
9366
+ /* @__PURE__ */ jsx55(
9147
9367
  ScrollAreaPrimitive.Viewport,
9148
9368
  {
9149
9369
  "data-slot": "scroll-area-viewport",
@@ -9151,8 +9371,8 @@ function ScrollArea({
9151
9371
  children
9152
9372
  }
9153
9373
  ),
9154
- /* @__PURE__ */ jsx54(ScrollBar, {}),
9155
- /* @__PURE__ */ jsx54(ScrollAreaPrimitive.Corner, {})
9374
+ /* @__PURE__ */ jsx55(ScrollBar, {}),
9375
+ /* @__PURE__ */ jsx55(ScrollAreaPrimitive.Corner, {})
9156
9376
  ]
9157
9377
  }
9158
9378
  );
@@ -9162,7 +9382,7 @@ function ScrollBar({
9162
9382
  orientation = "vertical",
9163
9383
  ...props
9164
9384
  }) {
9165
- return /* @__PURE__ */ jsx54(
9385
+ return /* @__PURE__ */ jsx55(
9166
9386
  ScrollAreaPrimitive.ScrollAreaScrollbar,
9167
9387
  {
9168
9388
  "data-slot": "scroll-area-scrollbar",
@@ -9174,7 +9394,7 @@ function ScrollBar({
9174
9394
  className
9175
9395
  ),
9176
9396
  ...props,
9177
- children: /* @__PURE__ */ jsx54(
9397
+ children: /* @__PURE__ */ jsx55(
9178
9398
  ScrollAreaPrimitive.ScrollAreaThumb,
9179
9399
  {
9180
9400
  "data-slot": "scroll-area-thumb",
@@ -9186,7 +9406,7 @@ function ScrollBar({
9186
9406
  }
9187
9407
 
9188
9408
  // src/components/ui/progress.tsx
9189
- import { jsx as jsx55 } from "react/jsx-runtime";
9409
+ import { jsx as jsx56 } from "react/jsx-runtime";
9190
9410
  var progressFillByStatus = {
9191
9411
  active: "bg-[var(--primary)]",
9192
9412
  success: "bg-[var(--success)]",
@@ -9207,7 +9427,7 @@ function Progress({
9207
9427
  const clamped = Math.max(0, Math.min(safeMax, value));
9208
9428
  const percent = clamped / safeMax * 100;
9209
9429
  const w = typeof width === "number" ? `${width}px` : width;
9210
- return /* @__PURE__ */ jsx55(
9430
+ return /* @__PURE__ */ jsx56(
9211
9431
  "div",
9212
9432
  {
9213
9433
  role: "progressbar",
@@ -9221,7 +9441,7 @@ function Progress({
9221
9441
  ),
9222
9442
  style: { width: w, height: `${height}px`, ...style },
9223
9443
  ...props,
9224
- children: /* @__PURE__ */ jsx55(
9444
+ children: /* @__PURE__ */ jsx56(
9225
9445
  "div",
9226
9446
  {
9227
9447
  className: cn(
@@ -9236,10 +9456,10 @@ function Progress({
9236
9456
  }
9237
9457
 
9238
9458
  // src/components/ui/tree-view.tsx
9239
- import * as React44 from "react";
9459
+ import * as React46 from "react";
9240
9460
  import { ChevronRight as ChevronRight3 } from "lucide-react";
9241
9461
  import { cva as cva25 } from "class-variance-authority";
9242
- import { jsx as jsx56, jsxs as jsxs49 } from "react/jsx-runtime";
9462
+ import { jsx as jsx57, jsxs as jsxs50 } from "react/jsx-runtime";
9243
9463
  var treeViewVariants = cva25(
9244
9464
  "m-0 list-none p-[var(--space-1)] text-body-sm text-foreground"
9245
9465
  );
@@ -9342,27 +9562,27 @@ function TreeView({
9342
9562
  ...rest
9343
9563
  }) {
9344
9564
  const isExpandedControlled = expandedIds !== void 0;
9345
- const [internalExpanded, setInternalExpanded] = React44.useState(
9565
+ const [internalExpanded, setInternalExpanded] = React46.useState(
9346
9566
  () => defaultExpandedIds ?? []
9347
9567
  );
9348
9568
  const expandedList = isExpandedControlled ? expandedIds : internalExpanded;
9349
- const expandedSet = React44.useMemo(() => new Set(expandedList), [expandedList]);
9350
- const items = React44.useMemo(
9569
+ const expandedSet = React46.useMemo(() => new Set(expandedList), [expandedList]);
9570
+ const items = React46.useMemo(
9351
9571
  () => flattenVisibleNodes(nodes, getChildren, expandedSet),
9352
9572
  [nodes, getChildren, expandedSet]
9353
9573
  );
9354
- const [focusedId, setFocusedId] = React44.useState(null);
9574
+ const [focusedId, setFocusedId] = React46.useState(null);
9355
9575
  const visibleIds = items.map((item) => item.id);
9356
9576
  const activeId = focusedId && visibleIds.includes(focusedId) ? focusedId : selectedId && visibleIds.includes(selectedId) ? selectedId : visibleIds[0] ?? null;
9357
- const itemRefs = React44.useRef(/* @__PURE__ */ new Map());
9358
- const commitExpanded = React44.useCallback(
9577
+ const itemRefs = React46.useRef(/* @__PURE__ */ new Map());
9578
+ const commitExpanded = React46.useCallback(
9359
9579
  (next) => {
9360
9580
  if (!isExpandedControlled) setInternalExpanded(next);
9361
9581
  onExpandedChange?.(next);
9362
9582
  },
9363
9583
  [isExpandedControlled, onExpandedChange]
9364
9584
  );
9365
- const setExpanded = React44.useCallback(
9585
+ const setExpanded = React46.useCallback(
9366
9586
  (id, expand) => {
9367
9587
  const has = expandedSet.has(id);
9368
9588
  if (expand && !has) {
@@ -9373,7 +9593,7 @@ function TreeView({
9373
9593
  },
9374
9594
  [commitExpanded, expandedList, expandedSet]
9375
9595
  );
9376
- const focusItem = React44.useCallback((id) => {
9596
+ const focusItem = React46.useCallback((id) => {
9377
9597
  setFocusedId(id);
9378
9598
  itemRefs.current.get(id)?.focus();
9379
9599
  }, []);
@@ -9409,7 +9629,7 @@ function TreeView({
9409
9629
  const selected = node.id === selectedId;
9410
9630
  const isActive = node.id === activeId;
9411
9631
  const itemState = { expanded, selected, depth, hasChildren };
9412
- return /* @__PURE__ */ jsxs49(
9632
+ return /* @__PURE__ */ jsxs50(
9413
9633
  "li",
9414
9634
  {
9415
9635
  ref: (element) => {
@@ -9434,7 +9654,7 @@ function TreeView({
9434
9654
  onSelect?.(node.id, node);
9435
9655
  },
9436
9656
  children: [
9437
- /* @__PURE__ */ jsxs49(
9657
+ /* @__PURE__ */ jsxs50(
9438
9658
  "span",
9439
9659
  {
9440
9660
  "data-slot": "treeitem-row",
@@ -9443,7 +9663,7 @@ function TreeView({
9443
9663
  },
9444
9664
  className: treeItemRowVariants({ selected }),
9445
9665
  children: [
9446
- hasChildren ? /* @__PURE__ */ jsx56(
9666
+ hasChildren ? /* @__PURE__ */ jsx57(
9447
9667
  "span",
9448
9668
  {
9449
9669
  "data-slot": "treeitem-toggle",
@@ -9453,7 +9673,7 @@ function TreeView({
9453
9673
  setExpanded(node.id, !expanded);
9454
9674
  },
9455
9675
  className: "flex size-[var(--space-4)] shrink-0 items-center justify-center text-text-tertiary",
9456
- children: /* @__PURE__ */ jsx56(
9676
+ children: /* @__PURE__ */ jsx57(
9457
9677
  ChevronRight3,
9458
9678
  {
9459
9679
  "aria-hidden": "true",
@@ -9466,7 +9686,7 @@ function TreeView({
9466
9686
  }
9467
9687
  )
9468
9688
  }
9469
- ) : /* @__PURE__ */ jsx56(
9689
+ ) : /* @__PURE__ */ jsx57(
9470
9690
  "span",
9471
9691
  {
9472
9692
  "data-slot": "treeitem-spacer",
@@ -9474,18 +9694,18 @@ function TreeView({
9474
9694
  className: "size-[var(--space-4)] shrink-0"
9475
9695
  }
9476
9696
  ),
9477
- /* @__PURE__ */ jsx56("span", { className: "flex min-w-0 flex-1 items-center gap-[var(--space-2)]", children: renderItem(node, itemState) })
9697
+ /* @__PURE__ */ jsx57("span", { className: "flex min-w-0 flex-1 items-center gap-[var(--space-2)]", children: renderItem(node, itemState) })
9478
9698
  ]
9479
9699
  }
9480
9700
  ),
9481
- hasChildren && expanded && children ? /* @__PURE__ */ jsx56("ul", { role: "group", "data-slot": "tree-group", className: "m-0 list-none p-0", children: renderLevel(children, depth + 1) }) : null
9701
+ hasChildren && expanded && children ? /* @__PURE__ */ jsx57("ul", { role: "group", "data-slot": "tree-group", className: "m-0 list-none p-0", children: renderLevel(children, depth + 1) }) : null
9482
9702
  ]
9483
9703
  },
9484
9704
  node.id
9485
9705
  );
9486
9706
  });
9487
9707
  }
9488
- return /* @__PURE__ */ jsx56(
9708
+ return /* @__PURE__ */ jsx57(
9489
9709
  "ul",
9490
9710
  {
9491
9711
  role: "tree",
@@ -9501,9 +9721,9 @@ function TreeView({
9501
9721
  }
9502
9722
 
9503
9723
  // src/components/branding/olun-logo.tsx
9504
- import { jsx as jsx57, jsxs as jsxs50 } from "react/jsx-runtime";
9724
+ import { jsx as jsx58, jsxs as jsxs51 } from "react/jsx-runtime";
9505
9725
  function OlunSymbol({ size = 28, className }) {
9506
- return /* @__PURE__ */ jsxs50(
9726
+ return /* @__PURE__ */ jsxs51(
9507
9727
  "svg",
9508
9728
  {
9509
9729
  width: size,
@@ -9514,7 +9734,7 @@ function OlunSymbol({ size = 28, className }) {
9514
9734
  className,
9515
9735
  "aria-hidden": "true",
9516
9736
  children: [
9517
- /* @__PURE__ */ jsx57(
9737
+ /* @__PURE__ */ jsx58(
9518
9738
  "circle",
9519
9739
  {
9520
9740
  cx: "108",
@@ -9526,7 +9746,7 @@ function OlunSymbol({ size = 28, className }) {
9526
9746
  style: { color: "var(--text-primary)" }
9527
9747
  }
9528
9748
  ),
9529
- /* @__PURE__ */ jsx57("circle", { cx: "185", cy: "175", r: "22", fill: "var(--accent-pop)" })
9749
+ /* @__PURE__ */ jsx58("circle", { cx: "185", cy: "175", r: "22", fill: "var(--accent-pop)" })
9530
9750
  ]
9531
9751
  }
9532
9752
  );
@@ -9537,7 +9757,7 @@ function OlunLogo({
9537
9757
  showSymbol = true,
9538
9758
  className
9539
9759
  }) {
9540
- return /* @__PURE__ */ jsxs50(
9760
+ return /* @__PURE__ */ jsxs51(
9541
9761
  "div",
9542
9762
  {
9543
9763
  className,
@@ -9547,8 +9767,8 @@ function OlunLogo({
9547
9767
  gap: "var(--space-3)"
9548
9768
  },
9549
9769
  children: [
9550
- showSymbol && /* @__PURE__ */ jsx57(OlunSymbol, { size: symbolSize }),
9551
- /* @__PURE__ */ jsxs50(
9770
+ showSymbol && /* @__PURE__ */ jsx58(OlunSymbol, { size: symbolSize }),
9771
+ /* @__PURE__ */ jsxs51(
9552
9772
  "span",
9553
9773
  {
9554
9774
  style: {
@@ -9560,7 +9780,7 @@ function OlunLogo({
9560
9780
  },
9561
9781
  children: [
9562
9782
  "OLUN",
9563
- /* @__PURE__ */ jsx57("span", { style: { color: "var(--accent)" }, children: "." })
9783
+ /* @__PURE__ */ jsx58("span", { style: { color: "var(--accent)" }, children: "." })
9564
9784
  ]
9565
9785
  }
9566
9786
  )
@@ -9571,30 +9791,30 @@ function OlunLogo({
9571
9791
 
9572
9792
  // src/components/branding/theme-toggle.tsx
9573
9793
  import { Sun, Moon } from "lucide-react";
9574
- import { jsx as jsx58 } from "react/jsx-runtime";
9794
+ import { jsx as jsx59 } from "react/jsx-runtime";
9575
9795
  function ThemeToggle({ className }) {
9576
9796
  const { resolvedTheme, toggleTheme } = useOlunTheme();
9577
9797
  const Icon = resolvedTheme === "dark" ? Moon : Sun;
9578
- return /* @__PURE__ */ jsx58(
9798
+ return /* @__PURE__ */ jsx59(
9579
9799
  "button",
9580
9800
  {
9581
9801
  onClick: () => toggleTheme(),
9582
9802
  className: cn(
9583
- "inline-flex size-[36px] items-center justify-center rounded-sm",
9803
+ "inline-flex size-[36px] items-center justify-center rounded-[var(--radius-md)]",
9584
9804
  "text-text-secondary hover:bg-[var(--action-hover)] hover:text-foreground",
9585
9805
  "transition-colors motion-reduce:transition-none",
9586
9806
  className
9587
9807
  ),
9588
9808
  "aria-label": "\uD14C\uB9C8 \uC804\uD658",
9589
9809
  title: resolvedTheme === "dark" ? "\uB77C\uC774\uD2B8 \uBAA8\uB4DC\uB85C" : "\uB2E4\uD06C \uBAA8\uB4DC\uB85C",
9590
- children: /* @__PURE__ */ jsx58(Icon, { className: "size-[18px]", strokeWidth: 1.75 })
9810
+ children: /* @__PURE__ */ jsx59(Icon, { className: "size-[18px]", strokeWidth: 1.75 })
9591
9811
  }
9592
9812
  );
9593
9813
  }
9594
9814
 
9595
9815
  // src/components/branding/theme-fab.tsx
9596
9816
  import { Sun as Sun2, Moon as Moon2 } from "lucide-react";
9597
- import { jsx as jsx59 } from "react/jsx-runtime";
9817
+ import { jsx as jsx60 } from "react/jsx-runtime";
9598
9818
  function ThemeFab({ variant = "square" } = {}) {
9599
9819
  const { mounted, resolvedTheme, toggleTheme } = useOlunTheme();
9600
9820
  if (!mounted) {
@@ -9614,7 +9834,7 @@ function ThemeFab({ variant = "square" } = {}) {
9614
9834
  right: "12px",
9615
9835
  width: "36px",
9616
9836
  height: "36px",
9617
- borderRadius: "var(--radius-sm)",
9837
+ borderRadius: "var(--radius-md)",
9618
9838
  border: "1px solid var(--border-subtle)",
9619
9839
  background: "var(--bg-surface)",
9620
9840
  color: "var(--text-secondary)",
@@ -9634,7 +9854,7 @@ function ThemeFab({ variant = "square" } = {}) {
9634
9854
  WebkitBackdropFilter: "blur(16px)",
9635
9855
  zIndex: 9999
9636
9856
  };
9637
- return /* @__PURE__ */ jsx59(
9857
+ return /* @__PURE__ */ jsx60(
9638
9858
  "button",
9639
9859
  {
9640
9860
  onClick: () => toggleTheme(),
@@ -9659,7 +9879,7 @@ function ThemeFab({ variant = "square" } = {}) {
9659
9879
  e.currentTarget.style.color = "var(--text-secondary)";
9660
9880
  }
9661
9881
  },
9662
- children: /* @__PURE__ */ jsx59(
9882
+ children: /* @__PURE__ */ jsx60(
9663
9883
  Icon,
9664
9884
  {
9665
9885
  size: isCircle ? 22 : 16,
@@ -9671,7 +9891,7 @@ function ThemeFab({ variant = "square" } = {}) {
9671
9891
  }
9672
9892
 
9673
9893
  // src/components/logos/organization-logo.tsx
9674
- import { jsx as jsx60 } from "react/jsx-runtime";
9894
+ import { jsx as jsx61 } from "react/jsx-runtime";
9675
9895
  var organizationLogoRegistry = {
9676
9896
  jbnu: {
9677
9897
  label: "\uC804\uBD81\uB300\uD559\uAD50 \uC5E0\uBE14\uB7FC",
@@ -9700,7 +9920,7 @@ function OrganizationLogo({
9700
9920
  }) {
9701
9921
  const asset = organizationLogoRegistry[organization];
9702
9922
  const isDecorative = ariaHidden === true || ariaHidden === "true";
9703
- return /* @__PURE__ */ jsx60(
9923
+ return /* @__PURE__ */ jsx61(
9704
9924
  "svg",
9705
9925
  {
9706
9926
  viewBox: asset.viewBox,
@@ -9718,12 +9938,13 @@ function OrganizationLogo({
9718
9938
  ...style
9719
9939
  },
9720
9940
  ...props,
9721
- children: asset.paths.map((path) => /* @__PURE__ */ jsx60("path", { d: path }, path))
9941
+ children: asset.paths.map((path) => /* @__PURE__ */ jsx61("path", { d: path }, path))
9722
9942
  }
9723
9943
  );
9724
9944
  }
9725
9945
  export {
9726
9946
  ActionFooter,
9947
+ ActionSheet,
9727
9948
  Alert,
9728
9949
  Avatar,
9729
9950
  AvatarFallback,