@tsiky/components-r19 1.0.0 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (61) hide show
  1. package/index.ts +35 -33
  2. package/package.json +1 -1
  3. package/src/components/AnnouncementPanel/FlexRowContainer.css +17 -17
  4. package/src/components/AnnouncementPanel/FlexRowContainer.stories.tsx +329 -329
  5. package/src/components/AnnouncementPanel/FlexRowContainer.tsx +24 -24
  6. package/src/components/AnnouncementPanel/ListBox/CounterListBox.css +56 -56
  7. package/src/components/AnnouncementPanel/ListBox/CounterListBox.stories.tsx +292 -292
  8. package/src/components/AnnouncementPanel/ListBox/CounterListBox.tsx +106 -106
  9. package/src/components/AnnouncementPanel/ListBox/SimpleListBox.css +57 -57
  10. package/src/components/AnnouncementPanel/ListBox/SimpleListBox.stories.tsx +189 -189
  11. package/src/components/AnnouncementPanel/ListBox/SimpleListBox.tsx +138 -138
  12. package/src/components/AnnouncementPanel/ListBox/TrendListBox.css +61 -61
  13. package/src/components/AnnouncementPanel/ListBox/TrendListBox.stories.tsx +257 -257
  14. package/src/components/AnnouncementPanel/ListBox/TrendListBox.tsx +90 -90
  15. package/src/components/AnnouncementPanel/ListBox/index.ts +3 -3
  16. package/src/components/AnnouncementPanel/ListContentContainer.css +23 -23
  17. package/src/components/AnnouncementPanel/ListContentContainer.stories.tsx +212 -212
  18. package/src/components/AnnouncementPanel/ListContentContainer.tsx +33 -33
  19. package/src/components/AnnouncementPanel/index.ts +3 -3
  20. package/src/components/Charts/area-chart-admission/AreaChartAdmission.tsx +129 -89
  21. package/src/components/Charts/bar-chart/BarChart.tsx +171 -132
  22. package/src/components/Charts/boxplot-chart/BoxPlotChart.tsx +114 -114
  23. package/src/components/Charts/mixed-chart/MixedChart.tsx +65 -9
  24. package/src/components/Charts/sankey-adaptation/sankey.tsx +70 -70
  25. package/src/components/Charts/sankey-chart/SankeyChart.tsx +183 -155
  26. package/src/components/Confirmationpopup/ConfirmationPopup.module.css +88 -0
  27. package/src/components/Confirmationpopup/ConfirmationPopup.stories.tsx +94 -0
  28. package/src/components/Confirmationpopup/ConfirmationPopup.tsx +47 -0
  29. package/src/components/Confirmationpopup/index.ts +6 -0
  30. package/src/components/Confirmationpopup/useConfirmationPopup.ts +48 -0
  31. package/src/components/DayStatCard/DayStatCard.tsx +96 -69
  32. package/src/components/DraggableSwitcher/DraggableSwitcherButton.tsx +58 -58
  33. package/src/components/DraggableSwitcher/context/useDraggableSwitcher.tsx +45 -45
  34. package/src/components/DraggableSwitcher/index.ts +2 -2
  35. package/src/components/DynamicInput/input/SelectInput.tsx +75 -75
  36. package/src/components/DynamicInput/input/assets/SelectInput.module.css +95 -95
  37. package/src/components/DynamicTable/TableCell.tsx +38 -30
  38. package/src/components/DynamicTable/TableHeader.tsx +39 -34
  39. package/src/components/DynamicTable/TableauDynamique.module.css +1333 -1287
  40. package/src/components/DynamicTable/TableauDynamique.tsx +154 -154
  41. package/src/components/DynamicTable/tools/tableTypes.ts +63 -63
  42. package/src/components/Grid/Grid.tsx +5 -0
  43. package/src/components/Grid/grid.css +285 -285
  44. package/src/components/Header/Header.tsx +4 -2
  45. package/src/components/Header/header.css +61 -31
  46. package/src/components/MetricsPanel/MetricsPanel.module.css +688 -636
  47. package/src/components/MetricsPanel/MetricsPanel.tsx +220 -282
  48. package/src/components/MetricsPanel/renderers/CompactRenderer.tsx +148 -125
  49. package/src/components/NavBar/NavBar.tsx +1 -1
  50. package/src/components/NavItem/NavItem.tsx +58 -58
  51. package/src/components/PeriodRange/PeriodRange.module.css +158 -158
  52. package/src/components/PeriodRange/PeriodRange.tsx +130 -130
  53. package/src/components/SearchBar/SearchBar.css +40 -40
  54. package/src/components/SelectFilter/SelectFilter.module.css +249 -0
  55. package/src/components/SelectFilter/SelectFilter.stories.tsx +321 -0
  56. package/src/components/SelectFilter/SelectFilter.tsx +219 -0
  57. package/src/components/SelectFilter/index.ts +2 -0
  58. package/src/components/SelectFilter/types.ts +19 -0
  59. package/src/components/TranslationKey/TranslationKey.css +272 -272
  60. package/src/components/TranslationKey/TranslationKey.tsx +266 -245
  61. package/src/components/TrendList/TrendList.tsx +72 -45
@@ -1,154 +1,154 @@
1
- 'use client';
2
-
3
- import React, { useState, useRef, useEffect } from 'react';
4
- import TableHeader from './TableHeader';
5
- import TableBody from './TableBody';
6
- import Pagination from './Pagination';
7
- import ColumnSorter from './ColumnSorter';
8
- import AdvancedFilters from './AdvancedFilters';
9
- import type { TableauDynamiqueProps, SortConfig } from './tools/tableTypes';
10
- import type { FilterConfig, AppliedFilter } from './tools/filterTypes';
11
- import styles from './TableauDynamique.module.css';
12
- import { useTableData } from './hooks/useTableData';
13
-
14
- export interface EnhancedTableauDynamiqueProps<T> extends TableauDynamiqueProps<T> {
15
- columnFilterable?: boolean;
16
- filterConfig?: FilterConfig[];
17
- externalFilters?: AppliedFilter[];
18
- onFiltersChange?: (filters: AppliedFilter[]) => void;
19
- onApplyFilters?: (filters: AppliedFilter[]) => void;
20
- filtersControlled?: boolean;
21
- debounceTimeout?: number;
22
- getRowStyle?: (row: T) => React.CSSProperties;
23
- background?: string;
24
- }
25
-
26
- export const TableauDynamique = <T,>({
27
- columns = [],
28
- data = [],
29
- pagination = { pageSize: 10, currentPage: 1 },
30
- onRowClick,
31
- searchTerm = '',
32
- className = '',
33
- filterConfig = [],
34
- externalFilters = [],
35
- onFiltersChange,
36
- onApplyFilters,
37
- filtersControlled = false,
38
- debounceTimeout = 300,
39
- getRowStyle,
40
- background,
41
- onNewPage,
42
- }: EnhancedTableauDynamiqueProps<T>) => {
43
- const [sortConfig, setSortConfig] = useState<SortConfig>({ key: null, direction: 'asc' });
44
- const [currentPage, setCurrentPage] = useState(pagination.currentPage ?? 1);
45
- const [pageSize, setPageSize] = useState(pagination.pageSize ?? 10);
46
-
47
- const [filtersExpanded, setFiltersExpanded] = useState(false);
48
- const containerRef = useRef<HTMLDivElement | null>(null);
49
- const [internalFilters, setInternalFilters] = useState<AppliedFilter[]>([]);
50
- const appliedFilters = filtersControlled ? externalFilters : internalFilters;
51
-
52
- const { paginatedData, sortedData, totalPages, startIndex } = useTableData<T>(
53
- data,
54
- columns,
55
- searchTerm,
56
- sortConfig,
57
- currentPage,
58
- pageSize,
59
- appliedFilters
60
- );
61
-
62
- useEffect(() => {
63
- const safeTotal = Math.max(1, Math.floor(totalPages));
64
- if (currentPage > safeTotal) {
65
- setCurrentPage(safeTotal);
66
- }
67
- if (currentPage < 1) {
68
- setCurrentPage(1);
69
- }
70
- }, [totalPages]);
71
-
72
- const handleFiltersChange = (filters: AppliedFilter[]) => {
73
- if (!filtersControlled) setInternalFilters(filters);
74
- onFiltersChange?.(filters);
75
- setCurrentPage(1);
76
- };
77
-
78
- const handleApplyFilters = (filters: AppliedFilter[]) => {
79
- if (!filtersControlled) setInternalFilters(filters);
80
- onApplyFilters?.(filters);
81
- setCurrentPage(1);
82
- setFiltersExpanded(false);
83
- if (containerRef.current)
84
- containerRef.current.style.setProperty('--filters-panel-height', `0px`);
85
- };
86
-
87
- const handlePageChange = (page: number) => setCurrentPage(page);
88
- const handlePageSizeChange = (size: number) => {
89
- setPageSize(size);
90
- setCurrentPage(1);
91
- };
92
-
93
- const handlePanelHeightChange = (h: number) => {
94
- if (containerRef.current) {
95
- containerRef.current.style.setProperty('--filters-panel-height', `${Math.round(h)}px`);
96
- }
97
- };
98
-
99
- return (
100
- <div
101
- ref={containerRef}
102
- className={`${styles.container} ${className} ${filtersExpanded ? 'filters-open' : ''}`}
103
- style={{ background }}
104
- >
105
- <div className={styles.tableControls}>
106
- <div className={styles.controlsRight}>
107
- <ColumnSorter columns={columns} sortConfig={sortConfig} onSort={setSortConfig} />
108
- {filterConfig.length > 0 && (
109
- <AdvancedFilters
110
- filters={filterConfig}
111
- externalFilters={externalFilters}
112
- onFiltersChange={handleFiltersChange}
113
- onApply={handleApplyFilters}
114
- isControlled={filtersControlled}
115
- debounceTimeout={debounceTimeout}
116
- resultsCount={sortedData.length}
117
- expanded={filtersExpanded}
118
- onToggle={(v: boolean | ((prevState: boolean) => boolean)) => setFiltersExpanded(v)}
119
- panelPlacement='top'
120
- onPanelHeightChange={handlePanelHeightChange}
121
- />
122
- )}
123
- </div>
124
- </div>
125
-
126
- <div className={styles.topPagination}>
127
- <Pagination
128
- currentPage={currentPage}
129
- totalPages={Math.max(1, totalPages)}
130
- pageSize={pageSize}
131
- totalItems={sortedData.length}
132
- onPageChange={handlePageChange}
133
- onPageSizeChange={handlePageSizeChange}
134
- onNewPage={onNewPage}
135
- />
136
- </div>
137
-
138
- <div className={styles.tableWrapper} data-table-wrapper>
139
- <table className={styles.table}>
140
- <TableHeader columns={columns} />
141
- <TableBody
142
- data={paginatedData}
143
- columns={columns}
144
- onRowClick={onRowClick}
145
- startIndex={startIndex}
146
- getRowStyle={getRowStyle}
147
- />
148
- </table>
149
- </div>
150
- </div>
151
- );
152
- };
153
-
154
- export default TableauDynamique;
1
+ 'use client';
2
+
3
+ import React, { useState, useRef, useEffect } from 'react';
4
+ import TableHeader from './TableHeader';
5
+ import TableBody from './TableBody';
6
+ import Pagination from './Pagination';
7
+ import ColumnSorter from './ColumnSorter';
8
+ import AdvancedFilters from './AdvancedFilters';
9
+ import type { TableauDynamiqueProps, SortConfig } from './tools/tableTypes';
10
+ import type { FilterConfig, AppliedFilter } from './tools/filterTypes';
11
+ import styles from './TableauDynamique.module.css';
12
+ import { useTableData } from './hooks/useTableData';
13
+
14
+ export interface EnhancedTableauDynamiqueProps<T> extends TableauDynamiqueProps<T> {
15
+ columnFilterable?: boolean;
16
+ filterConfig?: FilterConfig[];
17
+ externalFilters?: AppliedFilter[];
18
+ onFiltersChange?: (filters: AppliedFilter[]) => void;
19
+ onApplyFilters?: (filters: AppliedFilter[]) => void;
20
+ filtersControlled?: boolean;
21
+ debounceTimeout?: number;
22
+ getRowStyle?: (row: T) => React.CSSProperties;
23
+ background?: string;
24
+ }
25
+
26
+ export const TableauDynamique = <T,>({
27
+ columns = [],
28
+ data = [],
29
+ pagination = { pageSize: 10, currentPage: 1 },
30
+ onRowClick,
31
+ searchTerm = '',
32
+ className = '',
33
+ filterConfig = [],
34
+ externalFilters = [],
35
+ onFiltersChange,
36
+ onApplyFilters,
37
+ filtersControlled = false,
38
+ debounceTimeout = 300,
39
+ getRowStyle,
40
+ background,
41
+ onNewPage,
42
+ }: EnhancedTableauDynamiqueProps<T>) => {
43
+ const [sortConfig, setSortConfig] = useState<SortConfig>({ key: null, direction: 'asc' });
44
+ const [currentPage, setCurrentPage] = useState(pagination.currentPage ?? 1);
45
+ const [pageSize, setPageSize] = useState(pagination.pageSize ?? 10);
46
+
47
+ const [filtersExpanded, setFiltersExpanded] = useState(false);
48
+ const containerRef = useRef<HTMLDivElement | null>(null);
49
+ const [internalFilters, setInternalFilters] = useState<AppliedFilter[]>([]);
50
+ const appliedFilters = filtersControlled ? externalFilters : internalFilters;
51
+
52
+ const { paginatedData, sortedData, totalPages, startIndex } = useTableData<T>(
53
+ data,
54
+ columns,
55
+ searchTerm,
56
+ sortConfig,
57
+ currentPage,
58
+ pageSize,
59
+ appliedFilters
60
+ );
61
+
62
+ useEffect(() => {
63
+ const safeTotal = Math.max(1, Math.floor(totalPages));
64
+ if (currentPage > safeTotal) {
65
+ setCurrentPage(safeTotal);
66
+ }
67
+ if (currentPage < 1) {
68
+ setCurrentPage(1);
69
+ }
70
+ }, [totalPages]);
71
+
72
+ const handleFiltersChange = (filters: AppliedFilter[]) => {
73
+ if (!filtersControlled) setInternalFilters(filters);
74
+ onFiltersChange?.(filters);
75
+ setCurrentPage(1);
76
+ };
77
+
78
+ const handleApplyFilters = (filters: AppliedFilter[]) => {
79
+ if (!filtersControlled) setInternalFilters(filters);
80
+ onApplyFilters?.(filters);
81
+ setCurrentPage(1);
82
+ setFiltersExpanded(false);
83
+ if (containerRef.current)
84
+ containerRef.current.style.setProperty('--filters-panel-height', `0px`);
85
+ };
86
+
87
+ const handlePageChange = (page: number) => setCurrentPage(page);
88
+ const handlePageSizeChange = (size: number) => {
89
+ setPageSize(size);
90
+ setCurrentPage(1);
91
+ };
92
+
93
+ const handlePanelHeightChange = (h: number) => {
94
+ if (containerRef.current) {
95
+ containerRef.current.style.setProperty('--filters-panel-height', `${Math.round(h)}px`);
96
+ }
97
+ };
98
+
99
+ return (
100
+ <div
101
+ ref={containerRef}
102
+ className={`${styles.container} ${className} ${filtersExpanded ? 'filters-open' : ''}`}
103
+ style={{ background }}
104
+ >
105
+ <div className={styles.tableControls}>
106
+ <div className={styles.controlsRight}>
107
+ <ColumnSorter columns={columns} sortConfig={sortConfig} onSort={setSortConfig} />
108
+ {filterConfig.length > 0 && (
109
+ <AdvancedFilters
110
+ filters={filterConfig}
111
+ externalFilters={externalFilters}
112
+ onFiltersChange={handleFiltersChange}
113
+ onApply={handleApplyFilters}
114
+ isControlled={filtersControlled}
115
+ debounceTimeout={debounceTimeout}
116
+ resultsCount={sortedData.length}
117
+ expanded={filtersExpanded}
118
+ onToggle={(v: boolean | ((prevState: boolean) => boolean)) => setFiltersExpanded(v)}
119
+ panelPlacement='top'
120
+ onPanelHeightChange={handlePanelHeightChange}
121
+ />
122
+ )}
123
+ </div>
124
+ </div>
125
+
126
+ <div className={styles.topPagination}>
127
+ <Pagination
128
+ currentPage={currentPage}
129
+ totalPages={Math.max(1, totalPages)}
130
+ pageSize={pageSize}
131
+ totalItems={sortedData.length}
132
+ onPageChange={handlePageChange}
133
+ onPageSizeChange={handlePageSizeChange}
134
+ onNewPage={onNewPage}
135
+ />
136
+ </div>
137
+
138
+ <div className={styles.tableWrapper} data-table-wrapper>
139
+ <table className={styles.table}>
140
+ <TableHeader columns={columns} />
141
+ <TableBody
142
+ data={paginatedData}
143
+ columns={columns}
144
+ onRowClick={onRowClick}
145
+ startIndex={startIndex}
146
+ getRowStyle={getRowStyle}
147
+ />
148
+ </table>
149
+ </div>
150
+ </div>
151
+ );
152
+ };
153
+
154
+ export default TableauDynamique;
@@ -1,63 +1,63 @@
1
- /* eslint-disable @typescript-eslint/no-explicit-any */
2
- import type { ComponentType } from 'react';
3
-
4
- export interface TableColumn<T = any> {
5
- id: string;
6
- label: string;
7
- width?: string | number;
8
- align?: 'left' | 'center' | 'right';
9
- sortable?: boolean; // Rendre optionnel
10
- render?: (value: any, row: T, column: TableColumn<T>) => React.ReactNode;
11
- component?: ComponentType<{ value: any; row: T; column: TableColumn<T> }>;
12
- type?: string;
13
- options?: { value: string; label: string }[];
14
- }
15
-
16
- export interface TableRowData<T = any> {
17
- id: string;
18
- data: T;
19
- }
20
-
21
- export interface RendererProps<T = any> {
22
- value: any;
23
- row: T;
24
- column: TableColumn<T>;
25
- }
26
-
27
- export interface TableConfigType {
28
- renderers: Record<string, ComponentType<RendererProps>>;
29
- icons: {
30
- sortAsc: React.ReactElement;
31
- sortDesc: React.ReactElement;
32
- sortDefault: React.ReactElement;
33
- };
34
- }
35
-
36
- export interface SortConfig {
37
- key: string | null;
38
- direction: 'asc' | 'desc';
39
- }
40
-
41
- export interface TableauDynamiqueProps<T = any> {
42
- columns?: TableColumn<T>[];
43
- data?: TableRowData<T>[];
44
- pagination?: { pageSize: number; currentPage: number };
45
- onSort?: (sortConfig: SortConfig) => void;
46
- onPageChange?: (page: number) => void;
47
- onPageSizeChange?: (size: number) => void;
48
- onRowClick?: (row: T, index: number) => void;
49
- filterable?: boolean;
50
- searchTerm?: string;
51
- onSearch?: (term: string) => void;
52
- className?: string;
53
- onNewPage?: (page: number) => void;
54
- }
55
-
56
- export interface TableBodyProps<T> {
57
- data: TableRowData<T>[];
58
- columns: TableColumn<T>[];
59
- onRowClick?: (row: T, index: number) => void;
60
- startIndex: number;
61
- searchTerm?: string;
62
- getRowStyle?: (row: T) => React.CSSProperties;
63
- }
1
+ /* eslint-disable @typescript-eslint/no-explicit-any */
2
+ import type { ComponentType } from 'react';
3
+
4
+ export interface TableColumn<T = any> {
5
+ id: string;
6
+ label: string;
7
+ width?: string | number;
8
+ align?: 'left' | 'center' | 'right';
9
+ sortable?: boolean; // Rendre optionnel
10
+ render?: (value: any, row: T, column: TableColumn<T>) => React.ReactNode;
11
+ component?: ComponentType<{ value: any; row: T; column: TableColumn<T> }>;
12
+ type?: string;
13
+ options?: { value: string; label: string }[];
14
+ }
15
+
16
+ export interface TableRowData<T = any> {
17
+ id: string;
18
+ data: T;
19
+ }
20
+
21
+ export interface RendererProps<T = any> {
22
+ value: any;
23
+ row: T;
24
+ column: TableColumn<T>;
25
+ }
26
+
27
+ export interface TableConfigType {
28
+ renderers: Record<string, ComponentType<RendererProps>>;
29
+ icons: {
30
+ sortAsc: React.ReactElement;
31
+ sortDesc: React.ReactElement;
32
+ sortDefault: React.ReactElement;
33
+ };
34
+ }
35
+
36
+ export interface SortConfig {
37
+ key: string | null;
38
+ direction: 'asc' | 'desc';
39
+ }
40
+
41
+ export interface TableauDynamiqueProps<T = any> {
42
+ columns?: TableColumn<T>[];
43
+ data?: TableRowData<T>[];
44
+ pagination?: { pageSize: number; currentPage: number };
45
+ onSort?: (sortConfig: SortConfig) => void;
46
+ onPageChange?: (page: number) => void;
47
+ onPageSizeChange?: (size: number) => void;
48
+ onRowClick?: (row: T, index: number) => void;
49
+ filterable?: boolean;
50
+ searchTerm?: string;
51
+ onSearch?: (term: string) => void;
52
+ className?: string;
53
+ onNewPage?: (page: number) => void;
54
+ }
55
+
56
+ export interface TableBodyProps<T> {
57
+ data: TableRowData<T>[];
58
+ columns: TableColumn<T>[];
59
+ onRowClick?: (row: T, index: number) => void;
60
+ startIndex: number;
61
+ searchTerm?: string;
62
+ getRowStyle?: (row: T) => React.CSSProperties;
63
+ }
@@ -94,6 +94,7 @@ const Grid: React.FC<GridProps> = ({
94
94
  const handleDragStart = (e: React.DragEvent<HTMLDivElement>, index: number) => {
95
95
  e.stopPropagation();
96
96
  e.dataTransfer.setData('dragIndex', index.toString());
97
+ e.dataTransfer.setData('parentKey', uniqueKey.toString());
97
98
  };
98
99
 
99
100
  const handleDragOver = (e: React.DragEvent<HTMLDivElement>) => {
@@ -104,6 +105,10 @@ const Grid: React.FC<GridProps> = ({
104
105
  const handleDrop = (e: React.DragEvent<HTMLDivElement>, dropIndex: number) => {
105
106
  e.preventDefault();
106
107
  const dragIndex = Number(e.dataTransfer.getData('dragIndex'));
108
+ const dragParent = Number(e.dataTransfer.getData('parentKey'));
109
+ if (container && dragParent !== uniqueKey) {
110
+ return;
111
+ }
107
112
  const updatedItems = [...items];
108
113
 
109
114
  let dropInd = -1;