react-better-html 1.1.79 → 1.1.80

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
@@ -37,6 +37,7 @@ __export(index_exports, {
37
37
  Div: () => Div_default,
38
38
  Divider: () => Divider_default,
39
39
  Dropdown: () => Dropdown_default,
40
+ Foldable: () => Foldable_default,
40
41
  Form: () => Form_default,
41
42
  FormRow: () => FormRow_default,
42
43
  Icon: () => Icon_default,
@@ -48,6 +49,7 @@ __export(index_exports, {
48
49
  PageHeader: () => PageHeader_default,
49
50
  PageHolder: () => PageHolder_default,
50
51
  Table: () => Table_default,
52
+ Tabs: () => Tabs_default,
51
53
  Text: () => Text_default,
52
54
  ToggleInput: () => ToggleInput_default,
53
55
  formatPhoneNumber: () => formatPhoneNumber,
@@ -1574,9 +1576,17 @@ var useBetterHtmlContext = () => {
1574
1576
  throw new Error(
1575
1577
  "`useBetterHtmlContext()` must be used within a `<BetterHtmlProvider>`. Make sure to add one at the root of your component tree."
1576
1578
  );
1577
- const { setLoaders, plugins, ...rest } = context;
1579
+ const { setLoaders, plugins, tabsComponentState, ...rest } = context;
1578
1580
  return rest;
1579
1581
  };
1582
+ var useBetterHtmlContextInternal = () => {
1583
+ const context = (0, import_react.useContext)(betterHtmlContext);
1584
+ if (context === void 0)
1585
+ throw new Error(
1586
+ "`useBetterHtmlContextInternal()` must be used within a `<BetterHtmlProvider>`. Make sure to add one at the root of your component tree."
1587
+ );
1588
+ return context;
1589
+ };
1580
1590
  var useTheme = () => {
1581
1591
  const context = (0, import_react.useContext)(betterHtmlContext);
1582
1592
  if (context === void 0)
@@ -1643,11 +1653,13 @@ function BetterHtmlProviderContent({ children }) {
1643
1653
  ] });
1644
1654
  }
1645
1655
  function BetterHtmlProvider({ value, plugins: pluginsToUse, children }) {
1646
- const [loaders, setLoaders] = (0, import_react.useState)(value?.loaders ?? {});
1647
- const [plugins] = (0, import_react.useState)(pluginsToUse ?? []);
1648
1656
  const [colorTheme, setColorTheme] = (0, import_react.useState)(
1649
1657
  localStorage.getItem("theme") === "dark" ? "dark" : value?.colorTheme ?? "light"
1650
1658
  );
1659
+ const [loaders, setLoaders] = (0, import_react.useState)(value?.loaders ?? {});
1660
+ const [plugins] = (0, import_react.useState)(pluginsToUse ?? []);
1661
+ const [tabGroups, setTabGroups] = (0, import_react.useState)([]);
1662
+ const [tabsWithDots, setTabsWithDots] = (0, import_react.useState)([]);
1651
1663
  const readyValue = (0, import_react.useMemo)(
1652
1664
  () => ({
1653
1665
  app: {
@@ -1684,9 +1696,15 @@ function BetterHtmlProvider({ value, plugins: pluginsToUse, children }) {
1684
1696
  components: {
1685
1697
  ...value?.components
1686
1698
  },
1687
- plugins
1699
+ plugins,
1700
+ tabsComponentState: {
1701
+ tabGroups,
1702
+ setTabGroups,
1703
+ tabsWithDots,
1704
+ setTabsWithDots
1705
+ }
1688
1706
  }),
1689
- [value, colorTheme, loaders, plugins]
1707
+ [value, colorTheme, loaders, plugins, tabGroups, tabsWithDots]
1690
1708
  );
1691
1709
  (0, import_react.useEffect)(() => {
1692
1710
  plugins.forEach((plugin) => {
@@ -2387,7 +2405,7 @@ var IconElement = import_styled_components5.default.svg.withConfig({
2387
2405
  `;
2388
2406
  var Icon = (0, import_react6.forwardRef)(function Icon2({ name, size = 16, ...props }, ref) {
2389
2407
  const theme2 = useTheme();
2390
- const { icons: icons2 } = useBetterHtmlContext();
2408
+ const { icons: icons2 } = useBetterHtmlContextInternal();
2391
2409
  const styledComponentStyles = useStyledComponentStyles(props, theme2);
2392
2410
  const dataProps = useComponentPropsWithPrefix(props, "data");
2393
2411
  const ariaProps = useComponentPropsWithPrefix(props, "aria");
@@ -2446,7 +2464,7 @@ var ImageElement = import_styled_components6.default.img.withConfig({
2446
2464
  `;
2447
2465
  var Image = (0, import_react8.forwardRef)(function Image2({ name, src, ...props }, ref) {
2448
2466
  const theme2 = useTheme();
2449
- const { assets: assets2 } = useBetterHtmlContext();
2467
+ const { assets: assets2 } = useBetterHtmlContextInternal();
2450
2468
  const styledComponentStyles = useStyledComponentStyles(props, theme2);
2451
2469
  const dataProps = useComponentPropsWithPrefix(props, "data");
2452
2470
  const ariaProps = useComponentPropsWithPrefix(props, "aria");
@@ -2483,7 +2501,7 @@ var import_react9 = require("react");
2483
2501
  var import_styled_components7 = __toESM(require("styled-components"));
2484
2502
  var import_jsx_runtime7 = require("react/jsx-runtime");
2485
2503
  var ButtonElement = import_styled_components7.default.button.withConfig({
2486
- shouldForwardProp: (prop) => !["theme", "normalStyle", "hoverStyle", "isSmall", "withText", "isLoading"].includes(prop)
2504
+ shouldForwardProp: (prop) => !["theme", "colorTheme", "normalStyle", "hoverStyle", "isSmall", "withText", "isLoading"].includes(prop)
2487
2505
  })`
2488
2506
  display: block;
2489
2507
  position: relative;
@@ -2505,15 +2523,11 @@ var ButtonElement = import_styled_components7.default.button.withConfig({
2505
2523
  ${(props) => props.disabled ? import_styled_components7.css`
2506
2524
  opacity: 0.6;
2507
2525
  cursor: not-allowed;
2508
-
2509
- &.secondary:disabled {
2510
- filter: brightness(0.9);
2511
- }
2512
2526
  ` : !props.isLoading ? import_styled_components7.css`
2513
2527
  cursor: pointer;
2514
2528
 
2515
2529
  &:not(.secondary):hover {
2516
- filter: brightness(0.9);
2530
+ filter: ${props.colorTheme === "dark" ? "brightness(1.2)" : "brightness(0.9)"};
2517
2531
  }
2518
2532
 
2519
2533
  &.secondary:hover {
@@ -2562,7 +2576,7 @@ var ButtonComponent = function Button({
2562
2576
  }) {
2563
2577
  const theme2 = useTheme();
2564
2578
  const isLoadingHook = useLoader(loaderName);
2565
- const betterHtmlContext2 = useBetterHtmlContext();
2579
+ const betterHtmlContext2 = useBetterHtmlContextInternal();
2566
2580
  const isLoadingElement = isLoading ?? isLoadingHook;
2567
2581
  const styledComponentStyles = useStyledComponentStyles(
2568
2582
  {
@@ -2603,6 +2617,7 @@ var ButtonComponent = function Button({
2603
2617
  {
2604
2618
  as: href ? "a" : "button",
2605
2619
  theme: theme2,
2620
+ colorTheme: betterHtmlContext2.colorTheme,
2606
2621
  isSmall,
2607
2622
  withText: text !== void 0,
2608
2623
  isLoading: isLoadingElement,
@@ -2664,7 +2679,7 @@ var ButtonComponent = function Button({
2664
2679
  };
2665
2680
  ButtonComponent.secondary = function Secondary({ className, ...props }) {
2666
2681
  const theme2 = useTheme();
2667
- const betterHtmlContext2 = useBetterHtmlContext();
2682
+ const betterHtmlContext2 = useBetterHtmlContextInternal();
2668
2683
  return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
2669
2684
  ButtonComponent,
2670
2685
  {
@@ -2677,7 +2692,7 @@ ButtonComponent.secondary = function Secondary({ className, ...props }) {
2677
2692
  };
2678
2693
  ButtonComponent.destructive = function Destructive(props) {
2679
2694
  const theme2 = useTheme();
2680
- const betterHtmlContext2 = useBetterHtmlContext();
2695
+ const betterHtmlContext2 = useBetterHtmlContextInternal();
2681
2696
  return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
2682
2697
  ButtonComponent,
2683
2698
  {
@@ -2690,7 +2705,7 @@ ButtonComponent.destructive = function Destructive(props) {
2690
2705
  };
2691
2706
  ButtonComponent.icon = function Icon3({ size = 16, backgroundButtonColor, ...props }) {
2692
2707
  const theme2 = useTheme();
2693
- const betterHtmlContext2 = useBetterHtmlContext();
2708
+ const betterHtmlContext2 = useBetterHtmlContextInternal();
2694
2709
  const buttonSize = size + theme2.styles.space;
2695
2710
  const backgroundButtonColorReady = backgroundButtonColor ?? theme2.colors.textPrimary;
2696
2711
  return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
@@ -2714,7 +2729,7 @@ ButtonComponent.icon = function Icon3({ size = 16, backgroundButtonColor, ...pro
2714
2729
  );
2715
2730
  };
2716
2731
  ButtonComponent.upload = function Upload({ accept, multiple, onUpload, ...props }) {
2717
- const betterHtmlContext2 = useBetterHtmlContext();
2732
+ const betterHtmlContext2 = useBetterHtmlContextInternal();
2718
2733
  const onClickElement = (0, import_react9.useCallback)(() => {
2719
2734
  const input = document.createElement("input");
2720
2735
  input.setAttribute("type", "file");
@@ -2836,7 +2851,7 @@ var ModalComponent = (0, import_react11.forwardRef)(function Modal({
2836
2851
  const reactRouterDomPlugin2 = usePlugin("react-router-dom");
2837
2852
  const urlQuery = reactRouterDomPlugin2 ? useUrlQuery() : void 0;
2838
2853
  const theme2 = useTheme();
2839
- const { app, colorTheme } = useBetterHtmlContext();
2854
+ const { app, colorTheme } = useBetterHtmlContextInternal();
2840
2855
  const dialogRef = (0, import_react11.useRef)(null);
2841
2856
  const [isOpened, setIsOpened] = (0, import_react11.useState)(false);
2842
2857
  const [isOpenedLate, setIsOpenedLate] = (0, import_react11.useState)(false);
@@ -2844,13 +2859,14 @@ var ModalComponent = (0, import_react11.forwardRef)(function Modal({
2844
2859
  dialogRef.current?.showModal();
2845
2860
  setIsOpened(true);
2846
2861
  setIsOpenedLate(true);
2847
- if (urlQuery && name)
2862
+ if (urlQuery && name) {
2848
2863
  urlQuery.setQuery(
2849
2864
  {
2850
2865
  [`${name}-modal`]: "opened"
2851
2866
  },
2852
2867
  false
2853
2868
  );
2869
+ }
2854
2870
  onOpen?.();
2855
2871
  }, [onOpen, urlQuery, name]);
2856
2872
  const onClickClose = (0, import_react11.useCallback)(() => {
@@ -3046,7 +3062,7 @@ var import_react12 = require("react");
3046
3062
  var import_jsx_runtime10 = require("react/jsx-runtime");
3047
3063
  function PageHolder({ noMaxContentWidth, children }) {
3048
3064
  const theme2 = useTheme();
3049
- const { app } = useBetterHtmlContext();
3065
+ const { app } = useBetterHtmlContextInternal();
3050
3066
  return /* @__PURE__ */ (0, import_jsx_runtime10.jsx)(
3051
3067
  Div_default,
3052
3068
  {
@@ -3077,7 +3093,7 @@ function PageHeader({
3077
3093
  marginBottom
3078
3094
  }) {
3079
3095
  const theme2 = useTheme();
3080
- const { app } = useBetterHtmlContext();
3096
+ const { app } = useBetterHtmlContextInternal();
3081
3097
  const mediaQuery = useMediaQuery();
3082
3098
  return /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(Div_default.row, { alignItems: "center", gap: theme2.styles.space, marginBottom: marginBottom ?? theme2.styles.space * 2, children: [
3083
3099
  imageUrl && /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(Image_default.profileImage, { src: imageUrl, size: imageSize ?? (mediaQuery.size600 ? 46 : 60) }),
@@ -4881,7 +4897,7 @@ var DropdownComponent = (0, import_react16.forwardRef)(function Dropdown({
4881
4897
  const displayValue = withSearch && isFocused ? searchQuery : selectedOption?.label ?? "";
4882
4898
  const withClearButton = isOpen && selectedOption;
4883
4899
  const readyPlaceholder = placeholder ? placeholder : `Select an ${label?.toLowerCase() ?? "option"}`;
4884
- return /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(Div_default.column, { width: "100%", position: "relative", userSelect: "none", ...props, children: /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(Div_default.row, { position: "relative", width: "100%", children: [
4900
+ return /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(Div_default.column, { width: "100%", position: "relative", userSelect: "none", ...props, children: /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(Div_default.row, { position: "relative", width: "100%", ref: inputFieldHolderRef, children: [
4885
4901
  /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
4886
4902
  InputField_default,
4887
4903
  {
@@ -4901,7 +4917,6 @@ var DropdownComponent = (0, import_react16.forwardRef)(function Dropdown({
4901
4917
  onFocus: setIsFocused.setTrue,
4902
4918
  onBlur: setIsFocused.setFalse,
4903
4919
  onKeyDown: onKeyDownInputField,
4904
- holderRef: inputFieldHolderRef,
4905
4920
  onChangeValue: withSearch ? onChangeValue : void 0,
4906
4921
  insideInputFieldComponent: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
4907
4922
  Div_default,
@@ -5976,6 +5991,8 @@ var InputElement2 = import_styled_components10.default.input.withConfig({
5976
5991
  ${(props) => props.normalStyle}
5977
5992
 
5978
5993
  &:hover {
5994
+ border-color: ${(props) => props.theme.colors.primary};
5995
+
5979
5996
  ${(props) => props.hoverStyle}
5980
5997
  }
5981
5998
  `;
@@ -6461,7 +6478,7 @@ var TableComponent = (0, import_react23.forwardRef)(function Table({
6461
6478
  onClickAllCheckboxes,
6462
6479
  ...props
6463
6480
  }, ref) {
6464
- const { colorTheme } = useBetterHtmlContext();
6481
+ const { colorTheme } = useBetterHtmlContextInternal();
6465
6482
  const theme2 = useTheme();
6466
6483
  const [checkedItems, setCheckedItems] = (0, import_react23.useState)([]);
6467
6484
  const renderCellContent = (0, import_react23.useCallback)(
@@ -6571,6 +6588,301 @@ var TableComponent = (0, import_react23.forwardRef)(function Table({
6571
6588
  var Table2 = (0, import_react23.memo)(TableComponent);
6572
6589
  var Table_default = Table2;
6573
6590
 
6591
+ // src/components/Tabs.tsx
6592
+ var import_react24 = require("react");
6593
+ var import_jsx_runtime22 = require("react/jsx-runtime");
6594
+ var tabBottomLineWidth = 2;
6595
+ var tabDotSize = 6;
6596
+ var defaultTabName = "tab";
6597
+ var TabsComponent = function Tabs({
6598
+ tabs,
6599
+ name,
6600
+ accentColor,
6601
+ style = "default",
6602
+ children,
6603
+ ...props
6604
+ }) {
6605
+ const reactRouterDomPlugin2 = usePlugin("react-router-dom");
6606
+ const theme2 = useTheme();
6607
+ const urlQuery = reactRouterDomPlugin2 ? useUrlQuery() : void 0;
6608
+ const { colorTheme, tabsComponentState } = useBetterHtmlContextInternal();
6609
+ const tabsRef = (0, import_react24.useRef)({});
6610
+ const [selectedTab, setSelectedTab] = (0, import_react24.useState)(() => {
6611
+ const selectedTabValue = tabs[0] ?? "";
6612
+ if (urlQuery) {
6613
+ const tabQueryValue = urlQuery.getQuery(name ?? defaultTabName);
6614
+ if (!tabQueryValue) return selectedTabValue;
6615
+ if (tabs.includes(tabQueryValue)) return tabQueryValue;
6616
+ }
6617
+ return selectedTabValue;
6618
+ });
6619
+ const [rerenderState, setRerenderState] = (0, import_react24.useState)(0);
6620
+ const tabsGap = style === "box" ? theme2.styles.gap / 2 : 0;
6621
+ const onClickTab = (0, import_react24.useCallback)(
6622
+ (tab) => {
6623
+ setSelectedTab(tab);
6624
+ if (urlQuery) {
6625
+ urlQuery.setQuery({
6626
+ [name ?? defaultTabName]: tab
6627
+ });
6628
+ }
6629
+ },
6630
+ [name, urlQuery]
6631
+ );
6632
+ const width = (0, import_react24.useMemo)(
6633
+ () => tabsRef.current[selectedTab]?.getBoundingClientRect().width ?? 0,
6634
+ [rerenderState, selectedTab]
6635
+ );
6636
+ const leftSpacing = (0, import_react24.useMemo)(() => {
6637
+ const selectedTabIndex = tabs.findIndex((tab) => tab === selectedTab);
6638
+ let totalWidth = 0;
6639
+ Object.values(tabsRef.current).forEach((tab, index) => {
6640
+ if (index < selectedTabIndex) totalWidth += (tab?.getBoundingClientRect().width ?? 0) + tabsGap;
6641
+ });
6642
+ return totalWidth;
6643
+ }, [selectedTab, tabs, tabsGap]);
6644
+ (0, import_react24.useEffect)(() => {
6645
+ const timeout = setTimeout(() => setRerenderState(Math.random()), 0.01 * 1e3);
6646
+ return () => {
6647
+ clearTimeout(timeout);
6648
+ };
6649
+ }, []);
6650
+ (0, import_react24.useEffect)(() => {
6651
+ tabsComponentState.setTabGroups((oldValue) => {
6652
+ const thisTabGroup = oldValue.find((item) => item.name === (name ?? defaultTabName));
6653
+ if (thisTabGroup) {
6654
+ return oldValue.map(
6655
+ (item) => item.name === (name ?? defaultTabName) ? {
6656
+ ...item,
6657
+ selectedTab
6658
+ } : item
6659
+ );
6660
+ } else {
6661
+ return [
6662
+ ...oldValue,
6663
+ {
6664
+ name: name ?? defaultTabName,
6665
+ selectedTab
6666
+ }
6667
+ ];
6668
+ }
6669
+ });
6670
+ }, [selectedTab, name]);
6671
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(Div_default.column, { width: "100%", gap: theme2.styles.space, ...props, children: [
6672
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(Div_default, { position: "relative", className: "react-better-html-no-scrollbar", overflowY: "auto", children: [
6673
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Div_default.row, { position: "relative", width: "fit-content", gap: tabsGap, userSelect: "none", children: tabs.map((tab) => {
6674
+ const selected = tab === selectedTab;
6675
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
6676
+ Div_default,
6677
+ {
6678
+ position: "relative",
6679
+ width: "fit-content",
6680
+ backgroundColor: style === "box" ? selected ? theme2.colors.primary : theme2.colors.backgroundContent : theme2.colors.backgroundBase,
6681
+ borderRadius: style === "box" ? theme2.styles.borderRadius : void 0,
6682
+ borderTopLeftRadius: style === "borderRadiusTop" ? theme2.styles.borderRadius : void 0,
6683
+ borderTopRightRadius: style === "borderRadiusTop" ? theme2.styles.borderRadius : void 0,
6684
+ border: style === "box" ? `1px solid ${selected ? "transparent" : theme2.colors.border}` : void 0,
6685
+ filterHover: colorTheme === "dark" ? style === "box" ? "brightness(1.2)" : "brightness(2)" : "brightness(0.9)",
6686
+ paddingInline: theme2.styles.space,
6687
+ paddingBlock: theme2.styles.gap,
6688
+ value: tab,
6689
+ cursor: "pointer",
6690
+ isTabAccessed: true,
6691
+ onClickWithValue: onClickTab,
6692
+ ref: (ref) => {
6693
+ tabsRef.current[tab] = ref;
6694
+ },
6695
+ children: [
6696
+ tabsComponentState.tabsWithDots.includes(tab) && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
6697
+ Div_default,
6698
+ {
6699
+ position: "absolute",
6700
+ top: (theme2.styles.space - tabDotSize) / 2,
6701
+ right: (theme2.styles.space - tabDotSize) / 2,
6702
+ width: tabDotSize,
6703
+ height: tabDotSize,
6704
+ backgroundColor: style === "box" && selected ? theme2.colors.base : theme2.colors.primary,
6705
+ borderRadius: 999,
6706
+ transition: theme2.styles.transition
6707
+ }
6708
+ ),
6709
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
6710
+ Text_default,
6711
+ {
6712
+ fontWeight: 700,
6713
+ color: !selected ? theme2.colors.textSecondary : style === "box" ? theme2.colors.base : void 0,
6714
+ transition: theme2.styles.transition,
6715
+ whiteSpace: "nowrap",
6716
+ children: tab
6717
+ }
6718
+ )
6719
+ ]
6720
+ },
6721
+ tab
6722
+ );
6723
+ }) }),
6724
+ style !== "box" && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
6725
+ Div_default,
6726
+ {
6727
+ position: "absolute",
6728
+ width,
6729
+ height: tabBottomLineWidth,
6730
+ bottom: 0,
6731
+ left: leftSpacing,
6732
+ backgroundColor: accentColor ?? theme2.colors.primary,
6733
+ transition: theme2.styles.transition
6734
+ }
6735
+ )
6736
+ ] }),
6737
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Div_default, { width: "100%", children })
6738
+ ] });
6739
+ };
6740
+ TabsComponent.content = function Content({ tab, tabWithDot, tabsGroupName, children }) {
6741
+ const { tabsComponentState } = useBetterHtmlContextInternal();
6742
+ const thisTabGroupData = (0, import_react24.useMemo)(
6743
+ () => tabsComponentState.tabGroups.find((item) => item.name === (tabsGroupName ?? defaultTabName)),
6744
+ [tabsComponentState, tabsGroupName]
6745
+ );
6746
+ (0, import_react24.useEffect)(() => {
6747
+ if (tabWithDot) {
6748
+ tabsComponentState.setTabsWithDots?.((oldValue) => oldValue.includes(tab) ? oldValue : [...oldValue, tab]);
6749
+ } else {
6750
+ tabsComponentState.setTabsWithDots?.(
6751
+ (oldValue) => oldValue.includes(tab) ? oldValue.filter((tab2) => tab2 !== tab2) : oldValue
6752
+ );
6753
+ }
6754
+ }, [tabWithDot]);
6755
+ return thisTabGroupData?.selectedTab === tab ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Div_default, { width: "100%", children }) : void 0;
6756
+ };
6757
+ var Tabs2 = (0, import_react24.memo)(TabsComponent);
6758
+ Tabs2.content = TabsComponent.content;
6759
+ var Tabs_default = Tabs2;
6760
+
6761
+ // src/components/Foldable.tsx
6762
+ var import_react25 = require("react");
6763
+ var import_jsx_runtime23 = require("react/jsx-runtime");
6764
+ var animationDuration = 0.2;
6765
+ var FoldableComponent = (0, import_react25.forwardRef)(function Foldable({
6766
+ isOpen: controlledIsOpen,
6767
+ defaultOpen = false,
6768
+ title,
6769
+ description,
6770
+ icon,
6771
+ image,
6772
+ headerPaddingInline,
6773
+ renderHeader,
6774
+ onOpenChange,
6775
+ children,
6776
+ ...props
6777
+ }, ref) {
6778
+ const theme2 = useTheme();
6779
+ const bodyRef = (0, import_react25.useRef)(null);
6780
+ const [internalIsOpen, setInternalIsOpen] = useBooleanState(defaultOpen);
6781
+ const [bodyHeight, setBodyHeight] = (0, import_react25.useState)(defaultOpen ? void 0 : 0);
6782
+ const isOpen = controlledIsOpen !== void 0 ? controlledIsOpen : internalIsOpen;
6783
+ const open = (0, import_react25.useCallback)(() => {
6784
+ if (controlledIsOpen === void 0) setInternalIsOpen.setTrue();
6785
+ onOpenChange?.(true);
6786
+ }, [controlledIsOpen, onOpenChange]);
6787
+ const close = (0, import_react25.useCallback)(() => {
6788
+ if (controlledIsOpen === void 0) setInternalIsOpen.setFalse();
6789
+ onOpenChange?.(false);
6790
+ }, [controlledIsOpen, onOpenChange]);
6791
+ const toggleOpen = (0, import_react25.useCallback)(() => {
6792
+ if (controlledIsOpen === void 0) setInternalIsOpen.toggle();
6793
+ onOpenChange?.(!isOpen);
6794
+ }, [controlledIsOpen, isOpen, onOpenChange]);
6795
+ (0, import_react25.useEffect)(() => {
6796
+ if (!bodyRef.current) return;
6797
+ if (isOpen) {
6798
+ const height = bodyRef.current.scrollHeight;
6799
+ setBodyHeight(height);
6800
+ const timeout = setTimeout(() => {
6801
+ setBodyHeight(void 0);
6802
+ }, animationDuration * 1e3);
6803
+ return () => {
6804
+ clearTimeout(timeout);
6805
+ };
6806
+ } else {
6807
+ if (bodyHeight === void 0) {
6808
+ const height = bodyRef.current.scrollHeight;
6809
+ setBodyHeight(height);
6810
+ bodyRef.current.offsetHeight;
6811
+ }
6812
+ const timeout = setTimeout(() => {
6813
+ setBodyHeight(0);
6814
+ }, 0.01 * 1e3);
6815
+ return () => {
6816
+ clearTimeout(timeout);
6817
+ };
6818
+ }
6819
+ }, [isOpen, animationDuration, bodyHeight]);
6820
+ (0, import_react25.useImperativeHandle)(
6821
+ ref,
6822
+ () => {
6823
+ return {
6824
+ open,
6825
+ close,
6826
+ toggle: toggleOpen,
6827
+ isOpen
6828
+ };
6829
+ },
6830
+ [open, close, toggleOpen, isOpen]
6831
+ );
6832
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(Div_default.column, { width: "100%", overflow: "hidden", ...props, children: [
6833
+ renderHeader ? renderHeader(isOpen, toggleOpen) : /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(
6834
+ Div_default.row,
6835
+ {
6836
+ width: "100%",
6837
+ alignItems: "center",
6838
+ gap: theme2.styles.gap,
6839
+ paddingBlock: theme2.styles.gap,
6840
+ paddingInline: headerPaddingInline,
6841
+ cursor: "pointer",
6842
+ onClick: toggleOpen,
6843
+ userSelect: "none",
6844
+ children: [
6845
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(Div_default.row, { flex: 1, alignItems: "center", gap: theme2.styles.space, children: [
6846
+ icon && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Icon_default, { name: icon, size: 20, flexShrink: 0 }),
6847
+ image && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Image_default.profileImage, { name: image, size: 24, flexShrink: 0 }),
6848
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(Div_default.column, { gap: theme2.styles.gap / 2, children: [
6849
+ title && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Text_default, { as: "h3", fontWeight: 700, children: title }),
6850
+ description && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Text_default, { color: theme2.colors.textSecondary, children: description })
6851
+ ] })
6852
+ ] }),
6853
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
6854
+ Icon_default,
6855
+ {
6856
+ name: "chevronDown",
6857
+ transform: `rotate(${isOpen ? 180 : 0}deg)`,
6858
+ transition: theme2.styles.transition
6859
+ }
6860
+ )
6861
+ ]
6862
+ }
6863
+ ),
6864
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Div_default, { height: isOpen ? 1 : 0, opacity: isOpen ? 1 : 0, transition: theme2.styles.transition, children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Divider_default.horizontal, {}) }),
6865
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Div_default, { height: bodyHeight, transition: `height ${animationDuration}s ease`, ref: bodyRef, children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Div_default, { paddingBlock: theme2.styles.gap, paddingInline: headerPaddingInline, children }) })
6866
+ ] });
6867
+ });
6868
+ FoldableComponent.box = (0, import_react25.forwardRef)(function Box3({ ...props }, ref) {
6869
+ const theme2 = useTheme();
6870
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(
6871
+ FoldableComponent,
6872
+ {
6873
+ backgroundColor: theme2.colors.backgroundContent,
6874
+ border: `1px solid ${theme2.colors.border}`,
6875
+ borderRadius: theme2.styles.borderRadius,
6876
+ headerPaddingInline: theme2.styles.space,
6877
+ ...props,
6878
+ ref
6879
+ }
6880
+ );
6881
+ });
6882
+ var Foldable2 = (0, import_react25.memo)(FoldableComponent);
6883
+ Foldable2.box = FoldableComponent.box;
6884
+ var Foldable_default = Foldable2;
6885
+
6574
6886
  // src/utils/variableFunctions.ts
6575
6887
  var checkBetterHtmlContextValue = (value, functionsName) => {
6576
6888
  if (value === void 0) {
@@ -6618,6 +6930,7 @@ var reactRouterDomPlugin = {
6618
6930
  Div,
6619
6931
  Divider,
6620
6932
  Dropdown,
6933
+ Foldable,
6621
6934
  Form,
6622
6935
  FormRow,
6623
6936
  Icon,
@@ -6629,6 +6942,7 @@ var reactRouterDomPlugin = {
6629
6942
  PageHeader,
6630
6943
  PageHolder,
6631
6944
  Table,
6945
+ Tabs,
6632
6946
  Text,
6633
6947
  ToggleInput,
6634
6948
  formatPhoneNumber,