@dragunio/fe-libs 0.1.5 → 0.1.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -20,8 +20,13 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
20
20
  // src/index.ts
21
21
  var index_exports = {};
22
22
  __export(index_exports, {
23
+ Avatar: () => Avatar,
24
+ AvatarGroup: () => AvatarGroup,
23
25
  Button: () => Button,
26
+ ButtonBar: () => ButtonBar,
27
+ Checkbox: () => Checkbox,
24
28
  ChevronDownIcon: () => ChevronDownIcon,
29
+ ChevronUpIcon: () => ChevronUpIcon,
25
30
  Chip: () => Chip,
26
31
  CloseIcon: () => CloseIcon,
27
32
  CurrencyInput: () => CurrencyInput,
@@ -31,10 +36,14 @@ __export(index_exports, {
31
36
  Loading: () => Loading,
32
37
  Message: () => Message,
33
38
  Modal: () => Modal,
39
+ MoreHorizontalIcon: () => MoreHorizontalIcon,
40
+ MoreVerticalIcon: () => MoreVerticalIcon,
34
41
  NumberInput: () => NumberInput,
35
42
  Pagination: () => Pagination,
36
43
  PlusIcon: () => PlusIcon,
37
44
  ProgressBar: () => ProgressBar,
45
+ RadioButton: () => RadioButton,
46
+ RadioGroup: () => RadioGroup,
38
47
  SearchIcon: () => SearchIcon,
39
48
  Selection: () => Selection,
40
49
  Skeleton: () => Skeleton,
@@ -143,6 +152,9 @@ var Button = (0, import_react.forwardRef)(
143
152
  );
144
153
  Button.displayName = "Button";
145
154
 
155
+ // packages/button-bar/src/index.tsx
156
+ var import_react2 = require("react");
157
+
146
158
  // packages/icons/src/svgItems/general.tsx
147
159
  var import_jsx_runtime2 = require("react/jsx-runtime");
148
160
  var primaryColor = "#101828";
@@ -263,6 +275,18 @@ function ChevronDownIcon(props) {
263
275
  }
264
276
  ) });
265
277
  }
278
+ function ChevronUpIcon(props) {
279
+ return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("svg", { ...iconProps4(props), children: /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(
280
+ "path",
281
+ {
282
+ d: "m6 15 6-6 6 6",
283
+ stroke: "currentColor",
284
+ strokeWidth: "2",
285
+ strokeLinecap: "round",
286
+ strokeLinejoin: "round"
287
+ }
288
+ ) });
289
+ }
266
290
  function CloseIcon(props) {
267
291
  return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("svg", { ...iconProps4(props), children: /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(
268
292
  "path",
@@ -274,6 +298,20 @@ function CloseIcon(props) {
274
298
  }
275
299
  ) });
276
300
  }
301
+ function MoreHorizontalIcon(props) {
302
+ return /* @__PURE__ */ (0, import_jsx_runtime5.jsxs)("svg", { ...iconProps4(props), children: [
303
+ /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "5", cy: "12", r: "1.75", fill: "currentColor" }),
304
+ /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "12", cy: "12", r: "1.75", fill: "currentColor" }),
305
+ /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "19", cy: "12", r: "1.75", fill: "currentColor" })
306
+ ] });
307
+ }
308
+ function MoreVerticalIcon(props) {
309
+ return /* @__PURE__ */ (0, import_jsx_runtime5.jsxs)("svg", { ...iconProps4(props), children: [
310
+ /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "12", cy: "5", r: "1.75", fill: "currentColor" }),
311
+ /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "12", cy: "12", r: "1.75", fill: "currentColor" }),
312
+ /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "12", cy: "19", r: "1.75", fill: "currentColor" })
313
+ ] });
314
+ }
277
315
  function SearchIcon(props) {
278
316
  return /* @__PURE__ */ (0, import_jsx_runtime5.jsxs)("svg", { ...iconProps4(props), children: [
279
317
  /* @__PURE__ */ (0, import_jsx_runtime5.jsx)("circle", { cx: "11", cy: "11", r: "6.5", stroke: "currentColor", strokeWidth: "2" }),
@@ -289,12 +327,111 @@ function SearchIcon(props) {
289
327
  ] });
290
328
  }
291
329
 
292
- // packages/table/src/index.tsx
330
+ // packages/button-bar/src/index.tsx
331
+ var import_jsx_runtime6 = require("react/jsx-runtime");
293
332
  var import_react3 = require("react");
333
+ function ButtonBar({
334
+ actions,
335
+ maxVisible = actions.length,
336
+ moreButtonProps,
337
+ moreLabel = "More actions",
338
+ className,
339
+ ...props
340
+ }) {
341
+ const [isMoreOpen, setIsMoreOpen] = (0, import_react2.useState)(false);
342
+ const rootRef = (0, import_react2.useRef)(null);
343
+ const moreMenuId = (0, import_react2.useId)();
344
+ const visibleCount = Math.max(0, Math.floor(maxVisible));
345
+ const visibleActions = actions.slice(0, visibleCount);
346
+ const overflowActions = actions.slice(visibleCount);
347
+ const hasOverflow = overflowActions.length > 0;
348
+ const {
349
+ onClick: onMoreClick,
350
+ disabled: moreDisabled,
351
+ "aria-label": moreAriaLabel,
352
+ ...moreButtonRestProps
353
+ } = moreButtonProps ?? {};
354
+ (0, import_react2.useEffect)(() => {
355
+ if (!isMoreOpen) return;
356
+ const onPointerDown = (event) => {
357
+ if (!rootRef.current?.contains(event.target)) {
358
+ setIsMoreOpen(false);
359
+ }
360
+ };
361
+ const onKeyDown = (event) => {
362
+ if (event.key === "Escape") setIsMoreOpen(false);
363
+ };
364
+ document.addEventListener("pointerdown", onPointerDown);
365
+ document.addEventListener("keydown", onKeyDown);
366
+ return () => {
367
+ document.removeEventListener("pointerdown", onPointerDown);
368
+ document.removeEventListener("keydown", onKeyDown);
369
+ };
370
+ }, [isMoreOpen]);
371
+ const renderAction = (action, shouldCloseMore = false) => {
372
+ const { id, onClick, disabled, ...buttonProps } = action;
373
+ return /* @__PURE__ */ (0, import_react3.createElement)(
374
+ Button,
375
+ {
376
+ ...buttonProps,
377
+ disabled,
378
+ key: id,
379
+ onClick: (event) => {
380
+ onClick?.(event);
381
+ if (shouldCloseMore && !disabled) setIsMoreOpen(false);
382
+ }
383
+ }
384
+ );
385
+ };
386
+ return /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
387
+ "div",
388
+ {
389
+ ...props,
390
+ className: ["fe-button-bar", className].filter(Boolean).join(" "),
391
+ ref: rootRef,
392
+ children: [
393
+ visibleActions.map((action) => renderAction(action)),
394
+ hasOverflow && /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)("div", { className: "fe-button-bar__more", children: [
395
+ /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
396
+ Button,
397
+ {
398
+ hierarchy: "secondary-gray",
399
+ ...moreButtonRestProps,
400
+ "aria-controls": moreMenuId,
401
+ "aria-expanded": isMoreOpen,
402
+ "aria-haspopup": "true",
403
+ "aria-label": moreAriaLabel ?? moreLabel,
404
+ disabled: moreDisabled,
405
+ icon: /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(MoreHorizontalIcon, {}),
406
+ iconOnly: true,
407
+ onClick: (event) => {
408
+ onMoreClick?.(event);
409
+ if (!event.defaultPrevented) setIsMoreOpen((open) => !open);
410
+ }
411
+ }
412
+ ),
413
+ isMoreOpen && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
414
+ "div",
415
+ {
416
+ "aria-label": moreLabel,
417
+ className: "fe-button-bar__menu",
418
+ id: moreMenuId,
419
+ role: "group",
420
+ children: overflowActions.map((action) => renderAction(action, true))
421
+ }
422
+ )
423
+ ] })
424
+ ]
425
+ }
426
+ );
427
+ }
428
+
429
+ // packages/table/src/index.tsx
430
+ var import_react5 = require("react");
294
431
 
295
432
  // packages/pagination/src/index.tsx
296
- var import_react2 = require("react");
297
- var import_jsx_runtime6 = require("react/jsx-runtime");
433
+ var import_react4 = require("react");
434
+ var import_jsx_runtime7 = require("react/jsx-runtime");
298
435
  var clamp = (value, min, max) => Math.min(Math.max(value, min), max);
299
436
  var range = (start, end) => Array.from({ length: Math.max(0, end - start + 1) }, (_, index) => start + index);
300
437
  function getItems(totalPages, page, siblingCount, boundaryCount) {
@@ -326,9 +463,9 @@ function Pagination({
326
463
  ...props
327
464
  }) {
328
465
  const safeTotalPages = Math.max(1, Math.floor(totalPages));
329
- const [uncontrolledPage, setUncontrolledPage] = (0, import_react2.useState)(() => clamp(defaultPage, 1, safeTotalPages));
466
+ const [uncontrolledPage, setUncontrolledPage] = (0, import_react4.useState)(() => clamp(defaultPage, 1, safeTotalPages));
330
467
  const currentPage = clamp(page ?? uncontrolledPage, 1, safeTotalPages);
331
- const items = (0, import_react2.useMemo)(
468
+ const items = (0, import_react4.useMemo)(
332
469
  () => getItems(safeTotalPages, currentPage, Math.max(0, siblingCount), Math.max(0, boundaryCount)),
333
470
  [safeTotalPages, currentPage, siblingCount, boundaryCount]
334
471
  );
@@ -337,9 +474,9 @@ function Pagination({
337
474
  if (page === void 0) setUncontrolledPage(resolvedPage);
338
475
  if (resolvedPage !== currentPage) onPageChange?.(resolvedPage);
339
476
  };
340
- return /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)("nav", { className: ["fe-pagination", className].filter(Boolean).join(" "), "aria-label": "Pagination", ...props, children: [
341
- /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(Button, { className: "fe-pagination__button fe-pagination__button--control", hierarchy: "secondary-gray", size: "40", iconOnly: true, icon: "\u2039", "aria-label": previousLabel, disabled: disabled || currentPage === 1, onClick: () => selectPage(currentPage - 1) }),
342
- items.map((item, index) => item === "start-ellipsis" || item === "end-ellipsis" ? /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("span", { className: "fe-pagination__ellipsis", "aria-hidden": "true", children: "\u2026" }, `${item}-${index}`) : /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
477
+ return /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("nav", { className: ["fe-pagination", className].filter(Boolean).join(" "), "aria-label": "Pagination", ...props, children: [
478
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(Button, { className: "fe-pagination__button fe-pagination__button--control", hierarchy: "secondary-gray", size: "40", iconOnly: true, icon: "\u2039", "aria-label": previousLabel, disabled: disabled || currentPage === 1, onClick: () => selectPage(currentPage - 1) }),
479
+ items.map((item, index) => item === "start-ellipsis" || item === "end-ellipsis" ? /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "fe-pagination__ellipsis", "aria-hidden": "true", children: "\u2026" }, `${item}-${index}`) : /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
343
480
  Button,
344
481
  {
345
482
  className: "fe-pagination__button",
@@ -353,13 +490,13 @@ function Pagination({
353
490
  },
354
491
  item
355
492
  )),
356
- /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(Button, { className: "fe-pagination__button fe-pagination__button--control", hierarchy: "secondary-gray", size: "40", iconOnly: true, icon: "\u203A", "aria-label": nextLabel, disabled: disabled || currentPage === safeTotalPages, onClick: () => selectPage(currentPage + 1) })
493
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(Button, { className: "fe-pagination__button fe-pagination__button--control", hierarchy: "secondary-gray", size: "40", iconOnly: true, icon: "\u203A", "aria-label": nextLabel, disabled: disabled || currentPage === safeTotalPages, onClick: () => selectPage(currentPage + 1) })
357
494
  ] });
358
495
  }
359
496
 
360
497
  // packages/table/src/index.tsx
361
- var import_jsx_runtime7 = require("react/jsx-runtime");
362
- var TableContext = (0, import_react3.createContext)({ striped: false });
498
+ var import_jsx_runtime8 = require("react/jsx-runtime");
499
+ var TableContext = (0, import_react5.createContext)({ striped: false });
363
500
  var MIN_COLUMN_WIDTH = 96;
364
501
  var MAX_COLUMN_WIDTH = 1200;
365
502
  function getColumnCount(headers, data) {
@@ -368,7 +505,7 @@ function getColumnCount(headers, data) {
368
505
  function getText(value) {
369
506
  if (typeof value === "string" || typeof value === "number") return String(value);
370
507
  if (Array.isArray(value)) return value.map(getText).join("");
371
- if ((0, import_react3.isValidElement)(value)) return getText(value.props.children);
508
+ if ((0, import_react5.isValidElement)(value)) return getText(value.props.children);
372
509
  return "";
373
510
  }
374
511
  function autoColumnSize(columnIndex, headers, data) {
@@ -404,37 +541,37 @@ function DataTable({
404
541
  }) {
405
542
  const columnCount = getColumnCount(headers, data);
406
543
  const safeMinWidth = Math.max(1, minColumnWidth);
407
- const generatedSizes = (0, import_react3.useMemo)(
544
+ const generatedSizes = (0, import_react5.useMemo)(
408
545
  () => getInitialColumnSizes(headers, data, defaultColumnSizes, safeMinWidth),
409
546
  [headers, data, defaultColumnSizes, safeMinWidth]
410
547
  );
411
- const [uncontrolledSizes, setUncontrolledSizes] = (0, import_react3.useState)(generatedSizes);
548
+ const [uncontrolledSizes, setUncontrolledSizes] = (0, import_react5.useState)(generatedSizes);
412
549
  const shouldPaginate = pagination ?? pageSize !== void 0;
413
550
  const safePageSize = Math.max(1, Math.floor(pageSize ?? 10));
414
551
  const totalPages = Math.max(1, Math.ceil(data.length / safePageSize));
415
- const [uncontrolledPage, setUncontrolledPage] = (0, import_react3.useState)(() => Math.min(Math.max(1, defaultPage), totalPages));
552
+ const [uncontrolledPage, setUncontrolledPage] = (0, import_react5.useState)(() => Math.min(Math.max(1, defaultPage), totalPages));
416
553
  const currentPage = Math.min(Math.max(1, page ?? uncontrolledPage), totalPages);
417
554
  const pagedData = shouldPaginate ? data.slice((currentPage - 1) * safePageSize, currentPage * safePageSize) : data;
418
- const resizeState = (0, import_react3.useRef)();
419
- const [isResizing, setIsResizing] = (0, import_react3.useState)(false);
555
+ const resizeState = (0, import_react5.useRef)();
556
+ const [isResizing, setIsResizing] = (0, import_react5.useState)(false);
420
557
  const sizes2 = columnSizes ? getInitialColumnSizes(headers, data, columnSizes, safeMinWidth).map((size) => Math.max(safeMinWidth, size)) : uncontrolledSizes.map((size) => Math.max(safeMinWidth, size));
421
- (0, import_react3.useEffect)(() => {
558
+ (0, import_react5.useEffect)(() => {
422
559
  if (columnSizes) return;
423
560
  setUncontrolledSizes((currentSizes) => {
424
561
  const nextSizes = generatedSizes.map((generatedSize, index) => currentSizes[index] ?? generatedSize);
425
562
  return sameSizes(currentSizes, nextSizes) ? currentSizes : nextSizes;
426
563
  });
427
564
  }, [columnSizes, generatedSizes]);
428
- (0, import_react3.useEffect)(() => {
565
+ (0, import_react5.useEffect)(() => {
429
566
  if (page === void 0 && uncontrolledPage > totalPages) setUncontrolledPage(totalPages);
430
567
  }, [page, totalPages, uncontrolledPage]);
431
- const updateColumnSize = (0, import_react3.useCallback)((columnIndex, nextSize) => {
568
+ const updateColumnSize = (0, import_react5.useCallback)((columnIndex, nextSize) => {
432
569
  const clampedSize = Math.min(MAX_COLUMN_WIDTH, Math.max(safeMinWidth, Math.round(nextSize)));
433
570
  const nextSizes = sizes2.map((size, index) => index === columnIndex ? clampedSize : size);
434
571
  if (!columnSizes) setUncontrolledSizes(nextSizes);
435
572
  onColumnResize?.(nextSizes, columnIndex);
436
573
  }, [columnSizes, onColumnResize, safeMinWidth, sizes2]);
437
- (0, import_react3.useEffect)(() => {
574
+ (0, import_react5.useEffect)(() => {
438
575
  const onPointerMove = (event) => {
439
576
  const activeResize = resizeState.current;
440
577
  if (!activeResize) return;
@@ -458,14 +595,14 @@ function DataTable({
458
595
  if (nextPage !== currentPage) onPageChange?.(nextPage);
459
596
  };
460
597
  const resolvedPaginationPosition = paginationPosition === "middle-bottom" ? "bottom-center" : paginationPosition;
461
- const paginationControl = shouldPaginate && totalPages > 1 ? /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { className: `fe-table__pagination fe-table__pagination--${resolvedPaginationPosition}`, children: /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(Pagination, { page: currentPage, totalPages, onPageChange: changePage }) }) : null;
462
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { className: "fe-table", "data-resizing": isResizing || void 0, children: [
598
+ const paginationControl = shouldPaginate && totalPages > 1 ? /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("div", { className: `fe-table__pagination fe-table__pagination--${resolvedPaginationPosition}`, children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(Pagination, { page: currentPage, totalPages, onPageChange: changePage }) }) : null;
599
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("div", { className: "fe-table", "data-resizing": isResizing || void 0, children: [
463
600
  resolvedPaginationPosition === "top-right" && paginationControl,
464
- /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("table", { className: ["fe-table__table", className].filter(Boolean).join(" "), "data-fe-table": true, "data-striped": striped || void 0, ...props, children: [
465
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("colgroup", { children: sizes2.map((size, index) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("col", { style: { width: `${size}px` } }, index)) }),
466
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("thead", { children: /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("tr", { children: Array.from({ length: columnCount }, (_, columnIndex) => /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("th", { scope: "col", children: [
467
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("span", { className: "fe-table__header-content", children: headers[columnIndex] ?? `Column ${columnIndex + 1}` }),
468
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
601
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("table", { className: ["fe-table__table", className].filter(Boolean).join(" "), "data-fe-table": true, "data-striped": striped || void 0, ...props, children: [
602
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("colgroup", { children: sizes2.map((size, index) => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("col", { style: { width: `${size}px` } }, index)) }),
603
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("thead", { children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("tr", { children: Array.from({ length: columnCount }, (_, columnIndex) => /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("th", { scope: "col", children: [
604
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { className: "fe-table__header-content", children: headers[columnIndex] ?? `Column ${columnIndex + 1}` }),
605
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
469
606
  "span",
470
607
  {
471
608
  className: "fe-table__resize-handle",
@@ -489,7 +626,7 @@ function DataTable({
489
626
  }
490
627
  )
491
628
  ] }, columnIndex)) }) }),
492
- /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("tbody", { children: pagedData.map((row, rowIndex) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("tr", { children: Array.from({ length: columnCount }, (_, columnIndex) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("td", { children: row[columnIndex] }, columnIndex)) }, shouldPaginate ? (currentPage - 1) * safePageSize + rowIndex : rowIndex)) })
629
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("tbody", { children: pagedData.map((row, rowIndex) => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("tr", { children: Array.from({ length: columnCount }, (_, columnIndex) => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("td", { children: row[columnIndex] }, columnIndex)) }, shouldPaginate ? (currentPage - 1) * safePageSize + rowIndex : rowIndex)) })
493
630
  ] }),
494
631
  resolvedPaginationPosition !== "top-right" && paginationControl
495
632
  ] });
@@ -507,52 +644,71 @@ function Table({
507
644
  paginationPosition,
508
645
  ...props
509
646
  }) {
510
- if (headers || data) return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(DataTable, { headers: headers ?? [], data: data ?? [], striped: striped ?? true, pagination, pageSize, page, defaultPage, onPageChange, paginationPosition, ...props });
511
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(TableContext.Provider, { value: { striped: striped ?? false }, children: /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("table", { "data-fe-table": true, "data-striped": striped || void 0, ...props, children }) });
647
+ if (headers || data) return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(DataTable, { headers: headers ?? [], data: data ?? [], striped: striped ?? true, pagination, pageSize, page, defaultPage, onPageChange, paginationPosition, ...props });
648
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(TableContext.Provider, { value: { striped: striped ?? false }, children: /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("table", { "data-fe-table": true, "data-striped": striped || void 0, ...props, children }) });
512
649
  }
513
650
  function TableHead(props) {
514
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("thead", { ...props });
651
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("thead", { ...props });
515
652
  }
516
653
  function TableBody(props) {
517
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("tbody", { ...props });
654
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("tbody", { ...props });
518
655
  }
519
656
  function TableRow({ children, ...props }) {
520
- const { striped } = (0, import_react3.useContext)(TableContext);
521
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("tr", { "data-striped": striped || void 0, ...props, children });
657
+ const { striped } = (0, import_react5.useContext)(TableContext);
658
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("tr", { "data-striped": striped || void 0, ...props, children });
522
659
  }
523
660
  function TableCell({ children, ...props }) {
524
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("td", { ...props, children });
661
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("td", { ...props, children });
525
662
  }
526
663
  function TableHeader({ children, ...props }) {
527
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("th", { scope: "col", ...props, children });
664
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("th", { scope: "col", ...props, children });
528
665
  }
529
666
  function TableCaption(props) {
530
- return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("caption", { ...props });
667
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("caption", { ...props });
531
668
  }
532
669
 
533
670
  // packages/toggle/src/index.tsx
534
- var import_react4 = require("react");
535
- var import_jsx_runtime8 = require("react/jsx-runtime");
536
- var Toggle = (0, import_react4.forwardRef)(function Toggle2({ color = "#16a34a", label, className, style, id, ...props }, ref) {
537
- const classes = ["fe-toggle", className].filter(Boolean).join(" ");
671
+ var import_react6 = require("react");
672
+ var import_jsx_runtime9 = require("react/jsx-runtime");
673
+ var Toggle = (0, import_react6.forwardRef)(function Toggle2({
674
+ color = "#16a34a",
675
+ label,
676
+ labelPosition = "right",
677
+ className,
678
+ style,
679
+ id,
680
+ ...props
681
+ }, ref) {
682
+ const classes = ["fe-toggle", `fe-toggle--label-${labelPosition}`, className].filter(Boolean).join(" ");
538
683
  const toggleStyle = {
539
684
  "--fe-toggle-color": color,
540
685
  ...style
541
686
  };
542
- return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("label", { className: classes, style: toggleStyle, children: [
543
- /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("input", { ref, id, className: "fe-toggle__input", type: "checkbox", role: "switch", ...props }),
544
- /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { className: "fe-toggle__control", "aria-hidden": "true" }),
545
- label && /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { className: "fe-toggle__label", children: label })
687
+ return /* @__PURE__ */ (0, import_jsx_runtime9.jsxs)("label", { className: classes, style: toggleStyle, children: [
688
+ label && labelPosition === "top" && /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("span", { className: "fe-toggle__label", children: label }),
689
+ /* @__PURE__ */ (0, import_jsx_runtime9.jsx)(
690
+ "input",
691
+ {
692
+ ref,
693
+ id,
694
+ className: "fe-toggle__input",
695
+ type: "checkbox",
696
+ role: "switch",
697
+ ...props
698
+ }
699
+ ),
700
+ /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("span", { className: "fe-toggle__control", "aria-hidden": "true" }),
701
+ label && labelPosition === "right" && /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("span", { className: "fe-toggle__label", children: label })
546
702
  ] });
547
703
  });
548
704
  Toggle.displayName = "Toggle";
549
705
 
550
706
  // packages/drawer/src/index.tsx
551
- var import_react5 = require("react");
707
+ var import_react7 = require("react");
552
708
  var import_react_dom = require("react-dom");
553
- var import_jsx_runtime9 = require("react/jsx-runtime");
709
+ var import_jsx_runtime10 = require("react/jsx-runtime");
554
710
  function Drawer({ open, onClose, title, footer, side = "right", width = 400, fullScreen = false, children, closeOnBackdropClick = true, className, style, ...props }) {
555
- (0, import_react5.useEffect)(() => {
711
+ (0, import_react7.useEffect)(() => {
556
712
  if (!open) return;
557
713
  const onKeyDown = (event) => {
558
714
  if (event.key === "Escape") onClose();
@@ -562,28 +718,28 @@ function Drawer({ open, onClose, title, footer, side = "right", width = 400, ful
562
718
  }, [onClose, open]);
563
719
  if (!open || typeof document === "undefined") return null;
564
720
  const panelStyle = !fullScreen && (side === "left" || side === "right") ? { ...style, width: typeof width === "number" ? `${width}px` : width } : style;
565
- return (0, import_react_dom.createPortal)(/* @__PURE__ */ (0, import_jsx_runtime9.jsx)("div", { className: "fe-drawer-backdrop", role: "presentation", onMouseDown: (event) => {
721
+ return (0, import_react_dom.createPortal)(/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("div", { className: "fe-drawer-backdrop", role: "presentation", onMouseDown: (event) => {
566
722
  if (event.target === event.currentTarget && closeOnBackdropClick) onClose();
567
- }, children: /* @__PURE__ */ (0, import_jsx_runtime9.jsxs)("aside", { className: ["fe-drawer", `fe-drawer--${side}`, fullScreen && "fe-drawer--full-screen", className].filter(Boolean).join(" "), style: panelStyle, role: "dialog", "aria-modal": "true", "aria-label": typeof title === "string" ? title : "Drawer", ...props, children: [
568
- /* @__PURE__ */ (0, import_jsx_runtime9.jsxs)("header", { className: "fe-drawer__header", children: [
569
- title && /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("h2", { children: title }),
570
- /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("button", { type: "button", "aria-label": "Close drawer", onClick: onClose, children: "\xD7" })
723
+ }, children: /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("aside", { className: ["fe-drawer", `fe-drawer--${side}`, fullScreen && "fe-drawer--full-screen", className].filter(Boolean).join(" "), style: panelStyle, role: "dialog", "aria-modal": "true", "aria-label": typeof title === "string" ? title : "Drawer", ...props, children: [
724
+ /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("header", { className: "fe-drawer__header", children: [
725
+ title && /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("h2", { children: title }),
726
+ /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("button", { type: "button", "aria-label": "Close drawer", onClick: onClose, children: "\xD7" })
571
727
  ] }),
572
- /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("div", { className: "fe-drawer__body", children }),
573
- footer && /* @__PURE__ */ (0, import_jsx_runtime9.jsx)("footer", { className: "fe-drawer__footer", children: footer })
728
+ /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("div", { className: "fe-drawer__body", children }),
729
+ footer && /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("footer", { className: "fe-drawer__footer", children: footer })
574
730
  ] }) }), document.body);
575
731
  }
576
732
 
577
733
  // packages/form-controls/src/controls/TextInput/text-input.tsx
578
- var import_react7 = require("react");
734
+ var import_react9 = require("react");
579
735
 
580
736
  // packages/tooltip/src/index.tsx
581
- var import_react6 = require("react");
582
- var import_jsx_runtime10 = require("react/jsx-runtime");
737
+ var import_react8 = require("react");
738
+ var import_jsx_runtime11 = require("react/jsx-runtime");
583
739
  function Tooltip({ content, children, placement = "top", disabled, className, ...props }) {
584
- const [visible, setVisible] = (0, import_react6.useState)(false);
585
- const id = (0, import_react6.useId)();
586
- const trigger = (0, import_react6.cloneElement)(children, { "aria-describedby": visible ? id : void 0, onMouseEnter: (event) => {
740
+ const [visible, setVisible] = (0, import_react8.useState)(false);
741
+ const id = (0, import_react8.useId)();
742
+ const trigger = (0, import_react8.cloneElement)(children, { "aria-describedby": visible ? id : void 0, onMouseEnter: (event) => {
587
743
  children.props.onMouseEnter?.(event);
588
744
  setVisible(true);
589
745
  }, onMouseLeave: (event) => {
@@ -596,14 +752,14 @@ function Tooltip({ content, children, placement = "top", disabled, className, ..
596
752
  children.props.onBlur?.(event);
597
753
  setVisible(false);
598
754
  } });
599
- return /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: ["fe-tooltip", `fe-tooltip--${placement}`, className].filter(Boolean).join(" "), ...props, children: [
755
+ return /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)("span", { className: ["fe-tooltip", `fe-tooltip--${placement}`, className].filter(Boolean).join(" "), ...props, children: [
600
756
  trigger,
601
- visible && !disabled && /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { id, role: "tooltip", className: "fe-tooltip__content", children: content })
757
+ visible && !disabled && /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { id, role: "tooltip", className: "fe-tooltip__content", children: content })
602
758
  ] });
603
759
  }
604
760
 
605
761
  // packages/form-controls/src/controls/Field/field.tsx
606
- var import_jsx_runtime11 = require("react/jsx-runtime");
762
+ var import_jsx_runtime12 = require("react/jsx-runtime");
607
763
  function getFieldError(error, errorMessage) {
608
764
  if (errorMessage !== void 0 && errorMessage !== null) return errorMessage;
609
765
  if (typeof error !== "boolean") return error;
@@ -620,10 +776,10 @@ function FieldLabel({
620
776
  isRequired = false
621
777
  }) {
622
778
  if (!label) return null;
623
- return /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)("span", { className: "fe-field__label", children: [
624
- /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { id, children: label }),
625
- isRequired && /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { className: "fe-field__required", "aria-hidden": "true", children: "*" }),
626
- description && descriptionDisplay === "tooltip" && /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(Tooltip, { content: description, children: /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(
779
+ return /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("span", { className: "fe-field__label", children: [
780
+ /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { id, children: label }),
781
+ isRequired && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { className: "fe-field__required", "aria-hidden": "true", children: "*" }),
782
+ description && descriptionDisplay === "tooltip" && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(Tooltip, { content: description, children: /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
627
783
  "span",
628
784
  {
629
785
  className: "fe-field__info",
@@ -642,7 +798,7 @@ function FieldMessage({
642
798
  descriptionDisplay
643
799
  }) {
644
800
  if (error !== void 0 && error !== false && error !== null)
645
- return /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(
801
+ return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
646
802
  "span",
647
803
  {
648
804
  id,
@@ -652,13 +808,13 @@ function FieldMessage({
652
808
  }
653
809
  );
654
810
  if (description && descriptionDisplay === "inline")
655
- return /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { id, className: "fe-field__message", children: description });
811
+ return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { id, className: "fe-field__message", children: description });
656
812
  return null;
657
813
  }
658
814
 
659
815
  // packages/form-controls/src/controls/TextInput/text-input.tsx
660
- var import_jsx_runtime12 = require("react/jsx-runtime");
661
- var TextInput = (0, import_react7.forwardRef)(
816
+ var import_jsx_runtime13 = require("react/jsx-runtime");
817
+ var TextInput = (0, import_react9.forwardRef)(
662
818
  function TextInput2({
663
819
  value,
664
820
  defaultValue = "",
@@ -688,12 +844,12 @@ var TextInput = (0, import_react7.forwardRef)(
688
844
  "aria-labelledby": ariaLabelledBy,
689
845
  ...props
690
846
  }, ref) {
691
- const generatedId = (0, import_react7.useId)();
847
+ const generatedId = (0, import_react9.useId)();
692
848
  const inputId = id ?? generatedId + "-input";
693
849
  const labelId = generatedId + "-label";
694
850
  const messageId2 = generatedId + "-message";
695
851
  const controlled = value !== void 0;
696
- const [internalValue, setInternalValue] = (0, import_react7.useState)(defaultValue);
852
+ const [internalValue, setInternalValue] = (0, import_react9.useState)(defaultValue);
697
853
  const currentValue = controlled ? value : internalValue;
698
854
  const fieldError = getFieldError(error, errorMessage);
699
855
  const hasError = fieldError !== void 0 && fieldError !== false && fieldError !== null;
@@ -714,7 +870,7 @@ var TextInput = (0, import_react7.forwardRef)(
714
870
  onValueChange?.("");
715
871
  onClear?.();
716
872
  };
717
- return /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)(
873
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
718
874
  "div",
719
875
  {
720
876
  className: [
@@ -723,7 +879,7 @@ var TextInput = (0, import_react7.forwardRef)(
723
879
  className
724
880
  ].filter(Boolean).join(" "),
725
881
  children: [
726
- /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
882
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
727
883
  FieldLabel,
728
884
  {
729
885
  id: labelId,
@@ -733,10 +889,10 @@ var TextInput = (0, import_react7.forwardRef)(
733
889
  isRequired
734
890
  }
735
891
  ),
736
- /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("span", { className: "fe-text-input__control", children: [
737
- resolvedPrefix && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { className: "fe-text-input__prefix", children: resolvedPrefix }),
738
- /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("span", { className: "fe-text-input__input-wrap", children: [
739
- /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
892
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("span", { className: "fe-text-input__control", children: [
893
+ resolvedPrefix && /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { className: "fe-text-input__prefix", children: resolvedPrefix }),
894
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("span", { className: "fe-text-input__input-wrap", children: [
895
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
740
896
  "input",
741
897
  {
742
898
  ref,
@@ -758,26 +914,26 @@ var TextInput = (0, import_react7.forwardRef)(
758
914
  ...props
759
915
  }
760
916
  ),
761
- isRequired && placeholder && !currentValue && /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("span", { className: "fe-text-input__placeholder", "aria-hidden": "true", children: [
762
- /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { children: placeholder }),
763
- /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { className: "fe-field__required", children: "*" })
917
+ isRequired && placeholder && !currentValue && /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("span", { className: "fe-text-input__placeholder", "aria-hidden": "true", children: [
918
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { children: placeholder }),
919
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { className: "fe-field__required", children: "*" })
764
920
  ] })
765
921
  ] }),
766
- resolvedSuffix && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("span", { className: "fe-text-input__suffix", children: resolvedSuffix }),
767
- clearable && currentValue && !disabled && !readOnly && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
922
+ resolvedSuffix && /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { className: "fe-text-input__suffix", children: resolvedSuffix }),
923
+ clearable && currentValue && !disabled && !readOnly && /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
768
924
  Button,
769
925
  {
770
926
  hierarchy: "tertiary-gray",
771
927
  size: "24",
772
928
  iconOnly: true,
773
- icon: /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(CloseIcon, { size: 14 }),
929
+ icon: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(CloseIcon, { size: 14 }),
774
930
  "aria-label": clearLabel,
775
931
  onClick: clear,
776
932
  className: "fe-text-input__clear"
777
933
  }
778
934
  )
779
935
  ] }),
780
- /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
936
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
781
937
  FieldMessage,
782
938
  {
783
939
  id: messageId2,
@@ -794,9 +950,9 @@ var TextInput = (0, import_react7.forwardRef)(
794
950
  TextInput.displayName = "TextInput";
795
951
 
796
952
  // packages/form-controls/src/controls/TextArea/text-area.tsx
797
- var import_react8 = require("react");
798
- var import_jsx_runtime13 = require("react/jsx-runtime");
799
- var TextArea = (0, import_react8.forwardRef)(
953
+ var import_react10 = require("react");
954
+ var import_jsx_runtime14 = require("react/jsx-runtime");
955
+ var TextArea = (0, import_react10.forwardRef)(
800
956
  function TextArea2({
801
957
  value,
802
958
  defaultValue = "",
@@ -808,6 +964,7 @@ var TextArea = (0, import_react8.forwardRef)(
808
964
  helperText,
809
965
  error,
810
966
  errorMessage,
967
+ autosize = false,
811
968
  clearable = false,
812
969
  onClear,
813
970
  clearLabel = "Clear text area",
@@ -822,12 +979,13 @@ var TextArea = (0, import_react8.forwardRef)(
822
979
  "aria-labelledby": ariaLabelledBy,
823
980
  ...props
824
981
  }, ref) {
825
- const generatedId = (0, import_react8.useId)();
982
+ const generatedId = (0, import_react10.useId)();
826
983
  const inputId = id ?? generatedId + "-input";
827
984
  const labelId = generatedId + "-label";
828
985
  const messageId2 = generatedId + "-message";
829
986
  const controlled = value !== void 0;
830
- const [internalValue, setInternalValue] = (0, import_react8.useState)(defaultValue);
987
+ const [internalValue, setInternalValue] = (0, import_react10.useState)(defaultValue);
988
+ const textareaRef = (0, import_react10.useRef)(null);
831
989
  const currentValue = controlled ? value : internalValue;
832
990
  const fieldError = getFieldError(error, errorMessage);
833
991
  const hasError = fieldError !== void 0 && fieldError !== false && fieldError !== null;
@@ -841,21 +999,32 @@ var TextArea = (0, import_react8.forwardRef)(
841
999
  ariaLabelledBy,
842
1000
  label ? labelId : void 0
843
1001
  );
1002
+ const resizeToContent = (textarea) => {
1003
+ textarea.style.height = "auto";
1004
+ textarea.style.height = `${textarea.scrollHeight}px`;
1005
+ };
1006
+ (0, import_react10.useImperativeHandle)(ref, () => textareaRef.current, []);
1007
+ (0, import_react10.useLayoutEffect)(() => {
1008
+ if (autosize && textareaRef.current) {
1009
+ resizeToContent(textareaRef.current);
1010
+ }
1011
+ }, [autosize, currentValue]);
844
1012
  const clear = () => {
845
1013
  if (!controlled) setInternalValue("");
846
1014
  onValueChange?.("");
847
1015
  onClear?.();
848
1016
  };
849
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
1017
+ return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
850
1018
  "div",
851
1019
  {
852
1020
  className: [
853
1021
  "fe-text-area",
854
1022
  hasError && "fe-text-area--error",
1023
+ autosize && "fe-text-area--autosize",
855
1024
  className
856
1025
  ].filter(Boolean).join(" "),
857
1026
  children: [
858
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
1027
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
859
1028
  FieldLabel,
860
1029
  {
861
1030
  id: labelId,
@@ -865,11 +1034,11 @@ var TextArea = (0, import_react8.forwardRef)(
865
1034
  isRequired
866
1035
  }
867
1036
  ),
868
- /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("span", { className: "fe-text-area__control", children: [
869
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
1037
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "fe-text-area__control", children: [
1038
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
870
1039
  "textarea",
871
1040
  {
872
- ref,
1041
+ ref: textareaRef,
873
1042
  id: inputId,
874
1043
  value: currentValue,
875
1044
  placeholder,
@@ -882,30 +1051,31 @@ var TextArea = (0, import_react8.forwardRef)(
882
1051
  "aria-describedby": describedBy,
883
1052
  onChange: (event) => {
884
1053
  if (!controlled) setInternalValue(event.target.value);
1054
+ if (autosize) resizeToContent(event.currentTarget);
885
1055
  onValueChange?.(event.target.value);
886
1056
  onChange?.(event);
887
1057
  },
888
1058
  ...props
889
1059
  }
890
1060
  ),
891
- isRequired && placeholder && !currentValue && /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("span", { className: "fe-text-area__placeholder", "aria-hidden": "true", children: [
892
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { children: placeholder }),
893
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { className: "fe-field__required", children: "*" })
1061
+ isRequired && placeholder && !currentValue && /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "fe-text-area__placeholder", "aria-hidden": "true", children: [
1062
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { children: placeholder }),
1063
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "fe-field__required", children: "*" })
894
1064
  ] }),
895
- clearable && currentValue && !disabled && !readOnly && /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
1065
+ clearable && currentValue && !disabled && !readOnly && /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
896
1066
  Button,
897
1067
  {
898
1068
  hierarchy: "tertiary-gray",
899
1069
  size: "24",
900
1070
  iconOnly: true,
901
- icon: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(CloseIcon, { size: 14 }),
1071
+ icon: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(CloseIcon, { size: 14 }),
902
1072
  "aria-label": clearLabel,
903
1073
  onClick: clear,
904
1074
  className: "fe-text-area__clear"
905
1075
  }
906
1076
  )
907
1077
  ] }),
908
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
1078
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
909
1079
  FieldMessage,
910
1080
  {
911
1081
  id: messageId2,
@@ -922,10 +1092,10 @@ var TextArea = (0, import_react8.forwardRef)(
922
1092
  TextArea.displayName = "TextArea";
923
1093
 
924
1094
  // packages/form-controls/src/controls/Selection/selection.tsx
925
- var import_react9 = require("react");
1095
+ var import_react11 = require("react");
926
1096
  var import_react_dom2 = require("react-dom");
927
- var import_jsx_runtime14 = require("react/jsx-runtime");
928
- var Selection = (0, import_react9.forwardRef)(
1097
+ var import_jsx_runtime15 = require("react/jsx-runtime");
1098
+ var Selection = (0, import_react11.forwardRef)(
929
1099
  function Selection2({
930
1100
  className,
931
1101
  label,
@@ -954,7 +1124,7 @@ var Selection = (0, import_react9.forwardRef)(
954
1124
  "aria-labelledby": ariaLabelledBy,
955
1125
  ...props
956
1126
  }, ref) {
957
- const generatedId = (0, import_react9.useId)();
1127
+ const generatedId = (0, import_react11.useId)();
958
1128
  const triggerId = id ?? generatedId + "-trigger";
959
1129
  const listboxId = triggerId + "-listbox";
960
1130
  const labelId = generatedId + "-label";
@@ -972,7 +1142,7 @@ var Selection = (0, import_react9.forwardRef)(
972
1142
  label ? labelId : void 0
973
1143
  );
974
1144
  const isControlled = value !== void 0;
975
- const [internalValue, setInternalValue] = (0, import_react9.useState)(
1145
+ const [internalValue, setInternalValue] = (0, import_react11.useState)(
976
1146
  defaultValue ?? (multiple ? [] : "")
977
1147
  );
978
1148
  const selectedValue = isControlled ? value : internalValue;
@@ -980,13 +1150,13 @@ var Selection = (0, import_react9.forwardRef)(
980
1150
  const selectedOptions = options.filter(
981
1151
  (option) => selectedValues.some((item) => String(item) === String(option.value))
982
1152
  );
983
- const [open, setOpen] = (0, import_react9.useState)(false);
984
- const [query, setQuery] = (0, import_react9.useState)("");
985
- const [activeIndex, setActiveIndex] = (0, import_react9.useState)(0);
986
- const rootRef = (0, import_react9.useRef)(null);
987
- const menuRef = (0, import_react9.useRef)(null);
988
- const [menuPosition, setMenuPosition] = (0, import_react9.useState)(null);
989
- (0, import_react9.useEffect)(() => {
1153
+ const [open, setOpen] = (0, import_react11.useState)(false);
1154
+ const [query, setQuery] = (0, import_react11.useState)("");
1155
+ const [activeIndex, setActiveIndex] = (0, import_react11.useState)(0);
1156
+ const rootRef = (0, import_react11.useRef)(null);
1157
+ const menuRef = (0, import_react11.useRef)(null);
1158
+ const [menuPosition, setMenuPosition] = (0, import_react11.useState)(null);
1159
+ (0, import_react11.useEffect)(() => {
990
1160
  const close = (event) => {
991
1161
  const target = event.target;
992
1162
  if (!rootRef.current?.contains(target) && !menuRef.current?.contains(target))
@@ -995,7 +1165,7 @@ var Selection = (0, import_react9.forwardRef)(
995
1165
  document.addEventListener("mousedown", close);
996
1166
  return () => document.removeEventListener("mousedown", close);
997
1167
  }, []);
998
- (0, import_react9.useLayoutEffect)(() => {
1168
+ (0, import_react11.useLayoutEffect)(() => {
999
1169
  if (!open) return;
1000
1170
  const updateMenuPosition = () => {
1001
1171
  const rect = rootRef.current?.getBoundingClientRect();
@@ -1072,7 +1242,7 @@ var Selection = (0, import_react9.forwardRef)(
1072
1242
  }
1073
1243
  if (event.key === "Escape") setOpen(false);
1074
1244
  };
1075
- return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
1245
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
1076
1246
  "div",
1077
1247
  {
1078
1248
  ref,
@@ -1087,7 +1257,7 @@ var Selection = (0, import_react9.forwardRef)(
1087
1257
  ].filter(Boolean).join(" "),
1088
1258
  ...props,
1089
1259
  children: [
1090
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1260
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1091
1261
  FieldLabel,
1092
1262
  {
1093
1263
  id: labelId,
@@ -1097,8 +1267,8 @@ var Selection = (0, import_react9.forwardRef)(
1097
1267
  isRequired
1098
1268
  }
1099
1269
  ),
1100
- /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { ref: rootRef, className: "fe-selection__control", children: [
1101
- name && selectedValues.map((item) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1270
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { ref: rootRef, className: "fe-selection__control", children: [
1271
+ name && selectedValues.map((item) => /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1102
1272
  "input",
1103
1273
  {
1104
1274
  type: "hidden",
@@ -1107,7 +1277,7 @@ var Selection = (0, import_react9.forwardRef)(
1107
1277
  },
1108
1278
  String(item)
1109
1279
  )),
1110
- /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
1280
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
1111
1281
  "button",
1112
1282
  {
1113
1283
  id: triggerId,
@@ -1125,7 +1295,7 @@ var Selection = (0, import_react9.forwardRef)(
1125
1295
  onClick: () => setOpen((current) => !current),
1126
1296
  onKeyDown: onTriggerKeyDown,
1127
1297
  children: [
1128
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1298
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1129
1299
  "span",
1130
1300
  {
1131
1301
  className: [
@@ -1133,30 +1303,30 @@ var Selection = (0, import_react9.forwardRef)(
1133
1303
  !selectedOptions.length && "is-placeholder",
1134
1304
  tag && selectedOptions.length > 1 && "is-tags"
1135
1305
  ].filter(Boolean).join(" "),
1136
- children: displayLabel ? tag && multiple ? selectedOptions.map((option) => /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
1306
+ children: displayLabel ? tag && multiple ? selectedOptions.map((option) => /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
1137
1307
  "span",
1138
1308
  {
1139
1309
  className: "fe-selection__tag",
1140
1310
  children: [
1141
1311
  option.label,
1142
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { "aria-hidden": "true", children: "\xD7" })
1312
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { "aria-hidden": "true", children: "\xD7" })
1143
1313
  ]
1144
1314
  },
1145
1315
  String(option.value)
1146
- )) : displayLabel.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { children: [
1316
+ )) : displayLabel.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("span", { children: [
1147
1317
  item,
1148
1318
  index < displayLabel.length - 1 ? ", " : ""
1149
- ] }, index)) : /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(import_jsx_runtime14.Fragment, { children: [
1150
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { children: placeholder }),
1151
- isRequired && /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "fe-field__required", "aria-hidden": "true", children: "*" })
1319
+ ] }, index)) : /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(import_jsx_runtime15.Fragment, { children: [
1320
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { children: placeholder }),
1321
+ isRequired && /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "fe-field__required", "aria-hidden": "true", children: "*" })
1152
1322
  ] })
1153
1323
  }
1154
1324
  ),
1155
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "fe-selection__actions", children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "fe-selection__chevron", "aria-hidden": "true" }) })
1325
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "fe-selection__actions", children: /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "fe-selection__chevron", "aria-hidden": "true" }) })
1156
1326
  ]
1157
1327
  }
1158
1328
  ),
1159
- clearable && selectedOptions.length > 0 && !disabled && /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1329
+ clearable && selectedOptions.length > 0 && !disabled && /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1160
1330
  "button",
1161
1331
  {
1162
1332
  type: "button",
@@ -1166,7 +1336,7 @@ var Selection = (0, import_react9.forwardRef)(
1166
1336
  }
1167
1337
  ),
1168
1338
  open && menuPosition && (0, import_react_dom2.createPortal)(
1169
- /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
1339
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
1170
1340
  "div",
1171
1341
  {
1172
1342
  ref: menuRef,
@@ -1181,9 +1351,9 @@ var Selection = (0, import_react9.forwardRef)(
1181
1351
  role: "listbox",
1182
1352
  "aria-multiselectable": multiple || void 0,
1183
1353
  children: [
1184
- searchable && /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "fe-selection__search", children: [
1185
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { "aria-hidden": "true", children: "\u2315" }),
1186
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1354
+ searchable && /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className: "fe-selection__search", children: [
1355
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { "aria-hidden": "true", children: "\u2315" }),
1356
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1187
1357
  "input",
1188
1358
  {
1189
1359
  autoFocus: true,
@@ -1197,11 +1367,11 @@ var Selection = (0, import_react9.forwardRef)(
1197
1367
  }
1198
1368
  )
1199
1369
  ] }),
1200
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("div", { className: "fe-selection__options", children: filteredOptions.length ? filteredOptions.map((option, index) => {
1370
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("div", { className: "fe-selection__options", children: filteredOptions.length ? filteredOptions.map((option, index) => {
1201
1371
  const isSelected = selectedValues.some(
1202
1372
  (item) => String(item) === String(option.value)
1203
1373
  );
1204
- return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
1374
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
1205
1375
  "button",
1206
1376
  {
1207
1377
  type: "button",
@@ -1215,8 +1385,8 @@ var Selection = (0, import_react9.forwardRef)(
1215
1385
  onMouseMove: () => setActiveIndex(index),
1216
1386
  onClick: () => choose(option),
1217
1387
  children: [
1218
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { children: option.label }),
1219
- isSelected && /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1388
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { children: option.label }),
1389
+ isSelected && /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1220
1390
  "span",
1221
1391
  {
1222
1392
  className: "fe-selection__check",
@@ -1228,14 +1398,14 @@ var Selection = (0, import_react9.forwardRef)(
1228
1398
  },
1229
1399
  String(option.value)
1230
1400
  );
1231
- }) : /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("p", { className: "fe-selection__empty", children: "No matching options" }) })
1401
+ }) : /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("p", { className: "fe-selection__empty", children: "No matching options" }) })
1232
1402
  ]
1233
1403
  }
1234
1404
  ),
1235
1405
  document.body
1236
1406
  )
1237
1407
  ] }),
1238
- /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
1408
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1239
1409
  FieldMessage,
1240
1410
  {
1241
1411
  id: messageId2,
@@ -1252,8 +1422,8 @@ var Selection = (0, import_react9.forwardRef)(
1252
1422
  Selection.displayName = "Selection";
1253
1423
 
1254
1424
  // packages/form-controls/src/controls/NumberInput/number-input.tsx
1255
- var import_react10 = require("react");
1256
- var import_jsx_runtime15 = require("react/jsx-runtime");
1425
+ var import_react12 = require("react");
1426
+ var import_jsx_runtime16 = require("react/jsx-runtime");
1257
1427
  function formatNumber(value, decimals = 2, thousandSeparator = ",", decimalSeparator = ".") {
1258
1428
  return new Intl.NumberFormat("en-US", {
1259
1429
  minimumFractionDigits: 0,
@@ -1267,6 +1437,11 @@ function escapeRegExp(value) {
1267
1437
  function groupInteger(value, separator) {
1268
1438
  return value.replace(/\B(?=(\d{3})+(?!\d))/g, separator);
1269
1439
  }
1440
+ function roundToDecimals(value, decimals) {
1441
+ const precision = Math.min(Math.max(0, decimals), 15);
1442
+ const multiplier = 10 ** precision;
1443
+ return Math.round((value + Number.EPSILON) * multiplier) / multiplier;
1444
+ }
1270
1445
  function normalizeNumberInput(raw, options) {
1271
1446
  const { allowDecimal, decimalSeparator, thousandSeparator, min, max } = options;
1272
1447
  const decimals = Math.max(0, options.decimals);
@@ -1305,7 +1480,7 @@ function normalizeNumberInput(raw, options) {
1305
1480
  value
1306
1481
  };
1307
1482
  }
1308
- var NumberInput = (0, import_react10.forwardRef)(
1483
+ var NumberInput = (0, import_react12.forwardRef)(
1309
1484
  function NumberInput2({
1310
1485
  value,
1311
1486
  defaultValue = null,
@@ -1329,17 +1504,27 @@ var NumberInput = (0, import_react10.forwardRef)(
1329
1504
  placeholder,
1330
1505
  required,
1331
1506
  endAdornment,
1507
+ prefix,
1508
+ suffix,
1509
+ Prefix,
1510
+ Suffix,
1511
+ step = 1,
1512
+ showStepper = true,
1513
+ incrementLabel = "Increase value",
1514
+ decrementLabel = "Decrease value",
1332
1515
  "aria-describedby": ariaDescribedBy,
1333
1516
  "aria-labelledby": ariaLabelledBy,
1517
+ onKeyDown,
1334
1518
  ...props
1335
1519
  }, ref) {
1336
- const generatedId = (0, import_react10.useId)();
1520
+ const inputRef = (0, import_react12.useRef)(null);
1521
+ const generatedId = (0, import_react12.useId)();
1337
1522
  const messageId2 = generatedId + "-message";
1338
1523
  const isControlled = value !== void 0;
1339
- const [internalValue, setInternalValue] = (0, import_react10.useState)(defaultValue);
1340
- const [focused, setFocused] = (0, import_react10.useState)(false);
1524
+ const [internalValue, setInternalValue] = (0, import_react12.useState)(defaultValue);
1525
+ const [focused, setFocused] = (0, import_react12.useState)(false);
1341
1526
  const actualValue = isControlled ? value ?? null : internalValue;
1342
- const [text, setText] = (0, import_react10.useState)(
1527
+ const [text, setText] = (0, import_react12.useState)(
1343
1528
  actualValue === null ? "" : formatNumber(
1344
1529
  actualValue,
1345
1530
  decimals,
@@ -1360,7 +1545,9 @@ var NumberInput = (0, import_react10.forwardRef)(
1360
1545
  ariaLabelledBy,
1361
1546
  label ? labelId : void 0
1362
1547
  );
1363
- (0, import_react10.useEffect)(() => {
1548
+ const resolvedPrefix = prefix ?? Prefix;
1549
+ const resolvedSuffix = suffix ?? Suffix;
1550
+ (0, import_react12.useEffect)(() => {
1364
1551
  if (!focused)
1365
1552
  setText(
1366
1553
  actualValue === null ? "" : formatNumber(
@@ -1384,8 +1571,38 @@ var NumberInput = (0, import_react10.forwardRef)(
1384
1571
  if (!isControlled) setInternalValue(next.value);
1385
1572
  onValueChange?.(next.value);
1386
1573
  };
1387
- return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
1388
- "label",
1574
+ const setValue = (nextValue) => {
1575
+ const clamped = Math.min(
1576
+ max ?? Number.POSITIVE_INFINITY,
1577
+ Math.max(min ?? Number.NEGATIVE_INFINITY, nextValue)
1578
+ );
1579
+ const normalized = roundToDecimals(
1580
+ clamped,
1581
+ allowDecimal ? decimals : 0
1582
+ );
1583
+ setText(
1584
+ formatNumber(
1585
+ normalized,
1586
+ decimals,
1587
+ thousandSeparator,
1588
+ decimalSeparator
1589
+ )
1590
+ );
1591
+ if (!isControlled) setInternalValue(normalized);
1592
+ onValueChange?.(normalized);
1593
+ };
1594
+ const adjustValue = (direction) => {
1595
+ if (props.disabled || props.readOnly || !Number.isFinite(step) || step <= 0)
1596
+ return;
1597
+ const baseValue = actualValue ?? min ?? 0;
1598
+ setValue(baseValue + direction * step);
1599
+ inputRef.current?.focus();
1600
+ };
1601
+ const stepIsUsable = Number.isFinite(step) && step > 0;
1602
+ const disableIncrement = Boolean(props.disabled || props.readOnly) || !stepIsUsable || max !== void 0 && actualValue !== null && actualValue >= max;
1603
+ const disableDecrement = Boolean(props.disabled || props.readOnly) || !stepIsUsable || min !== void 0 && actualValue !== null && actualValue <= min;
1604
+ return /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)(
1605
+ "div",
1389
1606
  {
1390
1607
  className: [
1391
1608
  "fe-number-input",
@@ -1393,7 +1610,7 @@ var NumberInput = (0, import_react10.forwardRef)(
1393
1610
  className
1394
1611
  ].filter(Boolean).join(" "),
1395
1612
  children: [
1396
- /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1613
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1397
1614
  FieldLabel,
1398
1615
  {
1399
1616
  id: labelId,
@@ -1403,38 +1620,89 @@ var NumberInput = (0, import_react10.forwardRef)(
1403
1620
  isRequired
1404
1621
  }
1405
1622
  ),
1406
- /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("span", { className: "fe-number-input__control", children: [
1407
- /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1408
- "input",
1409
- {
1410
- ref,
1411
- inputMode: allowDecimal ? "decimal" : "numeric",
1412
- value: text,
1413
- placeholder,
1414
- required: isRequired || required,
1415
- onFocus: (event) => {
1416
- setFocused(true);
1417
- onFocus?.(event);
1418
- },
1419
- onChange: (event) => updateValue(event.target.value),
1420
- onBlur: (event) => {
1421
- setFocused(false);
1422
- onBlur?.(event);
1423
- },
1424
- ...props,
1425
- "aria-invalid": hasError || void 0,
1426
- "aria-required": isRequired || void 0,
1427
- "aria-labelledby": labelledBy,
1428
- "aria-describedby": describedBy
1429
- }
1430
- ),
1431
- isRequired && placeholder && !text && /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("span", { className: "fe-number-input__placeholder", "aria-hidden": "true", children: [
1432
- /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { children: placeholder }),
1433
- /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "fe-field__required", children: "*" })
1623
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("span", { className: "fe-number-input__control", children: [
1624
+ resolvedPrefix && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("span", { className: "fe-number-input__prefix", children: resolvedPrefix }),
1625
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("span", { className: "fe-number-input__input-wrap", children: [
1626
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1627
+ "input",
1628
+ {
1629
+ ref: (node) => {
1630
+ inputRef.current = node;
1631
+ if (typeof ref === "function") ref(node);
1632
+ else if (ref) ref.current = node;
1633
+ },
1634
+ inputMode: allowDecimal ? "decimal" : "numeric",
1635
+ value: text,
1636
+ placeholder,
1637
+ required: isRequired || required,
1638
+ onFocus: (event) => {
1639
+ setFocused(true);
1640
+ onFocus?.(event);
1641
+ },
1642
+ onChange: (event) => updateValue(event.target.value),
1643
+ onBlur: (event) => {
1644
+ setFocused(false);
1645
+ onBlur?.(event);
1646
+ },
1647
+ onKeyDown: (event) => {
1648
+ onKeyDown?.(event);
1649
+ if (event.defaultPrevented) return;
1650
+ if (event.key === "ArrowUp" || event.key === "ArrowDown") {
1651
+ event.preventDefault();
1652
+ adjustValue(event.key === "ArrowUp" ? 1 : -1);
1653
+ }
1654
+ },
1655
+ ...props,
1656
+ "aria-invalid": hasError || void 0,
1657
+ "aria-required": isRequired || void 0,
1658
+ "aria-labelledby": labelledBy,
1659
+ "aria-describedby": describedBy
1660
+ }
1661
+ ),
1662
+ isRequired && placeholder && !text && /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)(
1663
+ "span",
1664
+ {
1665
+ className: "fe-number-input__placeholder",
1666
+ "aria-hidden": "true",
1667
+ children: [
1668
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("span", { children: placeholder }),
1669
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("span", { className: "fe-field__required", children: "*" })
1670
+ ]
1671
+ }
1672
+ )
1434
1673
  ] }),
1435
- endAdornment
1674
+ resolvedSuffix && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("span", { className: "fe-number-input__suffix", children: resolvedSuffix }),
1675
+ endAdornment,
1676
+ showStepper && /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("span", { className: "fe-number-input__stepper", children: [
1677
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1678
+ Button,
1679
+ {
1680
+ hierarchy: "tertiary-gray",
1681
+ size: "24",
1682
+ iconOnly: true,
1683
+ icon: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(ChevronUpIcon, { size: 12 }),
1684
+ "aria-label": incrementLabel,
1685
+ disabled: disableIncrement,
1686
+ onMouseDown: (event) => event.preventDefault(),
1687
+ onClick: () => adjustValue(1)
1688
+ }
1689
+ ),
1690
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1691
+ Button,
1692
+ {
1693
+ hierarchy: "tertiary-gray",
1694
+ size: "24",
1695
+ iconOnly: true,
1696
+ icon: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(ChevronDownIcon, { size: 12 }),
1697
+ "aria-label": decrementLabel,
1698
+ disabled: disableDecrement,
1699
+ onMouseDown: (event) => event.preventDefault(),
1700
+ onClick: () => adjustValue(-1)
1701
+ }
1702
+ )
1703
+ ] })
1436
1704
  ] }),
1437
- /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1705
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1438
1706
  FieldMessage,
1439
1707
  {
1440
1708
  id: messageId2,
@@ -1451,8 +1719,8 @@ var NumberInput = (0, import_react10.forwardRef)(
1451
1719
  NumberInput.displayName = "NumberInput";
1452
1720
 
1453
1721
  // packages/form-controls/src/controls/CurrencyInput/currency-input.tsx
1454
- var import_react11 = require("react");
1455
- var import_jsx_runtime16 = require("react/jsx-runtime");
1722
+ var import_react13 = require("react");
1723
+ var import_jsx_runtime17 = require("react/jsx-runtime");
1456
1724
  function CurrencyInput({
1457
1725
  suffix = "VND",
1458
1726
  currencies,
@@ -1463,13 +1731,13 @@ function CurrencyInput({
1463
1731
  disabled,
1464
1732
  ...props
1465
1733
  }) {
1466
- const [internalCurrency, setInternalCurrency] = (0, import_react11.useState)(
1734
+ const [internalCurrency, setInternalCurrency] = (0, import_react13.useState)(
1467
1735
  defaultCurrency ?? currencies?.[0]?.code ?? ""
1468
1736
  );
1469
1737
  const selectedCurrency = currency ?? internalCurrency;
1470
1738
  const current = currencies?.find((item) => item.code === selectedCurrency);
1471
1739
  const currencySuffix = current?.suffix ?? current?.code ?? suffix;
1472
- const endAdornment = currencies?.length ? /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1740
+ const endAdornment = currencies?.length ? /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1473
1741
  Selection,
1474
1742
  {
1475
1743
  className: "fe-currency-input__currency",
@@ -1488,8 +1756,8 @@ function CurrencyInput({
1488
1756
  onCurrencyChange?.(next);
1489
1757
  }
1490
1758
  }
1491
- ) : /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("span", { className: "fe-currency-input__suffix", children: currencySuffix });
1492
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1759
+ ) : /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "fe-currency-input__suffix", children: currencySuffix });
1760
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1493
1761
  NumberInput,
1494
1762
  {
1495
1763
  ...props,
@@ -1501,8 +1769,8 @@ function CurrencyInput({
1501
1769
  }
1502
1770
 
1503
1771
  // packages/form-controls/src/controls/DateTimePicker/date-time-picker.tsx
1504
- var import_react12 = require("react");
1505
- var import_jsx_runtime17 = require("react/jsx-runtime");
1772
+ var import_react14 = require("react");
1773
+ var import_jsx_runtime18 = require("react/jsx-runtime");
1506
1774
  var pad = (value) => String(value).padStart(2, "0");
1507
1775
  function formatDate(date, format) {
1508
1776
  return format.replace(/yyyy/g, String(date.getFullYear())).replace(/MM/g, pad(date.getMonth() + 1)).replace(/dd/g, pad(date.getDate())).replace(/HH/g, pad(date.getHours())).replace(/mm/g, pad(date.getMinutes()));
@@ -1538,7 +1806,7 @@ function DateTimePicker(props) {
1538
1806
  "aria-describedby": ariaDescribedBy,
1539
1807
  "aria-labelledby": ariaLabelledBy
1540
1808
  } = props;
1541
- const generatedId = (0, import_react12.useId)();
1809
+ const generatedId = (0, import_react14.useId)();
1542
1810
  const triggerId = id ?? generatedId + "-trigger";
1543
1811
  const labelId = generatedId + "-label";
1544
1812
  const messageId2 = generatedId + "-message";
@@ -1556,28 +1824,28 @@ function DateTimePicker(props) {
1556
1824
  );
1557
1825
  const isRange = mode === "range";
1558
1826
  const controlled = props.value !== void 0;
1559
- const [singleInternal, setSingleInternal] = (0, import_react12.useState)(
1827
+ const [singleInternal, setSingleInternal] = (0, import_react14.useState)(
1560
1828
  (!isRange ? props.defaultValue : null) ?? null
1561
1829
  );
1562
- const [rangeInternal, setRangeInternal] = (0, import_react12.useState)(
1830
+ const [rangeInternal, setRangeInternal] = (0, import_react14.useState)(
1563
1831
  (isRange ? props.defaultValue : void 0) ?? [null, null]
1564
1832
  );
1565
1833
  const singleValue = !isRange ? props.value ?? singleInternal : null;
1566
1834
  const rangeValue = isRange ? props.value ?? rangeInternal : [null, null];
1567
- const [open, setOpen] = (0, import_react12.useState)(false);
1568
- const [month, setMonth] = (0, import_react12.useState)(
1835
+ const [open, setOpen] = (0, import_react14.useState)(false);
1836
+ const [month, setMonth] = (0, import_react14.useState)(
1569
1837
  () => new Date((isRange ? rangeValue[0] : singleValue) ?? /* @__PURE__ */ new Date())
1570
1838
  );
1571
- const [editingEnd, setEditingEnd] = (0, import_react12.useState)(false);
1572
- const rootRef = (0, import_react12.useRef)(null);
1573
- (0, import_react12.useEffect)(() => {
1839
+ const [editingEnd, setEditingEnd] = (0, import_react14.useState)(false);
1840
+ const rootRef = (0, import_react14.useRef)(null);
1841
+ (0, import_react14.useEffect)(() => {
1574
1842
  const onPointerDown = (event) => {
1575
1843
  if (!rootRef.current?.contains(event.target)) setOpen(false);
1576
1844
  };
1577
1845
  document.addEventListener("mousedown", onPointerDown);
1578
1846
  return () => document.removeEventListener("mousedown", onPointerDown);
1579
1847
  }, []);
1580
- (0, import_react12.useEffect)(() => {
1848
+ (0, import_react14.useEffect)(() => {
1581
1849
  if (disabled) setOpen(false);
1582
1850
  }, [disabled]);
1583
1851
  const setSingle = (next) => {
@@ -1633,7 +1901,7 @@ function DateTimePicker(props) {
1633
1901
  setRange(editingEnd ? [rangeValue[0], next] : [next, rangeValue[1]]);
1634
1902
  else setSingle(next);
1635
1903
  };
1636
- return /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
1904
+ return /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
1637
1905
  "div",
1638
1906
  {
1639
1907
  ref: rootRef,
@@ -1643,7 +1911,7 @@ function DateTimePicker(props) {
1643
1911
  className
1644
1912
  ].filter(Boolean).join(" "),
1645
1913
  children: [
1646
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1914
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1647
1915
  FieldLabel,
1648
1916
  {
1649
1917
  id: labelId,
@@ -1653,7 +1921,7 @@ function DateTimePicker(props) {
1653
1921
  isRequired
1654
1922
  }
1655
1923
  ),
1656
- /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
1924
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
1657
1925
  "button",
1658
1926
  {
1659
1927
  id: triggerId,
@@ -1667,29 +1935,29 @@ function DateTimePicker(props) {
1667
1935
  "aria-expanded": open,
1668
1936
  onClick: () => setOpen((current) => !current),
1669
1937
  children: [
1670
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { "aria-hidden": "true", children: "\u25F7" }),
1671
- /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
1938
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { "aria-hidden": "true", children: "\u25F7" }),
1939
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
1672
1940
  "span",
1673
1941
  {
1674
1942
  className: !shownValue && placeholder ? "fe-datetime-picker__value is-placeholder" : "fe-datetime-picker__value",
1675
1943
  children: [
1676
1944
  shownValue || placeholder || (isRange ? "Select date range" : "Select date and time"),
1677
- isRequired && placeholder && !shownValue && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "fe-field__required", "aria-hidden": "true", children: "*" })
1945
+ isRequired && placeholder && !shownValue && /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "fe-field__required", "aria-hidden": "true", children: "*" })
1678
1946
  ]
1679
1947
  }
1680
1948
  )
1681
1949
  ]
1682
1950
  }
1683
1951
  ),
1684
- open && /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
1952
+ open && /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
1685
1953
  "div",
1686
1954
  {
1687
1955
  className: "fe-datetime-picker__popper",
1688
1956
  role: "dialog",
1689
1957
  "aria-label": "Date and time picker",
1690
1958
  children: [
1691
- /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "fe-datetime-picker__month", children: [
1692
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1959
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "fe-datetime-picker__month", children: [
1960
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1693
1961
  "button",
1694
1962
  {
1695
1963
  type: "button",
@@ -1700,11 +1968,11 @@ function DateTimePicker(props) {
1700
1968
  children: "\u2039"
1701
1969
  }
1702
1970
  ),
1703
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("strong", { children: month.toLocaleDateString(locale, {
1971
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("strong", { children: month.toLocaleDateString(locale, {
1704
1972
  month: "long",
1705
1973
  year: "numeric"
1706
1974
  }) }),
1707
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1975
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1708
1976
  "button",
1709
1977
  {
1710
1978
  type: "button",
@@ -1716,12 +1984,12 @@ function DateTimePicker(props) {
1716
1984
  }
1717
1985
  )
1718
1986
  ] }),
1719
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "fe-datetime-picker__weekdays", children: ["Mo", "Tu", "We", "Th", "Fr", "Sa", "Su"].map((day) => /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { children: day }, day)) }),
1720
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "fe-datetime-picker__days", children: days.map((day) => {
1987
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { className: "fe-datetime-picker__weekdays", children: ["Mo", "Tu", "We", "Th", "Fr", "Sa", "Su"].map((day) => /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { children: day }, day)) }),
1988
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { className: "fe-datetime-picker__days", children: days.map((day) => {
1721
1989
  const inMonth = day.getMonth() === month.getMonth();
1722
1990
  const selected = isRange ? sameDay(day, rangeValue[0]) || sameDay(day, rangeValue[1]) : sameDay(day, singleValue);
1723
1991
  const inRange = isRange && rangeValue[0] && rangeValue[1] && day > startOfDay(rangeValue[0]) && day < startOfDay(rangeValue[1]);
1724
- return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1992
+ return /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1725
1993
  "button",
1726
1994
  {
1727
1995
  type: "button",
@@ -1736,8 +2004,8 @@ function DateTimePicker(props) {
1736
2004
  day.toISOString()
1737
2005
  );
1738
2006
  }) }),
1739
- isRange && /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "fe-datetime-picker__range-tabs", children: [
1740
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
2007
+ isRange && /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "fe-datetime-picker__range-tabs", children: [
2008
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1741
2009
  "button",
1742
2010
  {
1743
2011
  type: "button",
@@ -1746,7 +2014,7 @@ function DateTimePicker(props) {
1746
2014
  children: "Start"
1747
2015
  }
1748
2016
  ),
1749
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
2017
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1750
2018
  "button",
1751
2019
  {
1752
2020
  type: "button",
@@ -1756,9 +2024,9 @@ function DateTimePicker(props) {
1756
2024
  }
1757
2025
  )
1758
2026
  ] }),
1759
- /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("label", { className: "fe-datetime-picker__time", children: [
2027
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("label", { className: "fe-datetime-picker__time", children: [
1760
2028
  "Time",
1761
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
2029
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1762
2030
  "input",
1763
2031
  {
1764
2032
  type: "time",
@@ -1771,7 +2039,7 @@ function DateTimePicker(props) {
1771
2039
  ]
1772
2040
  }
1773
2041
  ),
1774
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
2042
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1775
2043
  FieldMessage,
1776
2044
  {
1777
2045
  id: messageId2,
@@ -1785,30 +2053,190 @@ function DateTimePicker(props) {
1785
2053
  );
1786
2054
  }
1787
2055
 
2056
+ // packages/form-controls/src/controls/Checkbox/checkbox.tsx
2057
+ var import_react15 = require("react");
2058
+ var import_jsx_runtime19 = require("react/jsx-runtime");
2059
+ var Checkbox = (0, import_react15.forwardRef)(
2060
+ function Checkbox2({
2061
+ label,
2062
+ labelPosition = "right",
2063
+ className,
2064
+ style,
2065
+ id,
2066
+ disabled,
2067
+ ...props
2068
+ }, ref) {
2069
+ const classes = [
2070
+ "fe-checkbox",
2071
+ `fe-checkbox--label-${labelPosition}`,
2072
+ disabled && "fe-checkbox--disabled",
2073
+ className
2074
+ ].filter(Boolean).join(" ");
2075
+ return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("label", { className: classes, style, children: [
2076
+ label && labelPosition === "top" && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "fe-checkbox__label", children: label }),
2077
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("span", { className: "fe-checkbox__content", children: [
2078
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
2079
+ "input",
2080
+ {
2081
+ ref,
2082
+ id,
2083
+ className: "fe-checkbox__input",
2084
+ type: "checkbox",
2085
+ disabled,
2086
+ ...props
2087
+ }
2088
+ ),
2089
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "fe-checkbox__control", "aria-hidden": "true" }),
2090
+ label && labelPosition === "right" && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "fe-checkbox__label", children: label })
2091
+ ] })
2092
+ ] });
2093
+ }
2094
+ );
2095
+ Checkbox.displayName = "Checkbox";
2096
+
2097
+ // packages/form-controls/src/controls/RadioButton/radio-button.tsx
2098
+ var import_react16 = require("react");
2099
+ var import_jsx_runtime20 = require("react/jsx-runtime");
2100
+ var RadioButton = (0, import_react16.forwardRef)(
2101
+ function RadioButton2({
2102
+ label,
2103
+ labelPosition = "right",
2104
+ className,
2105
+ style,
2106
+ id,
2107
+ disabled,
2108
+ ...props
2109
+ }, ref) {
2110
+ const classes = [
2111
+ "fe-radio-button",
2112
+ `fe-radio-button--label-${labelPosition}`,
2113
+ disabled && "fe-radio-button--disabled",
2114
+ className
2115
+ ].filter(Boolean).join(" ");
2116
+ return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("label", { className: classes, style, children: [
2117
+ label && labelPosition === "top" && /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "fe-radio-button__label", children: label }),
2118
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("span", { className: "fe-radio-button__content", children: [
2119
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
2120
+ "input",
2121
+ {
2122
+ ref,
2123
+ id,
2124
+ className: "fe-radio-button__input",
2125
+ type: "radio",
2126
+ disabled,
2127
+ ...props
2128
+ }
2129
+ ),
2130
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "fe-radio-button__control", "aria-hidden": "true" }),
2131
+ label && labelPosition === "right" && /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "fe-radio-button__label", children: label })
2132
+ ] })
2133
+ ] });
2134
+ }
2135
+ );
2136
+ RadioButton.displayName = "RadioButton";
2137
+
2138
+ // packages/form-controls/src/controls/RadioGroup/radio-group.tsx
2139
+ var import_react17 = require("react");
2140
+ var import_jsx_runtime21 = require("react/jsx-runtime");
2141
+ var RadioGroup = (0, import_react17.forwardRef)(
2142
+ function RadioGroup2({
2143
+ label,
2144
+ labelPosition = "top",
2145
+ options,
2146
+ name,
2147
+ value,
2148
+ defaultValue,
2149
+ onChange,
2150
+ disabled = false,
2151
+ direction = "vertical",
2152
+ isRequired = false,
2153
+ className,
2154
+ id,
2155
+ "aria-label": ariaLabel,
2156
+ "aria-labelledby": ariaLabelledBy,
2157
+ ...props
2158
+ }, ref) {
2159
+ const generatedId = (0, import_react17.useId)();
2160
+ const groupName = name ?? `fe-radio-group-${generatedId}`;
2161
+ const labelId = `${id ?? generatedId}-label`;
2162
+ const isControlled = value !== void 0;
2163
+ const classes = [
2164
+ "fe-radio-group",
2165
+ `fe-radio-group--label-${labelPosition}`,
2166
+ `fe-radio-group--${direction}`,
2167
+ disabled && "fe-radio-group--disabled",
2168
+ className
2169
+ ].filter(Boolean).join(" ");
2170
+ const handleChange = (option, event) => {
2171
+ if (event.target.checked) onChange?.(option.value, option, event);
2172
+ };
2173
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { ref, className: classes, ...props, children: [
2174
+ label && labelPosition === "top" && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("span", { id: labelId, className: "fe-radio-group__label", children: [
2175
+ label,
2176
+ isRequired && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "fe-radio-group__required", "aria-hidden": "true", children: "*" })
2177
+ ] }),
2178
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
2179
+ "div",
2180
+ {
2181
+ id,
2182
+ className: "fe-radio-group__options",
2183
+ role: "radiogroup",
2184
+ "aria-label": label ? void 0 : ariaLabel,
2185
+ "aria-labelledby": label ? labelId : ariaLabelledBy,
2186
+ "aria-required": isRequired || void 0,
2187
+ children: options.map((option) => {
2188
+ const optionDisabled = disabled || option.disabled;
2189
+ const optionValue = String(option.value);
2190
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
2191
+ RadioButton,
2192
+ {
2193
+ name: groupName,
2194
+ value: optionValue,
2195
+ label: option.label,
2196
+ disabled: optionDisabled,
2197
+ required: isRequired,
2198
+ checked: isControlled ? option.value === value : void 0,
2199
+ defaultChecked: !isControlled ? option.value === defaultValue : void 0,
2200
+ onChange: (event) => handleChange(option, event)
2201
+ },
2202
+ optionValue
2203
+ );
2204
+ })
2205
+ }
2206
+ ),
2207
+ label && labelPosition === "right" && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("span", { id: labelId, className: "fe-radio-group__label", children: [
2208
+ label,
2209
+ isRequired && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "fe-radio-group__required", "aria-hidden": "true", children: "*" })
2210
+ ] })
2211
+ ] });
2212
+ }
2213
+ );
2214
+ RadioGroup.displayName = "RadioGroup";
2215
+
1788
2216
  // packages/expandable-section/src/index.tsx
1789
- var import_react13 = require("react");
1790
- var import_jsx_runtime18 = require("react/jsx-runtime");
2217
+ var import_react18 = require("react");
2218
+ var import_jsx_runtime22 = require("react/jsx-runtime");
1791
2219
  function ExpandableSection({ title, children, expanded, defaultExpanded = false, onExpandedChange, disabled, className, ...props }) {
1792
- const [internalExpanded, setInternalExpanded] = (0, import_react13.useState)(defaultExpanded);
2220
+ const [internalExpanded, setInternalExpanded] = (0, import_react18.useState)(defaultExpanded);
1793
2221
  const isExpanded = expanded ?? internalExpanded;
1794
- const id = (0, import_react13.useId)();
2222
+ const id = (0, import_react18.useId)();
1795
2223
  const toggle = () => {
1796
2224
  if (disabled) return;
1797
2225
  const next = !isExpanded;
1798
2226
  if (expanded === void 0) setInternalExpanded(next);
1799
2227
  onExpandedChange?.(next);
1800
2228
  };
1801
- return /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("section", { className: ["fe-expandable-section", isExpanded && "fe-expandable-section--expanded", disabled && "fe-expandable-section--disabled", className].filter(Boolean).join(" "), ...props, children: [
1802
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("button", { className: "fe-expandable-section__trigger", type: "button", "aria-expanded": isExpanded, "aria-controls": id, disabled, onClick: toggle, children: [
1803
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { children: title }),
1804
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "fe-expandable-section__chevron", "aria-hidden": "true" })
2229
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("section", { className: ["fe-expandable-section", isExpanded && "fe-expandable-section--expanded", disabled && "fe-expandable-section--disabled", className].filter(Boolean).join(" "), ...props, children: [
2230
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("button", { className: "fe-expandable-section__trigger", type: "button", "aria-expanded": isExpanded, "aria-controls": id, disabled, onClick: toggle, children: [
2231
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { children: title }),
2232
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "fe-expandable-section__chevron", "aria-hidden": "true" })
1805
2233
  ] }),
1806
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { id, className: "fe-expandable-section__content", "aria-hidden": !isExpanded, children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { className: "fe-expandable-section__content-inner", children }) })
2234
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { id, className: "fe-expandable-section__content", "aria-hidden": !isExpanded, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "fe-expandable-section__content-inner", children }) })
1807
2235
  ] });
1808
2236
  }
1809
2237
 
1810
2238
  // packages/loading/src/index.tsx
1811
- var import_jsx_runtime19 = require("react/jsx-runtime");
2239
+ var import_jsx_runtime23 = require("react/jsx-runtime");
1812
2240
  var sizes = {
1813
2241
  small: "16px",
1814
2242
  medium: "24px",
@@ -1821,15 +2249,15 @@ function Loading({ size = "medium", color = "#2878f0", label, className, style,
1821
2249
  "--fe-loading-color": color,
1822
2250
  ...style
1823
2251
  };
1824
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("span", { className: ["fe-loading", className].filter(Boolean).join(" "), style: loadingStyle, role: "status", ...props, children: [
1825
- /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "fe-loading__spinner", "aria-hidden": "true" }),
1826
- label && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "fe-loading__label", children: label }),
1827
- !label && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "fe-loading__sr-only", children: "Loading" })
2252
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)("span", { className: ["fe-loading", className].filter(Boolean).join(" "), style: loadingStyle, role: "status", ...props, children: [
2253
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "fe-loading__spinner", "aria-hidden": "true" }),
2254
+ label && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "fe-loading__label", children: label }),
2255
+ !label && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "fe-loading__sr-only", children: "Loading" })
1828
2256
  ] });
1829
2257
  }
1830
2258
 
1831
2259
  // packages/skeleton/src/index.tsx
1832
- var import_jsx_runtime20 = require("react/jsx-runtime");
2260
+ var import_jsx_runtime24 = require("react/jsx-runtime");
1833
2261
  var pixels = (value) => typeof value === "number" ? `${value}px` : value;
1834
2262
  function SkeletonBase({ variant = "box", shape, width, height, count = 1, animated = true, className, style, ...props }) {
1835
2263
  const resolvedVariant = shape ?? variant;
@@ -1840,7 +2268,7 @@ function SkeletonBase({ variant = "box", shape, width, height, count = 1, animat
1840
2268
  "--fe-skeleton-height": resolvedHeight,
1841
2269
  ...style
1842
2270
  };
1843
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_jsx_runtime20.Fragment, { children: Array.from({ length: Math.max(1, count) }, (_, index) => /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
2271
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(import_jsx_runtime24.Fragment, { children: Array.from({ length: Math.max(1, count) }, (_, index) => /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
1844
2272
  "div",
1845
2273
  {
1846
2274
  className: ["fe-skeleton", `fe-skeleton--${resolvedVariant}`, animated && "fe-skeleton--animated", className].filter(Boolean).join(" "),
@@ -1852,16 +2280,16 @@ function SkeletonBase({ variant = "box", shape, width, height, count = 1, animat
1852
2280
  )) });
1853
2281
  }
1854
2282
  function SkeletonCircle({ size = 40, ...props }) {
1855
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(SkeletonBase, { variant: "circle", width: size, height: size, ...props });
2283
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SkeletonBase, { variant: "circle", width: size, height: size, ...props });
1856
2284
  }
1857
2285
  function SkeletonSquare({ size = 80, ...props }) {
1858
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(SkeletonBase, { variant: "box", width: size, height: size, ...props });
2286
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SkeletonBase, { variant: "box", width: size, height: size, ...props });
1859
2287
  }
1860
2288
  function SkeletonBox({ width = "100%", height = 80, ...props }) {
1861
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(SkeletonBase, { variant: "box", width, height, ...props });
2289
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SkeletonBase, { variant: "box", width, height, ...props });
1862
2290
  }
1863
2291
  function SkeletonLine({ width = "100%", height = 12, ...props }) {
1864
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(SkeletonBase, { variant: "line", width, height, ...props });
2292
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(SkeletonBase, { variant: "line", width, height, ...props });
1865
2293
  }
1866
2294
  var Skeleton = Object.assign(SkeletonBase, {
1867
2295
  Circle: SkeletonCircle,
@@ -1871,9 +2299,9 @@ var Skeleton = Object.assign(SkeletonBase, {
1871
2299
  });
1872
2300
 
1873
2301
  // packages/modal/src/index.tsx
1874
- var import_react14 = require("react");
2302
+ var import_react19 = require("react");
1875
2303
  var import_react_dom3 = require("react-dom");
1876
- var import_jsx_runtime21 = require("react/jsx-runtime");
2304
+ var import_jsx_runtime25 = require("react/jsx-runtime");
1877
2305
  function Modal({
1878
2306
  open,
1879
2307
  onClose,
@@ -1889,9 +2317,9 @@ function Modal({
1889
2317
  className,
1890
2318
  ...props
1891
2319
  }) {
1892
- const titleId = (0, import_react14.useId)();
1893
- const panelRef = (0, import_react14.useRef)(null);
1894
- (0, import_react14.useEffect)(() => {
2320
+ const titleId = (0, import_react19.useId)();
2321
+ const panelRef = (0, import_react19.useRef)(null);
2322
+ (0, import_react19.useEffect)(() => {
1895
2323
  if (!open) return;
1896
2324
  const onKeyDown = (event) => {
1897
2325
  if (event.key === "Escape") onClose();
@@ -1903,9 +2331,9 @@ function Modal({
1903
2331
  if (!open || typeof document === "undefined") return null;
1904
2332
  const hasFooter = footer || actions.length > 0;
1905
2333
  return (0, import_react_dom3.createPortal)(
1906
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "fe-modal-backdrop", role: "presentation", onMouseDown: (event) => {
2334
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "fe-modal-backdrop", role: "presentation", onMouseDown: (event) => {
1907
2335
  if (event.target === event.currentTarget && closeOnBackdropClick) onClose();
1908
- }, children: /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(
2336
+ }, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
1909
2337
  "div",
1910
2338
  {
1911
2339
  ref: panelRef,
@@ -1917,17 +2345,17 @@ function Modal({
1917
2345
  tabIndex: -1,
1918
2346
  ...props,
1919
2347
  children: [
1920
- (title || description || closeButton) && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("header", { className: "fe-modal__header", children: [
1921
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "fe-modal__heading", children: [
1922
- title && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("h2", { id: titleId, children: title }),
1923
- description && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("p", { children: description })
2348
+ (title || description || closeButton) && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("header", { className: "fe-modal__header", children: [
2349
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "fe-modal__heading", children: [
2350
+ title && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("h2", { id: titleId, children: title }),
2351
+ description && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("p", { children: description })
1924
2352
  ] }),
1925
- closeButton && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(Button, { hierarchy: "tertiary-gray", size: "32", iconOnly: true, icon: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CloseIcon, {}), "aria-label": closeLabel, onClick: onClose })
2353
+ closeButton && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(Button, { hierarchy: "tertiary-gray", size: "32", iconOnly: true, icon: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CloseIcon, {}), "aria-label": closeLabel, onClick: onClose })
1926
2354
  ] }),
1927
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "fe-modal__body", children }),
1928
- hasFooter && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("footer", { className: "fe-modal__footer", children: [
1929
- footer && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "fe-modal__footer-content", children: footer }),
1930
- actions.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "fe-modal__actions", children: actions.map(({ label, ...action }, index) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(Button, { ...action, children: label }, index)) })
2355
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "fe-modal__body", children }),
2356
+ hasFooter && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("footer", { className: "fe-modal__footer", children: [
2357
+ footer && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "fe-modal__footer-content", children: footer }),
2358
+ actions.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "fe-modal__actions", children: actions.map(({ label, ...action }, index) => /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(Button, { ...action, children: label }, index)) })
1931
2359
  ] })
1932
2360
  ]
1933
2361
  }
@@ -1937,7 +2365,7 @@ function Modal({
1937
2365
  }
1938
2366
 
1939
2367
  // packages/progress/src/index.tsx
1940
- var import_jsx_runtime22 = require("react/jsx-runtime");
2368
+ var import_jsx_runtime26 = require("react/jsx-runtime");
1941
2369
  function ProgressBar({ value, max = 100, label, showValue = true, size = "medium", color = "#2878f0", className, style, "aria-label": ariaLabel, ...props }) {
1942
2370
  const indeterminate = value === null || value === void 0;
1943
2371
  const percentage = indeterminate ? 0 : Math.min(100, Math.max(0, Number(value) / Math.max(1, max) * 100));
@@ -1947,17 +2375,17 @@ function ProgressBar({ value, max = 100, label, showValue = true, size = "medium
1947
2375
  ...style
1948
2376
  };
1949
2377
  const visibleValue = `${Math.round(percentage)}%`;
1950
- return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: ["fe-progress", `fe-progress--${size}`, indeterminate && "fe-progress--indeterminate", className].filter(Boolean).join(" "), style: progressStyle, ...props, children: [
1951
- (label || !indeterminate && showValue) && /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "fe-progress__meta", children: [
1952
- label && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "fe-progress__label", children: label }),
1953
- !indeterminate && showValue && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("output", { className: "fe-progress__value", children: visibleValue })
2378
+ return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: ["fe-progress", `fe-progress--${size}`, indeterminate && "fe-progress--indeterminate", className].filter(Boolean).join(" "), style: progressStyle, ...props, children: [
2379
+ (label || !indeterminate && showValue) && /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)("div", { className: "fe-progress__meta", children: [
2380
+ label && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", { className: "fe-progress__label", children: label }),
2381
+ !indeterminate && showValue && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("output", { className: "fe-progress__value", children: visibleValue })
1954
2382
  ] }),
1955
- /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "fe-progress__track", role: "progressbar", "aria-label": ariaLabel ?? (typeof label === "string" ? label : "Progress"), "aria-valuemin": indeterminate ? void 0 : 0, "aria-valuemax": indeterminate ? void 0 : max, "aria-valuenow": indeterminate ? void 0 : Number(value), "aria-valuetext": indeterminate ? "Loading" : visibleValue, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "fe-progress__indicator" }) })
2383
+ /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("div", { className: "fe-progress__track", role: "progressbar", "aria-label": ariaLabel ?? (typeof label === "string" ? label : "Progress"), "aria-valuemin": indeterminate ? void 0 : 0, "aria-valuemax": indeterminate ? void 0 : max, "aria-valuenow": indeterminate ? void 0 : Number(value), "aria-valuetext": indeterminate ? "Loading" : visibleValue, children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("span", { className: "fe-progress__indicator" }) })
1956
2384
  ] });
1957
2385
  }
1958
2386
 
1959
2387
  // packages/chip/src/index.tsx
1960
- var import_jsx_runtime23 = require("react/jsx-runtime");
2388
+ var import_jsx_runtime27 = require("react/jsx-runtime");
1961
2389
  var statuses = ["default", "info", "success", "warning", "error", "neutral", "pending", "processing"];
1962
2390
  function Chip({ children, status = "default", color, variant = "subtle", dot = false, onRemove, removeLabel = "Remove", className, style, ...props }) {
1963
2391
  const usesCustomColor = Boolean(color);
@@ -1966,16 +2394,16 @@ function Chip({ children, status = "default", color, variant = "subtle", dot = f
1966
2394
  ...style
1967
2395
  };
1968
2396
  const resolvedStatus = statuses.includes(status) ? status : "default";
1969
- return /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)("span", { className: ["fe-chip", `fe-chip--${variant}`, `fe-chip--${usesCustomColor ? "custom" : resolvedStatus}`, className].filter(Boolean).join(" "), style: chipStyle, ...props, children: [
1970
- dot && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "fe-chip__dot", "aria-hidden": "true" }),
1971
- /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "fe-chip__content", children }),
1972
- onRemove && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Button, { hierarchy: "tertiary-gray", size: "24", iconOnly: true, icon: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(CloseIcon, { size: 14 }), "aria-label": removeLabel, onClick: onRemove, className: "fe-chip__remove" })
2397
+ return /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("span", { className: ["fe-chip", `fe-chip--${variant}`, `fe-chip--${usesCustomColor ? "custom" : resolvedStatus}`, className].filter(Boolean).join(" "), style: chipStyle, ...props, children: [
2398
+ dot && /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "fe-chip__dot", "aria-hidden": "true" }),
2399
+ /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "fe-chip__content", children }),
2400
+ onRemove && /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(Button, { hierarchy: "tertiary-gray", size: "24", iconOnly: true, icon: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(CloseIcon, { size: 14 }), "aria-label": removeLabel, onClick: onRemove, className: "fe-chip__remove" })
1973
2401
  ] });
1974
2402
  }
1975
2403
 
1976
2404
  // packages/message/src/index.tsx
1977
- var import_react15 = require("react");
1978
- var import_jsx_runtime24 = require("react/jsx-runtime");
2405
+ var import_react20 = require("react");
2406
+ var import_jsx_runtime28 = require("react/jsx-runtime");
1979
2407
  var messageId = 0;
1980
2408
  var entries = [];
1981
2409
  var listeners = /* @__PURE__ */ new Set();
@@ -2008,22 +2436,22 @@ var message = {
2008
2436
  };
2009
2437
  var icons = { success: "\u2713", info: "i", warning: "!", error: "\xD7" };
2010
2438
  function Message({ maxCount = 4, closeLabel = "Close notification", className, ...props }) {
2011
- const [visibleEntries, setVisibleEntries] = (0, import_react15.useState)(entries);
2012
- (0, import_react15.useEffect)(() => {
2439
+ const [visibleEntries, setVisibleEntries] = (0, import_react20.useState)(entries);
2440
+ (0, import_react20.useEffect)(() => {
2013
2441
  const listener = (nextEntries) => setVisibleEntries(nextEntries);
2014
2442
  listeners.add(listener);
2015
2443
  return () => {
2016
2444
  listeners.delete(listener);
2017
2445
  };
2018
2446
  }, []);
2019
- return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: ["fe-message-viewport", className].filter(Boolean).join(" "), "aria-live": "polite", ...props, children: visibleEntries.slice(-Math.max(1, maxCount)).map((entry) => /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: `fe-message fe-message--${entry.severity ?? "info"}`, role: entry.severity === "error" ? "alert" : "status", children: [
2020
- /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "fe-message__icon", "aria-hidden": "true", children: icons[entry.severity ?? "info"] }),
2021
- /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "fe-message__body", children: [
2022
- entry.title && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("strong", { className: "fe-message__title", children: entry.title }),
2023
- /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "fe-message__content", children: entry.content })
2447
+ return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: ["fe-message-viewport", className].filter(Boolean).join(" "), "aria-live": "polite", ...props, children: visibleEntries.slice(-Math.max(1, maxCount)).map((entry) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: `fe-message fe-message--${entry.severity ?? "info"}`, role: entry.severity === "error" ? "alert" : "status", children: [
2448
+ /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "fe-message__icon", "aria-hidden": "true", children: icons[entry.severity ?? "info"] }),
2449
+ /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "fe-message__body", children: [
2450
+ entry.title && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("strong", { className: "fe-message__title", children: entry.title }),
2451
+ /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "fe-message__content", children: entry.content })
2024
2452
  ] }),
2025
- entry.action && /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "fe-message__action", children: entry.action }),
2026
- /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(Button, { className: "fe-message__close", hierarchy: "tertiary-gray", size: "24", iconOnly: true, icon: "\xD7", "aria-label": closeLabel, onClick: () => dismiss(entry.id) })
2453
+ entry.action && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "fe-message__action", children: entry.action }),
2454
+ /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(Button, { className: "fe-message__close", hierarchy: "tertiary-gray", size: "24", iconOnly: true, icon: "\xD7", "aria-label": closeLabel, onClick: () => dismiss(entry.id) })
2027
2455
  ] }, entry.id)) });
2028
2456
  }
2029
2457
  ((Message2) => {
@@ -2037,8 +2465,8 @@ function Message({ maxCount = 4, closeLabel = "Close notification", className, .
2037
2465
  })(Message || (Message = {}));
2038
2466
 
2039
2467
  // packages/snackbar/src/index.tsx
2040
- var import_react16 = require("react");
2041
- var import_jsx_runtime25 = require("react/jsx-runtime");
2468
+ var import_react21 = require("react");
2469
+ var import_jsx_runtime29 = require("react/jsx-runtime");
2042
2470
  function Snackbar({
2043
2471
  open,
2044
2472
  message: message2,
@@ -2052,12 +2480,12 @@ function Snackbar({
2052
2480
  }) {
2053
2481
  const vertical = anchorOrigin.vertical ?? "bottom";
2054
2482
  const horizontal = anchorOrigin.horizontal ?? "center";
2055
- (0, import_react16.useEffect)(() => {
2483
+ (0, import_react21.useEffect)(() => {
2056
2484
  if (!open || autoHideDuration === null) return void 0;
2057
2485
  const timer = window.setTimeout(() => onClose?.("timeout"), autoHideDuration);
2058
2486
  return () => window.clearTimeout(timer);
2059
2487
  }, [open, autoHideDuration, onClose]);
2060
- (0, import_react16.useEffect)(() => {
2488
+ (0, import_react21.useEffect)(() => {
2061
2489
  if (!open) return void 0;
2062
2490
  const onKeyDown = (event) => {
2063
2491
  if (event.key === "Escape") onClose?.("escapeKeyDown");
@@ -2066,16 +2494,562 @@ function Snackbar({
2066
2494
  return () => window.removeEventListener("keydown", onKeyDown);
2067
2495
  }, [open, onClose]);
2068
2496
  if (!open) return null;
2069
- return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: ["fe-snackbar", `fe-snackbar--${vertical}`, `fe-snackbar--${horizontal}`, className].filter(Boolean).join(" "), ...props, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "fe-snackbar__content", role: "status", "aria-live": "polite", children: [
2070
- /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "fe-snackbar__message", children: message2 }),
2071
- action && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "fe-snackbar__action", children: action }),
2072
- onClose && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(Button, { className: "fe-snackbar__close", hierarchy: "tertiary-gray", size: "24", iconOnly: true, icon: "\xD7", "aria-label": closeLabel, onClick: () => onClose("closeButton") })
2497
+ return /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("div", { className: ["fe-snackbar", `fe-snackbar--${vertical}`, `fe-snackbar--${horizontal}`, className].filter(Boolean).join(" "), ...props, children: /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)("div", { className: "fe-snackbar__content", role: "status", "aria-live": "polite", children: [
2498
+ /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: "fe-snackbar__message", children: message2 }),
2499
+ action && /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: "fe-snackbar__action", children: action }),
2500
+ onClose && /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(Button, { className: "fe-snackbar__close", hierarchy: "tertiary-gray", size: "24", iconOnly: true, icon: "\xD7", "aria-label": closeLabel, onClick: () => onClose("closeButton") })
2073
2501
  ] }) });
2074
2502
  }
2503
+
2504
+ // packages/avatar/src/index.tsx
2505
+ var import_react22 = require("react");
2506
+ var import_jsx_runtime30 = require("react/jsx-runtime");
2507
+ var FALLBACK_AVATARS = [
2508
+ {
2509
+ background: "#E0E7FF",
2510
+ skin: "#F6C6A6",
2511
+ hair: "#432818",
2512
+ shirt: "#5B5BD6",
2513
+ accent: "#A5B4FC",
2514
+ hairStyle: 0,
2515
+ expression: 0
2516
+ },
2517
+ {
2518
+ background: "#FDE68A",
2519
+ skin: "#E7AF87",
2520
+ hair: "#5A3424",
2521
+ shirt: "#D97706",
2522
+ accent: "#FCD34D",
2523
+ hairStyle: 1,
2524
+ expression: 1
2525
+ },
2526
+ {
2527
+ background: "#CCFBF1",
2528
+ skin: "#F4C7A1",
2529
+ hair: "#1F2937",
2530
+ shirt: "#0F766E",
2531
+ accent: "#5EEAD4",
2532
+ hairStyle: 2,
2533
+ expression: 2
2534
+ },
2535
+ {
2536
+ background: "#FCE7F3",
2537
+ skin: "#E5A47F",
2538
+ hair: "#6B2D2D",
2539
+ shirt: "#BE185D",
2540
+ accent: "#F9A8D4",
2541
+ hairStyle: 3,
2542
+ expression: 3,
2543
+ glasses: true
2544
+ },
2545
+ {
2546
+ background: "#DBEAFE",
2547
+ skin: "#8B5E3C",
2548
+ hair: "#24130B",
2549
+ shirt: "#2563EB",
2550
+ accent: "#93C5FD",
2551
+ hairStyle: 0,
2552
+ expression: 1
2553
+ },
2554
+ {
2555
+ background: "#DCFCE7",
2556
+ skin: "#D99B72",
2557
+ hair: "#3F2A20",
2558
+ shirt: "#15803D",
2559
+ accent: "#86EFAC",
2560
+ hairStyle: 1,
2561
+ expression: 2,
2562
+ glasses: true
2563
+ },
2564
+ {
2565
+ background: "#EDE9FE",
2566
+ skin: "#F3C9AD",
2567
+ hair: "#33221A",
2568
+ shirt: "#7C3AED",
2569
+ accent: "#C4B5FD",
2570
+ hairStyle: 2,
2571
+ expression: 3
2572
+ },
2573
+ {
2574
+ background: "#FFE4E6",
2575
+ skin: "#9B6547",
2576
+ hair: "#27150D",
2577
+ shirt: "#E11D48",
2578
+ accent: "#FDA4AF",
2579
+ hairStyle: 3,
2580
+ expression: 0
2581
+ },
2582
+ {
2583
+ background: "#FEF3C7",
2584
+ skin: "#F0B88B",
2585
+ hair: "#855F3B",
2586
+ shirt: "#B45309",
2587
+ accent: "#FBBF24",
2588
+ hairStyle: 0,
2589
+ expression: 2,
2590
+ glasses: true
2591
+ },
2592
+ {
2593
+ background: "#D1FAE5",
2594
+ skin: "#F8D0B0",
2595
+ hair: "#593A28",
2596
+ shirt: "#047857",
2597
+ accent: "#6EE7B7",
2598
+ hairStyle: 1,
2599
+ expression: 3
2600
+ },
2601
+ {
2602
+ background: "#E0F2FE",
2603
+ skin: "#CE8D65",
2604
+ hair: "#372015",
2605
+ shirt: "#0369A1",
2606
+ accent: "#7DD3FC",
2607
+ hairStyle: 2,
2608
+ expression: 0
2609
+ },
2610
+ {
2611
+ background: "#F3E8FF",
2612
+ skin: "#F4C6A3",
2613
+ hair: "#2B1B15",
2614
+ shirt: "#9333EA",
2615
+ accent: "#D8B4FE",
2616
+ hairStyle: 3,
2617
+ expression: 1,
2618
+ glasses: true
2619
+ },
2620
+ {
2621
+ background: "#FFE4C7",
2622
+ skin: "#A96D4C",
2623
+ hair: "#3A2116",
2624
+ shirt: "#C2410C",
2625
+ accent: "#FDBA74",
2626
+ hairStyle: 0,
2627
+ expression: 3
2628
+ },
2629
+ {
2630
+ background: "#ECFCCB",
2631
+ skin: "#F6CCA9",
2632
+ hair: "#7C5135",
2633
+ shirt: "#4D7C0F",
2634
+ accent: "#BEF264",
2635
+ hairStyle: 1,
2636
+ expression: 0
2637
+ },
2638
+ {
2639
+ background: "#CFFAFE",
2640
+ skin: "#E7A27A",
2641
+ hair: "#1F1814",
2642
+ shirt: "#0E7490",
2643
+ accent: "#67E8F9",
2644
+ hairStyle: 2,
2645
+ expression: 1,
2646
+ glasses: true
2647
+ },
2648
+ {
2649
+ background: "#FAE8FF",
2650
+ skin: "#F5C9AA",
2651
+ hair: "#5F3344",
2652
+ shirt: "#A21CAF",
2653
+ accent: "#F0ABFC",
2654
+ hairStyle: 3,
2655
+ expression: 2
2656
+ },
2657
+ {
2658
+ background: "#E0E7FF",
2659
+ skin: "#CF8F67",
2660
+ hair: "#1E1B18",
2661
+ shirt: "#4338CA",
2662
+ accent: "#A5B4FC",
2663
+ hairStyle: 0,
2664
+ expression: 3,
2665
+ glasses: true
2666
+ },
2667
+ {
2668
+ background: "#FFEDD5",
2669
+ skin: "#F7C9A6",
2670
+ hair: "#4E3326",
2671
+ shirt: "#EA580C",
2672
+ accent: "#FDBA74",
2673
+ hairStyle: 1,
2674
+ expression: 0
2675
+ },
2676
+ {
2677
+ background: "#D9F99D",
2678
+ skin: "#A66A49",
2679
+ hair: "#2B1911",
2680
+ shirt: "#65A30D",
2681
+ accent: "#BEF264",
2682
+ hairStyle: 2,
2683
+ expression: 1
2684
+ },
2685
+ {
2686
+ background: "#FCE7F3",
2687
+ skin: "#E9B08A",
2688
+ hair: "#4A2F24",
2689
+ shirt: "#DB2777",
2690
+ accent: "#F9A8D4",
2691
+ hairStyle: 3,
2692
+ expression: 2,
2693
+ glasses: true
2694
+ },
2695
+ {
2696
+ background: "#DBEAFE",
2697
+ skin: "#F2C3A1",
2698
+ hair: "#312018",
2699
+ shirt: "#1D4ED8",
2700
+ accent: "#93C5FD",
2701
+ hairStyle: 0,
2702
+ expression: 0
2703
+ },
2704
+ {
2705
+ background: "#CCFBF1",
2706
+ skin: "#9D6244",
2707
+ hair: "#1F130E",
2708
+ shirt: "#0D9488",
2709
+ accent: "#5EEAD4",
2710
+ hairStyle: 1,
2711
+ expression: 1,
2712
+ glasses: true
2713
+ },
2714
+ {
2715
+ background: "#FEE2E2",
2716
+ skin: "#F6CBAA",
2717
+ hair: "#75452A",
2718
+ shirt: "#DC2626",
2719
+ accent: "#FCA5A5",
2720
+ hairStyle: 2,
2721
+ expression: 2
2722
+ },
2723
+ {
2724
+ background: "#EDE9FE",
2725
+ skin: "#D98E65",
2726
+ hair: "#412720",
2727
+ shirt: "#6D28D9",
2728
+ accent: "#C4B5FD",
2729
+ hairStyle: 3,
2730
+ expression: 3
2731
+ },
2732
+ {
2733
+ background: "#FEF9C3",
2734
+ skin: "#F5C7A4",
2735
+ hair: "#2B1A12",
2736
+ shirt: "#A16207",
2737
+ accent: "#FDE047",
2738
+ hairStyle: 0,
2739
+ expression: 1,
2740
+ glasses: true
2741
+ },
2742
+ {
2743
+ background: "#DCFCE7",
2744
+ skin: "#B97855",
2745
+ hair: "#291A13",
2746
+ shirt: "#16A34A",
2747
+ accent: "#86EFAC",
2748
+ hairStyle: 1,
2749
+ expression: 2
2750
+ },
2751
+ {
2752
+ background: "#E0F2FE",
2753
+ skin: "#F6C5A2",
2754
+ hair: "#6A4031",
2755
+ shirt: "#0284C7",
2756
+ accent: "#7DD3FC",
2757
+ hairStyle: 2,
2758
+ expression: 3,
2759
+ glasses: true
2760
+ },
2761
+ {
2762
+ background: "#FAE8FF",
2763
+ skin: "#DE9B72",
2764
+ hair: "#211714",
2765
+ shirt: "#C026D3",
2766
+ accent: "#F0ABFC",
2767
+ hairStyle: 3,
2768
+ expression: 0
2769
+ },
2770
+ {
2771
+ background: "#FFE4E6",
2772
+ skin: "#F7CEAF",
2773
+ hair: "#42291E",
2774
+ shirt: "#E11D48",
2775
+ accent: "#FDA4AF",
2776
+ hairStyle: 0,
2777
+ expression: 2
2778
+ },
2779
+ {
2780
+ background: "#ECFCCB",
2781
+ skin: "#CE8C65",
2782
+ hair: "#3C2419",
2783
+ shirt: "#3F6212",
2784
+ accent: "#BEF264",
2785
+ hairStyle: 1,
2786
+ expression: 3,
2787
+ glasses: true
2788
+ },
2789
+ {
2790
+ background: "#CFFAFE",
2791
+ skin: "#F0BE99",
2792
+ hair: "#29201B",
2793
+ shirt: "#0891B2",
2794
+ accent: "#67E8F9",
2795
+ hairStyle: 2,
2796
+ expression: 0
2797
+ },
2798
+ {
2799
+ background: "#F3E8FF",
2800
+ skin: "#A76B4B",
2801
+ hair: "#241710",
2802
+ shirt: "#7E22CE",
2803
+ accent: "#D8B4FE",
2804
+ hairStyle: 3,
2805
+ expression: 1,
2806
+ glasses: true
2807
+ }
2808
+ ];
2809
+ function getInitials(content) {
2810
+ const words = content.trim().split(/\s+/).filter(Boolean);
2811
+ return words.slice(-2).map((word) => Array.from(word)[0] ?? "").join("").toLocaleUpperCase();
2812
+ }
2813
+ function resolveSize(size) {
2814
+ if (typeof size === "number") return `${size}px`;
2815
+ return /^\d+(?:\.\d+)?$/.test(size) ? `${size}px` : size;
2816
+ }
2817
+ function resolveFontSize(size) {
2818
+ const numericSize = typeof size === "number" ? size : Number(size);
2819
+ if (Number.isFinite(numericSize)) {
2820
+ return `${Math.min(28, Math.max(10, numericSize * 0.38))}px`;
2821
+ }
2822
+ return "1em";
2823
+ }
2824
+ function getFallbackIndex(index) {
2825
+ if (!Number.isFinite(index)) return 0;
2826
+ return Math.abs(Math.trunc(index)) % FALLBACK_AVATARS.length;
2827
+ }
2828
+ function AvatarFallbackIcon({ avatar }) {
2829
+ const {
2830
+ accent,
2831
+ background,
2832
+ expression,
2833
+ glasses,
2834
+ hair,
2835
+ hairStyle,
2836
+ shirt,
2837
+ skin
2838
+ } = avatar;
2839
+ return /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)(
2840
+ "svg",
2841
+ {
2842
+ className: "fe-avatar__fallback-icon",
2843
+ viewBox: "0 0 24 24",
2844
+ focusable: "false",
2845
+ "aria-hidden": "true",
2846
+ children: [
2847
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("rect", { width: "24", height: "24", fill: background }),
2848
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2849
+ "path",
2850
+ {
2851
+ d: "M3 24c.52-3.79 3.58-6.25 9-6.25S20.48 20.21 21 24",
2852
+ fill: shirt
2853
+ }
2854
+ ),
2855
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2856
+ "path",
2857
+ {
2858
+ d: "M8.1 17.65h7.8l1.05 2.05H7.05l1.05-2.05Z",
2859
+ fill: accent,
2860
+ opacity: ".72"
2861
+ }
2862
+ ),
2863
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { cx: "12", cy: "10.25", r: "5.25", fill: skin }),
2864
+ hairStyle === 0 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2865
+ "path",
2866
+ {
2867
+ d: "M6.75 10.25C6.75 6.34 9.02 4 12.15 4c3.22 0 5.1 2.33 5.1 5.54-1.6-1.41-3.46-2.1-5.59-2.1-1.63 0-3.27.56-4.91 1.68Z",
2868
+ fill: hair
2869
+ }
2870
+ ),
2871
+ hairStyle === 1 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2872
+ "path",
2873
+ {
2874
+ d: "M6.6 10.1c.16-3.93 2.57-6.2 5.62-6.2 3.57 0 5.3 2.75 5.08 6.32-1.42-1.23-2.91-1.82-4.48-1.82-2.4 0-3.9.65-6.22 1.7Z",
2875
+ fill: hair
2876
+ }
2877
+ ),
2878
+ hairStyle === 2 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2879
+ "path",
2880
+ {
2881
+ d: "M6.8 10.55C6.8 6.28 9.43 4 12.2 4c3.46 0 5.13 2.83 4.93 6.38-1.38-1.58-3.03-2.38-4.92-2.38-1.81 0-3.61.85-5.41 2.55Z",
2882
+ fill: hair
2883
+ }
2884
+ ),
2885
+ hairStyle === 3 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2886
+ "path",
2887
+ {
2888
+ d: "M6.66 10.1C6.94 6.12 9.18 4 12.1 4c3.77 0 5.2 2.95 5.18 6.21-1.5-1.07-3.1-1.6-4.8-1.6-2.18 0-3.98.5-5.82 1.49Z",
2889
+ fill: hair
2890
+ }
2891
+ ),
2892
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { cx: "10.05", cy: "10.65", r: ".48", fill: "#3B2924" }),
2893
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { cx: "13.95", cy: "10.65", r: ".48", fill: "#3B2924" }),
2894
+ expression === 0 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2895
+ "path",
2896
+ {
2897
+ d: "M10.25 13.2c1.08.66 2.42.66 3.5 0",
2898
+ fill: "none",
2899
+ stroke: "#A94F4F",
2900
+ strokeWidth: ".7",
2901
+ strokeLinecap: "round"
2902
+ }
2903
+ ),
2904
+ expression === 1 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2905
+ "path",
2906
+ {
2907
+ d: "M10.5 13.2h3",
2908
+ fill: "none",
2909
+ stroke: "#A94F4F",
2910
+ strokeWidth: ".7",
2911
+ strokeLinecap: "round"
2912
+ }
2913
+ ),
2914
+ expression === 2 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2915
+ "path",
2916
+ {
2917
+ d: "M10.6 13.38c.84-.44 1.96-.44 2.8 0",
2918
+ fill: "none",
2919
+ stroke: "#A94F4F",
2920
+ strokeWidth: ".7",
2921
+ strokeLinecap: "round"
2922
+ }
2923
+ ),
2924
+ expression === 3 && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { cx: "12", cy: "13.2", r: ".82", fill: "#B95A5A" }),
2925
+ glasses && /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)("g", { fill: "none", stroke: "#3C4355", strokeWidth: ".65", children: [
2926
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { cx: "10", cy: "10.55", r: "1.45" }),
2927
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { cx: "14", cy: "10.55", r: "1.45" }),
2928
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("path", { d: "M11.45 10.55h1.1M8.55 10.55H7.5m9 0h-1.05" })
2929
+ ] })
2930
+ ]
2931
+ }
2932
+ );
2933
+ }
2934
+ function Avatar({
2935
+ src,
2936
+ content,
2937
+ alt,
2938
+ size = 40,
2939
+ shape = "circle",
2940
+ fallbackIndex,
2941
+ className,
2942
+ style,
2943
+ role,
2944
+ "aria-label": ariaLabel,
2945
+ ...props
2946
+ }) {
2947
+ const [generatedFallbackIndex] = (0, import_react22.useState)(
2948
+ () => Math.floor(Math.random() * FALLBACK_AVATARS.length)
2949
+ );
2950
+ const [failedImageSrc, setFailedImageSrc] = (0, import_react22.useState)();
2951
+ const imageSrc = src?.trim();
2952
+ const trimmedContent = content?.trim() ?? "";
2953
+ const showImage = Boolean(imageSrc && failedImageSrc !== imageSrc);
2954
+ const initials = trimmedContent ? getInitials(trimmedContent) : "";
2955
+ const selectedFallback = FALLBACK_AVATARS[getFallbackIndex(fallbackIndex ?? generatedFallbackIndex)];
2956
+ const avatarStyle = {
2957
+ "--fe-avatar-size": resolveSize(size),
2958
+ "--fe-avatar-font-size": resolveFontSize(size),
2959
+ ...style
2960
+ };
2961
+ const fallbackLabel = (alt ?? trimmedContent) || "Avatar";
2962
+ return /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)(
2963
+ "span",
2964
+ {
2965
+ className: ["fe-avatar", `fe-avatar--${shape}`, className].filter(Boolean).join(" "),
2966
+ style: avatarStyle,
2967
+ role: showImage ? role : role ?? "img",
2968
+ "aria-label": showImage ? ariaLabel : ariaLabel ?? fallbackLabel,
2969
+ ...props,
2970
+ children: [
2971
+ showImage && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
2972
+ "img",
2973
+ {
2974
+ className: "fe-avatar__image",
2975
+ src: imageSrc,
2976
+ alt: alt ?? trimmedContent,
2977
+ onError: () => setFailedImageSrc(imageSrc)
2978
+ }
2979
+ ),
2980
+ !showImage && initials && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("span", { className: "fe-avatar__initials", "aria-hidden": "true", children: initials }),
2981
+ !showImage && !initials && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(AvatarFallbackIcon, { avatar: selectedFallback })
2982
+ ]
2983
+ }
2984
+ );
2985
+ }
2986
+ function AvatarGroup({
2987
+ children,
2988
+ maxCount,
2989
+ className,
2990
+ style,
2991
+ role,
2992
+ ...props
2993
+ }) {
2994
+ const avatars = import_react22.Children.toArray(children).filter(import_react22.isValidElement);
2995
+ const hasMaxCount = typeof maxCount === "number" && Number.isFinite(maxCount) && maxCount > 0;
2996
+ const itemLimit = hasMaxCount ? Math.floor(maxCount) : avatars.length;
2997
+ const hasOverflow = avatars.length > itemLimit;
2998
+ const visibleCount = hasOverflow ? Math.max(0, itemLimit - 1) : itemLimit;
2999
+ const visibleAvatars = avatars.slice(0, visibleCount);
3000
+ const overflowCount = avatars.length - visibleAvatars.length;
3001
+ const firstAvatarSize = avatars[0]?.props.size ?? 40;
3002
+ const overflowStyle = {
3003
+ "--fe-avatar-size": resolveSize(firstAvatarSize),
3004
+ "--fe-avatar-font-size": resolveFontSize(firstAvatarSize)
3005
+ };
3006
+ const singleContent = avatars.length === 1 ? avatars[0]?.props.content?.trim() ?? "" : "";
3007
+ return /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)(
3008
+ "div",
3009
+ {
3010
+ className: ["fe-avatar-group", className].filter(Boolean).join(" "),
3011
+ style,
3012
+ role: role ?? "group",
3013
+ ...props,
3014
+ children: [
3015
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)("div", { className: "fe-avatar-group__items", children: [
3016
+ visibleAvatars.map((avatar, index) => /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
3017
+ "span",
3018
+ {
3019
+ className: "fe-avatar-group__item",
3020
+ style: { zIndex: visibleAvatars.length - index },
3021
+ children: avatar
3022
+ },
3023
+ avatar.key ?? index
3024
+ )),
3025
+ hasOverflow && /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)(
3026
+ "span",
3027
+ {
3028
+ className: "fe-avatar-group__more",
3029
+ style: overflowStyle,
3030
+ role: "img",
3031
+ "aria-label": `${overflowCount} more avatars`,
3032
+ children: [
3033
+ "+",
3034
+ overflowCount
3035
+ ]
3036
+ }
3037
+ )
3038
+ ] }),
3039
+ singleContent && /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("span", { className: "fe-avatar-group__content", children: singleContent })
3040
+ ]
3041
+ }
3042
+ );
3043
+ }
2075
3044
  // Annotate the CommonJS export names for ESM import in node:
2076
3045
  0 && (module.exports = {
3046
+ Avatar,
3047
+ AvatarGroup,
2077
3048
  Button,
3049
+ ButtonBar,
3050
+ Checkbox,
2078
3051
  ChevronDownIcon,
3052
+ ChevronUpIcon,
2079
3053
  Chip,
2080
3054
  CloseIcon,
2081
3055
  CurrencyInput,
@@ -2085,10 +3059,14 @@ function Snackbar({
2085
3059
  Loading,
2086
3060
  Message,
2087
3061
  Modal,
3062
+ MoreHorizontalIcon,
3063
+ MoreVerticalIcon,
2088
3064
  NumberInput,
2089
3065
  Pagination,
2090
3066
  PlusIcon,
2091
3067
  ProgressBar,
3068
+ RadioButton,
3069
+ RadioGroup,
2092
3070
  SearchIcon,
2093
3071
  Selection,
2094
3072
  Skeleton,