@tonyarbor/components 0.2.1 → 0.6.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 (118) hide show
  1. package/dist/Avatar.d.mts +42 -0
  2. package/dist/Avatar.d.ts +42 -0
  3. package/dist/Avatar.js +158 -0
  4. package/dist/Avatar.js.map +1 -0
  5. package/dist/Avatar.mjs +7 -0
  6. package/dist/Avatar.mjs.map +1 -0
  7. package/dist/Breadcrumbs.d.mts +51 -0
  8. package/dist/Breadcrumbs.d.ts +51 -0
  9. package/dist/Breadcrumbs.js +276 -0
  10. package/dist/Breadcrumbs.js.map +1 -0
  11. package/dist/Breadcrumbs.mjs +7 -0
  12. package/dist/Breadcrumbs.mjs.map +1 -0
  13. package/dist/ButtonSegmented.d.mts +61 -0
  14. package/dist/ButtonSegmented.d.ts +61 -0
  15. package/dist/ButtonSegmented.js +167 -0
  16. package/dist/ButtonSegmented.js.map +1 -0
  17. package/dist/ButtonSegmented.mjs +7 -0
  18. package/dist/ButtonSegmented.mjs.map +1 -0
  19. package/dist/ListRow.d.mts +72 -0
  20. package/dist/ListRow.d.ts +72 -0
  21. package/dist/ListRow.js +194 -0
  22. package/dist/ListRow.js.map +1 -0
  23. package/dist/ListRow.mjs +7 -0
  24. package/dist/ListRow.mjs.map +1 -0
  25. package/dist/ListRowMultiLine.d.mts +56 -0
  26. package/dist/ListRowMultiLine.d.ts +56 -0
  27. package/dist/ListRowMultiLine.js +182 -0
  28. package/dist/ListRowMultiLine.js.map +1 -0
  29. package/dist/ListRowMultiLine.mjs +7 -0
  30. package/dist/ListRowMultiLine.mjs.map +1 -0
  31. package/dist/Logo.d.mts +39 -0
  32. package/dist/Logo.d.ts +39 -0
  33. package/dist/Logo.js +119 -0
  34. package/dist/Logo.js.map +1 -0
  35. package/dist/Logo.mjs +7 -0
  36. package/dist/Logo.mjs.map +1 -0
  37. package/dist/SearchGlobal.d.mts +45 -0
  38. package/dist/SearchGlobal.d.ts +45 -0
  39. package/dist/SearchGlobal.js +209 -0
  40. package/dist/SearchGlobal.js.map +1 -0
  41. package/dist/SearchGlobal.mjs +7 -0
  42. package/dist/SearchGlobal.mjs.map +1 -0
  43. package/dist/SearchOnPage.d.mts +45 -0
  44. package/dist/SearchOnPage.d.ts +45 -0
  45. package/dist/SearchOnPage.js +171 -0
  46. package/dist/SearchOnPage.js.map +1 -0
  47. package/dist/SearchOnPage.mjs +7 -0
  48. package/dist/SearchOnPage.mjs.map +1 -0
  49. package/dist/Section.d.mts +57 -0
  50. package/dist/Section.d.ts +57 -0
  51. package/dist/Section.js +72 -0
  52. package/dist/Section.js.map +1 -0
  53. package/dist/Section.mjs +7 -0
  54. package/dist/Section.mjs.map +1 -0
  55. package/dist/SectionHeading.d.mts +111 -0
  56. package/dist/SectionHeading.d.ts +111 -0
  57. package/dist/SectionHeading.js +385 -0
  58. package/dist/SectionHeading.js.map +1 -0
  59. package/dist/SectionHeading.mjs +8 -0
  60. package/dist/SectionHeading.mjs.map +1 -0
  61. package/dist/SectionHeadingInteractive.d.mts +67 -0
  62. package/dist/SectionHeadingInteractive.d.ts +67 -0
  63. package/dist/SectionHeadingInteractive.js +225 -0
  64. package/dist/SectionHeadingInteractive.js.map +1 -0
  65. package/dist/SectionHeadingInteractive.mjs +7 -0
  66. package/dist/SectionHeadingInteractive.mjs.map +1 -0
  67. package/dist/SectionIcon.d.mts +35 -0
  68. package/dist/SectionIcon.d.ts +35 -0
  69. package/dist/SectionIcon.js +142 -0
  70. package/dist/SectionIcon.js.map +1 -0
  71. package/dist/SectionIcon.mjs +7 -0
  72. package/dist/SectionIcon.mjs.map +1 -0
  73. package/dist/SubSectionHeading.d.mts +75 -0
  74. package/dist/SubSectionHeading.d.ts +75 -0
  75. package/dist/SubSectionHeading.js +225 -0
  76. package/dist/SubSectionHeading.js.map +1 -0
  77. package/dist/SubSectionHeading.mjs +7 -0
  78. package/dist/SubSectionHeading.mjs.map +1 -0
  79. package/dist/SubSectionInteractive.d.mts +65 -0
  80. package/dist/SubSectionInteractive.d.ts +65 -0
  81. package/dist/SubSectionInteractive.js +211 -0
  82. package/dist/SubSectionInteractive.js.map +1 -0
  83. package/dist/SubSectionInteractive.mjs +7 -0
  84. package/dist/SubSectionInteractive.mjs.map +1 -0
  85. package/dist/chunk-7NYBJKJS.mjs +106 -0
  86. package/dist/chunk-7NYBJKJS.mjs.map +1 -0
  87. package/dist/chunk-ALLCJATI.mjs +189 -0
  88. package/dist/chunk-ALLCJATI.mjs.map +1 -0
  89. package/dist/chunk-B7RX3TPX.mjs +135 -0
  90. package/dist/chunk-B7RX3TPX.mjs.map +1 -0
  91. package/dist/chunk-F6JVEIWC.mjs +158 -0
  92. package/dist/chunk-F6JVEIWC.mjs.map +1 -0
  93. package/dist/chunk-GHATS25Y.mjs +249 -0
  94. package/dist/chunk-GHATS25Y.mjs.map +1 -0
  95. package/dist/chunk-ILLGBZ6R.mjs +131 -0
  96. package/dist/chunk-ILLGBZ6R.mjs.map +1 -0
  97. package/dist/chunk-JSG27ZZS.mjs +122 -0
  98. package/dist/chunk-JSG27ZZS.mjs.map +1 -0
  99. package/dist/chunk-NNYU4DPD.mjs +83 -0
  100. package/dist/chunk-NNYU4DPD.mjs.map +1 -0
  101. package/dist/chunk-ODKT7LGV.mjs +146 -0
  102. package/dist/chunk-ODKT7LGV.mjs.map +1 -0
  103. package/dist/chunk-RL4G7MR3.mjs +189 -0
  104. package/dist/chunk-RL4G7MR3.mjs.map +1 -0
  105. package/dist/chunk-RQP6ZGD7.mjs +240 -0
  106. package/dist/chunk-RQP6ZGD7.mjs.map +1 -0
  107. package/dist/chunk-UPBHDBAK.mjs +173 -0
  108. package/dist/chunk-UPBHDBAK.mjs.map +1 -0
  109. package/dist/chunk-X2CW5GF3.mjs +175 -0
  110. package/dist/chunk-X2CW5GF3.mjs.map +1 -0
  111. package/dist/chunk-YJ36ZZJQ.mjs +36 -0
  112. package/dist/chunk-YJ36ZZJQ.mjs.map +1 -0
  113. package/dist/index.d.mts +14 -0
  114. package/dist/index.d.ts +14 -0
  115. package/dist/index.js +2102 -0
  116. package/dist/index.js.map +1 -1
  117. package/dist/index.mjs +56 -0
  118. package/package.json +71 -1
@@ -0,0 +1,240 @@
1
+ // src/Breadcrumbs/Breadcrumbs.tsx
2
+ import * as React from "react";
3
+ import { Link, ChevronDown, MoreHorizontal } from "lucide-react";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+ var Breadcrumbs = React.forwardRef(
6
+ ({
7
+ items,
8
+ onCopy,
9
+ className,
10
+ style,
11
+ "data-testid": dataTestId
12
+ }, ref) => {
13
+ const [hoveredIndex, setHoveredIndex] = React.useState(null);
14
+ const [focusedIndex, setFocusedIndex] = React.useState(null);
15
+ const [showCopyTooltip, setShowCopyTooltip] = React.useState(false);
16
+ const [ellipsisFocused, setEllipsisFocused] = React.useState(false);
17
+ const [ellipsisHovered, setEllipsisHovered] = React.useState(false);
18
+ const displayItems = React.useMemo(() => {
19
+ if (items.length > 6) {
20
+ return [items[0], { label: "...", isEllipsis: true }, items[items.length - 1]];
21
+ }
22
+ return items;
23
+ }, [items]);
24
+ const handleCopy = () => {
25
+ onCopy?.();
26
+ const trail = items.map((item) => item.label).join(" / ");
27
+ navigator.clipboard.writeText(trail);
28
+ };
29
+ const containerStyles = {
30
+ display: "flex",
31
+ alignItems: "center",
32
+ gap: "8px",
33
+ ...style
34
+ };
35
+ const breadcrumbItemStyles = (index, isActive, isEllipsis) => {
36
+ const isFocused = focusedIndex === index;
37
+ if (isEllipsis) {
38
+ return {
39
+ display: "flex",
40
+ alignItems: "center",
41
+ gap: "4px",
42
+ height: "24px",
43
+ overflow: "hidden"
44
+ };
45
+ }
46
+ return {
47
+ display: "flex",
48
+ alignItems: "center",
49
+ gap: "4px",
50
+ height: "24px",
51
+ overflow: "hidden",
52
+ backgroundColor: isFocused ? "rgba(255, 255, 255, 0.01)" : "transparent",
53
+ borderRadius: "99px",
54
+ boxShadow: isFocused ? "0px 0px 0px 3px #3cad51" : "none",
55
+ padding: isFocused ? "0 6px" : "0 2px",
56
+ margin: isFocused ? "0" : "0 4px",
57
+ cursor: isActive ? "default" : "pointer",
58
+ textDecoration: "none"
59
+ };
60
+ };
61
+ const linkStyles = (isActive, isHovered) => ({
62
+ fontFamily: isActive ? "'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif" : "'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif",
63
+ fontSize: "13px",
64
+ fontWeight: isActive ? 600 : 400,
65
+ color: isActive ? isHovered ? "#0e8a0e" : "#2f2f2f" : isHovered ? "#0e8a0e" : "#595959",
66
+ lineHeight: "1.5",
67
+ whiteSpace: "nowrap"
68
+ });
69
+ const dividerStyles = {
70
+ fontFamily: "'PT Sans', sans-serif",
71
+ fontSize: "14px",
72
+ color: "#595959",
73
+ lineHeight: "normal",
74
+ whiteSpace: "nowrap"
75
+ };
76
+ const ellipsisButtonStyles = {
77
+ display: "flex",
78
+ alignItems: "center",
79
+ justifyContent: "center",
80
+ width: "24px",
81
+ height: "24px",
82
+ borderRadius: "99px",
83
+ border: "none",
84
+ background: "transparent",
85
+ cursor: "pointer",
86
+ backgroundColor: ellipsisFocused ? "rgba(255, 255, 255, 0.01)" : ellipsisHovered ? "#efefef" : "transparent",
87
+ boxShadow: ellipsisFocused ? "0px 0px 0px 3px #3cad51" : "none"
88
+ };
89
+ const copyButtonStyles = {
90
+ display: "flex",
91
+ alignItems: "center",
92
+ justifyContent: "center",
93
+ width: "24px",
94
+ height: "24px",
95
+ borderRadius: "99px",
96
+ border: "none",
97
+ background: showCopyTooltip ? "#efefef" : "transparent",
98
+ cursor: "pointer",
99
+ position: "relative"
100
+ };
101
+ const tooltipStyles = {
102
+ position: "absolute",
103
+ top: "100%",
104
+ left: "50%",
105
+ transform: "translateX(-50%)",
106
+ marginTop: "8px",
107
+ backgroundColor: "#2f2f2f",
108
+ color: "white",
109
+ padding: "12px",
110
+ borderRadius: "8px",
111
+ fontSize: "13px",
112
+ fontFamily: "'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif",
113
+ fontWeight: 400,
114
+ lineHeight: "1.5",
115
+ whiteSpace: "nowrap",
116
+ boxShadow: "0px 4px 12px rgba(32, 32, 32, 0.08)",
117
+ zIndex: 1e3
118
+ };
119
+ return /* @__PURE__ */ jsx(
120
+ "div",
121
+ {
122
+ ref,
123
+ className,
124
+ style: containerStyles,
125
+ "data-testid": dataTestId,
126
+ children: displayItems.map((item, index) => {
127
+ const isActive = index === displayItems.length - 1;
128
+ const isEllipsis = "isEllipsis" in item && item.isEllipsis;
129
+ if (isEllipsis) {
130
+ return /* @__PURE__ */ jsxs(React.Fragment, { children: [
131
+ /* @__PURE__ */ jsx(
132
+ "button",
133
+ {
134
+ style: ellipsisButtonStyles,
135
+ onFocus: () => setEllipsisFocused(true),
136
+ onBlur: () => setEllipsisFocused(false),
137
+ onMouseEnter: () => setEllipsisHovered(true),
138
+ onMouseLeave: () => setEllipsisHovered(false),
139
+ "aria-label": "More breadcrumbs",
140
+ children: /* @__PURE__ */ jsx(
141
+ MoreHorizontal,
142
+ {
143
+ size: 12,
144
+ color: "#2f2f2f",
145
+ strokeWidth: 2,
146
+ style: { display: "block", flexShrink: 0 }
147
+ }
148
+ )
149
+ }
150
+ ),
151
+ /* @__PURE__ */ jsx("span", { style: dividerStyles, children: " /" })
152
+ ] }, `ellipsis-${index}`);
153
+ }
154
+ const breadcrumbItem = item;
155
+ if (isActive) {
156
+ return /* @__PURE__ */ jsxs(React.Fragment, { children: [
157
+ /* @__PURE__ */ jsx(
158
+ "div",
159
+ {
160
+ style: breadcrumbItemStyles(index, true),
161
+ onMouseEnter: () => setHoveredIndex(index),
162
+ onMouseLeave: () => setHoveredIndex(null),
163
+ onFocus: () => setFocusedIndex(index),
164
+ onBlur: () => setFocusedIndex(null),
165
+ tabIndex: 0,
166
+ children: /* @__PURE__ */ jsx("span", { style: linkStyles(true, hoveredIndex === index), children: breadcrumbItem.label })
167
+ }
168
+ ),
169
+ onCopy && /* @__PURE__ */ jsxs(
170
+ "button",
171
+ {
172
+ style: copyButtonStyles,
173
+ onClick: handleCopy,
174
+ onMouseEnter: () => setShowCopyTooltip(true),
175
+ onMouseLeave: () => setShowCopyTooltip(false),
176
+ "aria-label": "Copy breadcrumb trail",
177
+ children: [
178
+ /* @__PURE__ */ jsx(
179
+ Link,
180
+ {
181
+ size: 12,
182
+ color: "#2f2f2f",
183
+ strokeWidth: 2,
184
+ style: { display: "block", flexShrink: 0 }
185
+ }
186
+ ),
187
+ showCopyTooltip && /* @__PURE__ */ jsx("div", { style: tooltipStyles, children: "Copy breadcrumb trail" })
188
+ ]
189
+ }
190
+ )
191
+ ] }, index);
192
+ }
193
+ const Element = breadcrumbItem.href ? "a" : "button";
194
+ return /* @__PURE__ */ jsxs(React.Fragment, { children: [
195
+ /* @__PURE__ */ jsxs(
196
+ Element,
197
+ {
198
+ ...breadcrumbItem.href ? { href: breadcrumbItem.href } : {},
199
+ style: {
200
+ ...breadcrumbItemStyles(index, false),
201
+ border: "none",
202
+ background: "transparent"
203
+ },
204
+ onClick: (e) => {
205
+ if (!breadcrumbItem.href && breadcrumbItem.onClick) {
206
+ e.preventDefault();
207
+ breadcrumbItem.onClick();
208
+ }
209
+ },
210
+ onMouseEnter: () => setHoveredIndex(index),
211
+ onMouseLeave: () => setHoveredIndex(null),
212
+ onFocus: () => setFocusedIndex(index),
213
+ onBlur: () => setFocusedIndex(null),
214
+ children: [
215
+ /* @__PURE__ */ jsx("span", { style: linkStyles(false, hoveredIndex === index), children: breadcrumbItem.label }),
216
+ breadcrumbItem.hasDropdown && /* @__PURE__ */ jsx(
217
+ ChevronDown,
218
+ {
219
+ size: 12,
220
+ color: hoveredIndex === index ? "#0e8a0e" : "#595959",
221
+ strokeWidth: 2,
222
+ style: { marginLeft: "2px", display: "inline-block", flexShrink: 0 }
223
+ }
224
+ )
225
+ ]
226
+ }
227
+ ),
228
+ /* @__PURE__ */ jsx("span", { style: dividerStyles, children: " /" })
229
+ ] }, index);
230
+ })
231
+ }
232
+ );
233
+ }
234
+ );
235
+ Breadcrumbs.displayName = "Breadcrumbs";
236
+
237
+ export {
238
+ Breadcrumbs
239
+ };
240
+ //# sourceMappingURL=chunk-RQP6ZGD7.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/Breadcrumbs/Breadcrumbs.tsx"],"sourcesContent":["import * as React from 'react';\nimport { Link, ChevronDown, MoreHorizontal } from 'lucide-react';\n\nexport interface BreadcrumbItem {\n /**\n * The label to display for this breadcrumb\n */\n label: string;\n /**\n * Optional href for the breadcrumb link\n */\n href?: string;\n /**\n * Optional click handler\n */\n onClick?: () => void;\n /**\n * Whether this breadcrumb has a dropdown menu\n */\n hasDropdown?: boolean;\n}\n\nexport interface BreadcrumbsProps {\n /**\n * Array of breadcrumb items\n */\n items: BreadcrumbItem[];\n /**\n * Callback when copy button is clicked\n */\n onCopy?: () => void;\n /**\n * Custom className\n */\n className?: string;\n /**\n * Custom style\n */\n style?: React.CSSProperties;\n /**\n * Test ID for testing\n */\n 'data-testid'?: string;\n}\n\n/**\n * Breadcrumbs component - Arbor Design System\n *\n * Navigation component showing the current page's location in the site hierarchy.\n * Automatically truncates to show first and last breadcrumb with ellipsis when more than 6 items.\n */\nexport const Breadcrumbs = React.forwardRef<HTMLDivElement, BreadcrumbsProps>(\n (\n {\n items,\n onCopy,\n className,\n style,\n 'data-testid': dataTestId,\n },\n ref\n ) => {\n const [hoveredIndex, setHoveredIndex] = React.useState<number | null>(null);\n const [focusedIndex, setFocusedIndex] = React.useState<number | null>(null);\n const [showCopyTooltip, setShowCopyTooltip] = React.useState(false);\n const [ellipsisFocused, setEllipsisFocused] = React.useState(false);\n const [ellipsisHovered, setEllipsisHovered] = React.useState(false);\n\n // Truncate breadcrumbs if more than 6 items\n const displayItems = React.useMemo(() => {\n if (items.length > 6) {\n // Show first item, ellipsis, and last item\n return [items[0], { label: '...', isEllipsis: true }, items[items.length - 1]];\n }\n return items;\n }, [items]);\n\n const handleCopy = () => {\n onCopy?.();\n // Copy the breadcrumb trail to clipboard\n const trail = items.map(item => item.label).join(' / ');\n navigator.clipboard.writeText(trail);\n };\n\n const containerStyles: React.CSSProperties = {\n display: 'flex',\n alignItems: 'center',\n gap: '8px',\n ...style,\n };\n\n const breadcrumbItemStyles = (index: number, isActive: boolean, isEllipsis?: boolean): React.CSSProperties => {\n const isFocused = focusedIndex === index;\n\n if (isEllipsis) {\n return {\n display: 'flex',\n alignItems: 'center',\n gap: '4px',\n height: '24px',\n overflow: 'hidden',\n };\n }\n\n return {\n display: 'flex',\n alignItems: 'center',\n gap: '4px',\n height: '24px',\n overflow: 'hidden',\n backgroundColor: isFocused ? 'rgba(255, 255, 255, 0.01)' : 'transparent',\n borderRadius: '99px',\n boxShadow: isFocused ? '0px 0px 0px 3px #3cad51' : 'none',\n padding: isFocused ? '0 6px' : '0 2px',\n margin: isFocused ? '0' : '0 4px',\n cursor: isActive ? 'default' : 'pointer',\n textDecoration: 'none',\n };\n };\n\n const linkStyles = (isActive: boolean, isHovered: boolean): React.CSSProperties => ({\n fontFamily: isActive\n ? \"'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif\"\n : \"'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif\",\n fontSize: '13px',\n fontWeight: isActive ? 600 : 400,\n color: isActive\n ? isHovered\n ? '#0e8a0e'\n : '#2f2f2f'\n : isHovered\n ? '#0e8a0e'\n : '#595959',\n lineHeight: '1.5',\n whiteSpace: 'nowrap',\n });\n\n const dividerStyles: React.CSSProperties = {\n fontFamily: \"'PT Sans', sans-serif\",\n fontSize: '14px',\n color: '#595959',\n lineHeight: 'normal',\n whiteSpace: 'nowrap',\n };\n\n const ellipsisButtonStyles: React.CSSProperties = {\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n width: '24px',\n height: '24px',\n borderRadius: '99px',\n border: 'none',\n background: 'transparent',\n cursor: 'pointer',\n backgroundColor: ellipsisFocused ? 'rgba(255, 255, 255, 0.01)' : ellipsisHovered ? '#efefef' : 'transparent',\n boxShadow: ellipsisFocused ? '0px 0px 0px 3px #3cad51' : 'none',\n };\n\n const copyButtonStyles: React.CSSProperties = {\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n width: '24px',\n height: '24px',\n borderRadius: '99px',\n border: 'none',\n background: showCopyTooltip ? '#efefef' : 'transparent',\n cursor: 'pointer',\n position: 'relative',\n };\n\n const tooltipStyles: React.CSSProperties = {\n position: 'absolute',\n top: '100%',\n left: '50%',\n transform: 'translateX(-50%)',\n marginTop: '8px',\n backgroundColor: '#2f2f2f',\n color: 'white',\n padding: '12px',\n borderRadius: '8px',\n fontSize: '13px',\n fontFamily: \"'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif\",\n fontWeight: 400,\n lineHeight: '1.5',\n whiteSpace: 'nowrap',\n boxShadow: '0px 4px 12px rgba(32, 32, 32, 0.08)',\n zIndex: 1000,\n };\n\n return (\n <div\n ref={ref}\n className={className}\n style={containerStyles}\n data-testid={dataTestId}\n >\n {displayItems.map((item, index) => {\n const isActive = index === displayItems.length - 1;\n const isEllipsis = 'isEllipsis' in item && item.isEllipsis;\n\n if (isEllipsis) {\n return (\n <React.Fragment key={`ellipsis-${index}`}>\n <button\n style={ellipsisButtonStyles}\n onFocus={() => setEllipsisFocused(true)}\n onBlur={() => setEllipsisFocused(false)}\n onMouseEnter={() => setEllipsisHovered(true)}\n onMouseLeave={() => setEllipsisHovered(false)}\n aria-label=\"More breadcrumbs\"\n >\n <MoreHorizontal\n size={12}\n color=\"#2f2f2f\"\n strokeWidth={2}\n style={{ display: 'block', flexShrink: 0 }}\n />\n </button>\n <span style={dividerStyles}> /</span>\n </React.Fragment>\n );\n }\n\n const breadcrumbItem = item as BreadcrumbItem;\n\n if (isActive) {\n // Active breadcrumb (last item) - not clickable\n return (\n <React.Fragment key={index}>\n <div\n style={breadcrumbItemStyles(index, true)}\n onMouseEnter={() => setHoveredIndex(index)}\n onMouseLeave={() => setHoveredIndex(null)}\n onFocus={() => setFocusedIndex(index)}\n onBlur={() => setFocusedIndex(null)}\n tabIndex={0}\n >\n <span style={linkStyles(true, hoveredIndex === index)}>\n {breadcrumbItem.label}\n </span>\n </div>\n {/* Copy button - appears immediately after active breadcrumb */}\n {onCopy && (\n <button\n style={copyButtonStyles}\n onClick={handleCopy}\n onMouseEnter={() => setShowCopyTooltip(true)}\n onMouseLeave={() => setShowCopyTooltip(false)}\n aria-label=\"Copy breadcrumb trail\"\n >\n <Link\n size={12}\n color=\"#2f2f2f\"\n strokeWidth={2}\n style={{ display: 'block', flexShrink: 0 }}\n />\n {showCopyTooltip && (\n <div style={tooltipStyles}>Copy breadcrumb trail</div>\n )}\n </button>\n )}\n </React.Fragment>\n );\n }\n\n // Regular breadcrumb link\n const Element = breadcrumbItem.href ? 'a' : 'button';\n return (\n <React.Fragment key={index}>\n <Element\n {...(breadcrumbItem.href ? { href: breadcrumbItem.href } : {})}\n style={{\n ...breadcrumbItemStyles(index, false),\n border: 'none',\n background: 'transparent',\n }}\n onClick={(e) => {\n if (!breadcrumbItem.href && breadcrumbItem.onClick) {\n e.preventDefault();\n breadcrumbItem.onClick();\n }\n }}\n onMouseEnter={() => setHoveredIndex(index)}\n onMouseLeave={() => setHoveredIndex(null)}\n onFocus={() => setFocusedIndex(index)}\n onBlur={() => setFocusedIndex(null)}\n >\n <span style={linkStyles(false, hoveredIndex === index)}>\n {breadcrumbItem.label}\n </span>\n {breadcrumbItem.hasDropdown && (\n <ChevronDown\n size={12}\n color={hoveredIndex === index ? '#0e8a0e' : '#595959'}\n strokeWidth={2}\n style={{ marginLeft: '2px', display: 'inline-block', flexShrink: 0 }}\n />\n )}\n </Element>\n <span style={dividerStyles}> /</span>\n </React.Fragment>\n );\n })}\n </div>\n );\n }\n);\n\nBreadcrumbs.displayName = 'Breadcrumbs';\n"],"mappings":"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","names":[]}
@@ -0,0 +1,173 @@
1
+ // src/SearchGlobal/SearchGlobal.tsx
2
+ import * as React from "react";
3
+ import { Search, X } from "lucide-react";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+ var SearchGlobal = React.forwardRef(
6
+ ({
7
+ value = "",
8
+ onChange,
9
+ onSubmit,
10
+ onClear,
11
+ placeholder = "Search",
12
+ className,
13
+ style,
14
+ "data-testid": dataTestId
15
+ }, ref) => {
16
+ const [isFocused, setIsFocused] = React.useState(false);
17
+ const [isHovered, setIsHovered] = React.useState(false);
18
+ const inputRef = React.useRef(null);
19
+ React.useImperativeHandle(ref, () => inputRef.current);
20
+ const handleFocus = () => {
21
+ setIsFocused(true);
22
+ };
23
+ const handleBlur = () => {
24
+ setIsFocused(false);
25
+ };
26
+ const handleChange = (e) => {
27
+ onChange?.(e.target.value);
28
+ };
29
+ const handleKeyDown = (e) => {
30
+ if (e.key === "Enter") {
31
+ onSubmit?.(value);
32
+ }
33
+ };
34
+ const handleClear = () => {
35
+ onChange?.("");
36
+ onClear?.();
37
+ inputRef.current?.focus();
38
+ };
39
+ const containerStyles = {
40
+ position: "relative",
41
+ width: isFocused ? "300px" : "160px",
42
+ height: "32px",
43
+ backgroundColor: isFocused ? "#ffffff" : isHovered ? "#efefef" : "#f8f8f8",
44
+ borderRadius: "16px",
45
+ padding: "8px 16px",
46
+ display: "flex",
47
+ alignItems: "center",
48
+ gap: isFocused ? "8px" : "8px",
49
+ cursor: "text",
50
+ transition: "all 0.2s ease-in-out",
51
+ boxSizing: "border-box",
52
+ border: isFocused ? "1px solid #efefef" : "none",
53
+ boxShadow: isFocused ? "0px 0px 0px 3px #3cad51" : "none",
54
+ marginLeft: isFocused ? "-140px" : "0",
55
+ // Expand to the left
56
+ ...style
57
+ };
58
+ const iconContainerStyles = {
59
+ display: "flex",
60
+ alignItems: "center",
61
+ justifyContent: "center",
62
+ flexShrink: 0,
63
+ padding: "2px"
64
+ };
65
+ const inputStyles = {
66
+ border: "none",
67
+ outline: "none",
68
+ backgroundColor: "transparent",
69
+ fontFamily: "'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif",
70
+ fontSize: "13px",
71
+ fontWeight: 400,
72
+ color: "#2f2f2f",
73
+ lineHeight: "1.5",
74
+ flex: 1,
75
+ width: "100%",
76
+ minWidth: 0
77
+ };
78
+ const keyboardShortcutStyles = {
79
+ display: "flex",
80
+ alignItems: "center",
81
+ gap: "0px",
82
+ flexShrink: 0
83
+ };
84
+ const keyStyles = {
85
+ border: "1px solid #2f2f2f",
86
+ borderRadius: "5px",
87
+ padding: "0px 3px",
88
+ height: "16px",
89
+ display: "flex",
90
+ alignItems: "center",
91
+ justifyContent: "center",
92
+ fontFamily: "'Work Sans', sans-serif",
93
+ fontSize: "8px",
94
+ fontWeight: 400,
95
+ color: "#2f2f2f",
96
+ letterSpacing: "-0.08px",
97
+ lineHeight: "1.5",
98
+ minWidth: "16px"
99
+ };
100
+ const plusStyles = {
101
+ fontFamily: "'Work Sans', sans-serif",
102
+ fontSize: "8px",
103
+ fontWeight: 400,
104
+ color: "#2f2f2f",
105
+ letterSpacing: "-0.08px",
106
+ lineHeight: "1.5",
107
+ padding: "0 2px"
108
+ };
109
+ const clearButtonStyles = {
110
+ display: "flex",
111
+ alignItems: "center",
112
+ justifyContent: "center",
113
+ flexShrink: 0,
114
+ width: "16px",
115
+ height: "16px",
116
+ cursor: "pointer",
117
+ border: "none",
118
+ background: "none",
119
+ padding: 0
120
+ };
121
+ const showKeyboardShortcut = isHovered && !isFocused;
122
+ const showClearButton = isFocused;
123
+ return /* @__PURE__ */ jsxs(
124
+ "div",
125
+ {
126
+ className,
127
+ style: containerStyles,
128
+ onMouseEnter: () => setIsHovered(true),
129
+ onMouseLeave: () => setIsHovered(false),
130
+ onClick: () => inputRef.current?.focus(),
131
+ "data-testid": dataTestId,
132
+ children: [
133
+ /* @__PURE__ */ jsx("div", { style: iconContainerStyles, children: /* @__PURE__ */ jsx(Search, { size: 12, color: "#2f2f2f", strokeWidth: 2 }) }),
134
+ /* @__PURE__ */ jsx(
135
+ "input",
136
+ {
137
+ ref: inputRef,
138
+ type: "text",
139
+ value,
140
+ onChange: handleChange,
141
+ onFocus: handleFocus,
142
+ onBlur: handleBlur,
143
+ onKeyDown: handleKeyDown,
144
+ placeholder: isFocused ? "" : placeholder,
145
+ style: inputStyles
146
+ }
147
+ ),
148
+ showKeyboardShortcut && /* @__PURE__ */ jsxs("div", { style: keyboardShortcutStyles, children: [
149
+ /* @__PURE__ */ jsx("div", { style: keyStyles, children: "\u2318" }),
150
+ /* @__PURE__ */ jsx("span", { style: plusStyles, children: "+" }),
151
+ /* @__PURE__ */ jsx("div", { style: keyStyles, children: "K" })
152
+ ] }),
153
+ showClearButton && /* @__PURE__ */ jsx(
154
+ "button",
155
+ {
156
+ type: "button",
157
+ onClick: handleClear,
158
+ style: clearButtonStyles,
159
+ "aria-label": "Clear search",
160
+ children: /* @__PURE__ */ jsx(X, { size: 13.333, color: "#2f2f2f", strokeWidth: 2 })
161
+ }
162
+ )
163
+ ]
164
+ }
165
+ );
166
+ }
167
+ );
168
+ SearchGlobal.displayName = "SearchGlobal";
169
+
170
+ export {
171
+ SearchGlobal
172
+ };
173
+ //# sourceMappingURL=chunk-UPBHDBAK.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/SearchGlobal/SearchGlobal.tsx"],"sourcesContent":["import * as React from 'react';\nimport { Search, X } from 'lucide-react';\n\nexport interface SearchGlobalProps {\n /**\n * Value of the search input\n */\n value?: string;\n /**\n * Callback when value changes\n */\n onChange?: (value: string) => void;\n /**\n * Callback when search is submitted\n */\n onSubmit?: (value: string) => void;\n /**\n * Callback when clear button is clicked\n */\n onClear?: () => void;\n /**\n * Placeholder text\n */\n placeholder?: string;\n /**\n * Custom className\n */\n className?: string;\n /**\n * Custom style\n */\n style?: React.CSSProperties;\n /**\n * Test ID for testing\n */\n 'data-testid'?: string;\n}\n\n/**\n * SearchGlobal component - Arbor Design System\n *\n * A search input that expands from 160px to 300px when focused.\n * Shows keyboard shortcut (⌘ K) on hover and X button when focused.\n */\nexport const SearchGlobal = React.forwardRef<HTMLInputElement, SearchGlobalProps>(\n (\n {\n value = '',\n onChange,\n onSubmit,\n onClear,\n placeholder = 'Search',\n className,\n style,\n 'data-testid': dataTestId,\n },\n ref\n ) => {\n const [isFocused, setIsFocused] = React.useState(false);\n const [isHovered, setIsHovered] = React.useState(false);\n const inputRef = React.useRef<HTMLInputElement>(null);\n\n // Merge refs\n React.useImperativeHandle(ref, () => inputRef.current as HTMLInputElement);\n\n const handleFocus = () => {\n setIsFocused(true);\n };\n\n const handleBlur = () => {\n setIsFocused(false);\n };\n\n const handleChange = (e: React.ChangeEvent<HTMLInputElement>) => {\n onChange?.(e.target.value);\n };\n\n const handleKeyDown = (e: React.KeyboardEvent<HTMLInputElement>) => {\n if (e.key === 'Enter') {\n onSubmit?.(value);\n }\n };\n\n const handleClear = () => {\n onChange?.('');\n onClear?.();\n inputRef.current?.focus();\n };\n\n const containerStyles: React.CSSProperties = {\n position: 'relative',\n width: isFocused ? '300px' : '160px',\n height: '32px',\n backgroundColor: isFocused ? '#ffffff' : isHovered ? '#efefef' : '#f8f8f8',\n borderRadius: '16px',\n padding: '8px 16px',\n display: 'flex',\n alignItems: 'center',\n gap: isFocused ? '8px' : '8px',\n cursor: 'text',\n transition: 'all 0.2s ease-in-out',\n boxSizing: 'border-box',\n border: isFocused ? '1px solid #efefef' : 'none',\n boxShadow: isFocused ? '0px 0px 0px 3px #3cad51' : 'none',\n marginLeft: isFocused ? '-140px' : '0', // Expand to the left\n ...style,\n };\n\n const iconContainerStyles: React.CSSProperties = {\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n flexShrink: 0,\n padding: '2px',\n };\n\n const inputStyles: React.CSSProperties = {\n border: 'none',\n outline: 'none',\n backgroundColor: 'transparent',\n fontFamily: \"'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif\",\n fontSize: '13px',\n fontWeight: 400,\n color: '#2f2f2f',\n lineHeight: '1.5',\n flex: 1,\n width: '100%',\n minWidth: 0,\n };\n\n const keyboardShortcutStyles: React.CSSProperties = {\n display: 'flex',\n alignItems: 'center',\n gap: '0px',\n flexShrink: 0,\n };\n\n const keyStyles: React.CSSProperties = {\n border: '1px solid #2f2f2f',\n borderRadius: '5px',\n padding: '0px 3px',\n height: '16px',\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n fontFamily: \"'Work Sans', sans-serif\",\n fontSize: '8px',\n fontWeight: 400,\n color: '#2f2f2f',\n letterSpacing: '-0.08px',\n lineHeight: '1.5',\n minWidth: '16px',\n };\n\n const plusStyles: React.CSSProperties = {\n fontFamily: \"'Work Sans', sans-serif\",\n fontSize: '8px',\n fontWeight: 400,\n color: '#2f2f2f',\n letterSpacing: '-0.08px',\n lineHeight: '1.5',\n padding: '0 2px',\n };\n\n const clearButtonStyles: React.CSSProperties = {\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n flexShrink: 0,\n width: '16px',\n height: '16px',\n cursor: 'pointer',\n border: 'none',\n background: 'none',\n padding: 0,\n };\n\n const showKeyboardShortcut = isHovered && !isFocused;\n const showClearButton = isFocused;\n\n return (\n <div\n className={className}\n style={containerStyles}\n onMouseEnter={() => setIsHovered(true)}\n onMouseLeave={() => setIsHovered(false)}\n onClick={() => inputRef.current?.focus()}\n data-testid={dataTestId}\n >\n <div style={iconContainerStyles}>\n <Search size={12} color=\"#2f2f2f\" strokeWidth={2} />\n </div>\n\n <input\n ref={inputRef}\n type=\"text\"\n value={value}\n onChange={handleChange}\n onFocus={handleFocus}\n onBlur={handleBlur}\n onKeyDown={handleKeyDown}\n placeholder={isFocused ? '' : placeholder}\n style={inputStyles}\n />\n\n {showKeyboardShortcut && (\n <div style={keyboardShortcutStyles}>\n <div style={keyStyles}>⌘</div>\n <span style={plusStyles}>+</span>\n <div style={keyStyles}>K</div>\n </div>\n )}\n\n {showClearButton && (\n <button\n type=\"button\"\n onClick={handleClear}\n style={clearButtonStyles}\n aria-label=\"Clear search\"\n >\n <X size={13.333} color=\"#2f2f2f\" strokeWidth={2} />\n </button>\n )}\n </div>\n );\n }\n);\n\nSearchGlobal.displayName = 'SearchGlobal';\n"],"mappings":"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","names":[]}
@@ -0,0 +1,175 @@
1
+ // src/SubSectionInteractive/SubSectionInteractive.tsx
2
+ import * as React from "react";
3
+ import { clsx } from "clsx";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+ var ChevronIcon = ({ expanded }) => /* @__PURE__ */ jsx(
6
+ "svg",
7
+ {
8
+ width: "16",
9
+ height: "16",
10
+ viewBox: "0 0 16 16",
11
+ fill: "none",
12
+ xmlns: "http://www.w3.org/2000/svg",
13
+ style: {
14
+ transform: expanded ? "rotate(0deg)" : "rotate(180deg)",
15
+ transition: "transform 0.2s ease-in-out"
16
+ },
17
+ children: /* @__PURE__ */ jsx(
18
+ "path",
19
+ {
20
+ d: "M4 6L8 10L12 6",
21
+ stroke: "#2f2f2f",
22
+ strokeWidth: "1.2",
23
+ strokeLinecap: "round",
24
+ strokeLinejoin: "round"
25
+ }
26
+ )
27
+ }
28
+ );
29
+ var subSectionInteractiveStyles = {
30
+ container: {
31
+ display: "flex",
32
+ flexDirection: "column",
33
+ width: "100%",
34
+ fontFamily: "'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif",
35
+ boxSizing: "border-box"
36
+ },
37
+ header: {
38
+ display: "flex",
39
+ alignItems: "center",
40
+ width: "100%",
41
+ cursor: "pointer",
42
+ border: "none",
43
+ background: "transparent",
44
+ padding: 0,
45
+ margin: 0,
46
+ textAlign: "left",
47
+ outline: "none"
48
+ },
49
+ headerContent: {
50
+ display: "flex",
51
+ alignItems: "center",
52
+ justifyContent: "space-between",
53
+ width: "100%",
54
+ padding: "12px 8px",
55
+ borderRadius: "8px",
56
+ transition: "background-color 0.15s ease-in-out",
57
+ minHeight: "16px",
58
+ gap: "12px"
59
+ },
60
+ headerContentHover: {
61
+ backgroundColor: "#f8f8f8"
62
+ },
63
+ headerContentFocus: {
64
+ outline: "3px solid #3cad51",
65
+ outlineOffset: "-3px"
66
+ },
67
+ title: {
68
+ fontSize: "18px",
69
+ fontWeight: "600",
70
+ color: "#2f2f2f",
71
+ lineHeight: "1.25",
72
+ margin: 0,
73
+ flex: 1,
74
+ whiteSpace: "nowrap"
75
+ },
76
+ iconWrapper: {
77
+ display: "flex",
78
+ alignItems: "center",
79
+ justifyContent: "center",
80
+ width: "16px",
81
+ height: "16px",
82
+ flexShrink: 0
83
+ },
84
+ content: {
85
+ overflow: "hidden",
86
+ transition: "max-height 0.3s ease-in-out, opacity 0.2s ease-in-out"
87
+ },
88
+ contentExpanded: {
89
+ maxHeight: "2000px",
90
+ opacity: 1
91
+ },
92
+ contentCollapsed: {
93
+ maxHeight: "0px",
94
+ opacity: 0
95
+ },
96
+ contentInner: {
97
+ borderBottom: "1px solid #f8f8f8"
98
+ }
99
+ };
100
+ var SubSectionInteractive = React.forwardRef(
101
+ ({
102
+ title,
103
+ children,
104
+ expanded: controlledExpanded,
105
+ defaultExpanded = true,
106
+ onExpandedChange,
107
+ className,
108
+ style,
109
+ ...props
110
+ }, ref) => {
111
+ const [internalExpanded, setInternalExpanded] = React.useState(defaultExpanded);
112
+ const isControlled = controlledExpanded !== void 0;
113
+ const isExpanded = isControlled ? controlledExpanded : internalExpanded;
114
+ const [isHovered, setIsHovered] = React.useState(false);
115
+ const [isFocused, setIsFocused] = React.useState(false);
116
+ const handleToggle = () => {
117
+ const newExpanded = !isExpanded;
118
+ if (!isControlled) {
119
+ setInternalExpanded(newExpanded);
120
+ }
121
+ onExpandedChange?.(newExpanded);
122
+ };
123
+ const handleKeyDown = (event) => {
124
+ if (event.key === "Enter" || event.key === " ") {
125
+ event.preventDefault();
126
+ handleToggle();
127
+ }
128
+ };
129
+ const headerContentStyle = {
130
+ ...subSectionInteractiveStyles.headerContent,
131
+ ...isHovered && subSectionInteractiveStyles.headerContentHover,
132
+ ...isFocused && subSectionInteractiveStyles.headerContentFocus
133
+ };
134
+ const contentStyle = {
135
+ ...subSectionInteractiveStyles.content,
136
+ ...isExpanded ? subSectionInteractiveStyles.contentExpanded : subSectionInteractiveStyles.contentCollapsed
137
+ };
138
+ return /* @__PURE__ */ jsxs(
139
+ "div",
140
+ {
141
+ ref,
142
+ className: clsx("arbor-sub-section-interactive", className),
143
+ style: { ...subSectionInteractiveStyles.container, ...style },
144
+ ...props,
145
+ children: [
146
+ /* @__PURE__ */ jsx(
147
+ "button",
148
+ {
149
+ type: "button",
150
+ style: subSectionInteractiveStyles.header,
151
+ onClick: handleToggle,
152
+ onMouseEnter: () => setIsHovered(true),
153
+ onMouseLeave: () => setIsHovered(false),
154
+ onFocus: () => setIsFocused(true),
155
+ onBlur: () => setIsFocused(false),
156
+ onKeyDown: handleKeyDown,
157
+ "aria-expanded": isExpanded,
158
+ children: /* @__PURE__ */ jsxs("div", { style: headerContentStyle, children: [
159
+ /* @__PURE__ */ jsx("h3", { style: subSectionInteractiveStyles.title, children: title }),
160
+ /* @__PURE__ */ jsx("span", { style: subSectionInteractiveStyles.iconWrapper, children: /* @__PURE__ */ jsx(ChevronIcon, { expanded: isExpanded }) })
161
+ ] })
162
+ }
163
+ ),
164
+ /* @__PURE__ */ jsx("div", { style: contentStyle, "aria-hidden": !isExpanded, children: children && /* @__PURE__ */ jsx("div", { style: subSectionInteractiveStyles.contentInner, children }) })
165
+ ]
166
+ }
167
+ );
168
+ }
169
+ );
170
+ SubSectionInteractive.displayName = "SubSectionInteractive";
171
+
172
+ export {
173
+ SubSectionInteractive
174
+ };
175
+ //# sourceMappingURL=chunk-X2CW5GF3.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/SubSectionInteractive/SubSectionInteractive.tsx"],"sourcesContent":["import * as React from 'react';\nimport { clsx } from 'clsx';\n\nexport interface SubSectionInteractiveProps {\n /**\n * The heading text (required)\n */\n title: string;\n /**\n * Content to display when expanded (list rows, etc.)\n */\n children?: React.ReactNode;\n /**\n * Whether the section is expanded (controlled mode)\n */\n expanded?: boolean;\n /**\n * Default expanded state (uncontrolled mode)\n * @default true\n */\n defaultExpanded?: boolean;\n /**\n * Callback when expanded state changes\n */\n onExpandedChange?: (expanded: boolean) => void;\n /**\n * Additional CSS class name\n */\n className?: string;\n /**\n * Additional inline styles\n */\n style?: React.CSSProperties;\n}\n\n// Chevron icon - rotates based on expanded state\nconst ChevronIcon = ({ expanded }: { expanded: boolean }) => (\n <svg\n width=\"16\"\n height=\"16\"\n viewBox=\"0 0 16 16\"\n fill=\"none\"\n xmlns=\"http://www.w3.org/2000/svg\"\n style={{\n transform: expanded ? 'rotate(0deg)' : 'rotate(180deg)',\n transition: 'transform 0.2s ease-in-out',\n }}\n >\n <path\n d=\"M4 6L8 10L12 6\"\n stroke=\"#2f2f2f\"\n strokeWidth=\"1.2\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n />\n </svg>\n);\n\n// Arbor Design System sub-section interactive styles\nconst subSectionInteractiveStyles = {\n container: {\n display: 'flex',\n flexDirection: 'column' as const,\n width: '100%',\n fontFamily: \"'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif\",\n boxSizing: 'border-box' as const,\n },\n header: {\n display: 'flex',\n alignItems: 'center',\n width: '100%',\n cursor: 'pointer',\n border: 'none',\n background: 'transparent',\n padding: 0,\n margin: 0,\n textAlign: 'left' as const,\n outline: 'none',\n },\n headerContent: {\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'space-between',\n width: '100%',\n padding: '12px 8px',\n borderRadius: '8px',\n transition: 'background-color 0.15s ease-in-out',\n minHeight: '16px',\n gap: '12px',\n },\n headerContentHover: {\n backgroundColor: '#f8f8f8',\n },\n headerContentFocus: {\n outline: '3px solid #3cad51',\n outlineOffset: '-3px',\n },\n title: {\n fontSize: '18px',\n fontWeight: '600',\n color: '#2f2f2f',\n lineHeight: '1.25',\n margin: 0,\n flex: 1,\n whiteSpace: 'nowrap' as const,\n },\n iconWrapper: {\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n width: '16px',\n height: '16px',\n flexShrink: 0,\n },\n content: {\n overflow: 'hidden',\n transition: 'max-height 0.3s ease-in-out, opacity 0.2s ease-in-out',\n },\n contentExpanded: {\n maxHeight: '2000px',\n opacity: 1,\n },\n contentCollapsed: {\n maxHeight: '0px',\n opacity: 0,\n },\n contentInner: {\n borderBottom: '1px solid #f8f8f8',\n },\n};\n\n/**\n * SubSectionInteractive component - Arbor Design System\n *\n * A collapsible sub-section component that can contain list rows and other content.\n * Click the header to expand/collapse the content area.\n *\n * @example\n * ```tsx\n * // Basic collapsible section\n * <SubSectionInteractive title=\"Personal Details\">\n * <ListRow label=\"Name\" value=\"John Smith\" />\n * <ListRow label=\"Email\" value=\"john@example.com\" />\n * </SubSectionInteractive>\n *\n * // Initially collapsed\n * <SubSectionInteractive title=\"Additional Info\" defaultExpanded={false}>\n * <ListRow label=\"Notes\" value=\"Some notes here\" />\n * </SubSectionInteractive>\n *\n * // Controlled mode\n * <SubSectionInteractive\n * title=\"Settings\"\n * expanded={isExpanded}\n * onExpandedChange={setIsExpanded}\n * >\n * <ListRow label=\"Theme\" value=\"Dark\" />\n * </SubSectionInteractive>\n * ```\n */\nexport const SubSectionInteractive = React.forwardRef<HTMLDivElement, SubSectionInteractiveProps>(\n (\n {\n title,\n children,\n expanded: controlledExpanded,\n defaultExpanded = true,\n onExpandedChange,\n className,\n style,\n ...props\n },\n ref\n ) => {\n // Support both controlled and uncontrolled modes\n const [internalExpanded, setInternalExpanded] = React.useState(defaultExpanded);\n const isControlled = controlledExpanded !== undefined;\n const isExpanded = isControlled ? controlledExpanded : internalExpanded;\n\n const [isHovered, setIsHovered] = React.useState(false);\n const [isFocused, setIsFocused] = React.useState(false);\n\n const handleToggle = () => {\n const newExpanded = !isExpanded;\n if (!isControlled) {\n setInternalExpanded(newExpanded);\n }\n onExpandedChange?.(newExpanded);\n };\n\n const handleKeyDown = (event: React.KeyboardEvent) => {\n if (event.key === 'Enter' || event.key === ' ') {\n event.preventDefault();\n handleToggle();\n }\n };\n\n const headerContentStyle: React.CSSProperties = {\n ...subSectionInteractiveStyles.headerContent,\n ...(isHovered && subSectionInteractiveStyles.headerContentHover),\n ...(isFocused && subSectionInteractiveStyles.headerContentFocus),\n };\n\n const contentStyle: React.CSSProperties = {\n ...subSectionInteractiveStyles.content,\n ...(isExpanded\n ? subSectionInteractiveStyles.contentExpanded\n : subSectionInteractiveStyles.contentCollapsed),\n };\n\n return (\n <div\n ref={ref}\n className={clsx('arbor-sub-section-interactive', className)}\n style={{ ...subSectionInteractiveStyles.container, ...style }}\n {...props}\n >\n <button\n type=\"button\"\n style={subSectionInteractiveStyles.header}\n onClick={handleToggle}\n onMouseEnter={() => setIsHovered(true)}\n onMouseLeave={() => setIsHovered(false)}\n onFocus={() => setIsFocused(true)}\n onBlur={() => setIsFocused(false)}\n onKeyDown={handleKeyDown}\n aria-expanded={isExpanded}\n >\n <div style={headerContentStyle}>\n <h3 style={subSectionInteractiveStyles.title}>{title}</h3>\n <span style={subSectionInteractiveStyles.iconWrapper}>\n <ChevronIcon expanded={isExpanded} />\n </span>\n </div>\n </button>\n <div style={contentStyle} aria-hidden={!isExpanded}>\n {children && (\n <div style={subSectionInteractiveStyles.contentInner}>{children}</div>\n )}\n </div>\n </div>\n );\n }\n);\n\nSubSectionInteractive.displayName = 'SubSectionInteractive';\n"],"mappings":"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","names":[]}