@udixio/ui-react 2.9.5 → 2.9.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/CHANGELOG.md +38 -0
- package/dist/index.cjs +3 -3
- package/dist/index.js +3436 -2702
- package/dist/lib/components/Chip.d.ts.map +1 -1
- package/dist/lib/components/Chips.d.ts.map +1 -1
- package/dist/lib/components/Tab.d.ts +1 -1
- package/dist/lib/components/Tab.d.ts.map +1 -1
- package/dist/lib/components/TabGroup.d.ts +9 -0
- package/dist/lib/components/TabGroup.d.ts.map +1 -0
- package/dist/lib/components/TabGroupContext.d.ts +10 -0
- package/dist/lib/components/TabGroupContext.d.ts.map +1 -0
- package/dist/lib/components/TabPanel.d.ts +10 -0
- package/dist/lib/components/TabPanel.d.ts.map +1 -0
- package/dist/lib/components/TabPanels.d.ts +10 -0
- package/dist/lib/components/TabPanels.d.ts.map +1 -0
- package/dist/lib/components/Tabs.d.ts.map +1 -1
- package/dist/lib/components/index.d.ts +3 -0
- package/dist/lib/components/index.d.ts.map +1 -1
- package/dist/lib/effects/smooth-scroll.effect.d.ts +35 -11
- package/dist/lib/effects/smooth-scroll.effect.d.ts.map +1 -1
- package/dist/lib/interfaces/index.d.ts +2 -0
- package/dist/lib/interfaces/index.d.ts.map +1 -1
- package/dist/lib/interfaces/tab-group.interface.d.ts +13 -0
- package/dist/lib/interfaces/tab-group.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/tab-panels.interface.d.ts +20 -0
- package/dist/lib/interfaces/tab-panels.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/tab.interface.d.ts +2 -1
- package/dist/lib/interfaces/tab.interface.d.ts.map +1 -1
- package/dist/lib/styles/index.d.ts +1 -0
- package/dist/lib/styles/index.d.ts.map +1 -1
- package/dist/lib/styles/tab-panels.style.d.ts +31 -0
- package/dist/lib/styles/tab-panels.style.d.ts.map +1 -0
- package/dist/lib/styles/tab.style.d.ts +2 -0
- package/dist/lib/styles/tab.style.d.ts.map +1 -1
- package/package.json +4 -3
- package/src/lib/components/Chip.tsx +2 -1
- package/src/lib/components/Chips.tsx +57 -16
- package/src/lib/components/Tab.tsx +5 -1
- package/src/lib/components/TabGroup.tsx +60 -0
- package/src/lib/components/TabGroupContext.tsx +11 -0
- package/src/lib/components/TabPanel.tsx +24 -0
- package/src/lib/components/TabPanels.tsx +71 -0
- package/src/lib/components/Tabs.tsx +17 -6
- package/src/lib/components/index.ts +3 -0
- package/src/lib/effects/smooth-scroll.effect.tsx +81 -125
- package/src/lib/interfaces/index.ts +2 -0
- package/src/lib/interfaces/tab-group.interface.ts +13 -0
- package/src/lib/interfaces/tab-panels.interface.ts +21 -0
- package/src/lib/interfaces/tab.interface.ts +2 -1
- package/src/lib/styles/index.ts +1 -0
- package/src/lib/styles/tab-panels.style.ts +35 -0
- package/src/stories/effect/smooth-scroll.stories.tsx +34 -25
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Chip.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Chip.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAc,UAAU,EAAE,MAAM,UAAU,CAAC;AAClD,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAO9C;;;;GAIG;AACH,eAAO,MAAM,IAAI,GAAI,4MAqBlB,UAAU,CAAC,aAAa,CAAC,
|
|
1
|
+
{"version":3,"file":"Chip.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Chip.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAc,UAAU,EAAE,MAAM,UAAU,CAAC;AAClD,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAO9C;;;;GAIG;AACH,eAAO,MAAM,IAAI,GAAI,4MAqBlB,UAAU,CAAC,aAAa,CAAC,4CA2S3B,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Chips.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Chips.tsx"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAY,cAAc,EAAE,MAAM,eAAe,CAAC;AAMzD,eAAO,MAAM,KAAK,GAAI,sEAOnB,UAAU,CAAC,cAAc,CAAC,
|
|
1
|
+
{"version":3,"file":"Chips.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Chips.tsx"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAY,cAAc,EAAE,MAAM,eAAe,CAAC;AAMzD,eAAO,MAAM,KAAK,GAAI,sEAOnB,UAAU,CAAC,cAAc,CAAC,4CAiT5B,CAAC"}
|
|
@@ -4,5 +4,5 @@ import { ReactProps } from '../utils/component';
|
|
|
4
4
|
* @status beta
|
|
5
5
|
* @parent Tabs
|
|
6
6
|
*/
|
|
7
|
-
export declare const Tab: ({ className, onClick, label, variant, href, icon, selectedTab, setSelectedTab, tabsId, index, onTabSelected, scrollable, selected, ref, ...restProps }: ReactProps<TabInterface>) => import("react/jsx-runtime").JSX.Element;
|
|
7
|
+
export declare const Tab: ({ className, onClick, label: labelProp, variant, href, icon, selectedTab, setSelectedTab, tabsId, index, onTabSelected, scrollable, selected, children, ref, ...restProps }: ReactProps<TabInterface>) => import("react/jsx-runtime").JSX.Element;
|
|
8
8
|
//# sourceMappingURL=Tab.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Tab.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Tab.tsx"],"names":[],"mappings":"AAKA,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAC3D,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAGhD;;;GAGG;AACH,eAAO,MAAM,GAAG,GAAI,
|
|
1
|
+
{"version":3,"file":"Tab.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Tab.tsx"],"names":[],"mappings":"AAKA,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAC3D,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAGhD;;;GAGG;AACH,eAAO,MAAM,GAAG,GAAI,6KAiBjB,UAAU,CAAC,YAAY,CAAC,4CAuF1B,CAAC"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { TabGroupInterface } from '../interfaces/tab-group.interface';
|
|
2
|
+
import { ReactProps } from '../utils/component';
|
|
3
|
+
/**
|
|
4
|
+
* TabGroup provides shared state for Tabs and TabPanels
|
|
5
|
+
* @status beta
|
|
6
|
+
* @category Navigation
|
|
7
|
+
*/
|
|
8
|
+
export declare const TabGroup: ({ children, selectedTab: externalSelectedTab, setSelectedTab: externalSetSelectedTab, defaultTab, }: ReactProps<TabGroupInterface>) => import("react/jsx-runtime").JSX.Element;
|
|
9
|
+
//# sourceMappingURL=TabGroup.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TabGroup.d.ts","sourceRoot":"","sources":["../../../src/lib/components/TabGroup.tsx"],"names":[],"mappings":"AAGA,OAAO,EAAE,iBAAiB,EAAE,MAAM,mCAAmC,CAAC;AACtE,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAEhD;;;;GAIG;AACH,eAAO,MAAM,QAAQ,GAAI,qGAKtB,UAAU,CAAC,iBAAiB,CAAC,4CA2C/B,CAAC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Dispatch, SetStateAction } from 'react';
|
|
2
|
+
export interface TabGroupContextValue {
|
|
3
|
+
selectedTab: number | null;
|
|
4
|
+
setSelectedTab: Dispatch<SetStateAction<number | null>>;
|
|
5
|
+
previousTab: number | null;
|
|
6
|
+
direction: number;
|
|
7
|
+
tabsId: string;
|
|
8
|
+
}
|
|
9
|
+
export declare const TabGroupContext: import('react').Context<TabGroupContextValue | null>;
|
|
10
|
+
//# sourceMappingURL=TabGroupContext.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TabGroupContext.d.ts","sourceRoot":"","sources":["../../../src/lib/components/TabGroupContext.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAiB,QAAQ,EAAE,cAAc,EAAE,MAAM,OAAO,CAAC;AAEhE,MAAM,WAAW,oBAAoB;IACnC,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,cAAc,EAAE,QAAQ,CAAC,cAAc,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC;IACxD,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,eAAO,MAAM,eAAe,sDAAmD,CAAC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { TabPanelInterface } from '../interfaces/tab-panels.interface';
|
|
2
|
+
import { ReactProps } from '../utils/component';
|
|
3
|
+
/**
|
|
4
|
+
* TabPanel contains the content for a single tab
|
|
5
|
+
* Must be used within TabPanels
|
|
6
|
+
* @status beta
|
|
7
|
+
* @category Navigation
|
|
8
|
+
*/
|
|
9
|
+
export declare const TabPanel: ({ children, className, isSelected, }: ReactProps<TabPanelInterface>) => import("react/jsx-runtime").JSX.Element;
|
|
10
|
+
//# sourceMappingURL=TabPanel.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TabPanel.d.ts","sourceRoot":"","sources":["../../../src/lib/components/TabPanel.tsx"],"names":[],"mappings":"AACA,OAAO,EAAE,iBAAiB,EAAE,MAAM,oCAAoC,CAAC;AACvE,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAGhD;;;;;GAKG;AACH,eAAO,MAAM,QAAQ,GAAI,sCAItB,UAAU,CAAC,iBAAiB,CAAC,4CAQ/B,CAAC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { TabPanelsInterface } from '../interfaces/tab-panels.interface';
|
|
2
|
+
import { ReactProps } from '../utils/component';
|
|
3
|
+
/**
|
|
4
|
+
* TabPanels renders the content panels with slide animation
|
|
5
|
+
* Must be used within a TabGroup
|
|
6
|
+
* @status beta
|
|
7
|
+
* @category Navigation
|
|
8
|
+
*/
|
|
9
|
+
export declare const TabPanels: ({ children, className, }: ReactProps<TabPanelsInterface>) => import("react/jsx-runtime").JSX.Element | null;
|
|
10
|
+
//# sourceMappingURL=TabPanels.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TabPanels.d.ts","sourceRoot":"","sources":["../../../src/lib/components/TabPanels.tsx"],"names":[],"mappings":"AAGA,OAAO,EAAE,kBAAkB,EAAE,MAAM,oCAAoC,CAAC;AACxE,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAIhD;;;;;GAKG;AACH,eAAO,MAAM,SAAS,GAAI,0BAGvB,UAAU,CAAC,kBAAkB,CAAC,mDAqDhC,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Tabs.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Tabs.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAE,aAAa,EAAE,MAAM,8BAA8B,CAAC;AAG7D,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;
|
|
1
|
+
{"version":3,"file":"Tabs.d.ts","sourceRoot":"","sources":["../../../src/lib/components/Tabs.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAE,aAAa,EAAE,MAAM,8BAA8B,CAAC;AAG7D,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC;AAKhD;;;;GAIG;AACH,eAAO,MAAM,IAAI,GAAI,wIAQlB,UAAU,CAAC,aAAa,CAAC,4CA6E3B,CAAC"}
|
|
@@ -17,6 +17,9 @@ export * from './Snackbar';
|
|
|
17
17
|
export * from './Switch';
|
|
18
18
|
export * from './Tab';
|
|
19
19
|
export * from './Tabs';
|
|
20
|
+
export * from './TabGroup';
|
|
21
|
+
export * from './TabPanels';
|
|
22
|
+
export * from './TabPanel';
|
|
20
23
|
export * from './TextField';
|
|
21
24
|
export * from './NavigationRailItem';
|
|
22
25
|
export * from './NavigationRail';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/components/index.ts"],"names":[],"mappings":"AAAA,cAAc,UAAU,CAAC;AACzB,cAAc,QAAQ,CAAC;AACvB,cAAc,YAAY,CAAC;AAC3B,cAAc,gBAAgB,CAAC;AAC/B,cAAc,gBAAgB,CAAC;AAC/B,cAAc,QAAQ,CAAC;AACvB,cAAc,SAAS,CAAC;AACxB,cAAc,WAAW,CAAC;AAC1B,cAAc,OAAO,CAAC;AACtB,cAAc,WAAW,CAAC;AAC1B,cAAc,cAAc,CAAC;AAC7B,cAAc,cAAc,CAAC;AAC7B,cAAc,qBAAqB,CAAC;AACpC,cAAc,UAAU,CAAC;AACzB,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,UAAU,CAAC;AACzB,cAAc,OAAO,CAAC;AACtB,cAAc,QAAQ,CAAC;AACvB,cAAc,aAAa,CAAC;AAC5B,cAAc,sBAAsB,CAAC;AACrC,cAAc,kBAAkB,CAAC;AACjC,cAAc,WAAW,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/components/index.ts"],"names":[],"mappings":"AAAA,cAAc,UAAU,CAAC;AACzB,cAAc,QAAQ,CAAC;AACvB,cAAc,YAAY,CAAC;AAC3B,cAAc,gBAAgB,CAAC;AAC/B,cAAc,gBAAgB,CAAC;AAC/B,cAAc,QAAQ,CAAC;AACvB,cAAc,SAAS,CAAC;AACxB,cAAc,WAAW,CAAC;AAC1B,cAAc,OAAO,CAAC;AACtB,cAAc,WAAW,CAAC;AAC1B,cAAc,cAAc,CAAC;AAC7B,cAAc,cAAc,CAAC;AAC7B,cAAc,qBAAqB,CAAC;AACpC,cAAc,UAAU,CAAC;AACzB,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,UAAU,CAAC;AACzB,cAAc,OAAO,CAAC;AACtB,cAAc,QAAQ,CAAC;AACvB,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,sBAAsB,CAAC;AACrC,cAAc,kBAAkB,CAAC;AACjC,cAAc,WAAW,CAAC"}
|
|
@@ -1,14 +1,38 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
export type SmoothScrollProps = {
|
|
3
|
+
/**
|
|
4
|
+
* Duration of the scroll animation in seconds or as a CSS string (e.g., '1s', '500ms').
|
|
5
|
+
* Default: 1.2
|
|
6
|
+
*/
|
|
7
|
+
transition?: number | string;
|
|
8
|
+
/**
|
|
9
|
+
* Easing function for the scroll animation.
|
|
10
|
+
* Default: easeOutQuint
|
|
11
|
+
*/
|
|
12
|
+
easing?: (t: number) => number;
|
|
13
|
+
/**
|
|
14
|
+
* Scroll orientation.
|
|
15
|
+
* Default: 'vertical'
|
|
16
|
+
*/
|
|
17
|
+
orientation?: 'vertical' | 'horizontal';
|
|
18
|
+
/**
|
|
19
|
+
* Enable smooth scrolling on touch devices.
|
|
20
|
+
* Default: false (native touch scrolling is usually preferred)
|
|
21
|
+
*/
|
|
22
|
+
smoothTouch?: boolean;
|
|
23
|
+
/**
|
|
24
|
+
* Multiplier for touch scroll sensitivity.
|
|
25
|
+
* Default: 2
|
|
26
|
+
*/
|
|
27
|
+
touchMultiplier?: number;
|
|
28
|
+
/**
|
|
29
|
+
* Children elements (optional, component works at document level)
|
|
30
|
+
*/
|
|
31
|
+
children?: ReactNode;
|
|
32
|
+
};
|
|
3
33
|
/**
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
* Rework it later (e.g., via Lenis or another solution) before using it in production.
|
|
34
|
+
* SmoothScroll component using Lenis for smooth scrolling.
|
|
35
|
+
* This component enables smooth scrolling at the document level.
|
|
7
36
|
*/
|
|
8
|
-
export declare const SmoothScroll: ({ transition, orientation,
|
|
9
|
-
transition?: {
|
|
10
|
-
ease: "linear" | "easeIn" | "easeOut" | "easeInOut" | "circIn" | "circOut" | "circInOut" | "backIn" | "backOut" | "backInOut" | "anticipate" | ((t: number) => number);
|
|
11
|
-
duration?: number;
|
|
12
|
-
};
|
|
13
|
-
} & ReactProps<CustomScrollInterface>) => import("react/jsx-runtime").JSX.Element | null;
|
|
37
|
+
export declare const SmoothScroll: ({ transition, easing, orientation, smoothTouch, touchMultiplier, children, }: SmoothScrollProps) => import("react/jsx-runtime").JSX.Element | null;
|
|
14
38
|
//# sourceMappingURL=smooth-scroll.effect.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"smooth-scroll.effect.d.ts","sourceRoot":"","sources":["../../../src/lib/effects/smooth-scroll.effect.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"smooth-scroll.effect.d.ts","sourceRoot":"","sources":["../../../src/lib/effects/smooth-scroll.effect.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,SAAS,EAAE,MAAM,OAAO,CAAC;AAGrD,MAAM,MAAM,iBAAiB,GAAG;IAC9B;;;OAGG;IACH,UAAU,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IAC7B;;;OAGG;IACH,MAAM,CAAC,EAAE,CAAC,CAAC,EAAE,MAAM,KAAK,MAAM,CAAC;IAC/B;;;OAGG;IACH,WAAW,CAAC,EAAE,UAAU,GAAG,YAAY,CAAC;IACxC;;;OAGG;IACH,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB;;;OAGG;IACH,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB;;OAEG;IACH,QAAQ,CAAC,EAAE,SAAS,CAAC;CACtB,CAAC;AAEF;;;GAGG;AACH,eAAO,MAAM,YAAY,GAAI,8EAO1B,iBAAiB,mDAmDnB,CAAC"}
|
|
@@ -15,6 +15,8 @@ export * from './snackbar.interface';
|
|
|
15
15
|
export * from './switch.interface';
|
|
16
16
|
export * from './tab.interface';
|
|
17
17
|
export * from './tabs.interface';
|
|
18
|
+
export * from './tab-group.interface';
|
|
19
|
+
export * from './tab-panels.interface';
|
|
18
20
|
export * from './text-field.interface';
|
|
19
21
|
export * from './navigation-rail-item.interface';
|
|
20
22
|
export * from './tooltip.interface';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/index.ts"],"names":[],"mappings":"AAAA,cAAc,oBAAoB,CAAC;AACnC,cAAc,kBAAkB,CAAC;AACjC,cAAc,2BAA2B,CAAC;AAC1C,cAAc,sBAAsB,CAAC;AACrC,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,cAAc,iBAAiB,CAAC;AAChC,cAAc,sBAAsB,CAAC;AACrC,cAAc,yBAAyB,CAAC;AACxC,cAAc,gCAAgC,CAAC;AAC/C,cAAc,wBAAwB,CAAC;AACvC,cAAc,oBAAoB,CAAC;AACnC,cAAc,sBAAsB,CAAC;AACrC,cAAc,oBAAoB,CAAC;AACnC,cAAc,iBAAiB,CAAC;AAChC,cAAc,kBAAkB,CAAC;AACjC,cAAc,wBAAwB,CAAC;AACvC,cAAc,kCAAkC,CAAC;AACjD,cAAc,qBAAqB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/index.ts"],"names":[],"mappings":"AAAA,cAAc,oBAAoB,CAAC;AACnC,cAAc,kBAAkB,CAAC;AACjC,cAAc,2BAA2B,CAAC;AAC1C,cAAc,sBAAsB,CAAC;AACrC,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,cAAc,iBAAiB,CAAC;AAChC,cAAc,sBAAsB,CAAC;AACrC,cAAc,yBAAyB,CAAC;AACxC,cAAc,gCAAgC,CAAC;AAC/C,cAAc,wBAAwB,CAAC;AACvC,cAAc,oBAAoB,CAAC;AACnC,cAAc,sBAAsB,CAAC;AACrC,cAAc,oBAAoB,CAAC;AACnC,cAAc,iBAAiB,CAAC;AAChC,cAAc,kBAAkB,CAAC;AACjC,cAAc,uBAAuB,CAAC;AACtC,cAAc,wBAAwB,CAAC;AACvC,cAAc,wBAAwB,CAAC;AACvC,cAAc,kCAAkC,CAAC;AACjD,cAAc,qBAAqB,CAAC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { Dispatch, ReactNode, SetStateAction } from 'react';
|
|
2
|
+
export interface TabGroupInterface {
|
|
3
|
+
type: 'div';
|
|
4
|
+
props: {
|
|
5
|
+
children: ReactNode;
|
|
6
|
+
selectedTab?: number | null;
|
|
7
|
+
setSelectedTab?: Dispatch<SetStateAction<number | null>>;
|
|
8
|
+
defaultTab?: number;
|
|
9
|
+
};
|
|
10
|
+
states: object;
|
|
11
|
+
elements: ['tabGroup'];
|
|
12
|
+
}
|
|
13
|
+
//# sourceMappingURL=tab-group.interface.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tab-group.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/tab-group.interface.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,cAAc,EAAE,MAAM,OAAO,CAAC;AAE5D,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,KAAK,CAAC;IACZ,KAAK,EAAE;QACL,QAAQ,EAAE,SAAS,CAAC;QACpB,WAAW,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;QAC5B,cAAc,CAAC,EAAE,QAAQ,CAAC,cAAc,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC;QACzD,UAAU,CAAC,EAAE,MAAM,CAAC;KACrB,CAAC;IACF,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,CAAC,UAAU,CAAC,CAAC;CACxB"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
export interface TabPanelsInterface {
|
|
3
|
+
type: 'div';
|
|
4
|
+
props: {
|
|
5
|
+
children: ReactNode;
|
|
6
|
+
};
|
|
7
|
+
states: object;
|
|
8
|
+
elements: ['tabPanels'];
|
|
9
|
+
}
|
|
10
|
+
export interface TabPanelInterface {
|
|
11
|
+
type: 'div';
|
|
12
|
+
props: {
|
|
13
|
+
children: ReactNode;
|
|
14
|
+
};
|
|
15
|
+
states: {
|
|
16
|
+
isSelected: boolean;
|
|
17
|
+
};
|
|
18
|
+
elements: ['tabPanel'];
|
|
19
|
+
}
|
|
20
|
+
//# sourceMappingURL=tab-panels.interface.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tab-panels.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/tab-panels.interface.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAElC,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,KAAK,CAAC;IACZ,KAAK,EAAE;QACL,QAAQ,EAAE,SAAS,CAAC;KACrB,CAAC;IACF,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,CAAC,WAAW,CAAC,CAAC;CACzB;AAED,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,KAAK,CAAC;IACZ,KAAK,EAAE;QACL,QAAQ,EAAE,SAAS,CAAC;KACrB,CAAC;IACF,MAAM,EAAE;QACN,UAAU,EAAE,OAAO,CAAC;KACrB,CAAC;IACF,QAAQ,EAAE,CAAC,UAAU,CAAC,CAAC;CACxB"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { ActionOrLink } from '../utils/component';
|
|
2
2
|
import { TabsVariant } from './tabs.interface';
|
|
3
|
-
import { Dispatch, RefObject, SetStateAction } from 'react';
|
|
3
|
+
import { Dispatch, ReactNode, RefObject, SetStateAction } from 'react';
|
|
4
4
|
import { Icon } from '../icon';
|
|
5
5
|
export type TabProps = {
|
|
6
6
|
selected?: boolean;
|
|
@@ -17,6 +17,7 @@ export type TabProps = {
|
|
|
17
17
|
}) => void;
|
|
18
18
|
index?: number;
|
|
19
19
|
scrollable?: boolean;
|
|
20
|
+
children?: ReactNode;
|
|
20
21
|
};
|
|
21
22
|
type Elements = ['tab', 'stateLayer', 'icon', 'label', 'content', 'underline'];
|
|
22
23
|
export type TabInterface = ActionOrLink<TabProps> & {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tab.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/tab.interface.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAC/C,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,cAAc,EAAE,MAAM,OAAO,CAAC;
|
|
1
|
+
{"version":3,"file":"tab.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/tab.interface.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAC/C,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,SAAS,EAAE,cAAc,EAAE,MAAM,OAAO,CAAC;AACvE,OAAO,EAAE,IAAI,EAAE,MAAM,SAAS,CAAC;AAE/B,MAAM,MAAM,QAAQ,GAAG;IACrB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,OAAO,CAAC,EAAE,WAAW,CAAC;IACtB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,IAAI,CAAC,EAAE,IAAI,CAAC;IACZ,WAAW,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,cAAc,CAAC,EAAE,QAAQ,CAAC,cAAc,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC;IACzD,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,aAAa,CAAC,EAAE,CACd,IAAI,EAAE;QAAE,KAAK,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC,QAAQ,EAAE,OAAO,GAAG,MAAM,CAAC,GAAG;QACzD,GAAG,EAAE,SAAS,CAAC,GAAG,CAAC,CAAC;KACrB,KACA,IAAI,CAAC;IACV,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,QAAQ,CAAC,EAAE,SAAS,CAAC;CACtB,CAAC;AAEF,KAAK,QAAQ,GAAG,CAAC,KAAK,EAAE,YAAY,EAAE,MAAM,EAAE,OAAO,EAAE,SAAS,EAAE,WAAW,CAAC,CAAC;AAE/E,MAAM,MAAM,YAAY,GAAG,YAAY,CAAC,QAAQ,CAAC,GAAG;IAClD,MAAM,EAAE;QACN,UAAU,EAAE,OAAO,CAAC;KACrB,CAAC;IACF,QAAQ,EAAE,QAAQ,CAAC;CACpB,CAAC"}
|
|
@@ -15,6 +15,7 @@ export * from './snackbar.style';
|
|
|
15
15
|
export * from './switch.style';
|
|
16
16
|
export * from './tab.style';
|
|
17
17
|
export * from './tabs.style';
|
|
18
|
+
export * from './tab-panels.style';
|
|
18
19
|
export * from './text-field.style';
|
|
19
20
|
export * from './tooltip.style';
|
|
20
21
|
export { useButtonStyle } from './button.style';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/styles/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAC;AAC/B,cAAc,cAAc,CAAC;AAC7B,cAAc,uBAAuB,CAAC;AACtC,cAAc,kBAAkB,CAAC;AACjC,cAAc,cAAc,CAAC;AAC7B,cAAc,eAAe,CAAC;AAC9B,cAAc,iBAAiB,CAAC;AAChC,cAAc,aAAa,CAAC;AAC5B,cAAc,kBAAkB,CAAC;AACjC,cAAc,qBAAqB,CAAC;AACpC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,oBAAoB,CAAC;AACnC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,oBAAoB,CAAC;AACnC,cAAc,iBAAiB,CAAC;AAChC,OAAO,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/styles/index.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAC;AAC/B,cAAc,cAAc,CAAC;AAC7B,cAAc,uBAAuB,CAAC;AACtC,cAAc,kBAAkB,CAAC;AACjC,cAAc,cAAc,CAAC;AAC7B,cAAc,eAAe,CAAC;AAC9B,cAAc,iBAAiB,CAAC;AAChC,cAAc,aAAa,CAAC;AAC5B,cAAc,kBAAkB,CAAC;AACjC,cAAc,qBAAqB,CAAC;AACpC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,oBAAoB,CAAC;AACnC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,oBAAoB,CAAC;AACnC,cAAc,oBAAoB,CAAC;AACnC,cAAc,iBAAiB,CAAC;AAChC,OAAO,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAC"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { TabPanelsInterface, TabPanelInterface } from '../interfaces';
|
|
2
|
+
import { ClassNameComponent } from '../utils';
|
|
3
|
+
export declare const tabPanelsStyle: (states: {
|
|
4
|
+
children: any;
|
|
5
|
+
} & {
|
|
6
|
+
children: import('react').ReactNode;
|
|
7
|
+
} & object & {
|
|
8
|
+
className: string | ClassNameComponent<TabPanelsInterface> | undefined;
|
|
9
|
+
}) => Record<"tabPanels", string>;
|
|
10
|
+
export declare const useTabPanelsStyle: (states: object & {
|
|
11
|
+
children: import('react').ReactNode;
|
|
12
|
+
} & {
|
|
13
|
+
className?: string | ClassNameComponent<TabPanelsInterface> | undefined;
|
|
14
|
+
}) => Record<"tabPanels", string>;
|
|
15
|
+
export declare const tabPanelStyle: (states: {
|
|
16
|
+
children: any;
|
|
17
|
+
} & {
|
|
18
|
+
children: import('react').ReactNode;
|
|
19
|
+
} & {
|
|
20
|
+
isSelected: boolean;
|
|
21
|
+
} & {
|
|
22
|
+
className: string | ClassNameComponent<TabPanelInterface> | undefined;
|
|
23
|
+
}) => Record<"tabPanel", string>;
|
|
24
|
+
export declare const useTabPanelStyle: (states: {
|
|
25
|
+
isSelected: boolean;
|
|
26
|
+
} & {
|
|
27
|
+
children: import('react').ReactNode;
|
|
28
|
+
} & {
|
|
29
|
+
className?: string | ClassNameComponent<TabPanelInterface> | undefined;
|
|
30
|
+
}) => Record<"tabPanel", string>;
|
|
31
|
+
//# sourceMappingURL=tab-panels.style.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tab-panels.style.d.ts","sourceRoot":"","sources":["../../../src/lib/styles/tab-panels.style.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAC;AACtE,OAAO,EACL,KAAK,kBAAkB,EAIxB,MAAM,UAAU,CAAC;AAMlB,eAAO,MAAM,cAAc;;;;;;iCAG1B,CAAC;AAEF,eAAO,MAAM,iBAAiB;;;;iCAG7B,CAAC;AAMF,eAAO,MAAM,aAAa;;;;;;;;gCAGzB,CAAC;AAEF,eAAO,MAAM,gBAAgB;;;;;;gCAG5B,CAAC"}
|
|
@@ -11,6 +11,7 @@ export declare const tabStyle: (states: (({
|
|
|
11
11
|
onTabSelected: any;
|
|
12
12
|
index: any;
|
|
13
13
|
scrollable: any;
|
|
14
|
+
children: any;
|
|
14
15
|
href: any;
|
|
15
16
|
} | {
|
|
16
17
|
selected: any;
|
|
@@ -23,6 +24,7 @@ export declare const tabStyle: (states: (({
|
|
|
23
24
|
onTabSelected: any;
|
|
24
25
|
index: any;
|
|
25
26
|
scrollable: any;
|
|
27
|
+
children: any;
|
|
26
28
|
href: any;
|
|
27
29
|
}) & ((import('..').TabProps & {
|
|
28
30
|
href?: string;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tab.style.d.ts","sourceRoot":"","sources":["../../../src/lib/styles/tab.style.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,KAAK,kBAAkB,EAIxB,MAAM,UAAU,CAAC;AAClB,OAAO,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAqE7C,eAAO,MAAM,QAAQ
|
|
1
|
+
{"version":3,"file":"tab.style.d.ts","sourceRoot":"","sources":["../../../src/lib/styles/tab.style.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,KAAK,kBAAkB,EAIxB,MAAM,UAAU,CAAC;AAClB,OAAO,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAqE7C,eAAO,MAAM,QAAQ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;uFAAoD,CAAC;AAE1E,eAAO,MAAM,WAAW;;;;;;;;wFAAsD,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@udixio/ui-react",
|
|
3
|
-
"version": "2.9.
|
|
3
|
+
"version": "2.9.7",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"main": "./dist/index.js",
|
|
6
6
|
"module": "./dist/index.js",
|
|
@@ -28,6 +28,7 @@
|
|
|
28
28
|
"motion": "^12.23.0",
|
|
29
29
|
"tailwind-merge": "^3.3.1",
|
|
30
30
|
"uuid": "^11.0.3",
|
|
31
|
+
"lenis": "^1.2.3",
|
|
31
32
|
"@fortawesome/fontawesome-svg-core": "^7.0.0",
|
|
32
33
|
"@fortawesome/free-regular-svg-icons": "^7.0.0",
|
|
33
34
|
"@fortawesome/free-solid-svg-icons": "^7.0.0",
|
|
@@ -36,8 +37,8 @@
|
|
|
36
37
|
"devDependencies": {
|
|
37
38
|
"react": "^19.1.1",
|
|
38
39
|
"react-dom": "^19.1.1",
|
|
39
|
-
"@udixio/theme": "2.1.
|
|
40
|
-
"@udixio/tailwind": "2.4.
|
|
40
|
+
"@udixio/theme": "2.1.10",
|
|
41
|
+
"@udixio/tailwind": "2.4.8"
|
|
41
42
|
},
|
|
42
43
|
"repository": {
|
|
43
44
|
"type": "git",
|
|
@@ -114,7 +114,8 @@ export const Chip = ({
|
|
|
114
114
|
}
|
|
115
115
|
};
|
|
116
116
|
|
|
117
|
-
const isInteractive =
|
|
117
|
+
const isInteractive =
|
|
118
|
+
!!onToggle || !!onRemove || !!onClick || !!href || !!editable;
|
|
118
119
|
|
|
119
120
|
if (activated) {
|
|
120
121
|
icon = faCheck;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import React, { useEffect, useState } from 'react';
|
|
1
|
+
import React, { useEffect, useRef, useState } from 'react';
|
|
2
2
|
import { ReactProps } from '../utils';
|
|
3
3
|
import { ChipItem, ChipsInterface } from '../interfaces';
|
|
4
4
|
import { useChipsStyle } from '../styles';
|
|
@@ -34,12 +34,19 @@ export const Chips = ({
|
|
|
34
34
|
|
|
35
35
|
React.useEffect(() => {
|
|
36
36
|
if (isFocused) {
|
|
37
|
-
|
|
37
|
+
if (variant == 'input') {
|
|
38
|
+
ghostChipRef.current?.focus();
|
|
39
|
+
} else {
|
|
40
|
+
ref.current?.focus();
|
|
41
|
+
}
|
|
38
42
|
}
|
|
39
43
|
}, [isFocused]);
|
|
40
44
|
|
|
41
45
|
const chipRefs = React.useRef<(HTMLElement | null)[]>([]);
|
|
42
46
|
|
|
47
|
+
// Guard to prevent multiple chip creation from fast typing
|
|
48
|
+
const isCreatingRef = React.useRef(false);
|
|
49
|
+
|
|
43
50
|
const updateItems = React.useCallback(
|
|
44
51
|
(updater: (prev: ChipItem[]) => ChipItem[]) => {
|
|
45
52
|
onItemsChange?.(updater(list));
|
|
@@ -64,6 +71,10 @@ export const Chips = ({
|
|
|
64
71
|
(seedLabel = '') => {
|
|
65
72
|
if (variant !== 'input') return;
|
|
66
73
|
|
|
74
|
+
// Guard against multiple rapid creations
|
|
75
|
+
if (isCreatingRef.current) return;
|
|
76
|
+
isCreatingRef.current = true;
|
|
77
|
+
|
|
67
78
|
const newItem: ChipItem = {
|
|
68
79
|
label: seedLabel,
|
|
69
80
|
} as ChipItem;
|
|
@@ -77,6 +88,8 @@ export const Chips = ({
|
|
|
77
88
|
|
|
78
89
|
requestAnimationFrame(() => {
|
|
79
90
|
setSelectedChip(newId);
|
|
91
|
+
// Reset guard after chip is selected
|
|
92
|
+
isCreatingRef.current = false;
|
|
80
93
|
});
|
|
81
94
|
},
|
|
82
95
|
[variant, onItemsChange, list, getInternalId],
|
|
@@ -102,6 +115,11 @@ export const Chips = ({
|
|
|
102
115
|
}, [selectedChip, list, getInternalId]);
|
|
103
116
|
|
|
104
117
|
// MODE ITEMS (source de vérité locale ou contrôlée)
|
|
118
|
+
|
|
119
|
+
const ghostChipRef = useRef<HTMLButtonElement>(null);
|
|
120
|
+
|
|
121
|
+
const isGhostChip = (isFocused || list.length === 0) && variant === 'input';
|
|
122
|
+
|
|
105
123
|
return (
|
|
106
124
|
<div
|
|
107
125
|
ref={ref}
|
|
@@ -114,7 +132,9 @@ export const Chips = ({
|
|
|
114
132
|
setIsFocused(true);
|
|
115
133
|
}
|
|
116
134
|
}}
|
|
117
|
-
onBlur={() =>
|
|
135
|
+
onBlur={() => {
|
|
136
|
+
setIsFocused(false);
|
|
137
|
+
}}
|
|
118
138
|
onKeyDown={(e) => {
|
|
119
139
|
if (variant !== 'input') return;
|
|
120
140
|
|
|
@@ -160,13 +180,7 @@ export const Chips = ({
|
|
|
160
180
|
setSelectedChip(elId);
|
|
161
181
|
return;
|
|
162
182
|
}
|
|
163
|
-
|
|
164
183
|
if (isContainerFocused) {
|
|
165
|
-
if (key === 'Enter') {
|
|
166
|
-
e.preventDefault();
|
|
167
|
-
createAndStartEdit('');
|
|
168
|
-
return;
|
|
169
|
-
}
|
|
170
184
|
if (key === 'Backspace') {
|
|
171
185
|
e.preventDefault();
|
|
172
186
|
// Focus last chip if any
|
|
@@ -176,12 +190,6 @@ export const Chips = ({
|
|
|
176
190
|
}
|
|
177
191
|
return;
|
|
178
192
|
}
|
|
179
|
-
// Start creation when typing a printable character
|
|
180
|
-
if (key.length === 1 && !e.altKey && !e.ctrlKey && !e.metaKey) {
|
|
181
|
-
createAndStartEdit(key);
|
|
182
|
-
e.preventDefault();
|
|
183
|
-
return;
|
|
184
|
-
}
|
|
185
193
|
}
|
|
186
194
|
}}
|
|
187
195
|
>
|
|
@@ -203,7 +211,7 @@ export const Chips = ({
|
|
|
203
211
|
onEditCancel: () => {
|
|
204
212
|
setIsFocused(true);
|
|
205
213
|
},
|
|
206
|
-
onChange: (
|
|
214
|
+
onChange: () => {
|
|
207
215
|
if (chipRefs.current.length == index + 1) {
|
|
208
216
|
const el = ref.current!;
|
|
209
217
|
requestAnimationFrame(() => {
|
|
@@ -275,6 +283,39 @@ export const Chips = ({
|
|
|
275
283
|
</style>
|
|
276
284
|
</>
|
|
277
285
|
)}
|
|
286
|
+
{isGhostChip && (
|
|
287
|
+
<Chip
|
|
288
|
+
ref={ghostChipRef}
|
|
289
|
+
className="opacity-0"
|
|
290
|
+
draggable={draggable}
|
|
291
|
+
editable={true}
|
|
292
|
+
editing={true}
|
|
293
|
+
onChange={(v) => {
|
|
294
|
+
v = v.replace(/( )+/g, ' ').trim();
|
|
295
|
+
console.log('Ghost chip onChange', v, !!v);
|
|
296
|
+
if (v) {
|
|
297
|
+
createAndStartEdit(v);
|
|
298
|
+
} else {
|
|
299
|
+
if (list.length > 0) {
|
|
300
|
+
const el = chipRefs.current[list.length - 1] as any;
|
|
301
|
+
el?.focus?.();
|
|
302
|
+
}
|
|
303
|
+
}
|
|
304
|
+
}}
|
|
305
|
+
onEditCommit={() => {
|
|
306
|
+
// Ghost chip doesn't commit - it creates a new chip via onChange
|
|
307
|
+
}}
|
|
308
|
+
onBlur={() => {
|
|
309
|
+
setIsFocused(false);
|
|
310
|
+
}}
|
|
311
|
+
onFocus={(e: React.FocusEvent) => {
|
|
312
|
+
setIsFocused(true);
|
|
313
|
+
e.stopPropagation();
|
|
314
|
+
}}
|
|
315
|
+
>
|
|
316
|
+
|
|
317
|
+
</Chip>
|
|
318
|
+
)}
|
|
278
319
|
</div>
|
|
279
320
|
);
|
|
280
321
|
};
|
|
@@ -14,7 +14,7 @@ import { State } from '../effects';
|
|
|
14
14
|
export const Tab = ({
|
|
15
15
|
className,
|
|
16
16
|
onClick,
|
|
17
|
-
label,
|
|
17
|
+
label: labelProp,
|
|
18
18
|
variant = 'primary',
|
|
19
19
|
href,
|
|
20
20
|
icon,
|
|
@@ -25,12 +25,16 @@ export const Tab = ({
|
|
|
25
25
|
onTabSelected,
|
|
26
26
|
scrollable = false,
|
|
27
27
|
selected = false,
|
|
28
|
+
children,
|
|
28
29
|
ref,
|
|
29
30
|
...restProps
|
|
30
31
|
}: ReactProps<TabInterface>) => {
|
|
31
32
|
const defaultRef = useRef(null);
|
|
32
33
|
const resolvedRef = ref || defaultRef;
|
|
33
34
|
|
|
35
|
+
// children (string) peut être utilisé comme alternative à label prop
|
|
36
|
+
const label = labelProp ?? (typeof children === 'string' ? children : undefined);
|
|
37
|
+
|
|
34
38
|
const [isSelected, setIsSelected] = useState<boolean>(selected);
|
|
35
39
|
|
|
36
40
|
useEffect(() => {
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import React, { useMemo, useRef, useState } from 'react';
|
|
2
|
+
import { v4 as uuidv4 } from 'uuid';
|
|
3
|
+
import { TabGroupContext, TabGroupContextValue } from './TabGroupContext';
|
|
4
|
+
import { TabGroupInterface } from '../interfaces/tab-group.interface';
|
|
5
|
+
import { ReactProps } from '../utils/component';
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* TabGroup provides shared state for Tabs and TabPanels
|
|
9
|
+
* @status beta
|
|
10
|
+
* @category Navigation
|
|
11
|
+
*/
|
|
12
|
+
export const TabGroup = ({
|
|
13
|
+
children,
|
|
14
|
+
selectedTab: externalSelectedTab,
|
|
15
|
+
setSelectedTab: externalSetSelectedTab,
|
|
16
|
+
defaultTab = 0,
|
|
17
|
+
}: ReactProps<TabGroupInterface>) => {
|
|
18
|
+
const [internalSelectedTab, internalSetSelectedTab] = useState<number | null>(
|
|
19
|
+
defaultTab,
|
|
20
|
+
);
|
|
21
|
+
const previousTabRef = useRef<number | null>(null);
|
|
22
|
+
|
|
23
|
+
// Priorité : props externes > état interne
|
|
24
|
+
const selectedTab =
|
|
25
|
+
externalSelectedTab !== undefined ? externalSelectedTab : internalSelectedTab;
|
|
26
|
+
|
|
27
|
+
const setSelectedTab = externalSetSelectedTab ?? internalSetSelectedTab;
|
|
28
|
+
|
|
29
|
+
// Calculer la direction du slide
|
|
30
|
+
const direction =
|
|
31
|
+
previousTabRef.current !== null && selectedTab !== null
|
|
32
|
+
? selectedTab > previousTabRef.current
|
|
33
|
+
? 1
|
|
34
|
+
: -1
|
|
35
|
+
: 0;
|
|
36
|
+
|
|
37
|
+
// Mettre à jour la référence précédente
|
|
38
|
+
if (selectedTab !== previousTabRef.current) {
|
|
39
|
+
previousTabRef.current = selectedTab;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
const tabsId = useMemo(() => uuidv4(), []);
|
|
43
|
+
|
|
44
|
+
const contextValue: TabGroupContextValue = useMemo(
|
|
45
|
+
() => ({
|
|
46
|
+
selectedTab,
|
|
47
|
+
setSelectedTab,
|
|
48
|
+
previousTab: previousTabRef.current,
|
|
49
|
+
direction,
|
|
50
|
+
tabsId,
|
|
51
|
+
}),
|
|
52
|
+
[selectedTab, setSelectedTab, direction, tabsId],
|
|
53
|
+
);
|
|
54
|
+
|
|
55
|
+
return (
|
|
56
|
+
<TabGroupContext.Provider value={contextValue}>
|
|
57
|
+
{children}
|
|
58
|
+
</TabGroupContext.Provider>
|
|
59
|
+
);
|
|
60
|
+
};
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { createContext, Dispatch, SetStateAction } from 'react';
|
|
2
|
+
|
|
3
|
+
export interface TabGroupContextValue {
|
|
4
|
+
selectedTab: number | null;
|
|
5
|
+
setSelectedTab: Dispatch<SetStateAction<number | null>>;
|
|
6
|
+
previousTab: number | null;
|
|
7
|
+
direction: number;
|
|
8
|
+
tabsId: string;
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
export const TabGroupContext = createContext<TabGroupContextValue | null>(null);
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { TabPanelInterface } from '../interfaces/tab-panels.interface';
|
|
3
|
+
import { ReactProps } from '../utils/component';
|
|
4
|
+
import { useTabPanelStyle } from '../styles/tab-panels.style';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* TabPanel contains the content for a single tab
|
|
8
|
+
* Must be used within TabPanels
|
|
9
|
+
* @status beta
|
|
10
|
+
* @category Navigation
|
|
11
|
+
*/
|
|
12
|
+
export const TabPanel = ({
|
|
13
|
+
children,
|
|
14
|
+
className,
|
|
15
|
+
isSelected = false,
|
|
16
|
+
}: ReactProps<TabPanelInterface>) => {
|
|
17
|
+
const styles = useTabPanelStyle({
|
|
18
|
+
children,
|
|
19
|
+
className,
|
|
20
|
+
isSelected,
|
|
21
|
+
});
|
|
22
|
+
|
|
23
|
+
return <div className={styles.tabPanel}>{children}</div>;
|
|
24
|
+
};
|