@gentleduck/registry-ui 0.2.1
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 +62 -0
- package/index.css +3 -0
- package/package.json +59 -0
- package/src/_old/_table/index.ts +5 -0
- package/src/_old/_table/table-advanced.constants.tsx +24 -0
- package/src/_old/_table/table-advanced.tsx +311 -0
- package/src/_old/_table/table-advanced.types.ts +272 -0
- package/src/_old/_table/table.constants.ts +2 -0
- package/src/_old/_table/table.hook.tsx +115 -0
- package/src/_old/_table/table.lib.ts +85 -0
- package/src/_old/_table/table.tsx +916 -0
- package/src/_old/_table/table.types.ts +118 -0
- package/src/_old/_table/todo.md +11 -0
- package/src/_old/_upload/index.ts +9 -0
- package/src/_old/_upload/todo.md +38 -0
- package/src/_old/_upload/upload-advanced-chunks.tsx +1624 -0
- package/src/_old/_upload/upload-advanced.tsx +507 -0
- package/src/_old/_upload/upload-sonner.tsx +58 -0
- package/src/_old/_upload/upload.assets.tsx +239 -0
- package/src/_old/_upload/upload.constants.tsx +75 -0
- package/src/_old/_upload/upload.dto.ts +19 -0
- package/src/_old/_upload/upload.lib.tsx +630 -0
- package/src/_old/_upload/upload.tsx +491 -0
- package/src/_old/_upload/upload.types.ts +436 -0
- package/src/accordion/accordion.tsx +247 -0
- package/src/accordion/index.ts +1 -0
- package/src/alert/alert.constants.ts +17 -0
- package/src/alert/alert.tsx +52 -0
- package/src/alert/index.ts +2 -0
- package/src/alert-dialog/alert-dialog.tsx +107 -0
- package/src/alert-dialog/index.ts +1 -0
- package/src/aspect-ratio/aspect-ratio.tsx +33 -0
- package/src/aspect-ratio/index.ts +1 -0
- package/src/audio/audio-record.tsx +776 -0
- package/src/audio/audio-visualizer.tsx +377 -0
- package/src/audio/audio.libs.ts +5 -0
- package/src/audio/audio.types.ts +50 -0
- package/src/audio/index.ts +2 -0
- package/src/avatar/avatar.tsx +78 -0
- package/src/avatar/index.ts +1 -0
- package/src/badge/badge.constants.ts +38 -0
- package/src/badge/badge.tsx +19 -0
- package/src/badge/index.ts +2 -0
- package/src/breadcrumb/breadcrumb.tsx +119 -0
- package/src/breadcrumb/index.ts +1 -0
- package/src/button/button.constants.ts +44 -0
- package/src/button/button.tsx +79 -0
- package/src/button/button.types.ts +38 -0
- package/src/button/index.ts +3 -0
- package/src/button-group/button-group.constants.ts +26 -0
- package/src/button-group/button-group.tsx +65 -0
- package/src/button-group/index.ts +2 -0
- package/src/calendar/calendar.tsx +191 -0
- package/src/calendar/index.ts +1 -0
- package/src/card/card.tsx +81 -0
- package/src/card/index.ts +1 -0
- package/src/carousel/carousel.tsx +211 -0
- package/src/carousel/carousel.types.ts +23 -0
- package/src/carousel/index.ts +2 -0
- package/src/chart/chart.libs.ts +27 -0
- package/src/chart/chart.tsx +260 -0
- package/src/chart/chart.types.ts +38 -0
- package/src/chart/index.ts +3 -0
- package/src/checkbox/checkbox.tsx +144 -0
- package/src/checkbox/checkbox.types.ts +24 -0
- package/src/checkbox/index.ts +2 -0
- package/src/collapsible/collapsible.tsx +151 -0
- package/src/collapsible/index.ts +1 -0
- package/src/combobox/combobox.tsx +132 -0
- package/src/combobox/index.ts +1 -0
- package/src/command/command.tsx +192 -0
- package/src/command/command.types.ts +11 -0
- package/src/command/index.ts +2 -0
- package/src/context-menu/context-menu.tsx +178 -0
- package/src/context-menu/index.ts +1 -0
- package/src/dialog/dialog-responsive.tsx +137 -0
- package/src/dialog/dialog.tsx +97 -0
- package/src/dialog/index.ts +2 -0
- package/src/direction/direction.tsx +13 -0
- package/src/direction/index.ts +1 -0
- package/src/drawer/drawer.tsx +185 -0
- package/src/drawer/index.ts +1 -0
- package/src/dropdown-menu/dropdown-menu.tsx +181 -0
- package/src/dropdown-menu/index.ts +1 -0
- package/src/empty/empty.constants.ts +15 -0
- package/src/empty/empty.tsx +73 -0
- package/src/empty/index.ts +2 -0
- package/src/field/field.constants.ts +22 -0
- package/src/field/field.tsx +203 -0
- package/src/field/index.ts +2 -0
- package/src/hover-card/hover-card.tsx +79 -0
- package/src/hover-card/index.ts +1 -0
- package/src/input/index.ts +1 -0
- package/src/input/input.tsx +45 -0
- package/src/input-group/index.ts +1 -0
- package/src/input-group/input-group.tsx +170 -0
- package/src/input-otp/index.ts +1 -0
- package/src/input-otp/input-otp.tsx +66 -0
- package/src/item/index.ts +2 -0
- package/src/item/item.constants.ts +22 -0
- package/src/item/item.tsx +185 -0
- package/src/json-editor/index.ts +4 -0
- package/src/json-editor/json-editor.hooks.ts +21 -0
- package/src/json-editor/json-editor.libs.ts +34 -0
- package/src/json-editor/json-editor.tsx +425 -0
- package/src/json-editor/json-editor.types.ts +80 -0
- package/src/json-editor/json-editor.view.tsx +110 -0
- package/src/json-editor/json-text-area.tsx +7 -0
- package/src/kbd/index.ts +1 -0
- package/src/kbd/kbd.tsx +39 -0
- package/src/label/index.ts +1 -0
- package/src/label/label.tsx +28 -0
- package/src/menubar/index.ts +1 -0
- package/src/menubar/menubar.tsx +213 -0
- package/src/navigation-menu/index.ts +1 -0
- package/src/navigation-menu/navigation-menu.tsx +152 -0
- package/src/pagination/index.ts +2 -0
- package/src/pagination/pagination.tsx +191 -0
- package/src/pagination/pagination.types.ts +17 -0
- package/src/popover/index.ts +1 -0
- package/src/popover/popover.tsx +35 -0
- package/src/preview-panel/index.ts +3 -0
- package/src/preview-panel/preview-panel-dialog.tsx +99 -0
- package/src/preview-panel/preview-panel.tsx +389 -0
- package/src/preview-panel/preview-panel.types.ts +49 -0
- package/src/progress/index.ts +1 -0
- package/src/progress/progress.tsx +32 -0
- package/src/radio-group/index.ts +1 -0
- package/src/radio-group/radio-group.tsx +92 -0
- package/src/resizable/index.ts +1 -0
- package/src/resizable/resizable.tsx +52 -0
- package/src/scroll-area/index.ts +1 -0
- package/src/scroll-area/scroll-area.tsx +30 -0
- package/src/select/index.ts +1 -0
- package/src/select/select.tsx +138 -0
- package/src/separator/index.ts +1 -0
- package/src/separator/separator.tsx +28 -0
- package/src/sheet/index.ts +2 -0
- package/src/sheet/sheet.constants.tsx +20 -0
- package/src/sheet/sheet.tsx +92 -0
- package/src/sidebar/index.ts +4 -0
- package/src/sidebar/sidebar.constants.ts +30 -0
- package/src/sidebar/sidebar.hooks.ts +13 -0
- package/src/sidebar/sidebar.tsx +676 -0
- package/src/sidebar/sidebar.types.ts +28 -0
- package/src/skeleton/index.ts +1 -0
- package/src/skeleton/skeleton.tsx +22 -0
- package/src/slider/index.ts +1 -0
- package/src/slider/slider.tsx +57 -0
- package/src/sonner/index.ts +4 -0
- package/src/sonner/sonner.chunks.tsx +80 -0
- package/src/sonner/sonner.libs.ts +13 -0
- package/src/sonner/sonner.tsx +31 -0
- package/src/sonner/sonner.types.ts +9 -0
- package/src/switch/index.ts +1 -0
- package/src/switch/switch.tsx +63 -0
- package/src/table/index.ts +1 -0
- package/src/table/table.tsx +95 -0
- package/src/tabs/index.ts +1 -0
- package/src/tabs/tabs.tsx +151 -0
- package/src/textarea/index.ts +1 -0
- package/src/textarea/textarea.tsx +24 -0
- package/src/toggle/index.ts +2 -0
- package/src/toggle/toggle.constants.ts +22 -0
- package/src/toggle/toggle.tsx +24 -0
- package/src/toggle-group/index.ts +1 -0
- package/src/toggle-group/toggle-group.tsx +69 -0
- package/src/tooltip/index.ts +1 -0
- package/src/tooltip/tooltip.tsx +32 -0
- package/src/upload/index.ts +1 -0
- package/src/upload/upload.constants.tsx +19 -0
- package/src/upload/upload.libs.ts +97 -0
- package/src/upload/upload.tsx +340 -0
- package/src/upload/upload.types.ts +44 -0
- package/tsconfig.json +25 -0
|
@@ -0,0 +1,272 @@
|
|
|
1
|
+
// @ts-noCheck
|
|
2
|
+
|
|
3
|
+
import React from 'react'
|
|
4
|
+
import { Button, LabelType } from '../button'
|
|
5
|
+
import { ScrollArea } from '../scroll-area'
|
|
6
|
+
import { Table, TableBody } from './table'
|
|
7
|
+
import { sortArray } from './table.lib'
|
|
8
|
+
|
|
9
|
+
// ------------------------------------------------------------------------------------------------
|
|
10
|
+
// NOTE: These types are used for the `table-advanced` context.
|
|
11
|
+
// ------------------------------------------------------------------------------------------------
|
|
12
|
+
|
|
13
|
+
export interface DuckTableProviderProps<TColumnName extends string[]> extends React.HTMLAttributes<HTMLDivElement> {
|
|
14
|
+
table_columns: readonly TableColumnType[]
|
|
15
|
+
table_rows: TableContentDataType<TColumnName>[]
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export type DuckTableContextType<TColumnName extends string[]> = {
|
|
19
|
+
tableColumns: Map<string, TableColumnType>
|
|
20
|
+
setTableColumns: React.Dispatch<React.SetStateAction<Map<string, TableColumnType>>>
|
|
21
|
+
tableRows: TableContentDataType<TColumnName>[]
|
|
22
|
+
selectedRows: Set<TableContentDataType<TColumnName>>
|
|
23
|
+
setSelectedRows: React.Dispatch<React.SetStateAction<Set<TableContentDataType<TColumnName>>>>
|
|
24
|
+
search: TableSearchStateType
|
|
25
|
+
setSearch: React.Dispatch<React.SetStateAction<TableSearchStateType>>
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
export type TableSortByStateType<TColumnName extends string[]> = {
|
|
29
|
+
label: TColumnName[number]
|
|
30
|
+
type: React.HTMLProps<HTMLDivElement>['aria-sort']
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
export interface TableSearchStateType {
|
|
34
|
+
query: string
|
|
35
|
+
queryBy: string[]
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
// ------------------------------------------------------------------------------------------------
|
|
39
|
+
// NOTE: These types are used for the `table-advanced` Components.
|
|
40
|
+
// ------------------------------------------------------------------------------------------------
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Interface for the `DuckTable` component
|
|
44
|
+
*/
|
|
45
|
+
export interface DuckTableProps extends React.ComponentPropsWithoutRef<typeof Table> {
|
|
46
|
+
wrapper?: React.ComponentPropsWithoutRef<typeof ScrollArea>
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Interface for the `DuckTableHeader` component
|
|
51
|
+
*/
|
|
52
|
+
export interface DuckTableHeaderProps {}
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* Interface for the `DuckTableHeadCheckbox` component
|
|
56
|
+
*/
|
|
57
|
+
export interface DuckTableHeadCheckboxProps extends React.HTMLProps<HTMLDivElement> {}
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* Interface for the `DuckTableRowCheckbox` component
|
|
61
|
+
*/
|
|
62
|
+
export interface DuckTableRowCheckboxProps<TColumnName extends readonly TableColumnType[]>
|
|
63
|
+
extends React.HTMLProps<HTMLDivElement> {
|
|
64
|
+
tableRow: TableContentDataType<GetColumnLabel<TColumnName>>
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* Interface for the `DuckTableHeadSelectable` component
|
|
69
|
+
*/
|
|
70
|
+
export interface DuckTableHeadSelectableProps<TSort extends boolean = true> extends React.HTMLProps<HTMLDivElement> {
|
|
71
|
+
column: TableColumnType<TSort>
|
|
72
|
+
label: string
|
|
73
|
+
showLabel?: boolean | undefined
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Interface for the `DuckTableBody` component
|
|
78
|
+
*/
|
|
79
|
+
export interface DuckTableBodyProps extends React.ComponentPropsWithoutRef<typeof TableBody> {}
|
|
80
|
+
|
|
81
|
+
// ------------------------------------------------------------------------------------------------
|
|
82
|
+
// NOTE: These types are used for the `table-advanced, hence i use them to get the types.
|
|
83
|
+
// ------------------------------------------------------------------------------------------------
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* Extracts the `label` property from an array of `TableColumnType` objects
|
|
87
|
+
* and returns a tuple of string literals representing the column labels.
|
|
88
|
+
*
|
|
89
|
+
* ### Type Safety Guidelines:
|
|
90
|
+
* 1. Ensure the `columns` array is defined as `const` to preserve type inference.
|
|
91
|
+
* 2. Use `readonly TableColumnType[]` to enforce immutability and proper inference.
|
|
92
|
+
*
|
|
93
|
+
* #### Inferring Labels as a Union
|
|
94
|
+
* - Append `[number]` to the type to extract a union of possible labels.
|
|
95
|
+
* ```ts
|
|
96
|
+
* type ColumnLabel = GetColumnLabel<typeof columns>[number]; // 'Name' | 'Age' | 'Email'
|
|
97
|
+
* ```
|
|
98
|
+
*
|
|
99
|
+
* #### Defining Columns and Extracting Labels
|
|
100
|
+
* ```ts
|
|
101
|
+
* // Define columns as a strongly typed readonly array
|
|
102
|
+
* const columns = [
|
|
103
|
+
* { label: "Name" },
|
|
104
|
+
* { label: "Age" },
|
|
105
|
+
* { label: "Email" }
|
|
106
|
+
* ] as const satisfies readonly TableColumnType[];
|
|
107
|
+
*
|
|
108
|
+
* // Extract column labels as a tuple of string literals
|
|
109
|
+
* type ColumnLabels = GetColumnLabel<typeof columns>; // ['Name', 'Age', 'Email']
|
|
110
|
+
* ```
|
|
111
|
+
*/
|
|
112
|
+
export type GetColumnLabel<TColumn extends readonly TableColumnType[]> = {
|
|
113
|
+
-readonly [K in keyof TColumn]: `${TColumn[K]['label']}`
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
/**
|
|
117
|
+
* Defines the column type for a table based on a dynamic set of column names.
|
|
118
|
+
*
|
|
119
|
+
* ### Type Safety Guidelines:
|
|
120
|
+
* 1. Define the columns array as `const` to infer the most precise type.
|
|
121
|
+
* 2. Ensure the type satisfies `readonly string[]` to preserve strict type checking.
|
|
122
|
+
*
|
|
123
|
+
* #### Inferring Column Names as a Union
|
|
124
|
+
* - Append `[number]` to the type to infer a union of possible column names.
|
|
125
|
+
* ```ts
|
|
126
|
+
* type ColumnName = TColumnName[number]; // Infers as a union of column names
|
|
127
|
+
* ```
|
|
128
|
+
*
|
|
129
|
+
* #### Defining Columns and Extracting Names
|
|
130
|
+
* ```ts
|
|
131
|
+
* // Define column names as a strongly typed readonly array
|
|
132
|
+
* const columnNames = ['name', 'age', 'email'] as const;
|
|
133
|
+
*
|
|
134
|
+
* // Extract column names as a union type
|
|
135
|
+
* type ColumnName = typeof columnNames[number]; // 'name' | 'age' | 'email'
|
|
136
|
+
* ```
|
|
137
|
+
*
|
|
138
|
+
* #### Example Usage
|
|
139
|
+
* ```ts
|
|
140
|
+
* type MyTableColumns = TableContentDataType<typeof columnNames>;
|
|
141
|
+
*
|
|
142
|
+
* const columns: MyTableColumns = {
|
|
143
|
+
* name: { label: "Full Name", children: "firstName", icon: { name: "user" } },
|
|
144
|
+
* age: { label: "Age", icon: { name: "calendar" } },
|
|
145
|
+
* email: { label: "Email Address" }
|
|
146
|
+
* };
|
|
147
|
+
* ```
|
|
148
|
+
*/
|
|
149
|
+
export type TableContentDataType<TColumnName extends readonly string[]> = {
|
|
150
|
+
[key in TColumnName[number]]: TableColumnType & {
|
|
151
|
+
children?: TColumnName[number]
|
|
152
|
+
icon?: React.ReactNode
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
/**
|
|
157
|
+
* **Utility Type: Mutable**
|
|
158
|
+
* Converts all properties of a type `T` from readonly to mutable.
|
|
159
|
+
*
|
|
160
|
+
* @template T - The type to make mutable.
|
|
161
|
+
*
|
|
162
|
+
* @example
|
|
163
|
+
* ```ts
|
|
164
|
+
* type ReadonlyUser = { readonly name: string; readonly age: number };
|
|
165
|
+
* type MutableUser = Mutable<ReadonlyUser>;
|
|
166
|
+
* // Result:
|
|
167
|
+
* // {
|
|
168
|
+
* // name: string;
|
|
169
|
+
* // age: number;
|
|
170
|
+
* // }
|
|
171
|
+
* ```
|
|
172
|
+
*/
|
|
173
|
+
export type Mutable<T> = {
|
|
174
|
+
-readonly [K in keyof T]: T[K]
|
|
175
|
+
} & {}
|
|
176
|
+
|
|
177
|
+
/**
|
|
178
|
+
* **Utility Type: Immutable**
|
|
179
|
+
* Converts all properties of a type `T` from mutable to readonly.
|
|
180
|
+
*
|
|
181
|
+
* @template T - The type to make immutable.
|
|
182
|
+
*
|
|
183
|
+
* @example
|
|
184
|
+
* ```ts
|
|
185
|
+
* type User = { name: string; age: number };
|
|
186
|
+
* type ReadonlyUser = Immutable<User>;
|
|
187
|
+
* // Result:
|
|
188
|
+
* // {
|
|
189
|
+
* // readonly name: string;
|
|
190
|
+
* // readonly age: number;
|
|
191
|
+
* // }
|
|
192
|
+
* ```
|
|
193
|
+
*/
|
|
194
|
+
export type Immutable<T> = {
|
|
195
|
+
readonly [K in keyof T]: T[K]
|
|
196
|
+
} & {}
|
|
197
|
+
|
|
198
|
+
/**
|
|
199
|
+
* **Utility Type: Mapped**
|
|
200
|
+
* A type that directly maps all keys of a given type `T` to themselves.
|
|
201
|
+
*
|
|
202
|
+
* @template T - The type to map.
|
|
203
|
+
*
|
|
204
|
+
* @example
|
|
205
|
+
* ```ts
|
|
206
|
+
* type User = { name: string; age: number };
|
|
207
|
+
* type MappedUser = Mapped<User>;
|
|
208
|
+
* // Result (Same as User):
|
|
209
|
+
* // {
|
|
210
|
+
* // name: string;
|
|
211
|
+
* // age: number;
|
|
212
|
+
* // }
|
|
213
|
+
* ```
|
|
214
|
+
*/
|
|
215
|
+
export type Mapped<T> = {
|
|
216
|
+
[K in keyof T]: T[K]
|
|
217
|
+
} & {}
|
|
218
|
+
|
|
219
|
+
// ------------------------------------------------------------------------------------------------
|
|
220
|
+
// NOTE: These types are used for the `table-advanced, constants.
|
|
221
|
+
// ------------------------------------------------------------------------------------------------
|
|
222
|
+
|
|
223
|
+
export type TableColumnSortableType = React.ComponentPropsWithoutRef<typeof Button> & {
|
|
224
|
+
children: React.HTMLProps<HTMLDivElement>['aria-sort']
|
|
225
|
+
}
|
|
226
|
+
|
|
227
|
+
// ------------------------------------------------------------------------------------------------
|
|
228
|
+
|
|
229
|
+
export interface TableColumnType<TSort extends boolean = true> extends Partial<React.HTMLProps<HTMLTableCellElement>> {
|
|
230
|
+
label: string
|
|
231
|
+
sortable?: boolean
|
|
232
|
+
showLabel?: boolean
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
export interface TableDropdownMenuOptionsType<T extends boolean> {
|
|
236
|
+
sortArray: typeof sortArray
|
|
237
|
+
setHeaders: React.Dispatch<React.SetStateAction<TableColumnType[]>>
|
|
238
|
+
headers: TableColumnType[]
|
|
239
|
+
tableData: TableContentDataType<T>[]
|
|
240
|
+
setTableData: React.Dispatch<React.SetStateAction<TableContentDataType<T>[]>>
|
|
241
|
+
data: TableContentDataType<T>[]
|
|
242
|
+
idx: number
|
|
243
|
+
column: TableColumnType
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
export interface TableColumnType extends React.HTMLProps<HTMLTableCellElement> {
|
|
247
|
+
// TODO: clean up these legacy props
|
|
248
|
+
// FIX: make sure to use these in the future
|
|
249
|
+
withLabel?: Omit<LabelType, 'showCommand' | 'showLabel'>
|
|
250
|
+
withIcon?: React.ReactNode
|
|
251
|
+
}
|
|
252
|
+
// ------------------------------------------------------------------------------------------------
|
|
253
|
+
//NOTE: not used yet.
|
|
254
|
+
export type TableDataFilteredType<T extends Record<string, unknown>> = {
|
|
255
|
+
[K in keyof T]: [K, T[K]]
|
|
256
|
+
}[keyof T][]
|
|
257
|
+
|
|
258
|
+
export interface TablePaginationStateType {
|
|
259
|
+
pageSize: number
|
|
260
|
+
pageIndex: number
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
export interface TableSelectionStateType {
|
|
264
|
+
rowSelected: Record<string, unknown>[]
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
export type ColumnsViewedStateType<T extends Record<string, unknown>> = TableColumnType<T> | null
|
|
268
|
+
|
|
269
|
+
export type OrderStateType = {
|
|
270
|
+
orderBy: string
|
|
271
|
+
orderDir: 'asc' | 'desc'
|
|
272
|
+
}
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
// @ts-noCheck
|
|
2
|
+
import React from 'react'
|
|
3
|
+
import { DuckTableContext } from './table-advanced'
|
|
4
|
+
import { DuckTableContextType } from './table-advanced.types'
|
|
5
|
+
|
|
6
|
+
export const useDuckTable = <
|
|
7
|
+
Column extends Record<string, unknown> = Record<string, unknown>,
|
|
8
|
+
>(): DuckTableContextType<Column> | null => {
|
|
9
|
+
const context = React.useContext(DuckTableContext)
|
|
10
|
+
if (!context) {
|
|
11
|
+
throw new Error('useTableProvider must be used within an TableProvider')
|
|
12
|
+
}
|
|
13
|
+
return context
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
// <TableRow key={idx}>
|
|
17
|
+
// {tableDataFiltered.map(([key, value], idx) => {
|
|
18
|
+
// const headersEntries = headers.map(
|
|
19
|
+
// item => item.label.toString().toLowerCase() ?? item.children?.toString().toLowerCase()
|
|
20
|
+
// )
|
|
21
|
+
// const { className, children, withLabel, ...props } = value
|
|
22
|
+
// const {
|
|
23
|
+
// className: labelClassName,
|
|
24
|
+
// children: labelChildren,
|
|
25
|
+
// type: labelType = 'default',
|
|
26
|
+
// ...labelProps
|
|
27
|
+
// } = item?.[key]?.withLabel ?? {}
|
|
28
|
+
//
|
|
29
|
+
// return (
|
|
30
|
+
// headersEntries.includes(key.toString().toLowerCase()) && (
|
|
31
|
+
// <TableCell
|
|
32
|
+
// key={key}
|
|
33
|
+
// className={cn('py-2 h-[50px]', selected.includes(item) && 'bg-muted', className)}
|
|
34
|
+
// {...props}
|
|
35
|
+
// >
|
|
36
|
+
// <div
|
|
37
|
+
// className={cn(
|
|
38
|
+
// 'items-center gap-2 flex w-full',
|
|
39
|
+
// headers?.[idx]?.className,
|
|
40
|
+
// className,
|
|
41
|
+
// idx === headersEntries.length - 1 && dropdownMenu && 'justify-between w-full'
|
|
42
|
+
// )}
|
|
43
|
+
// >
|
|
44
|
+
// {/*NOTE: Rendering Checkbox */}
|
|
45
|
+
// {selection && idx === 0 && (
|
|
46
|
+
// <Checkbox
|
|
47
|
+
// className="border-border"
|
|
48
|
+
// onClick={() =>
|
|
49
|
+
// setSelected(
|
|
50
|
+
// selected.includes(item) ? selected.filter(i => i !== item) : [...selected, item]
|
|
51
|
+
// )
|
|
52
|
+
// }
|
|
53
|
+
// checked={selected.includes(item)}
|
|
54
|
+
// />
|
|
55
|
+
// )}
|
|
56
|
+
//
|
|
57
|
+
// {/*NOTE: Rendering Label */}
|
|
58
|
+
// {labelChildren && (
|
|
59
|
+
// <Badge
|
|
60
|
+
// variant={'outline'}
|
|
61
|
+
// size={'sm'}
|
|
62
|
+
// className={cn(labelType === 'default' ? '' : 'bg-red-500', labelClassName)}
|
|
63
|
+
// {...labelProps}
|
|
64
|
+
// >
|
|
65
|
+
// {labelChildren}
|
|
66
|
+
// </Badge>
|
|
67
|
+
// )}
|
|
68
|
+
//
|
|
69
|
+
// <div className="flex items-center gap-2 text-ellipsis overflow-hidden whitespace-nowrap">
|
|
70
|
+
// {/*NOTE: Getting Icons from Filter Data */}
|
|
71
|
+
// {filtersData?.length &&
|
|
72
|
+
// filtersData?.map(item => {
|
|
73
|
+
// return item?.content?.data.map((item, idx) => {
|
|
74
|
+
// const { children: Icon, ...props } = item?.element?.icon ?? {}
|
|
75
|
+
// return item.label?.toString().toLowerCase() ===
|
|
76
|
+
// (children as string).toString().toLowerCase() ? (
|
|
77
|
+
// <span
|
|
78
|
+
// className="whitespace-nowrap"
|
|
79
|
+
// key={idx}
|
|
80
|
+
// >
|
|
81
|
+
// {(Icon ? <Icon {...props} /> : '') as React.ReactNode}
|
|
82
|
+
// </span>
|
|
83
|
+
// ) : null
|
|
84
|
+
// })
|
|
85
|
+
// })}
|
|
86
|
+
//
|
|
87
|
+
// {/*NOTE: Rendering the row column childrend */}
|
|
88
|
+
// <span className="text-ellipsis overflow-hidden whitespace-nowrap">{children}</span>
|
|
89
|
+
// </div>
|
|
90
|
+
// {/*NOTE: Dropdown Menu */}
|
|
91
|
+
// {idx === headersEntries.length - 1 && dropdownMenu.optionsData?.length && (
|
|
92
|
+
// <DropdownMenuView
|
|
93
|
+
// trigger={{
|
|
94
|
+
// className: 'flex h-8 w-8 p-0 data-[state=open]:bg-muted',
|
|
95
|
+
// children: <span className="sr-only">Open menu</span>,
|
|
96
|
+
// variant: 'ghost',
|
|
97
|
+
// size: 'icon',
|
|
98
|
+
// icon: {
|
|
99
|
+
// children: Ellipsis,
|
|
100
|
+
// className: 'h-4 w-4',
|
|
101
|
+
// },
|
|
102
|
+
// }}
|
|
103
|
+
// content={{
|
|
104
|
+
// align: 'end',
|
|
105
|
+
// options: dropdownMenu,
|
|
106
|
+
// }}
|
|
107
|
+
// />
|
|
108
|
+
// )}
|
|
109
|
+
// </div>
|
|
110
|
+
// </TableCell>
|
|
111
|
+
// )
|
|
112
|
+
// )
|
|
113
|
+
// })}
|
|
114
|
+
// </TableRow>
|
|
115
|
+
//
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
// @ts-noCheck
|
|
2
|
+
import { DropdownMenuOptionsDataType } from '@/registry/default/ui/dropdown-menu'
|
|
3
|
+
import { Order, TableHeaderType } from './table.types'
|
|
4
|
+
import { ColumnsViewedStateType, TableContentDataType } from './table-advanced.types'
|
|
5
|
+
|
|
6
|
+
export function sortArray<T>(columns: TableHeaderType[], array: T[], key?: keyof T, order: Order = 'desc') {
|
|
7
|
+
const toggleSortOrder = (currentOrder: Order): Order => {
|
|
8
|
+
if (currentOrder === 'not sorted') return order
|
|
9
|
+
if (currentOrder === 'asc' && order === 'asc') return 'not sorted'
|
|
10
|
+
if (currentOrder === 'asc' && order === 'desc') return 'desc'
|
|
11
|
+
if (currentOrder === 'desc' && order === 'desc') return 'not sorted'
|
|
12
|
+
if (currentOrder === 'desc' && order === 'asc') return 'asc'
|
|
13
|
+
return 'not sorted'
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
const updatedColumns = columns.map((col) => {
|
|
17
|
+
if (col.label === key) {
|
|
18
|
+
return {
|
|
19
|
+
...col,
|
|
20
|
+
currentSort: toggleSortOrder(col.currentSort ?? 'not sorted'),
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
return col
|
|
24
|
+
})
|
|
25
|
+
|
|
26
|
+
const sortedData = array.toSorted((a, b) => {
|
|
27
|
+
const valueA = key ? (a[key] as TableContentDataType).children : a
|
|
28
|
+
const valueB = key ? (b[key] as TableContentDataType).children : b
|
|
29
|
+
|
|
30
|
+
if (order === 'not sorted' || !key) return 0
|
|
31
|
+
|
|
32
|
+
if (typeof valueA === 'string' && typeof valueB === 'string') {
|
|
33
|
+
return order === 'asc' ? valueA.localeCompare(valueB) : valueB.localeCompare(valueA)
|
|
34
|
+
} else if (typeof valueA === 'number' && typeof valueB === 'number') {
|
|
35
|
+
return order === 'asc' ? valueA - valueB : valueB - valueA
|
|
36
|
+
} else {
|
|
37
|
+
return order === 'asc' ? (valueA > valueB ? 1 : -1) : valueA < valueB ? 1 : -1
|
|
38
|
+
}
|
|
39
|
+
})
|
|
40
|
+
|
|
41
|
+
return { sortedData, updatedColumns }
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
export type OptionsDataType<T extends Record<string, unknown>> = {
|
|
45
|
+
header: ColumnsViewedStateType<T>[]
|
|
46
|
+
columnsViewed?: ColumnsViewedStateType<T>[]
|
|
47
|
+
setColumnsViewed?: React.Dispatch<React.SetStateAction<ColumnsViewedStateType<T>[]>>
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
export function get_options_data<T extends Record<string, unknown> = Record<string, string>>({
|
|
51
|
+
header,
|
|
52
|
+
columnsViewed,
|
|
53
|
+
setColumnsViewed,
|
|
54
|
+
}: OptionsDataType<T>) {
|
|
55
|
+
return header.map((column, idx) => {
|
|
56
|
+
const { children, className, label, sortable, disabled, currentSort, dropdownMenuOptions, ...props } = column ?? {}
|
|
57
|
+
|
|
58
|
+
return {
|
|
59
|
+
checked: columnsViewed?.some((headerItem) => headerItem?.label === label),
|
|
60
|
+
children: label ?? children,
|
|
61
|
+
className: 'capitalize',
|
|
62
|
+
disabled: disabled,
|
|
63
|
+
key: idx,
|
|
64
|
+
onCheckedChange: () => {
|
|
65
|
+
setColumnsViewed?.((prevHeaders) => {
|
|
66
|
+
const exists = prevHeaders.some((headerItem) => headerItem?.label === label)
|
|
67
|
+
|
|
68
|
+
if (exists) {
|
|
69
|
+
return prevHeaders.filter((headerItem) => headerItem?.label !== label)
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
const originalIndex = header.findIndex((headerItem) => headerItem?.label === label)
|
|
73
|
+
const newHeaders = [...prevHeaders]
|
|
74
|
+
newHeaders.splice(originalIndex, 0, column)
|
|
75
|
+
return newHeaders.sort(
|
|
76
|
+
(a, b) =>
|
|
77
|
+
header.findIndex((headerItem) => headerItem?.label === a?.label) -
|
|
78
|
+
header.findIndex((headerItem) => headerItem?.label === b?.label),
|
|
79
|
+
)
|
|
80
|
+
})
|
|
81
|
+
},
|
|
82
|
+
...props,
|
|
83
|
+
}
|
|
84
|
+
}) as DropdownMenuOptionsDataType<T>[]
|
|
85
|
+
}
|