sellmate-design-system-react 2.1.2 → 3.0.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.
Files changed (47) hide show
  1. package/dist/components/SCallout/SCallout.cjs +76 -1
  2. package/dist/components/SCallout/SCallout.cjs.map +1 -1
  3. package/dist/components/SCallout/SCallout.d.ts +6 -2
  4. package/dist/components/SCallout/SCallout.js +76 -1
  5. package/dist/components/SCallout/SCallout.js.map +1 -1
  6. package/dist/components/SDraggableItem/SDraggableItem.cjs +3079 -0
  7. package/dist/components/SDraggableItem/SDraggableItem.cjs.map +1 -0
  8. package/dist/components/SDraggableItem/SDraggableItem.d.ts +33 -0
  9. package/dist/components/SDraggableItem/SDraggableItem.js +3077 -0
  10. package/dist/components/SDraggableItem/SDraggableItem.js.map +1 -0
  11. package/dist/components/SDraggableItem/index.d.ts +1 -0
  12. package/dist/components/SExpansionItem/SExpansionItem.cjs +6 -15
  13. package/dist/components/SExpansionItem/SExpansionItem.cjs.map +1 -1
  14. package/dist/components/SExpansionItem/SExpansionItem.js +6 -15
  15. package/dist/components/SExpansionItem/SExpansionItem.js.map +1 -1
  16. package/dist/components/SList/SList.cjs +38 -0
  17. package/dist/components/SList/SList.cjs.map +1 -0
  18. package/dist/components/SList/SList.d.ts +10 -0
  19. package/dist/components/SList/SList.js +36 -0
  20. package/dist/components/SList/SList.js.map +1 -0
  21. package/dist/components/SList/index.d.ts +1 -0
  22. package/dist/components/SListItem/SListItem.cjs +83 -0
  23. package/dist/components/SListItem/SListItem.cjs.map +1 -0
  24. package/dist/components/SListItem/SListItem.d.ts +26 -0
  25. package/dist/components/SListItem/SListItem.js +81 -0
  26. package/dist/components/SListItem/SListItem.js.map +1 -0
  27. package/dist/components/SListItem/index.d.ts +1 -0
  28. package/dist/components/SSectionHeaderCard/SSectionHeaderCard.cjs +3414 -0
  29. package/dist/components/SSectionHeaderCard/SSectionHeaderCard.cjs.map +1 -0
  30. package/dist/components/SSectionHeaderCard/SSectionHeaderCard.d.ts +32 -0
  31. package/dist/components/SSectionHeaderCard/SSectionHeaderCard.js +3392 -0
  32. package/dist/components/SSectionHeaderCard/SSectionHeaderCard.js.map +1 -0
  33. package/dist/components/SSectionHeaderCard/index.d.ts +1 -0
  34. package/dist/components/STable/STable.cjs +101 -80
  35. package/dist/components/STable/STable.cjs.map +1 -1
  36. package/dist/components/STable/STable.d.ts +36 -1
  37. package/dist/components/STable/STable.js +102 -81
  38. package/dist/components/STable/STable.js.map +1 -1
  39. package/dist/components/STable/index.d.ts +1 -1
  40. package/dist/index.cjs +1040 -623
  41. package/dist/index.cjs.map +1 -1
  42. package/dist/index.d.ts +4 -0
  43. package/dist/index.js +1040 -627
  44. package/dist/index.js.map +1 -1
  45. package/dist/styles.css +339 -19
  46. package/dist/theme.css +14 -0
  47. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -1,13 +1,13 @@
1
1
  "use client";
2
2
  import { clsx } from 'clsx';
3
3
  import { extendTailwindMerge } from 'tailwind-merge';
4
- import { forwardRef, useState, useId, useEffect, useRef, useCallback, createContext, useImperativeHandle, useMemo, useContext, useLayoutEffect, useSyncExternalStore, Fragment as Fragment$1 } from 'react';
4
+ import { forwardRef, useState, useRef, useEffect, useId, createContext, useImperativeHandle, useCallback, useMemo, useContext, Fragment as Fragment$1, useLayoutEffect, useSyncExternalStore } from 'react';
5
5
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
6
6
  import { createPortal } from 'react-dom';
7
+ import * as RPopover2 from '@radix-ui/react-popover';
7
8
  import { createRoot } from 'react-dom/client';
8
9
  import * as RTooltip from '@radix-ui/react-tooltip';
9
10
  import * as RDropdown from '@radix-ui/react-dropdown-menu';
10
- import * as RPopover2 from '@radix-ui/react-popover';
11
11
  import * as RSwitch from '@radix-ui/react-switch';
12
12
  import * as RDialog from '@radix-ui/react-dialog';
13
13
  import * as RCheckbox from '@radix-ui/react-checkbox';
@@ -2892,6 +2892,227 @@ var SCard = forwardRef(function SCard2({ bordered = false, className, children,
2892
2892
  }
2893
2893
  );
2894
2894
  });
2895
+ var setRefs = (refs, value) => {
2896
+ refs.forEach((ref) => {
2897
+ if (typeof ref === "function") {
2898
+ ref(value);
2899
+ return;
2900
+ }
2901
+ if (ref) {
2902
+ ref.current = value;
2903
+ }
2904
+ });
2905
+ };
2906
+ function renderSlot(slot, state2) {
2907
+ return typeof slot === "function" ? slot(state2) : slot;
2908
+ }
2909
+ var SDraggableItemView = forwardRef(
2910
+ function SDraggableItemView2({
2911
+ title,
2912
+ trailing,
2913
+ accentStripe,
2914
+ bordered,
2915
+ selected,
2916
+ dense,
2917
+ dragging,
2918
+ disabled,
2919
+ hovered,
2920
+ dragHandleProps,
2921
+ onDragHandleMouseDown,
2922
+ className,
2923
+ ...rest
2924
+ }, ref) {
2925
+ const renderState = { hovered, dragging, disabled };
2926
+ const titleNode = renderSlot(title, renderState);
2927
+ const trailingNode = renderSlot(trailing, renderState);
2928
+ return /* @__PURE__ */ jsxs(
2929
+ "div",
2930
+ {
2931
+ ref,
2932
+ "aria-disabled": disabled || void 0,
2933
+ "data-dragging": dragging || void 0,
2934
+ className: cn(
2935
+ "relative flex w-full items-center gap-(--cmp-listDraggableItem-gap) overflow-hidden px-(--cmp-listDraggableItem-paddingX) text-[12px] leading-[20px]",
2936
+ disabled ? "bg-(--cmp-listDraggableItem-bg-default) font-medium text-(--sys-color-disabled-text)" : selected ? "bg-(--cmp-listDraggableItem-bg-selected) font-bold text-(--cmp-listDraggableItem-text-selected)" : "bg-(--cmp-listDraggableItem-bg-default) font-medium text-(--cmp-listDraggableItem-text-default)",
2937
+ !disabled && !selected && !dragging && "hover:bg-(--cmp-listDraggableItem-bg-hover)",
2938
+ dense ? "h-[32px] py-(--cmp-listDraggableItem-paddingY-dense)" : "h-[40px] py-(--cmp-listDraggableItem-paddingY-normal)",
2939
+ bordered ? cn(
2940
+ "rounded-(--cmp-listDraggableItem-radius-bordered) border border-(--cmp-listDraggableItem-border-default)",
2941
+ !disabled && !selected && !dragging && "hover:border-(--cmp-listDraggableItem-bordered-border-hover)",
2942
+ !disabled && selected && !dragging && "border-(--cmp-listDraggableItem-bordered-border-selected)",
2943
+ !disabled && selected && dragging && "border-[length:var(--cmp-listDraggableItem-bordered-dragging-border-width)] border-(--cmp-listDraggableItem-bordered-dragging-border-color) bg-(--cmp-listDraggableItem-bordered-dragging-bg)"
2944
+ ) : "border-b border-(--cmp-listDraggableItem-border-default)",
2945
+ disabled && "cursor-not-allowed",
2946
+ className
2947
+ ),
2948
+ ...rest,
2949
+ children: [
2950
+ accentStripe && !bordered && !disabled && /* @__PURE__ */ jsx(
2951
+ "span",
2952
+ {
2953
+ "aria-hidden": "true",
2954
+ className: "pointer-events-none absolute bottom-[-1px] left-0 top-0 w-(--cmp-listDraggableItem-accentStripe-width) bg-(--cmp-listDraggableItem-accentStripe-color)"
2955
+ }
2956
+ ),
2957
+ /* @__PURE__ */ jsx(
2958
+ "div",
2959
+ {
2960
+ ...dragHandleProps,
2961
+ role: dragHandleProps?.role ?? "button",
2962
+ tabIndex: dragHandleProps?.tabIndex ?? (disabled ? -1 : 0),
2963
+ "aria-label": dragHandleProps?.["aria-label"] ?? "\uB4DC\uB798\uADF8 \uD578\uB4E4",
2964
+ "aria-disabled": disabled || void 0,
2965
+ onMouseDown: onDragHandleMouseDown,
2966
+ className: cn(
2967
+ "flex size-[24px] shrink-0 select-none items-center justify-center rounded-[4px]",
2968
+ disabled ? "cursor-not-allowed opacity-0" : "cursor-grab hover:bg-black/5 active:cursor-grabbing",
2969
+ dragging && "bg-black/5",
2970
+ dragHandleProps?.className
2971
+ ),
2972
+ children: /* @__PURE__ */ jsx(SIcon, { name: "drag", size: 16, color: "grey_65" })
2973
+ }
2974
+ ),
2975
+ /* @__PURE__ */ jsxs(
2976
+ "div",
2977
+ {
2978
+ className: cn(
2979
+ "flex min-w-0 flex-1 items-center gap-[8px]",
2980
+ dragging && "opacity-(--cmp-listDraggableItem-dragging-content-opacity)"
2981
+ ),
2982
+ children: [
2983
+ /* @__PURE__ */ jsx("span", { className: "min-w-0 flex-1 truncate", children: titleNode }),
2984
+ trailingNode
2985
+ ]
2986
+ }
2987
+ )
2988
+ ]
2989
+ }
2990
+ );
2991
+ }
2992
+ );
2993
+ var SDraggableItem = forwardRef(
2994
+ function SDraggableItem2({
2995
+ title,
2996
+ trailing,
2997
+ accentStripe = false,
2998
+ bordered = false,
2999
+ selected = false,
3000
+ dense = false,
3001
+ disabled = false,
3002
+ dragOverlay = true,
3003
+ dragOverlayOpacity = 0.75,
3004
+ dragHandleProps,
3005
+ onDragHandleMouseDown,
3006
+ className,
3007
+ onMouseEnter,
3008
+ onMouseLeave,
3009
+ ...rest
3010
+ }, ref) {
3011
+ const [hovered, setHovered] = useState(false);
3012
+ const [overlay, setOverlay] = useState(null);
3013
+ const rootRef = useRef(null);
3014
+ const overlayVisible = overlay != null;
3015
+ const handleMouseEnter = (event) => {
3016
+ if (!disabled) setHovered(true);
3017
+ onMouseEnter?.(event);
3018
+ };
3019
+ const handleMouseLeave = (event) => {
3020
+ setHovered(false);
3021
+ onMouseLeave?.(event);
3022
+ };
3023
+ const handleDragMouseDown = (event) => {
3024
+ if (disabled) return;
3025
+ const rect = rootRef.current?.getBoundingClientRect();
3026
+ if (dragOverlay && rect) {
3027
+ setOverlay({
3028
+ offsetX: event.clientX - rect.left,
3029
+ offsetY: event.clientY - rect.top,
3030
+ rect,
3031
+ x: event.clientX,
3032
+ y: event.clientY
3033
+ });
3034
+ }
3035
+ dragHandleProps?.onMouseDown?.(event);
3036
+ onDragHandleMouseDown?.(event);
3037
+ };
3038
+ useEffect(() => {
3039
+ if (!overlayVisible) return void 0;
3040
+ const handleMouseMove = (event) => {
3041
+ setOverlay(
3042
+ (current) => current ? {
3043
+ ...current,
3044
+ x: event.clientX,
3045
+ y: event.clientY
3046
+ } : current
3047
+ );
3048
+ };
3049
+ const handleMouseUp = () => {
3050
+ setOverlay(null);
3051
+ };
3052
+ window.addEventListener("mousemove", handleMouseMove);
3053
+ window.addEventListener("mouseup", handleMouseUp);
3054
+ return () => {
3055
+ window.removeEventListener("mousemove", handleMouseMove);
3056
+ window.removeEventListener("mouseup", handleMouseUp);
3057
+ };
3058
+ }, [overlayVisible]);
3059
+ return /* @__PURE__ */ jsxs(Fragment, { children: [
3060
+ /* @__PURE__ */ jsx(
3061
+ SDraggableItemView,
3062
+ {
3063
+ ref: (node) => setRefs([rootRef, ref], node),
3064
+ title,
3065
+ trailing,
3066
+ accentStripe,
3067
+ bordered,
3068
+ selected,
3069
+ dense,
3070
+ dragging: overlayVisible,
3071
+ disabled,
3072
+ hovered,
3073
+ dragHandleProps,
3074
+ onDragHandleMouseDown: handleDragMouseDown,
3075
+ onMouseEnter: handleMouseEnter,
3076
+ onMouseLeave: handleMouseLeave,
3077
+ className,
3078
+ ...rest
3079
+ }
3080
+ ),
3081
+ overlay && typeof document !== "undefined" && createPortal(
3082
+ /* @__PURE__ */ jsx(
3083
+ "div",
3084
+ {
3085
+ className: "pointer-events-none fixed z-[999999]",
3086
+ style: {
3087
+ left: overlay.x - overlay.offsetX,
3088
+ opacity: dragOverlayOpacity,
3089
+ top: overlay.y - overlay.offsetY,
3090
+ width: overlay.rect.width
3091
+ },
3092
+ children: /* @__PURE__ */ jsx(
3093
+ SDraggableItemView,
3094
+ {
3095
+ title,
3096
+ trailing,
3097
+ accentStripe,
3098
+ bordered,
3099
+ selected,
3100
+ dense,
3101
+ dragging: true,
3102
+ disabled,
3103
+ hovered: true,
3104
+ dragHandleProps,
3105
+ className
3106
+ }
3107
+ )
3108
+ }
3109
+ ),
3110
+ document.body
3111
+ )
3112
+ ] });
3113
+ }
3114
+ );
3115
+ SDraggableItem.displayName = "SDraggableItem";
2895
3116
  var SExpansionItem = forwardRef(
2896
3117
  function SExpansionItem2({
2897
3118
  title,
@@ -2918,7 +3139,7 @@ var SExpansionItem = forwardRef(
2918
3139
  {
2919
3140
  ref,
2920
3141
  className: cn(
2921
- "group/expansion-item overflow-hidden bg-[var(--cmp-listExpansionItem-title-bg-default)]",
3142
+ "group/expansion-item overflow-hidden bg-(--cmp-listExpansionItem-title-bg-default)",
2922
3143
  // TODO: expansionItem/bordered/radius 및 border intent 토큰 생성 후 고정값을 토큰으로 교체한다.
2923
3144
  bordered && "rounded-[8px] border border-[#E1E1E1] hover:border-[#AAAAAA] [&:has(>button:hover)]:border-[#AAAAAA]",
2924
3145
  bordered && isExpanded && "!border-[#93C4FF]",
@@ -2940,10 +3161,10 @@ var SExpansionItem = forwardRef(
2940
3161
  onToggle?.(next, event);
2941
3162
  },
2942
3163
  className: cn(
2943
- "flex w-full items-center justify-between border-0 text-left text-[14px] font-bold leading-[24px] text-[var(--cmp-listExpansionItem-title-text-default)] focus-visible:outline focus-visible:outline-2 focus-visible:outline-[var(--sys-color-border-accent)] disabled:cursor-not-allowed disabled:text-[var(--sys-color-disabled-text)] cursor-pointer",
3164
+ "flex w-full cursor-pointer items-center justify-between border-0 text-left text-[14px] font-bold leading-[24px] text-(--cmp-listExpansionItem-title-text-default) focus-visible:outline focus-visible:outline-2 focus-visible:outline-(--sys-color-border-accent) disabled:cursor-not-allowed disabled:text-(--sys-color-disabled-text)",
2944
3165
  isExpanded && "border-b border-(--cmp-listExpansionItem-title-border)",
2945
3166
  !isExpanded && "hover:bg-(--cmp-listExpansionItem-title-bg-hover)",
2946
- dense ? "min-h-8 py-(--cmp-listExpansionItem-title-paddingY-dense)" : "min-h-10 py-(--cmp-listExpansionItem-title-paddingY-normal)",
3167
+ dense ? "h-[32px] py-(--cmp-listExpansionItem-title-paddingY-dense)" : "h-[40px] py-(--cmp-listExpansionItem-title-paddingY-normal)",
2947
3168
  "gap-(--cmp-listExpansionItem-title-gap)",
2948
3169
  "pr-(--cmp-listExpansionItem-title-paddingX)",
2949
3170
  depth === 2 ? "pl-[calc(var(--cmp-listExpansionItem-title-paddingX)+32px)]" : depth === 3 ? "pl-[calc(var(--cmp-listExpansionItem-title-paddingX)+64px)]" : "pl-(--cmp-listExpansionItem-title-paddingX)",
@@ -2957,7 +3178,7 @@ var SExpansionItem = forwardRef(
2957
3178
  "flex transition-transform duration-200 ease-out motion-reduce:transition-none",
2958
3179
  isExpanded && "rotate-180"
2959
3180
  ),
2960
- children: /* @__PURE__ */ jsx(SIcon, { name: "caretDown", size: 12 })
3181
+ children: /* @__PURE__ */ jsx(SIcon, { name: "caretDown", size: 12, color: "var(--sys-color-fg-quaternary)" })
2961
3182
  }
2962
3183
  ),
2963
3184
  leadingNode,
@@ -2972,19 +3193,10 @@ var SExpansionItem = forwardRef(
2972
3193
  id,
2973
3194
  "aria-hidden": !isExpanded,
2974
3195
  className: cn(
2975
- "grid overflow-hidden bg-[var(--cmp-listExpansionItem-body-bg)] transition-[grid-template-rows] duration-200 ease-out motion-reduce:transition-none",
3196
+ "grid overflow-hidden bg-(--cmp-listExpansionItem-body-bg) transition-[grid-template-rows] duration-200 ease-out motion-reduce:transition-none",
2976
3197
  isExpanded ? "grid-rows-[1fr]" : "grid-rows-[0fr]"
2977
3198
  ),
2978
- children: /* @__PURE__ */ jsx(
2979
- "div",
2980
- {
2981
- className: cn(
2982
- "min-h-0 overflow-hidden",
2983
- bodyPadding && isExpanded && "p-(--cmp-listExpansionItem-body-padding)"
2984
- ),
2985
- children
2986
- }
2987
- )
3199
+ children: /* @__PURE__ */ jsx("div", { className: "min-h-0 overflow-hidden", children: /* @__PURE__ */ jsx("div", { className: cn(bodyPadding && "p-(--cmp-listExpansionItem-body-padding)"), children }) })
2988
3200
  }
2989
3201
  )
2990
3202
  ]
@@ -2992,69 +3204,182 @@ var SExpansionItem = forwardRef(
2992
3204
  );
2993
3205
  }
2994
3206
  );
2995
- var SDivider = forwardRef(function SDivider2({ vertical = false, className, style, ...rest }, ref) {
3207
+ var SList = forwardRef(function SList2({ className, children, useGap = false, usePadding = false, ...rest }, ref) {
2996
3208
  return /* @__PURE__ */ jsx(
2997
- "hr",
3209
+ "div",
2998
3210
  {
2999
3211
  ref,
3000
- "aria-orientation": vertical ? "vertical" : "horizontal",
3001
3212
  className: cn(
3002
- "shrink-0 border-0",
3003
- vertical ? "inline-block h-auto w-px self-stretch" : "block h-px w-full",
3213
+ useGap && "flex flex-col gap-(--cmp-list-group-gap)",
3214
+ usePadding && "p-(--cmp-list-group-padding)",
3004
3215
  className
3005
3216
  ),
3006
- style: { backgroundColor: "var(--sys-color-divider-default, #E1E1E1)", ...style },
3007
- ...rest
3217
+ ...rest,
3218
+ children
3008
3219
  }
3009
3220
  );
3010
3221
  });
3011
-
3012
- // src/lib/scrollbar.ts
3013
- var FIREFOX_SCROLLBAR_CLASS = "supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-width:thin] supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-color:var(--color-grey-45)_transparent]";
3014
- var SCROLLBAR_CLASS = `${FIREFOX_SCROLLBAR_CLASS} [&::-webkit-scrollbar]:h-[12px] [&::-webkit-scrollbar]:w-[12px] [&::-webkit-scrollbar]:bg-transparent [&::-webkit-scrollbar-track]:bg-transparent [&::-webkit-scrollbar-thumb]:rounded-full [&::-webkit-scrollbar-thumb]:border-2 [&::-webkit-scrollbar-thumb]:border-solid [&::-webkit-scrollbar-thumb]:border-transparent [&::-webkit-scrollbar-thumb]:bg-[var(--color-grey-45)] [&::-webkit-scrollbar-thumb]:bg-clip-padding`;
3015
- var SCROLLBAR_HIDDEN_CLASS = "[scrollbar-width:none] [&::-webkit-scrollbar]:hidden";
3016
- var SCROLLBAR_TRACK_BG_CLASS = "supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-color:var(--color-grey-45)_var(--color-grey-10)] [&::-webkit-scrollbar]:bg-[var(--color-grey-10)] [&::-webkit-scrollbar-track]:bg-[var(--color-grey-10)] [&::-webkit-scrollbar-corner]:bg-[var(--color-grey-10)]";
3017
- var SCROLLBAR_TRACK_BG_WHITE_CLASS = "supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-color:var(--color-grey-45)_var(--color-white)] [&::-webkit-scrollbar]:bg-[var(--color-white)] [&::-webkit-scrollbar-track]:bg-[var(--color-white)] [&::-webkit-scrollbar-corner]:bg-[var(--color-white)]";
3018
- var SCROLLBAR_TRACK_BORDER_CLASS = "[&::-webkit-scrollbar-track:vertical]:[border-left:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-track:horizontal]:[border-top:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-corner]:[border-top:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-corner]:[border-left:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-thumb:vertical]:[border-left-width:3px] [&::-webkit-scrollbar-thumb:horizontal]:[border-top-width:3px]";
3019
- var AXIS_CLASS = {
3020
- vertical: "overflow-x-hidden overflow-y-auto",
3021
- horizontal: "overflow-x-auto overflow-y-hidden",
3022
- both: "overflow-auto"
3023
- };
3024
- var SScrollArea = forwardRef(function SScrollArea2({
3025
- axis = "both",
3026
- background = false,
3222
+ SList.displayName = "SList";
3223
+ var SListItem = forwardRef(function SListItem2({
3224
+ title,
3225
+ depth = 1,
3226
+ leading,
3227
+ trailing,
3027
3228
  bordered = false,
3028
- maxHeight,
3029
- maxWidth,
3229
+ accentStripe = false,
3230
+ dense = false,
3231
+ disabled = false,
3030
3232
  className,
3031
- style,
3032
- children,
3233
+ onMouseEnter,
3234
+ onMouseLeave,
3033
3235
  ...rest
3034
3236
  }, ref) {
3035
- const mergedStyle = { ...style };
3036
- if (maxHeight) mergedStyle.maxHeight = maxHeight;
3037
- if (maxWidth) mergedStyle.maxWidth = maxWidth;
3038
- return /* @__PURE__ */ jsx(
3237
+ const [hovered, setHovered] = useState(false);
3238
+ const renderState = { hovered, disabled };
3239
+ const titleNode = typeof title === "function" ? title(renderState) : title;
3240
+ const leadingNode = typeof leading === "function" ? leading(renderState) : leading;
3241
+ const trailingNode = typeof trailing === "function" ? trailing(renderState) : trailing;
3242
+ const handleMouseEnter = (event) => {
3243
+ if (!disabled) setHovered(true);
3244
+ onMouseEnter?.(event);
3245
+ };
3246
+ const handleMouseLeave = (event) => {
3247
+ setHovered(false);
3248
+ onMouseLeave?.(event);
3249
+ };
3250
+ return /* @__PURE__ */ jsxs(
3039
3251
  "div",
3040
3252
  {
3041
3253
  ref,
3254
+ "aria-disabled": disabled || void 0,
3255
+ onMouseEnter: handleMouseEnter,
3256
+ onMouseLeave: handleMouseLeave,
3042
3257
  className: cn(
3043
- AXIS_CLASS[axis],
3044
- SCROLLBAR_CLASS,
3045
- background && SCROLLBAR_TRACK_BG_CLASS,
3046
- bordered && SCROLLBAR_TRACK_BORDER_CLASS,
3258
+ "group/list-item relative flex w-full items-center justify-between bg-(--cmp-listItem-bg-default) text-left text-[14px] font-bold leading-[24px] text-(--cmp-listItem-text-default)",
3259
+ disabled ? "pointer-events-none cursor-not-allowed text-(--sys-color-disabled-text)" : "hover:bg-(--cmp-listItem-bg-hover)",
3260
+ dense ? "h-[32px] py-(--cmp-listItem-paddingY-dense)" : "h-[40px] py-(--cmp-listItem-paddingY-normal)",
3261
+ "gap-(--cmp-listItem-gap)",
3262
+ "pr-(--cmp-listItem-paddingX)",
3263
+ depth === 2 ? "pl-[calc(var(--cmp-listItem-paddingX)+32px)]" : depth === 3 ? "pl-[calc(var(--cmp-listItem-paddingX)+64px)]" : "pl-(--cmp-listItem-paddingX)",
3264
+ bordered ? "overflow-hidden rounded-(--cmp-listItem-radius-bordered) border border-(--cmp-listItem-border-default) hover:border-(--cmp-listItem-bordered-border-hover)" : "border-b border-(--cmp-listItem-border-default)",
3047
3265
  className
3048
3266
  ),
3049
- style: mergedStyle,
3050
3267
  ...rest,
3051
- children
3268
+ children: [
3269
+ accentStripe && !bordered && /* @__PURE__ */ jsx(
3270
+ "span",
3271
+ {
3272
+ "aria-hidden": "true",
3273
+ className: "pointer-events-none absolute bottom-[-1px] left-0 top-0 w-(--cmp-listItem-accentStripe-width) bg-(--cmp-listItem-accentStripe-color)"
3274
+ }
3275
+ ),
3276
+ leadingNode,
3277
+ /* @__PURE__ */ jsx("span", { className: "flex min-w-0 flex-1 flex-col", children: /* @__PURE__ */ jsx("span", { children: titleNode }) }),
3278
+ trailingNode
3279
+ ]
3052
3280
  }
3053
3281
  );
3054
3282
  });
3283
+ SListItem.displayName = "SListItem";
3055
3284
 
3056
- // src/components/SScrollArea/scrollArea.config.ts
3057
- var SCROLL_AREA_AXES = ["vertical", "horizontal", "both"];
3285
+ // src/lib/floating-anim.ts
3286
+ var FLOATING_SLIDE_ANIM = [
3287
+ "data-[state=open]:data-[side=top]:animate-floating-in-top",
3288
+ "data-[state=delayed-open]:data-[side=top]:animate-floating-in-top",
3289
+ "data-[state=instant-open]:data-[side=top]:animate-floating-in-top",
3290
+ "data-[state=closed]:data-[side=top]:animate-floating-out-top",
3291
+ "data-[state=open]:data-[side=bottom]:animate-floating-in-bottom",
3292
+ "data-[state=delayed-open]:data-[side=bottom]:animate-floating-in-bottom",
3293
+ "data-[state=instant-open]:data-[side=bottom]:animate-floating-in-bottom",
3294
+ "data-[state=closed]:data-[side=bottom]:animate-floating-out-bottom",
3295
+ "data-[state=open]:data-[side=left]:animate-floating-in-left",
3296
+ "data-[state=delayed-open]:data-[side=left]:animate-floating-in-left",
3297
+ "data-[state=instant-open]:data-[side=left]:animate-floating-in-left",
3298
+ "data-[state=closed]:data-[side=left]:animate-floating-out-left",
3299
+ "data-[state=open]:data-[side=right]:animate-floating-in-right",
3300
+ "data-[state=delayed-open]:data-[side=right]:animate-floating-in-right",
3301
+ "data-[state=instant-open]:data-[side=right]:animate-floating-in-right",
3302
+ "data-[state=closed]:data-[side=right]:animate-floating-out-right"
3303
+ ].join(" ");
3304
+ var PortalContainerContext = createContext(null);
3305
+ var InsideModalContext = createContext(false);
3306
+ var PortalContainerProvider = PortalContainerContext.Provider;
3307
+ var InsideModalProvider = InsideModalContext.Provider;
3308
+ function usePortalContainer() {
3309
+ return useContext(PortalContainerContext) ?? void 0;
3310
+ }
3311
+ function useInsideModal() {
3312
+ return useContext(InsideModalContext);
3313
+ }
3314
+
3315
+ // src/lib/sanitize-inline-html.ts
3316
+ var ALLOWED_INLINE_TAGS = /* @__PURE__ */ new Set(["A", "B", "STRONG", "I", "EM", "BR", "SPAN"]);
3317
+ var ALLOWED_ATTRS_BY_TAG = {
3318
+ A: /* @__PURE__ */ new Set(["href", "target", "rel", "class"])
3319
+ };
3320
+ var COMMON_ALLOWED_ATTRS = /* @__PURE__ */ new Set(["class"]);
3321
+ var SAFE_HREF_RE = /^(https?:|mailto:|tel:|\/|#|\.)/i;
3322
+ var DROP_CONTENT_TAGS = /* @__PURE__ */ new Set([
3323
+ "SCRIPT",
3324
+ "STYLE",
3325
+ "IFRAME",
3326
+ "OBJECT",
3327
+ "EMBED",
3328
+ "META",
3329
+ "LINK",
3330
+ "BASE",
3331
+ "NOSCRIPT",
3332
+ // SVG/MATH 는 foreign-content 파싱 모드로 전환되어 재직렬화 시 다른 트리로
3333
+ // 재파싱될 수 있다(mXSS 벡터). 인라인 라벨에 필요 없으므로 통째로 제거한다.
3334
+ "SVG",
3335
+ "MATH",
3336
+ "TEMPLATE"
3337
+ ]);
3338
+ var escapeHtml = (value) => value.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;").replace(/'/g, "&#39;");
3339
+ var sanitizeNode = (node) => {
3340
+ if (node.nodeType === Node.COMMENT_NODE) {
3341
+ node.remove();
3342
+ return;
3343
+ }
3344
+ if (node.nodeType !== Node.ELEMENT_NODE) return;
3345
+ const element = node;
3346
+ const tagName = element.tagName;
3347
+ if (DROP_CONTENT_TAGS.has(tagName)) {
3348
+ element.remove();
3349
+ return;
3350
+ }
3351
+ Array.from(element.childNodes).forEach((child) => sanitizeNode(child));
3352
+ if (ALLOWED_INLINE_TAGS.has(tagName)) {
3353
+ if (element.hasAttribute("className")) {
3354
+ const val = element.getAttribute("className");
3355
+ element.removeAttribute("className");
3356
+ if (!element.hasAttribute("class")) element.setAttribute("class", val);
3357
+ }
3358
+ const allowedAttrs = ALLOWED_ATTRS_BY_TAG[tagName] ?? COMMON_ALLOWED_ATTRS;
3359
+ Array.from(element.attributes).forEach((attr) => {
3360
+ if (!allowedAttrs.has(attr.name)) element.removeAttribute(attr.name);
3361
+ });
3362
+ if (tagName === "A") {
3363
+ const href = element.getAttribute("href");
3364
+ if (href !== null && href !== "" && !SAFE_HREF_RE.test(href)) element.removeAttribute("href");
3365
+ if (element.hasAttribute("target")) {
3366
+ element.setAttribute("rel", "noopener noreferrer");
3367
+ }
3368
+ }
3369
+ return;
3370
+ }
3371
+ const parent = element.parentNode;
3372
+ if (parent == null) return;
3373
+ while (element.firstChild) parent.insertBefore(element.firstChild, element);
3374
+ parent.removeChild(element);
3375
+ };
3376
+ var sanitizeInlineHtml = (value) => {
3377
+ if (typeof document === "undefined") return escapeHtml(value);
3378
+ const template = document.createElement("template");
3379
+ template.innerHTML = value;
3380
+ Array.from(template.content.childNodes).forEach((child) => sanitizeNode(child));
3381
+ return template.innerHTML;
3382
+ };
3058
3383
 
3059
3384
  // src/components/STag/tag.config.ts
3060
3385
  var TAG_SHAPES = ["square", "pill"];
@@ -3148,12 +3473,421 @@ var STag = forwardRef(function STag2({
3148
3473
  }
3149
3474
  );
3150
3475
  });
3151
-
3152
- // src/components/SButton/button.config.ts
3153
- var BUTTON_COLORS = ["primary", "secondary", "neutral", "danger"];
3154
- var BUTTON_SIZES = ["xs", "sm", "md", "lg"];
3155
- var V = (path) => `var(--cmp-button-${path})`;
3156
- function buttonPreset(color, outline) {
3476
+ var SIZE = {
3477
+ xxs: { icon: 12, radius: "sm" },
3478
+ xs: { icon: 16, radius: "sm" },
3479
+ sm: { icon: 20, radius: "sm" },
3480
+ md: { icon: 24, radius: "md" },
3481
+ lg: { icon: 32, radius: "md" }
3482
+ };
3483
+ var TOOLTIP_HIDE_DELAY_MS = 100;
3484
+ function SGhostButton({
3485
+ icon,
3486
+ size = "sm",
3487
+ intent = "default",
3488
+ ariaLabel = "",
3489
+ ariaPressed,
3490
+ tooltipText,
3491
+ disabled = false,
3492
+ onClick,
3493
+ anchorClassName,
3494
+ anchorStyle,
3495
+ className,
3496
+ style
3497
+ }) {
3498
+ const portalContainer = usePortalContainer();
3499
+ const [open, setOpen] = useState(false);
3500
+ const hideTimer = useRef(void 0);
3501
+ const cancelHide = () => {
3502
+ if (hideTimer.current) {
3503
+ clearTimeout(hideTimer.current);
3504
+ hideTimer.current = void 0;
3505
+ }
3506
+ };
3507
+ const openNow = () => {
3508
+ cancelHide();
3509
+ setOpen(true);
3510
+ };
3511
+ const startHide = () => {
3512
+ cancelHide();
3513
+ hideTimer.current = setTimeout(() => setOpen(false), TOOLTIP_HIDE_DELAY_MS);
3514
+ };
3515
+ const s = SIZE[size];
3516
+ const contentColor = disabled ? intent === "inverse" ? "var(--cmp-ghostButton-inverse-disabled)" : "var(--cmp-ghostButton-icon-disabled)" : `var(--cmp-ghostButton-${intent}-content)`;
3517
+ const text = (tooltipText ?? "").trim();
3518
+ const hasTooltip = text !== "";
3519
+ const btn = /* @__PURE__ */ jsxs(
3520
+ "button",
3521
+ {
3522
+ type: "button",
3523
+ disabled,
3524
+ "aria-disabled": disabled ? "true" : void 0,
3525
+ "aria-label": ariaLabel.trim() || void 0,
3526
+ "aria-pressed": ariaPressed,
3527
+ tabIndex: disabled ? -1 : void 0,
3528
+ onClick: (e) => {
3529
+ if (disabled) {
3530
+ e.preventDefault();
3531
+ return;
3532
+ }
3533
+ onClick?.(e);
3534
+ },
3535
+ className: cn(
3536
+ "group/ghost-button relative box-border inline-flex items-center justify-center border-none bg-transparent p-0 transition-shadow",
3537
+ disabled ? "cursor-not-allowed" : "cursor-pointer",
3538
+ "focus-visible:outline-none focus-visible:shadow-[0_0_0_2px_var(--cmp-ghostButton-action-hover-bg)]",
3539
+ className
3540
+ ),
3541
+ style: {
3542
+ width: `var(--cmp-ghostButton-${size}-size)`,
3543
+ height: `var(--cmp-ghostButton-${size}-size)`,
3544
+ borderRadius: `var(--cmp-ghostButton-radius-${s.radius})`,
3545
+ ...style
3546
+ },
3547
+ children: [
3548
+ !disabled && /* @__PURE__ */ jsx(
3549
+ "span",
3550
+ {
3551
+ "aria-hidden": true,
3552
+ className: "pointer-events-none absolute inset-0 rounded-[inherit] opacity-0 transition-opacity duration-200 group-hover/ghost-button:opacity-5",
3553
+ style: { background: `var(--cmp-ghostButton-${intent}-hover-bg)` }
3554
+ }
3555
+ ),
3556
+ /* @__PURE__ */ jsx(SIcon, { name: icon, size: s.icon, color: contentColor })
3557
+ ]
3558
+ }
3559
+ );
3560
+ if (!hasTooltip) return btn;
3561
+ return /* @__PURE__ */ jsxs(RPopover2.Root, { open, onOpenChange: setOpen, children: [
3562
+ /* @__PURE__ */ jsx(RPopover2.Anchor, { asChild: true, children: /* @__PURE__ */ jsx(
3563
+ "span",
3564
+ {
3565
+ className: cn("inline-flex", anchorClassName),
3566
+ style: anchorStyle,
3567
+ onMouseEnter: openNow,
3568
+ onMouseLeave: startHide,
3569
+ onFocus: openNow,
3570
+ onBlur: startHide,
3571
+ children: btn
3572
+ }
3573
+ ) }),
3574
+ /* @__PURE__ */ jsx(RPopover2.Portal, { container: portalContainer, children: /* @__PURE__ */ jsx(
3575
+ RPopover2.Content,
3576
+ {
3577
+ side: "top",
3578
+ sideOffset: 4,
3579
+ className: cn("z-50", FLOATING_SLIDE_ANIM),
3580
+ "aria-hidden": true,
3581
+ onOpenAutoFocus: (e) => e.preventDefault(),
3582
+ onMouseEnter: cancelHide,
3583
+ onMouseLeave: startHide,
3584
+ children: /* @__PURE__ */ jsx(STag, { shape: "square", size: "xs", color: "grey", label: text })
3585
+ }
3586
+ ) })
3587
+ ] });
3588
+ }
3589
+ var HIDE_DELAY_MS = 100;
3590
+ function useBody(content, message = []) {
3591
+ if (content != null) return content;
3592
+ if (message.length === 0) return null;
3593
+ const singleLine = message.length === 1;
3594
+ return /* @__PURE__ */ jsx(Fragment, { children: message.map((line, i) => /* @__PURE__ */ jsx(
3595
+ "div",
3596
+ {
3597
+ className: singleLine ? "leading-[24px]" : void 0,
3598
+ dangerouslySetInnerHTML: { __html: sanitizeInlineHtml(line) }
3599
+ },
3600
+ i
3601
+ )) });
3602
+ }
3603
+ var STooltip = forwardRef(function STooltip2({
3604
+ content,
3605
+ message = [],
3606
+ trigger = "hover",
3607
+ placement = "top",
3608
+ tooltipType = "default",
3609
+ useClose = false,
3610
+ disabled = false,
3611
+ children,
3612
+ icon = "helpOutline",
3613
+ iconSize = 12,
3614
+ color = "#01BB4B",
3615
+ ariaLabel,
3616
+ className,
3617
+ triggerClassName,
3618
+ style
3619
+ }, ref) {
3620
+ const portalContainer = usePortalContainer();
3621
+ const [open, setOpen] = useState(false);
3622
+ const hideTimer = useRef(void 0);
3623
+ const cancelHide = () => {
3624
+ if (hideTimer.current) {
3625
+ clearTimeout(hideTimer.current);
3626
+ hideTimer.current = void 0;
3627
+ }
3628
+ };
3629
+ const openNow = () => {
3630
+ cancelHide();
3631
+ setOpen(true);
3632
+ };
3633
+ const startHide = () => {
3634
+ if (useClose) return;
3635
+ cancelHide();
3636
+ hideTimer.current = setTimeout(() => setOpen(false), HIDE_DELAY_MS);
3637
+ };
3638
+ useImperativeHandle(
3639
+ ref,
3640
+ () => ({
3641
+ show: () => {
3642
+ cancelHide();
3643
+ setOpen(true);
3644
+ },
3645
+ hide: () => {
3646
+ cancelHide();
3647
+ setOpen(false);
3648
+ }
3649
+ }),
3650
+ []
3651
+ );
3652
+ const body = useBody(content, message);
3653
+ const bg = `var(--cmp-tooltip-${tooltipType}-bg)`;
3654
+ const fg = `var(--cmp-tooltip-${tooltipType}-content)`;
3655
+ const triggerNode = children ?? /* @__PURE__ */ jsx("span", { className: cn("inline-flex cursor-pointer", triggerClassName), "aria-label": ariaLabel, children: /* @__PURE__ */ jsx(SIcon, { name: icon, size: iconSize, color }) });
3656
+ if (disabled || body == null) return /* @__PURE__ */ jsx(Fragment, { children: triggerNode });
3657
+ const isHover = trigger === "hover";
3658
+ const contentClass = cn(
3659
+ "z-50 w-fit whitespace-nowrap rounded-[6px] px-[16px] py-[12px] text-[12px] leading-[20px] shadow-normal-sm",
3660
+ FLOATING_SLIDE_ANIM,
3661
+ className
3662
+ );
3663
+ const contentStyle = {
3664
+ background: bg,
3665
+ color: fg,
3666
+ fontWeight: tooltipType === "default" ? 500 : 700,
3667
+ ...style
3668
+ };
3669
+ return /* @__PURE__ */ jsxs(RPopover2.Root, { open, onOpenChange: setOpen, children: [
3670
+ isHover ? (
3671
+ // hover: Anchor(위치 기준) + 직접 mouse 핸들러 — 클릭으로 토글되지 않도록 Trigger 미사용
3672
+ /* @__PURE__ */ jsx(RPopover2.Anchor, { asChild: true, children: /* @__PURE__ */ jsx(
3673
+ "span",
3674
+ {
3675
+ className: "inline-flex",
3676
+ onMouseEnter: openNow,
3677
+ onMouseLeave: startHide,
3678
+ onFocus: openNow,
3679
+ onBlur: startHide,
3680
+ children: triggerNode
3681
+ }
3682
+ ) })
3683
+ ) : /* @__PURE__ */ jsx(RPopover2.Trigger, { asChild: true, children: triggerNode }),
3684
+ /* @__PURE__ */ jsx(RPopover2.Portal, { container: portalContainer, children: /* @__PURE__ */ jsxs(
3685
+ RPopover2.Content,
3686
+ {
3687
+ side: placement,
3688
+ sideOffset: 8,
3689
+ className: contentClass,
3690
+ style: contentStyle,
3691
+ onOpenAutoFocus: (e) => e.preventDefault(),
3692
+ onInteractOutside: (e) => {
3693
+ if (useClose) e.preventDefault();
3694
+ },
3695
+ onEscapeKeyDown: (e) => {
3696
+ if (useClose) e.preventDefault();
3697
+ },
3698
+ onMouseEnter: isHover ? cancelHide : void 0,
3699
+ onMouseLeave: isHover ? startHide : void 0,
3700
+ children: [
3701
+ /* @__PURE__ */ jsxs("div", { className: "flex items-start gap-[12px]", children: [
3702
+ /* @__PURE__ */ jsx("div", { className: "min-w-0 flex-1", children: body }),
3703
+ useClose && /* @__PURE__ */ jsx(
3704
+ SGhostButton,
3705
+ {
3706
+ icon: "close",
3707
+ size: "xs",
3708
+ intent: tooltipType === "default" ? "inverse" : "default",
3709
+ ariaLabel: "\uB2EB\uAE30",
3710
+ className: "shrink-0",
3711
+ onClick: () => {
3712
+ cancelHide();
3713
+ setOpen(false);
3714
+ }
3715
+ }
3716
+ )
3717
+ ] }),
3718
+ /* @__PURE__ */ jsx(RPopover2.Arrow, { width: 16, height: 12, style: { fill: bg } })
3719
+ ]
3720
+ }
3721
+ ) })
3722
+ ] });
3723
+ });
3724
+ STooltip.displayName = "STooltip";
3725
+ var topBorderColorClass = {
3726
+ default: "bg-(--cmp-sectionHeaderCard-topBorder-color-default)",
3727
+ accent: "bg-(--cmp-sectionHeaderCard-topBorder-color-accent)"
3728
+ };
3729
+ var SSectionHeaderCardBody = forwardRef(
3730
+ function SSectionHeaderCardBody2({ className, children, ...rest }, ref) {
3731
+ return /* @__PURE__ */ jsx("div", { ref, className, ...rest, children });
3732
+ }
3733
+ );
3734
+ var SSectionHeaderCardHeader = forwardRef(
3735
+ function SSectionHeaderCardHeader2({
3736
+ title,
3737
+ marker = false,
3738
+ required = false,
3739
+ helpText,
3740
+ subtitle,
3741
+ slot,
3742
+ thickness = false,
3743
+ className,
3744
+ ...rest
3745
+ }, ref) {
3746
+ const hasHelp = helpText != null && helpText.length > 0;
3747
+ return /* @__PURE__ */ jsxs(Fragment, { children: [
3748
+ thickness && /* @__PURE__ */ jsx(
3749
+ "div",
3750
+ {
3751
+ className: cn(
3752
+ "h-(--cmp-sectionHeaderCard-topBorder-thickness) w-full shrink-0",
3753
+ topBorderColorClass[thickness]
3754
+ )
3755
+ }
3756
+ ),
3757
+ /* @__PURE__ */ jsxs(
3758
+ "div",
3759
+ {
3760
+ ref,
3761
+ className: cn(
3762
+ "box-border flex h-[40px] w-full shrink-0 items-center gap-[8px] overflow-hidden border-b border-(--sys-color-border-default) bg-(--sys-color-bg-frame) px-[16px] py-[4px]",
3763
+ className
3764
+ ),
3765
+ ...rest,
3766
+ children: [
3767
+ marker && /* @__PURE__ */ jsx(SBadge, { color: "darkblue", className: "shrink-0" }),
3768
+ /* @__PURE__ */ jsxs("div", { className: "flex min-w-0 shrink-0 items-center gap-[8px]", children: [
3769
+ /* @__PURE__ */ jsx("span", { className: "min-w-0 truncate text-[12px] font-bold leading-[20px] text-(--sys-color-fg-brand)", children: title }),
3770
+ required && /* @__PURE__ */ jsx(
3771
+ SIcon,
3772
+ {
3773
+ name: "star",
3774
+ size: 16,
3775
+ color: "var(--sys-color-fg-accent)",
3776
+ className: "shrink-0"
3777
+ }
3778
+ ),
3779
+ hasHelp && /* @__PURE__ */ jsx(
3780
+ STooltip,
3781
+ {
3782
+ trigger: "hover",
3783
+ icon: "helpOutline",
3784
+ iconSize: 16,
3785
+ color: "var(--sys-color-fg-success)",
3786
+ message: helpText,
3787
+ triggerClassName: "shrink-0 rounded-[4px]"
3788
+ }
3789
+ )
3790
+ ] }),
3791
+ subtitle && /* @__PURE__ */ jsx("span", { className: "min-w-0 truncate text-[12px] font-normal leading-[20px] text-(--sys-color-fg-secondary)", children: subtitle }),
3792
+ /* @__PURE__ */ jsx("div", { className: "ml-auto flex min-h-6 min-w-0 flex-1 items-center justify-end", children: slot })
3793
+ ]
3794
+ }
3795
+ )
3796
+ ] });
3797
+ }
3798
+ );
3799
+ var SSectionHeaderCardRoot = forwardRef(
3800
+ function SSectionHeaderCard({ className, children, ...rest }, ref) {
3801
+ return /* @__PURE__ */ jsx(
3802
+ "div",
3803
+ {
3804
+ ref,
3805
+ className: cn(
3806
+ "box-border flex w-full flex-col items-stretch overflow-hidden rounded-[8px] border border-(--sys-color-border-default) bg-(--sys-color-bg-frame)",
3807
+ className
3808
+ ),
3809
+ ...rest,
3810
+ children
3811
+ }
3812
+ );
3813
+ }
3814
+ );
3815
+ var SSectionHeaderCard2 = Object.assign(SSectionHeaderCardRoot, {
3816
+ Header: SSectionHeaderCardHeader,
3817
+ Body: SSectionHeaderCardBody
3818
+ });
3819
+ SSectionHeaderCardRoot.displayName = "SSectionHeaderCard";
3820
+ SSectionHeaderCardHeader.displayName = "SSectionHeaderCard.Header";
3821
+ SSectionHeaderCardBody.displayName = "SSectionHeaderCard.Body";
3822
+ var SDivider = forwardRef(function SDivider2({ vertical = false, className, style, ...rest }, ref) {
3823
+ return /* @__PURE__ */ jsx(
3824
+ "hr",
3825
+ {
3826
+ ref,
3827
+ "aria-orientation": vertical ? "vertical" : "horizontal",
3828
+ className: cn(
3829
+ "shrink-0 border-0",
3830
+ vertical ? "inline-block h-auto w-px self-stretch" : "block h-px w-full",
3831
+ className
3832
+ ),
3833
+ style: { backgroundColor: "var(--sys-color-divider-default, #E1E1E1)", ...style },
3834
+ ...rest
3835
+ }
3836
+ );
3837
+ });
3838
+
3839
+ // src/lib/scrollbar.ts
3840
+ var FIREFOX_SCROLLBAR_CLASS = "supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-width:thin] supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-color:var(--color-grey-45)_transparent]";
3841
+ var SCROLLBAR_CLASS = `${FIREFOX_SCROLLBAR_CLASS} [&::-webkit-scrollbar]:h-[12px] [&::-webkit-scrollbar]:w-[12px] [&::-webkit-scrollbar]:bg-transparent [&::-webkit-scrollbar-track]:bg-transparent [&::-webkit-scrollbar-thumb]:rounded-full [&::-webkit-scrollbar-thumb]:border-2 [&::-webkit-scrollbar-thumb]:border-solid [&::-webkit-scrollbar-thumb]:border-transparent [&::-webkit-scrollbar-thumb]:bg-[var(--color-grey-45)] [&::-webkit-scrollbar-thumb]:bg-clip-padding`;
3842
+ var SCROLLBAR_HIDDEN_CLASS = "[scrollbar-width:none] [&::-webkit-scrollbar]:hidden";
3843
+ var SCROLLBAR_TRACK_BG_CLASS = "supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-color:var(--color-grey-45)_var(--color-grey-10)] [&::-webkit-scrollbar]:bg-[var(--color-grey-10)] [&::-webkit-scrollbar-track]:bg-[var(--color-grey-10)] [&::-webkit-scrollbar-corner]:bg-[var(--color-grey-10)]";
3844
+ var SCROLLBAR_TRACK_BG_WHITE_CLASS = "supports-[not_selector(::-webkit-scrollbar)]:[scrollbar-color:var(--color-grey-45)_var(--color-white)] [&::-webkit-scrollbar]:bg-[var(--color-white)] [&::-webkit-scrollbar-track]:bg-[var(--color-white)] [&::-webkit-scrollbar-corner]:bg-[var(--color-white)]";
3845
+ var SCROLLBAR_TRACK_BORDER_CLASS = "[&::-webkit-scrollbar-track:vertical]:[border-left:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-track:horizontal]:[border-top:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-corner]:[border-top:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-corner]:[border-left:1px_solid_var(--sys-color-border-default)] [&::-webkit-scrollbar-thumb:vertical]:[border-left-width:3px] [&::-webkit-scrollbar-thumb:horizontal]:[border-top-width:3px]";
3846
+ var AXIS_CLASS = {
3847
+ vertical: "overflow-x-hidden overflow-y-auto",
3848
+ horizontal: "overflow-x-auto overflow-y-hidden",
3849
+ both: "overflow-auto"
3850
+ };
3851
+ var SScrollArea = forwardRef(function SScrollArea2({
3852
+ axis = "both",
3853
+ background = false,
3854
+ bordered = false,
3855
+ maxHeight,
3856
+ maxWidth,
3857
+ className,
3858
+ style,
3859
+ children,
3860
+ ...rest
3861
+ }, ref) {
3862
+ const mergedStyle = { ...style };
3863
+ if (maxHeight) mergedStyle.maxHeight = maxHeight;
3864
+ if (maxWidth) mergedStyle.maxWidth = maxWidth;
3865
+ return /* @__PURE__ */ jsx(
3866
+ "div",
3867
+ {
3868
+ ref,
3869
+ className: cn(
3870
+ AXIS_CLASS[axis],
3871
+ SCROLLBAR_CLASS,
3872
+ background && SCROLLBAR_TRACK_BG_CLASS,
3873
+ bordered && SCROLLBAR_TRACK_BORDER_CLASS,
3874
+ className
3875
+ ),
3876
+ style: mergedStyle,
3877
+ ...rest,
3878
+ children
3879
+ }
3880
+ );
3881
+ });
3882
+
3883
+ // src/components/SScrollArea/scrollArea.config.ts
3884
+ var SCROLL_AREA_AXES = ["vertical", "horizontal", "both"];
3885
+
3886
+ // src/components/SButton/button.config.ts
3887
+ var BUTTON_COLORS = ["primary", "secondary", "neutral", "danger"];
3888
+ var BUTTON_SIZES = ["xs", "sm", "md", "lg"];
3889
+ var V = (path) => `var(--cmp-button-${path})`;
3890
+ function buttonPreset(color, outline) {
3157
3891
  switch (color) {
3158
3892
  case "primary":
3159
3893
  return outline ? {
@@ -3332,7 +4066,13 @@ function renderItems(message, depth = 1) {
3332
4066
  className: cn("flex items-start", isDepth2 && "pl-[32px]"),
3333
4067
  children: [
3334
4068
  /* @__PURE__ */ jsx("span", { className: "w-[24px] shrink-0 text-center", "aria-hidden": true, children: isDepth2 ? "\u2022" : "-" }),
3335
- /* @__PURE__ */ jsx("p", { className: "m-0 min-w-0 flex-1 break-words", children: m })
4069
+ /* @__PURE__ */ jsx(
4070
+ "p",
4071
+ {
4072
+ className: "m-0 min-w-0 flex-1 break-words",
4073
+ dangerouslySetInnerHTML: { __html: sanitizeInlineHtml(m) }
4074
+ }
4075
+ )
3336
4076
  ]
3337
4077
  },
3338
4078
  `${depth}-${i}-${out.length}`
@@ -3635,36 +4375,6 @@ var loading = {
3635
4375
  setState({ open: false });
3636
4376
  }
3637
4377
  };
3638
-
3639
- // src/lib/floating-anim.ts
3640
- var FLOATING_SLIDE_ANIM = [
3641
- "data-[state=open]:data-[side=top]:animate-floating-in-top",
3642
- "data-[state=delayed-open]:data-[side=top]:animate-floating-in-top",
3643
- "data-[state=instant-open]:data-[side=top]:animate-floating-in-top",
3644
- "data-[state=closed]:data-[side=top]:animate-floating-out-top",
3645
- "data-[state=open]:data-[side=bottom]:animate-floating-in-bottom",
3646
- "data-[state=delayed-open]:data-[side=bottom]:animate-floating-in-bottom",
3647
- "data-[state=instant-open]:data-[side=bottom]:animate-floating-in-bottom",
3648
- "data-[state=closed]:data-[side=bottom]:animate-floating-out-bottom",
3649
- "data-[state=open]:data-[side=left]:animate-floating-in-left",
3650
- "data-[state=delayed-open]:data-[side=left]:animate-floating-in-left",
3651
- "data-[state=instant-open]:data-[side=left]:animate-floating-in-left",
3652
- "data-[state=closed]:data-[side=left]:animate-floating-out-left",
3653
- "data-[state=open]:data-[side=right]:animate-floating-in-right",
3654
- "data-[state=delayed-open]:data-[side=right]:animate-floating-in-right",
3655
- "data-[state=instant-open]:data-[side=right]:animate-floating-in-right",
3656
- "data-[state=closed]:data-[side=right]:animate-floating-out-right"
3657
- ].join(" ");
3658
- var PortalContainerContext = createContext(null);
3659
- var InsideModalContext = createContext(false);
3660
- var PortalContainerProvider = PortalContainerContext.Provider;
3661
- var InsideModalProvider = InsideModalContext.Provider;
3662
- function usePortalContainer() {
3663
- return useContext(PortalContainerContext) ?? void 0;
3664
- }
3665
- function useInsideModal() {
3666
- return useContext(InsideModalContext);
3667
- }
3668
4378
  var SIZE_CONFIG = {
3669
4379
  sm: {
3670
4380
  gap: 4,
@@ -3707,127 +4417,58 @@ var STextLink = forwardRef(function STextLink2({
3707
4417
  const handle = () => {
3708
4418
  if (!disabled) onClick?.();
3709
4419
  };
3710
- const portalContainer = usePortalContainer();
3711
- const link = /* @__PURE__ */ jsxs(
3712
- "span",
3713
- {
3714
- ref,
3715
- role: "button",
3716
- tabIndex: disabled ? -1 : 0,
3717
- onClick: handle,
3718
- onKeyDown: (e) => {
3719
- if (e.key === "Enter" || e.key === " ") {
3720
- e.preventDefault();
3721
- handle();
3722
- }
3723
- },
3724
- className: cn(
3725
- "inline-flex cursor-pointer items-center",
3726
- underline ? s.underlineTypo : s.typo,
3727
- !disabled && "hover:underline",
3728
- disabled && "cursor-not-allowed",
3729
- className
3730
- ),
3731
- style: { gap: s.gap, color: contentColor, ...style },
3732
- ...rest,
3733
- children: [
3734
- icon && /* @__PURE__ */ jsx(SIcon, { name: icon, size: s.iconSize, color: resolvedIconColor }),
3735
- /* @__PURE__ */ jsx(
3736
- "span",
3737
- {
3738
- className: cn(labelClass),
3739
- style: disabled ? { color: "var(--cmp-textLink-content-disabled)" } : void 0,
3740
- children: label || children
3741
- }
3742
- ),
3743
- rightArrow !== "none" && /* @__PURE__ */ jsx("span", { className: "inline-flex h-[16px] w-[16px] items-center justify-center", children: /* @__PURE__ */ jsx(
3744
- SIcon,
3745
- {
3746
- name: rightArrow === "chevron" ? "chevronRight" : "caretRight",
3747
- size: 12,
3748
- color: disabled ? "var(--cmp-textLink-icon-disabled)" : "var(--color-grey-65)"
3749
- }
3750
- ) })
3751
- ]
3752
- }
3753
- );
3754
- const text = (tooltipText ?? "").trim();
3755
- if (text === "") return link;
3756
- return /* @__PURE__ */ jsx(RTooltip.Provider, { delayDuration: 200, children: /* @__PURE__ */ jsxs(RTooltip.Root, { children: [
3757
- /* @__PURE__ */ jsx(RTooltip.Trigger, { asChild: true, children: link }),
3758
- /* @__PURE__ */ jsx(RTooltip.Portal, { container: portalContainer, children: /* @__PURE__ */ jsx(RTooltip.Content, { side: "top", sideOffset: 4, className: cn("z-50", FLOATING_SLIDE_ANIM), children: /* @__PURE__ */ jsx(STag, { shape: "square", size: "xs", color: "grey", label: text }) }) })
3759
- ] }) });
3760
- });
3761
-
3762
- // src/lib/sanitize-inline-html.ts
3763
- var ALLOWED_INLINE_TAGS = /* @__PURE__ */ new Set(["A", "B", "STRONG", "I", "EM", "BR", "SPAN"]);
3764
- var ALLOWED_ATTRS_BY_TAG = {
3765
- A: /* @__PURE__ */ new Set(["href", "target", "rel", "class"])
3766
- };
3767
- var COMMON_ALLOWED_ATTRS = /* @__PURE__ */ new Set(["class"]);
3768
- var SAFE_HREF_RE = /^(https?:|mailto:|tel:|\/|#|\.)/i;
3769
- var DROP_CONTENT_TAGS = /* @__PURE__ */ new Set([
3770
- "SCRIPT",
3771
- "STYLE",
3772
- "IFRAME",
3773
- "OBJECT",
3774
- "EMBED",
3775
- "META",
3776
- "LINK",
3777
- "BASE",
3778
- "NOSCRIPT",
3779
- // SVG/MATH 는 foreign-content 파싱 모드로 전환되어 재직렬화 시 다른 트리로
3780
- // 재파싱될 수 있다(mXSS 벡터). 인라인 라벨에 필요 없으므로 통째로 제거한다.
3781
- "SVG",
3782
- "MATH",
3783
- "TEMPLATE"
3784
- ]);
3785
- var escapeHtml = (value) => value.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;").replace(/'/g, "&#39;");
3786
- var sanitizeNode = (node) => {
3787
- if (node.nodeType === Node.COMMENT_NODE) {
3788
- node.remove();
3789
- return;
3790
- }
3791
- if (node.nodeType !== Node.ELEMENT_NODE) return;
3792
- const element = node;
3793
- const tagName = element.tagName;
3794
- if (DROP_CONTENT_TAGS.has(tagName)) {
3795
- element.remove();
3796
- return;
3797
- }
3798
- Array.from(element.childNodes).forEach((child) => sanitizeNode(child));
3799
- if (ALLOWED_INLINE_TAGS.has(tagName)) {
3800
- if (element.hasAttribute("className")) {
3801
- const val = element.getAttribute("className");
3802
- element.removeAttribute("className");
3803
- if (!element.hasAttribute("class")) element.setAttribute("class", val);
3804
- }
3805
- const allowedAttrs = ALLOWED_ATTRS_BY_TAG[tagName] ?? COMMON_ALLOWED_ATTRS;
3806
- Array.from(element.attributes).forEach((attr) => {
3807
- if (!allowedAttrs.has(attr.name)) element.removeAttribute(attr.name);
3808
- });
3809
- if (tagName === "A") {
3810
- const href = element.getAttribute("href");
3811
- if (href !== null && href !== "" && !SAFE_HREF_RE.test(href)) element.removeAttribute("href");
3812
- if (element.hasAttribute("target")) {
3813
- element.setAttribute("rel", "noopener noreferrer");
3814
- }
4420
+ const portalContainer = usePortalContainer();
4421
+ const link = /* @__PURE__ */ jsxs(
4422
+ "span",
4423
+ {
4424
+ ref,
4425
+ role: "button",
4426
+ tabIndex: disabled ? -1 : 0,
4427
+ onClick: handle,
4428
+ onKeyDown: (e) => {
4429
+ if (e.key === "Enter" || e.key === " ") {
4430
+ e.preventDefault();
4431
+ handle();
4432
+ }
4433
+ },
4434
+ className: cn(
4435
+ "inline-flex cursor-pointer items-center",
4436
+ underline ? s.underlineTypo : s.typo,
4437
+ !disabled && "hover:underline",
4438
+ disabled && "cursor-not-allowed",
4439
+ className
4440
+ ),
4441
+ style: { gap: s.gap, color: contentColor, ...style },
4442
+ ...rest,
4443
+ children: [
4444
+ icon && /* @__PURE__ */ jsx(SIcon, { name: icon, size: s.iconSize, color: resolvedIconColor }),
4445
+ /* @__PURE__ */ jsx(
4446
+ "span",
4447
+ {
4448
+ className: cn(labelClass),
4449
+ style: disabled ? { color: "var(--cmp-textLink-content-disabled)" } : void 0,
4450
+ children: label || children
4451
+ }
4452
+ ),
4453
+ rightArrow !== "none" && /* @__PURE__ */ jsx("span", { className: "inline-flex h-[16px] w-[16px] items-center justify-center", children: /* @__PURE__ */ jsx(
4454
+ SIcon,
4455
+ {
4456
+ name: rightArrow === "chevron" ? "chevronRight" : "caretRight",
4457
+ size: 12,
4458
+ color: disabled ? "var(--cmp-textLink-icon-disabled)" : "var(--color-grey-65)"
4459
+ }
4460
+ ) })
4461
+ ]
3815
4462
  }
3816
- return;
3817
- }
3818
- const parent = element.parentNode;
3819
- if (parent == null) return;
3820
- while (element.firstChild) parent.insertBefore(element.firstChild, element);
3821
- parent.removeChild(element);
3822
- };
3823
- var sanitizeInlineHtml = (value) => {
3824
- if (typeof document === "undefined") return escapeHtml(value);
3825
- const template = document.createElement("template");
3826
- template.innerHTML = value;
3827
- Array.from(template.content.childNodes).forEach((child) => sanitizeNode(child));
3828
- return template.innerHTML;
3829
- };
3830
- var SIZE = {
4463
+ );
4464
+ const text = (tooltipText ?? "").trim();
4465
+ if (text === "") return link;
4466
+ return /* @__PURE__ */ jsx(RTooltip.Provider, { delayDuration: 200, children: /* @__PURE__ */ jsxs(RTooltip.Root, { children: [
4467
+ /* @__PURE__ */ jsx(RTooltip.Trigger, { asChild: true, children: link }),
4468
+ /* @__PURE__ */ jsx(RTooltip.Portal, { container: portalContainer, children: /* @__PURE__ */ jsx(RTooltip.Content, { side: "top", sideOffset: 4, className: cn("z-50", FLOATING_SLIDE_ANIM), children: /* @__PURE__ */ jsx(STag, { shape: "square", size: "xs", color: "grey", label: text }) }) })
4469
+ ] }) });
4470
+ });
4471
+ var SIZE2 = {
3831
4472
  xs: { height: 24, paddingX: 8, gap: 6, arrow: 12, fontSize: 12, minWidth: 64, splitMinWidth: 72 },
3832
4473
  sm: {
3833
4474
  height: 28,
@@ -3913,7 +4554,7 @@ var SDropdownButton = forwardRef(
3913
4554
  }),
3914
4555
  []
3915
4556
  );
3916
- const s = SIZE[size];
4557
+ const s = SIZE2[size];
3917
4558
  const p = buttonPreset(color, outline);
3918
4559
  const colorVars = {
3919
4560
  "--dd-bg": disabled ? "var(--cmp-button-bg-disabled)" : p.bg,
@@ -3967,201 +4608,88 @@ var SDropdownButton = forwardRef(
3967
4608
  ]
3968
4609
  },
3969
4610
  it.value
3970
- ))
3971
- }
3972
- ) });
3973
- return /* @__PURE__ */ jsxs(
3974
- RDropdown.Root,
3975
- {
3976
- open,
3977
- onOpenChange: (o) => {
3978
- setOpen(o);
3979
- onOpenChange?.(o);
3980
- },
3981
- children: [
3982
- split ? /* @__PURE__ */ jsxs(
3983
- "div",
3984
- {
3985
- ref: splitWrapRef,
3986
- className: cn("inline-flex items-stretch", className),
3987
- style: { minWidth: s.splitMinWidth, ...style },
3988
- children: [
3989
- /* @__PURE__ */ jsx(
3990
- "button",
3991
- {
3992
- type: "button",
3993
- disabled,
3994
- onClick: onLabelClick,
3995
- className: cn(triggerBase, "flex-1 justify-center rounded-l-[4px] border-r-0"),
3996
- style: {
3997
- minHeight: s.height,
3998
- padding: `0 ${s.paddingX}px`,
3999
- fontSize: s.fontSize,
4000
- ...colorVars
4001
- },
4002
- children: label
4003
- }
4004
- ),
4005
- /* @__PURE__ */ jsx(RDropdown.Trigger, { asChild: true, children: /* @__PURE__ */ jsx(
4006
- "button",
4007
- {
4008
- ref: splitToggleRef,
4009
- type: "button",
4010
- disabled,
4011
- "aria-label": "\uBA54\uB274 \uC5F4\uAE30",
4012
- className: cn(triggerBase, "justify-center rounded-r-[4px] border-l"),
4013
- style: {
4014
- minHeight: s.height,
4015
- minWidth: s.height,
4016
- borderLeftColor: disabled ? "var(--cmp-button-border-disabled)" : splitDivider(color, outline),
4017
- ...colorVars
4018
- },
4019
- children: splitIcon
4020
- }
4021
- ) })
4022
- ]
4023
- }
4024
- ) : /* @__PURE__ */ jsx(RDropdown.Trigger, { asChild: true, children: /* @__PURE__ */ jsxs(
4025
- "button",
4026
- {
4027
- type: "button",
4028
- disabled,
4029
- className: cn(triggerBase, "justify-between rounded-[4px]", className),
4030
- style: {
4031
- minWidth: s.minWidth,
4032
- minHeight: s.height,
4033
- padding: `0 ${s.paddingX}px`,
4034
- gap: s.gap,
4035
- fontSize: s.fontSize,
4036
- ...colorVars,
4037
- ...style
4038
- },
4039
- children: [
4040
- /* @__PURE__ */ jsx("span", { className: "flex-1 truncate text-center", children: label }),
4041
- caret
4042
- ]
4043
- }
4044
- ) }),
4045
- menu
4046
- ]
4047
- }
4048
- );
4049
- }
4050
- );
4051
- SDropdownButton.displayName = "SDropdownButton";
4052
- var SIZE2 = {
4053
- xxs: { icon: 12, radius: "sm" },
4054
- xs: { icon: 16, radius: "sm" },
4055
- sm: { icon: 20, radius: "sm" },
4056
- md: { icon: 24, radius: "md" },
4057
- lg: { icon: 32, radius: "md" }
4058
- };
4059
- var TOOLTIP_HIDE_DELAY_MS = 100;
4060
- function SGhostButton({
4061
- icon,
4062
- size = "sm",
4063
- intent = "default",
4064
- ariaLabel = "",
4065
- ariaPressed,
4066
- tooltipText,
4067
- disabled = false,
4068
- onClick,
4069
- anchorClassName,
4070
- anchorStyle,
4071
- className,
4072
- style
4073
- }) {
4074
- const portalContainer = usePortalContainer();
4075
- const [open, setOpen] = useState(false);
4076
- const hideTimer = useRef(void 0);
4077
- const cancelHide = () => {
4078
- if (hideTimer.current) {
4079
- clearTimeout(hideTimer.current);
4080
- hideTimer.current = void 0;
4081
- }
4082
- };
4083
- const openNow = () => {
4084
- cancelHide();
4085
- setOpen(true);
4086
- };
4087
- const startHide = () => {
4088
- cancelHide();
4089
- hideTimer.current = setTimeout(() => setOpen(false), TOOLTIP_HIDE_DELAY_MS);
4090
- };
4091
- const s = SIZE2[size];
4092
- const contentColor = disabled ? intent === "inverse" ? "var(--cmp-ghostButton-inverse-disabled)" : "var(--cmp-ghostButton-icon-disabled)" : `var(--cmp-ghostButton-${intent}-content)`;
4093
- const text = (tooltipText ?? "").trim();
4094
- const hasTooltip = text !== "";
4095
- const btn = /* @__PURE__ */ jsxs(
4096
- "button",
4097
- {
4098
- type: "button",
4099
- disabled,
4100
- "aria-disabled": disabled ? "true" : void 0,
4101
- "aria-label": ariaLabel.trim() || void 0,
4102
- "aria-pressed": ariaPressed,
4103
- tabIndex: disabled ? -1 : void 0,
4104
- onClick: (e) => {
4105
- if (disabled) {
4106
- e.preventDefault();
4107
- return;
4108
- }
4109
- onClick?.(e);
4110
- },
4111
- className: cn(
4112
- "group/ghost-button relative box-border inline-flex items-center justify-center border-none bg-transparent p-0 transition-shadow",
4113
- disabled ? "cursor-not-allowed" : "cursor-pointer",
4114
- "focus-visible:outline-none focus-visible:shadow-[0_0_0_2px_var(--cmp-ghostButton-action-hover-bg)]",
4115
- className
4116
- ),
4117
- style: {
4118
- width: `var(--cmp-ghostButton-${size}-size)`,
4119
- height: `var(--cmp-ghostButton-${size}-size)`,
4120
- borderRadius: `var(--cmp-ghostButton-radius-${s.radius})`,
4121
- ...style
4122
- },
4123
- children: [
4124
- !disabled && /* @__PURE__ */ jsx(
4125
- "span",
4126
- {
4127
- "aria-hidden": true,
4128
- className: "pointer-events-none absolute inset-0 rounded-[inherit] opacity-0 transition-opacity duration-200 group-hover/ghost-button:opacity-5",
4129
- style: { background: `var(--cmp-ghostButton-${intent}-hover-bg)` }
4130
- }
4131
- ),
4132
- /* @__PURE__ */ jsx(SIcon, { name: icon, size: s.icon, color: contentColor })
4133
- ]
4134
- }
4135
- );
4136
- if (!hasTooltip) return btn;
4137
- return /* @__PURE__ */ jsxs(RPopover2.Root, { open, onOpenChange: setOpen, children: [
4138
- /* @__PURE__ */ jsx(RPopover2.Anchor, { asChild: true, children: /* @__PURE__ */ jsx(
4139
- "span",
4140
- {
4141
- className: cn("inline-flex", anchorClassName),
4142
- style: anchorStyle,
4143
- onMouseEnter: openNow,
4144
- onMouseLeave: startHide,
4145
- onFocus: openNow,
4146
- onBlur: startHide,
4147
- children: btn
4148
- }
4149
- ) }),
4150
- /* @__PURE__ */ jsx(RPopover2.Portal, { container: portalContainer, children: /* @__PURE__ */ jsx(
4151
- RPopover2.Content,
4152
- {
4153
- side: "top",
4154
- sideOffset: 4,
4155
- className: cn("z-50", FLOATING_SLIDE_ANIM),
4156
- "aria-hidden": true,
4157
- onOpenAutoFocus: (e) => e.preventDefault(),
4158
- onMouseEnter: cancelHide,
4159
- onMouseLeave: startHide,
4160
- children: /* @__PURE__ */ jsx(STag, { shape: "square", size: "xs", color: "grey", label: text })
4611
+ ))
4161
4612
  }
4162
- ) })
4163
- ] });
4164
- }
4613
+ ) });
4614
+ return /* @__PURE__ */ jsxs(
4615
+ RDropdown.Root,
4616
+ {
4617
+ open,
4618
+ onOpenChange: (o) => {
4619
+ setOpen(o);
4620
+ onOpenChange?.(o);
4621
+ },
4622
+ children: [
4623
+ split ? /* @__PURE__ */ jsxs(
4624
+ "div",
4625
+ {
4626
+ ref: splitWrapRef,
4627
+ className: cn("inline-flex items-stretch", className),
4628
+ style: { minWidth: s.splitMinWidth, ...style },
4629
+ children: [
4630
+ /* @__PURE__ */ jsx(
4631
+ "button",
4632
+ {
4633
+ type: "button",
4634
+ disabled,
4635
+ onClick: onLabelClick,
4636
+ className: cn(triggerBase, "flex-1 justify-center rounded-l-[4px] border-r-0"),
4637
+ style: {
4638
+ minHeight: s.height,
4639
+ padding: `0 ${s.paddingX}px`,
4640
+ fontSize: s.fontSize,
4641
+ ...colorVars
4642
+ },
4643
+ children: label
4644
+ }
4645
+ ),
4646
+ /* @__PURE__ */ jsx(RDropdown.Trigger, { asChild: true, children: /* @__PURE__ */ jsx(
4647
+ "button",
4648
+ {
4649
+ ref: splitToggleRef,
4650
+ type: "button",
4651
+ disabled,
4652
+ "aria-label": "\uBA54\uB274 \uC5F4\uAE30",
4653
+ className: cn(triggerBase, "justify-center rounded-r-[4px] border-l"),
4654
+ style: {
4655
+ minHeight: s.height,
4656
+ minWidth: s.height,
4657
+ borderLeftColor: disabled ? "var(--cmp-button-border-disabled)" : splitDivider(color, outline),
4658
+ ...colorVars
4659
+ },
4660
+ children: splitIcon
4661
+ }
4662
+ ) })
4663
+ ]
4664
+ }
4665
+ ) : /* @__PURE__ */ jsx(RDropdown.Trigger, { asChild: true, children: /* @__PURE__ */ jsxs(
4666
+ "button",
4667
+ {
4668
+ type: "button",
4669
+ disabled,
4670
+ className: cn(triggerBase, "justify-between rounded-[4px]", className),
4671
+ style: {
4672
+ minWidth: s.minWidth,
4673
+ minHeight: s.height,
4674
+ padding: `0 ${s.paddingX}px`,
4675
+ gap: s.gap,
4676
+ fontSize: s.fontSize,
4677
+ ...colorVars,
4678
+ ...style
4679
+ },
4680
+ children: [
4681
+ /* @__PURE__ */ jsx("span", { className: "flex-1 truncate text-center", children: label }),
4682
+ caret
4683
+ ]
4684
+ }
4685
+ ) }),
4686
+ menu
4687
+ ]
4688
+ }
4689
+ );
4690
+ }
4691
+ );
4692
+ SDropdownButton.displayName = "SDropdownButton";
4165
4693
  function SSwitch({
4166
4694
  value = false,
4167
4695
  leftLabel,
@@ -4243,142 +4771,6 @@ function SToggle({
4243
4771
  }
4244
4772
  );
4245
4773
  }
4246
- var HIDE_DELAY_MS = 100;
4247
- function useBody(content, message = []) {
4248
- if (content != null) return content;
4249
- if (message.length === 0) return null;
4250
- const singleLine = message.length === 1;
4251
- return /* @__PURE__ */ jsx(Fragment, { children: message.map((line, i) => /* @__PURE__ */ jsx(
4252
- "div",
4253
- {
4254
- className: singleLine ? "leading-[24px]" : void 0,
4255
- dangerouslySetInnerHTML: { __html: sanitizeInlineHtml(line) }
4256
- },
4257
- i
4258
- )) });
4259
- }
4260
- var STooltip = forwardRef(function STooltip2({
4261
- content,
4262
- message = [],
4263
- trigger = "hover",
4264
- placement = "top",
4265
- tooltipType = "default",
4266
- useClose = false,
4267
- disabled = false,
4268
- children,
4269
- icon = "helpOutline",
4270
- iconSize = 12,
4271
- color = "#01BB4B",
4272
- ariaLabel,
4273
- className,
4274
- triggerClassName,
4275
- style
4276
- }, ref) {
4277
- const portalContainer = usePortalContainer();
4278
- const [open, setOpen] = useState(false);
4279
- const hideTimer = useRef(void 0);
4280
- const cancelHide = () => {
4281
- if (hideTimer.current) {
4282
- clearTimeout(hideTimer.current);
4283
- hideTimer.current = void 0;
4284
- }
4285
- };
4286
- const openNow = () => {
4287
- cancelHide();
4288
- setOpen(true);
4289
- };
4290
- const startHide = () => {
4291
- if (useClose) return;
4292
- cancelHide();
4293
- hideTimer.current = setTimeout(() => setOpen(false), HIDE_DELAY_MS);
4294
- };
4295
- useImperativeHandle(
4296
- ref,
4297
- () => ({
4298
- show: () => {
4299
- cancelHide();
4300
- setOpen(true);
4301
- },
4302
- hide: () => {
4303
- cancelHide();
4304
- setOpen(false);
4305
- }
4306
- }),
4307
- []
4308
- );
4309
- const body = useBody(content, message);
4310
- const bg = `var(--cmp-tooltip-${tooltipType}-bg)`;
4311
- const fg = `var(--cmp-tooltip-${tooltipType}-content)`;
4312
- const triggerNode = children ?? /* @__PURE__ */ jsx("span", { className: cn("inline-flex cursor-pointer", triggerClassName), "aria-label": ariaLabel, children: /* @__PURE__ */ jsx(SIcon, { name: icon, size: iconSize, color }) });
4313
- if (disabled || body == null) return /* @__PURE__ */ jsx(Fragment, { children: triggerNode });
4314
- const isHover = trigger === "hover";
4315
- const contentClass = cn(
4316
- "z-50 w-fit whitespace-nowrap rounded-[6px] px-[16px] py-[12px] text-[12px] leading-[20px] shadow-normal-sm",
4317
- FLOATING_SLIDE_ANIM,
4318
- className
4319
- );
4320
- const contentStyle = {
4321
- background: bg,
4322
- color: fg,
4323
- fontWeight: tooltipType === "default" ? 500 : 700,
4324
- ...style
4325
- };
4326
- return /* @__PURE__ */ jsxs(RPopover2.Root, { open, onOpenChange: setOpen, children: [
4327
- isHover ? (
4328
- // hover: Anchor(위치 기준) + 직접 mouse 핸들러 — 클릭으로 토글되지 않도록 Trigger 미사용
4329
- /* @__PURE__ */ jsx(RPopover2.Anchor, { asChild: true, children: /* @__PURE__ */ jsx(
4330
- "span",
4331
- {
4332
- className: "inline-flex",
4333
- onMouseEnter: openNow,
4334
- onMouseLeave: startHide,
4335
- onFocus: openNow,
4336
- onBlur: startHide,
4337
- children: triggerNode
4338
- }
4339
- ) })
4340
- ) : /* @__PURE__ */ jsx(RPopover2.Trigger, { asChild: true, children: triggerNode }),
4341
- /* @__PURE__ */ jsx(RPopover2.Portal, { container: portalContainer, children: /* @__PURE__ */ jsxs(
4342
- RPopover2.Content,
4343
- {
4344
- side: placement,
4345
- sideOffset: 8,
4346
- className: contentClass,
4347
- style: contentStyle,
4348
- onOpenAutoFocus: (e) => e.preventDefault(),
4349
- onInteractOutside: (e) => {
4350
- if (useClose) e.preventDefault();
4351
- },
4352
- onEscapeKeyDown: (e) => {
4353
- if (useClose) e.preventDefault();
4354
- },
4355
- onMouseEnter: isHover ? cancelHide : void 0,
4356
- onMouseLeave: isHover ? startHide : void 0,
4357
- children: [
4358
- /* @__PURE__ */ jsxs("div", { className: "flex items-start gap-[12px]", children: [
4359
- /* @__PURE__ */ jsx("div", { className: "min-w-0 flex-1", children: body }),
4360
- useClose && /* @__PURE__ */ jsx(
4361
- SGhostButton,
4362
- {
4363
- icon: "close",
4364
- size: "xs",
4365
- intent: tooltipType === "default" ? "inverse" : "default",
4366
- ariaLabel: "\uB2EB\uAE30",
4367
- className: "shrink-0",
4368
- onClick: () => {
4369
- cancelHide();
4370
- setOpen(false);
4371
- }
4372
- }
4373
- )
4374
- ] }),
4375
- /* @__PURE__ */ jsx(RPopover2.Arrow, { width: 16, height: 12, style: { fill: bg } })
4376
- ]
4377
- }
4378
- ) })
4379
- ] });
4380
- });
4381
- STooltip.displayName = "STooltip";
4382
4774
  var BUTTON_PRESET = {
4383
4775
  default: { color: "primary", outline: false },
4384
4776
  accent: { color: "primary", outline: false },
@@ -7356,8 +7748,10 @@ var STable = forwardRef(function STable2({
7356
7748
  stickyColumn,
7357
7749
  radius = "default",
7358
7750
  noDataLabel = "\uB370\uC774\uD130\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4.",
7751
+ noDataSlot,
7359
7752
  isLoading = false,
7360
7753
  dense = false,
7754
+ noHover = false,
7361
7755
  pagination,
7362
7756
  onPageChange,
7363
7757
  useInternalPagination = false,
@@ -7443,7 +7837,10 @@ var STable = forwardRef(function STable2({
7443
7837
  );
7444
7838
  const handleScroll = useCallback(() => {
7445
7839
  const el = scrollRef.current;
7446
- if (!el) return;
7840
+ if (!el) {
7841
+ setHeaderGutter(0);
7842
+ return;
7843
+ }
7447
7844
  const header = headerScrollRef.current;
7448
7845
  if (header) header.scrollLeft = el.scrollLeft;
7449
7846
  setHeaderGutter(el.offsetWidth - el.clientWidth);
@@ -7575,6 +7972,7 @@ var STable = forwardRef(function STable2({
7575
7972
  bodyRows = rows.slice(pageInfo.startIndex, pageInfo.endIndex);
7576
7973
  }
7577
7974
  const isNoData = rowCount === 0 && !isLoading;
7975
+ const showNoDataSlot = isNoData && noDataSlot != null;
7578
7976
  const showPagination = !useVirtualScroll && (pagination != null || useInternalPagination);
7579
7977
  const lastPage = useInternalPagination ? Math.max(1, Math.ceil(rowCount / (innerRowsPerPage || 1))) : pagination?.lastPage ?? Math.max(1, Math.ceil(rowCount / (pagination?.rowsPerPage ?? 10)));
7580
7978
  const displayPage = useInternalPagination ? currentPage : pagination?.page ?? 1;
@@ -7636,6 +8034,12 @@ var STable = forwardRef(function STable2({
7636
8034
  isRightEdge && scrolledRight && "shadow-[-5px_0_8px_0_rgba(34,34,34,0.1)]"
7637
8035
  );
7638
8036
  };
8037
+ const bodyScrollClass = cn(
8038
+ "min-h-0 flex-1 overflow-auto border-t border-solid border-[color:var(--cmp-table-border-color)]",
8039
+ SCROLLBAR_CLASS,
8040
+ SCROLLBAR_TRACK_BG_CLASS,
8041
+ SCROLLBAR_TRACK_BORDER_CLASS
8042
+ );
7639
8043
  const colgroup = /* @__PURE__ */ jsxs("colgroup", { children: [
7640
8044
  selectable && /* @__PURE__ */ jsx("col", { style: { width: SELECTABLE_COLUMN_WIDTH } }),
7641
8045
  visibleCols.map((col, i) => /* @__PURE__ */ jsx("col", { style: col.autoWidth ? void 0 : { width: columnWidths[i] } }, col.name))
@@ -7757,97 +8161,106 @@ var STable = forwardRef(function STable2({
7757
8161
  )
7758
8162
  }
7759
8163
  ),
7760
- /* @__PURE__ */ jsx(
7761
- "div",
7762
- {
7763
- ref: scrollRef,
7764
- onScroll: handleScroll,
7765
- className: cn(
7766
- // 헤더 하단 구분선은 body 상단 border로 그린다. body 래퍼는 스크롤바를 포함한
7767
- // 전체 폭을 차지하므로(스크롤바는 border 안쪽) 헤더 거터의 border-right와 미터가
7768
- // 생기지 않아 색·길이가 균일한 한 줄이 된다.
7769
- "min-h-0 flex-1 overflow-auto border-t border-solid border-[color:var(--cmp-table-border-color)]",
7770
- SCROLLBAR_CLASS,
7771
- SCROLLBAR_TRACK_BG_CLASS,
7772
- SCROLLBAR_TRACK_BORDER_CLASS,
7773
- // 원본 sd-table__scroll-container--loading/--no-data: 로딩·데이터 없음 시 스크롤 차단
7774
- (isLoading || rowCount === 0) && "overflow-hidden"
7775
- ),
7776
- children: /* @__PURE__ */ jsxs(
7777
- "table",
7778
- {
7779
- className: "w-full table-fixed border-separate border-spacing-0 text-left",
7780
- style: { fontSize: 12 },
7781
- children: [
7782
- colgroup,
7783
- /* @__PURE__ */ jsxs("tbody", { children: [
7784
- useVirtualScroll && topSpacer > 0 && /* @__PURE__ */ jsx("tr", { "aria-hidden": true, style: { height: topSpacer }, children: /* @__PURE__ */ jsx("td", { colSpan: totalColSpan, className: "p-0" }) }),
7785
- rowCount === 0 ? null : bodyRows.map((row, ri) => {
7786
- const isSel = selectedKeys.has(row[rowKey]);
7787
- const rowBg = "bg-white";
7788
- return /* @__PURE__ */ jsxs(
7789
- "tr",
7790
- {
7791
- onClick: () => onRowClick?.(row),
7792
- className: cn(
7793
- "group/table-row hover:bg-[var(--color-grey-05)]",
7794
- onRowClick && "cursor-pointer"
7795
- ),
7796
- style: { height: useVirtualScroll ? effectiveRowHeight : rowH },
7797
- children: [
7798
- selectable && /* @__PURE__ */ jsx(
7799
- "td",
7800
- {
7801
- className: cn(
7802
- // 원본 .td--selected: 48px 고정폭, 항상 left sticky, 체크박스 중앙정렬
7803
- "sticky left-0 z-[2] border-b border-solid border-[color:var(--cmp-table-border-color)] align-middle group-hover/table-row:bg-[var(--color-grey-05)]",
7804
- rowBg,
7805
- stickyLeft === 0 && scrolledLeft && "shadow-[5px_0_8px_0_rgba(34,34,34,0.1)]"
7806
- ),
7807
- style: {
7808
- width: SELECTABLE_COLUMN_WIDTH,
7809
- minWidth: SELECTABLE_COLUMN_WIDTH,
7810
- maxWidth: SELECTABLE_COLUMN_WIDTH
7811
- },
7812
- onClick: (e) => e.stopPropagation(),
7813
- children: /* @__PURE__ */ jsx("div", { className: "flex items-center justify-center", children: /* @__PURE__ */ jsx(SCheckbox, { value: isSel, onValueChange: () => toggleRow(row) }) })
7814
- }
8164
+ showNoDataSlot ? /* @__PURE__ */ jsx("div", { className: cn(bodyScrollClass, "pointer-events-auto bg-white"), children: /* @__PURE__ */ jsx("div", { className: "flex h-full min-h-[60px] w-full items-center justify-center", children: noDataSlot }) }) : (
8165
+ /* 바디: 세로 스크롤은 이 컨테이너에만 생긴다 (헤더 제외) */
8166
+ /* @__PURE__ */ jsx(
8167
+ "div",
8168
+ {
8169
+ ref: scrollRef,
8170
+ onScroll: handleScroll,
8171
+ className: cn(
8172
+ bodyScrollClass,
8173
+ // 원본 sd-table__scroll-container--loading/--no-data: 로딩·데이터 없음 스크롤 차단
8174
+ (isLoading || rowCount === 0) && "overflow-hidden"
8175
+ ),
8176
+ children: /* @__PURE__ */ jsxs(
8177
+ "table",
8178
+ {
8179
+ className: "w-full table-fixed border-separate border-spacing-0 text-left",
8180
+ style: { fontSize: 12 },
8181
+ children: [
8182
+ colgroup,
8183
+ /* @__PURE__ */ jsxs("tbody", { children: [
8184
+ useVirtualScroll && topSpacer > 0 && /* @__PURE__ */ jsx("tr", { "aria-hidden": true, style: { height: topSpacer }, children: /* @__PURE__ */ jsx("td", { colSpan: totalColSpan, className: "p-0" }) }),
8185
+ rowCount === 0 ? null : bodyRows.map((row, ri) => {
8186
+ const isSel = selectedKeys.has(row[rowKey]);
8187
+ const rowBg = "bg-white";
8188
+ return /* @__PURE__ */ jsxs(
8189
+ "tr",
8190
+ {
8191
+ onClick: () => onRowClick?.(row),
8192
+ className: cn(
8193
+ "group/table-row",
8194
+ !noHover && "hover:bg-[var(--color-grey-05)]",
8195
+ onRowClick && "cursor-pointer"
7815
8196
  ),
7816
- visibleCols.map((col, i) => /* @__PURE__ */ jsx(
7817
- "td",
7818
- {
7819
- className: cn(
8197
+ style: { height: useVirtualScroll ? effectiveRowHeight : rowH },
8198
+ children: [
8199
+ selectable && /* @__PURE__ */ jsx(
8200
+ "td",
8201
+ {
8202
+ className: cn(
8203
+ // 원본 .td--selected: 48px 고정폭, 항상 left sticky, 체크박스 중앙정렬
8204
+ "sticky left-0 z-[2] border-b border-solid border-[color:var(--cmp-table-border-color)] align-middle",
8205
+ rowBg,
8206
+ !noHover && "group-hover/table-row:bg-[var(--color-grey-05)]",
8207
+ stickyLeft === 0 && scrolledLeft && "shadow-[5px_0_8px_0_rgba(34,34,34,0.1)]"
8208
+ ),
8209
+ style: {
8210
+ width: SELECTABLE_COLUMN_WIDTH,
8211
+ minWidth: SELECTABLE_COLUMN_WIDTH,
8212
+ maxWidth: SELECTABLE_COLUMN_WIDTH
8213
+ },
8214
+ onClick: (e) => e.stopPropagation(),
8215
+ children: /* @__PURE__ */ jsx("div", { className: "flex items-center justify-center", children: /* @__PURE__ */ jsx(SCheckbox, { value: isSel, onValueChange: () => toggleRow(row) }) })
8216
+ }
8217
+ ),
8218
+ visibleCols.map((col, i) => {
8219
+ const tdClassName = cn(
7820
8220
  // 원본 .td: 컬럼 폭에 맞춰 내용 말줄임(overflow hidden + ellipsis) + 행 구분선(border-b)
7821
8221
  // 셀 배경은 흰색으로 채워 뒤 배경이 비치지 않게 하고, hover 시 행 배경(grey_05)을 따른다.
7822
8222
  "overflow-hidden text-ellipsis whitespace-nowrap border-b border-solid border-[color:var(--cmp-table-border-color)] text-[12px] leading-[20px] text-[color:var(--sys-color-fg-primary)]",
7823
8223
  rowBg,
7824
- "group-hover/table-row:bg-[var(--color-grey-05)]",
8224
+ !noHover && "group-hover/table-row:bg-[var(--color-grey-05)]",
7825
8225
  stickyShadowClass(i),
7826
8226
  typeof col.tdClass === "function" ? col.tdClass(row) : col.tdClass
7827
- ),
7828
- style: {
8227
+ );
8228
+ const tdStyle = {
7829
8229
  paddingLeft: cellPadX,
7830
8230
  paddingRight: cellPadX,
7831
8231
  paddingTop: cellPadY,
7832
8232
  paddingBottom: cellPadY,
7833
8233
  textAlign: col.align ?? "left",
7834
8234
  ...cellStyle(i)
7835
- },
7836
- children: col.render ? col.render(row, cellValue(col, row)) : cellValue(col, row)
7837
- },
7838
- col.name
7839
- ))
7840
- ]
7841
- },
7842
- row[rowKey] ?? ri
7843
- );
7844
- }),
7845
- useVirtualScroll && bottomSpacer > 0 && /* @__PURE__ */ jsx("tr", { "aria-hidden": true, style: { height: bottomSpacer }, children: /* @__PURE__ */ jsx("td", { colSpan: totalColSpan, className: "p-0" }) })
7846
- ] })
7847
- ]
7848
- }
7849
- )
7850
- }
8235
+ };
8236
+ if (col.renderCell) {
8237
+ const cell = col.renderCell({
8238
+ row,
8239
+ value: cellValue(col, row),
8240
+ column: col,
8241
+ colIndex: i,
8242
+ rowIndex: ri,
8243
+ isSelected: isSel,
8244
+ className: tdClassName,
8245
+ style: tdStyle
8246
+ });
8247
+ if (cell == null || cell === false) return null;
8248
+ return /* @__PURE__ */ jsx(Fragment$1, { children: cell }, col.name);
8249
+ }
8250
+ return /* @__PURE__ */ jsx("td", { className: tdClassName, style: tdStyle, children: col.render ? col.render(row, cellValue(col, row)) : cellValue(col, row) }, col.name);
8251
+ })
8252
+ ]
8253
+ },
8254
+ row[rowKey] ?? ri
8255
+ );
8256
+ }),
8257
+ useVirtualScroll && bottomSpacer > 0 && /* @__PURE__ */ jsx("tr", { "aria-hidden": true, style: { height: bottomSpacer }, children: /* @__PURE__ */ jsx("td", { colSpan: totalColSpan, className: "p-0" }) })
8258
+ ] })
8259
+ ]
8260
+ }
8261
+ )
8262
+ }
8263
+ )
7851
8264
  ),
7852
8265
  isNoData && /* @__PURE__ */ jsxs(Fragment, { children: [
7853
8266
  /* @__PURE__ */ jsx(
@@ -7857,7 +8270,7 @@ var STable = forwardRef(function STable2({
7857
8270
  className: "pointer-events-none absolute left-0 right-0 top-0 z-[31] h-[var(--cmp-table-header-height)] bg-white/60"
7858
8271
  }
7859
8272
  ),
7860
- /* @__PURE__ */ jsx("div", { className: "pointer-events-none absolute bottom-0 left-0 right-0 top-[var(--cmp-table-header-height)] z-[30] flex items-center justify-center bg-white/60 text-[12px] text-[color:var(--color-grey-65)]", children: /* @__PURE__ */ jsx("div", { className: "flex min-h-[60px] w-full items-center justify-center", children: noDataLabel }) })
8273
+ !showNoDataSlot && /* @__PURE__ */ jsx("div", { className: "pointer-events-none absolute bottom-0 left-0 right-0 top-[var(--cmp-table-header-height)] z-[30] flex items-center justify-center bg-white/60 text-[12px] text-[color:var(--color-grey-65)]", children: /* @__PURE__ */ jsx("div", { className: "flex min-h-[60px] w-full items-center justify-center", children: noDataLabel }) })
7861
8274
  ] }),
7862
8275
  isLoading && /* @__PURE__ */ jsx("div", { className: "absolute inset-0 z-30 flex items-center justify-center bg-white/60", children: /* @__PURE__ */ jsx(SCircleProgress, { indeterminate: true }) })
7863
8276
  ]
@@ -8295,7 +8708,7 @@ var SNumberInput = forwardRef(function SNumberInput2({
8295
8708
  const [display, setDisplay] = useState(() => formatWithCommas(numValue));
8296
8709
  const [ruleError, setRuleError] = useState("");
8297
8710
  const innerRef = useRef(null);
8298
- const setRefs = (el) => {
8711
+ const setRefs2 = (el) => {
8299
8712
  innerRef.current = el;
8300
8713
  if (typeof ref === "function") ref(el);
8301
8714
  else if (ref) ref.current = el;
@@ -8469,7 +8882,7 @@ var SNumberInput = forwardRef(function SNumberInput2({
8469
8882
  /* @__PURE__ */ jsx(
8470
8883
  "input",
8471
8884
  {
8472
- ref: setRefs,
8885
+ ref: setRefs2,
8473
8886
  name,
8474
8887
  type: "text",
8475
8888
  inputMode: useDecimal ? "decimal" : "numeric",
@@ -11967,6 +12380,6 @@ function STimeRangePicker({
11967
12380
  );
11968
12381
  }
11969
12382
 
11970
- export { BADGE_COLORS, BUTTON_COLORS, BUTTON_SIZES, COLOR_KEYS, GNB_COLORS, GNB_COMMON, GNB_FOLD_MS, GNB_HEADER, GNB_MENU, GNB_MENU_WIDTH, GNB_RAIL, GNB_RAIL_WIDTH, ICONS, PAGE_BACKGROUNDS, SActionModal, SBadge, SBarcodeInput, SButton, SCROLL_AREA_AXES, SCalendar, SCallout, SCard, SCheckbox, SChip, SChipInput, SCircleProgress, SConfirmModal, SDatePicker, SDateRangePicker, SDivider, SDropdownButton, SExpansionItem, SField, SFilePicker, SForm, SGhostButton, SGnb, SGuide, SIcon, SInput, SKeyValueTable, SLayout, SLayoutContext, SLinearProgress, SLoadingContainer, SLoadingModal, SLoadingViewport, SModal, SNumberInput, SPage, SPagination, SPopover, SPopup, SPortal, SRadio, SRadioButton, SRadioGroup, SScrollArea, SSelect, SStepper, SSwitch, STEPPER_SIZES, STable, STableBar, STabs, STag, STextLink, STextarea, STimePicker, STimeRangePicker, SToast, SToastContainer, SToggle, STooltip, TAG_COLORS, TAG_SHAPES, TAG_SIZES, TIMEPICKER_SIZES, TIMEPICKER_SIZE_CONFIG, buttonPreset, cn, findGnbAncestors, findGnbRailValue, isColorKey, loading, resolveColor, useSLayout };
12383
+ export { BADGE_COLORS, BUTTON_COLORS, BUTTON_SIZES, COLOR_KEYS, GNB_COLORS, GNB_COMMON, GNB_FOLD_MS, GNB_HEADER, GNB_MENU, GNB_MENU_WIDTH, GNB_RAIL, GNB_RAIL_WIDTH, ICONS, PAGE_BACKGROUNDS, SActionModal, SBadge, SBarcodeInput, SButton, SCROLL_AREA_AXES, SCalendar, SCallout, SCard, SCheckbox, SChip, SChipInput, SCircleProgress, SConfirmModal, SDatePicker, SDateRangePicker, SDivider, SDraggableItem, SDropdownButton, SExpansionItem, SField, SFilePicker, SForm, SGhostButton, SGnb, SGuide, SIcon, SInput, SKeyValueTable, SLayout, SLayoutContext, SLinearProgress, SList, SListItem, SLoadingContainer, SLoadingModal, SLoadingViewport, SModal, SNumberInput, SPage, SPagination, SPopover, SPopup, SPortal, SRadio, SRadioButton, SRadioGroup, SScrollArea, SSectionHeaderCard2 as SSectionHeaderCard, SSelect, SStepper, SSwitch, STEPPER_SIZES, STable, STableBar, STabs, STag, STextLink, STextarea, STimePicker, STimeRangePicker, SToast, SToastContainer, SToggle, STooltip, TAG_COLORS, TAG_SHAPES, TAG_SIZES, TIMEPICKER_SIZES, TIMEPICKER_SIZE_CONFIG, buttonPreset, cn, findGnbAncestors, findGnbRailValue, isColorKey, loading, resolveColor, useSLayout };
11971
12384
  //# sourceMappingURL=index.js.map
11972
12385
  //# sourceMappingURL=index.js.map