@etsoo/materialui 1.2.49 → 1.2.50
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/lib/DnDList.d.ts +5 -1
- package/lib/DnDList.js +67 -49
- package/package.json +1 -1
- package/src/DnDList.tsx +130 -64
package/lib/DnDList.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { UniqueIdentifier } from "@dnd-kit/core";
|
|
1
|
+
import type { UniqueIdentifier } from "@dnd-kit/core";
|
|
2
2
|
import { DataTypes } from "@etsoo/shared";
|
|
3
3
|
import { Theme } from "@mui/material";
|
|
4
4
|
import React, { CSSProperties } from "react";
|
|
@@ -56,6 +56,10 @@ export interface DnDListPros<D extends object, K extends DataTypes.Keys<D>> {
|
|
|
56
56
|
* Item renderer
|
|
57
57
|
*/
|
|
58
58
|
itemRenderer: (item: D, index: number, nodeRef: React.ComponentProps<any>, actionNodeRef: React.ComponentProps<any>) => React.ReactElement;
|
|
59
|
+
/**
|
|
60
|
+
* Height
|
|
61
|
+
*/
|
|
62
|
+
height?: string | number;
|
|
59
63
|
/**
|
|
60
64
|
* List items
|
|
61
65
|
*/
|
package/lib/DnDList.js
CHANGED
|
@@ -1,16 +1,13 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { SortableContext, useSortable, verticalListSortingStrategy } from "@dnd-kit/sortable";
|
|
3
|
-
import { CSS } from "@dnd-kit/utilities";
|
|
4
|
-
import { useTheme } from "@mui/material";
|
|
1
|
+
import { Skeleton, useTheme } from "@mui/material";
|
|
5
2
|
import React from "react";
|
|
6
3
|
function SortableItem(props) {
|
|
7
4
|
// Destruct
|
|
8
|
-
const { id, itemRenderer, style = {} } = props;
|
|
5
|
+
const { id, useSortableType, CSSType, itemRenderer, style = {} } = props;
|
|
9
6
|
// Use sortable
|
|
10
|
-
const { attributes, listeners, setNodeRef, transform, transition, setActivatorNodeRef } =
|
|
7
|
+
const { attributes, listeners, setNodeRef, transform, transition, setActivatorNodeRef } = useSortableType({ id });
|
|
11
8
|
const allStyle = {
|
|
12
9
|
...style,
|
|
13
|
-
transform:
|
|
10
|
+
transform: CSSType.Transform.toString(transform),
|
|
14
11
|
transition
|
|
15
12
|
};
|
|
16
13
|
const nodeRef = {
|
|
@@ -47,52 +44,27 @@ export const DnDItemStyle = (index, isDragging, theme) => ({
|
|
|
47
44
|
*/
|
|
48
45
|
export function DnDList(props) {
|
|
49
46
|
// Destruct
|
|
50
|
-
const { keyField, itemRenderer, labelField, mRef, onChange, onFormChange, onDragEnd } = props;
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
// Theme
|
|
54
|
-
const theme = useTheme();
|
|
55
|
-
getItemStyle = (index, isDragging) => DnDItemStyle(index, isDragging, theme);
|
|
56
|
-
}
|
|
47
|
+
const { keyField, height = 360, itemRenderer, labelField, mRef, onChange, onFormChange, onDragEnd } = props;
|
|
48
|
+
// Theme
|
|
49
|
+
const theme = useTheme();
|
|
57
50
|
// States
|
|
58
51
|
const [items, setItems] = React.useState([]);
|
|
59
52
|
const [activeId, setActiveId] = React.useState();
|
|
60
|
-
|
|
53
|
+
React.useEffect(() => {
|
|
54
|
+
setItems(props.items);
|
|
55
|
+
}, [props.items]);
|
|
56
|
+
const doFormChange = React.useCallback((newItems) => {
|
|
61
57
|
if (onFormChange)
|
|
62
58
|
onFormChange(newItems !== null && newItems !== void 0 ? newItems : items);
|
|
63
|
-
};
|
|
64
|
-
const changeItems = (newItems) => {
|
|
59
|
+
}, [items, onFormChange]);
|
|
60
|
+
const changeItems = React.useCallback((newItems) => {
|
|
65
61
|
// Possible to alter items with the handler
|
|
66
62
|
if (onChange)
|
|
67
63
|
onChange(newItems);
|
|
68
64
|
doFormChange(newItems);
|
|
69
65
|
// Update state
|
|
70
66
|
setItems(newItems);
|
|
71
|
-
};
|
|
72
|
-
// Drag event handlers
|
|
73
|
-
function handleDragStart(event) {
|
|
74
|
-
const { active } = event;
|
|
75
|
-
setActiveId(active.id);
|
|
76
|
-
}
|
|
77
|
-
function handleDragEnd(event) {
|
|
78
|
-
const { active, over } = event;
|
|
79
|
-
if (over && active.id !== over.id) {
|
|
80
|
-
// Indices
|
|
81
|
-
const oldIndex = items.findIndex((item) => item.id === active.id);
|
|
82
|
-
const newIndex = items.findIndex((item) => item.id === over.id);
|
|
83
|
-
// Clone
|
|
84
|
-
const newItems = [...items];
|
|
85
|
-
// Removed item
|
|
86
|
-
const [removed] = newItems.splice(oldIndex, 1);
|
|
87
|
-
// Insert to the destination index
|
|
88
|
-
newItems.splice(newIndex, 0, removed);
|
|
89
|
-
changeItems(newItems);
|
|
90
|
-
// Drag end handler
|
|
91
|
-
if (onDragEnd)
|
|
92
|
-
onDragEnd(newItems);
|
|
93
|
-
}
|
|
94
|
-
setActiveId(undefined);
|
|
95
|
-
}
|
|
67
|
+
}, [onChange, doFormChange]);
|
|
96
68
|
// Methods
|
|
97
69
|
React.useImperativeHandle(mRef, () => {
|
|
98
70
|
return {
|
|
@@ -149,7 +121,56 @@ export function DnDList(props) {
|
|
|
149
121
|
return items;
|
|
150
122
|
}
|
|
151
123
|
};
|
|
152
|
-
}, [items]);
|
|
124
|
+
}, [items, labelField, changeItems]);
|
|
125
|
+
// Dynamic import library
|
|
126
|
+
const [dnd, setDnd] = React.useState();
|
|
127
|
+
React.useEffect(() => {
|
|
128
|
+
Promise.all([
|
|
129
|
+
import("@dnd-kit/core"),
|
|
130
|
+
import("@dnd-kit/sortable"),
|
|
131
|
+
import("@dnd-kit/utilities")
|
|
132
|
+
]).then(([{ DndContext }, { SortableContext, useSortable, verticalListSortingStrategy }, { CSS }]) => {
|
|
133
|
+
setDnd([
|
|
134
|
+
DndContext,
|
|
135
|
+
SortableContext,
|
|
136
|
+
useSortable,
|
|
137
|
+
verticalListSortingStrategy,
|
|
138
|
+
CSS
|
|
139
|
+
]);
|
|
140
|
+
});
|
|
141
|
+
}, []);
|
|
142
|
+
if (dnd == null) {
|
|
143
|
+
return React.createElement(Skeleton, { variant: "rectangular", width: "100%", height: height });
|
|
144
|
+
}
|
|
145
|
+
const [DndContextType, SortableContextType, useSortableType, verticalListSortingStrategyType, CSSType] = dnd;
|
|
146
|
+
let getItemStyle = props.getItemStyle;
|
|
147
|
+
if (getItemStyle == null) {
|
|
148
|
+
getItemStyle = (index, isDragging) => DnDItemStyle(index, isDragging, theme);
|
|
149
|
+
}
|
|
150
|
+
// Drag event handlers
|
|
151
|
+
function handleDragStart(event) {
|
|
152
|
+
const { active } = event;
|
|
153
|
+
setActiveId(active.id);
|
|
154
|
+
}
|
|
155
|
+
function handleDragEnd(event) {
|
|
156
|
+
const { active, over } = event;
|
|
157
|
+
if (over && active.id !== over.id) {
|
|
158
|
+
// Indices
|
|
159
|
+
const oldIndex = items.findIndex((item) => item.id === active.id);
|
|
160
|
+
const newIndex = items.findIndex((item) => item.id === over.id);
|
|
161
|
+
// Clone
|
|
162
|
+
const newItems = [...items];
|
|
163
|
+
// Removed item
|
|
164
|
+
const [removed] = newItems.splice(oldIndex, 1);
|
|
165
|
+
// Insert to the destination index
|
|
166
|
+
newItems.splice(newIndex, 0, removed);
|
|
167
|
+
changeItems(newItems);
|
|
168
|
+
// Drag end handler
|
|
169
|
+
if (onDragEnd)
|
|
170
|
+
onDragEnd(newItems);
|
|
171
|
+
}
|
|
172
|
+
setActiveId(undefined);
|
|
173
|
+
}
|
|
153
174
|
const setupDiv = (div) => {
|
|
154
175
|
// Inputs
|
|
155
176
|
div
|
|
@@ -164,13 +185,10 @@ export function DnDList(props) {
|
|
|
164
185
|
.querySelectorAll("select")
|
|
165
186
|
.forEach((input) => input.addEventListener("change", () => doFormChange()));
|
|
166
187
|
};
|
|
167
|
-
React.
|
|
168
|
-
|
|
169
|
-
}, [props.items]);
|
|
170
|
-
const children = (React.createElement(DndContext, { onDragStart: handleDragStart, onDragEnd: handleDragEnd },
|
|
171
|
-
React.createElement(SortableContext, { items: items, strategy: verticalListSortingStrategy }, items.map((item, index) => {
|
|
188
|
+
const children = (React.createElement(DndContextType, { onDragStart: handleDragStart, onDragEnd: handleDragEnd },
|
|
189
|
+
React.createElement(SortableContextType, { items: items, strategy: verticalListSortingStrategyType }, items.map((item, index) => {
|
|
172
190
|
const id = item[keyField];
|
|
173
|
-
return (React.createElement(SortableItem, { id: id, key: id, style: getItemStyle(index, id === activeId), itemRenderer: (nodeRef, actionNodeRef) => itemRenderer(item, index, nodeRef, actionNodeRef) }));
|
|
191
|
+
return (React.createElement(SortableItem, { id: id, useSortableType: useSortableType, CSSType: CSSType, key: id, style: getItemStyle(index, id === activeId), itemRenderer: (nodeRef, actionNodeRef) => itemRenderer(item, index, nodeRef, actionNodeRef) }));
|
|
174
192
|
}))));
|
|
175
193
|
if (onFormChange) {
|
|
176
194
|
return (React.createElement("div", { style: { width: "100%" }, ref: (div) => {
|
package/package.json
CHANGED
package/src/DnDList.tsx
CHANGED
|
@@ -1,21 +1,23 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import type {
|
|
2
2
|
DndContext,
|
|
3
3
|
DragEndEvent,
|
|
4
4
|
DragStartEvent,
|
|
5
5
|
UniqueIdentifier
|
|
6
6
|
} from "@dnd-kit/core";
|
|
7
|
-
import {
|
|
7
|
+
import type {
|
|
8
8
|
SortableContext,
|
|
9
9
|
useSortable,
|
|
10
10
|
verticalListSortingStrategy
|
|
11
11
|
} from "@dnd-kit/sortable";
|
|
12
|
-
import { CSS } from "@dnd-kit/utilities";
|
|
12
|
+
import type { CSS } from "@dnd-kit/utilities";
|
|
13
13
|
import { DataTypes } from "@etsoo/shared";
|
|
14
|
-
import { Theme, useTheme } from "@mui/material";
|
|
14
|
+
import { Skeleton, Theme, useTheme } from "@mui/material";
|
|
15
15
|
import React, { CSSProperties } from "react";
|
|
16
16
|
|
|
17
17
|
function SortableItem(props: {
|
|
18
18
|
id: UniqueIdentifier;
|
|
19
|
+
useSortableType: typeof useSortable;
|
|
20
|
+
CSSType: typeof CSS;
|
|
19
21
|
itemRenderer: (
|
|
20
22
|
nodeRef: React.ComponentProps<any>,
|
|
21
23
|
actionNodeRef: React.ComponentProps<any>
|
|
@@ -23,7 +25,7 @@ function SortableItem(props: {
|
|
|
23
25
|
style?: React.CSSProperties;
|
|
24
26
|
}) {
|
|
25
27
|
// Destruct
|
|
26
|
-
const { id, itemRenderer, style = {} } = props;
|
|
28
|
+
const { id, useSortableType, CSSType, itemRenderer, style = {} } = props;
|
|
27
29
|
|
|
28
30
|
// Use sortable
|
|
29
31
|
const {
|
|
@@ -33,11 +35,11 @@ function SortableItem(props: {
|
|
|
33
35
|
transform,
|
|
34
36
|
transition,
|
|
35
37
|
setActivatorNodeRef
|
|
36
|
-
} =
|
|
38
|
+
} = useSortableType({ id });
|
|
37
39
|
|
|
38
40
|
const allStyle = {
|
|
39
41
|
...style,
|
|
40
|
-
transform:
|
|
42
|
+
transform: CSSType.Transform.toString(transform),
|
|
41
43
|
transition
|
|
42
44
|
};
|
|
43
45
|
|
|
@@ -130,6 +132,11 @@ export interface DnDListPros<D extends object, K extends DataTypes.Keys<D>> {
|
|
|
130
132
|
actionNodeRef: React.ComponentProps<any>
|
|
131
133
|
) => React.ReactElement;
|
|
132
134
|
|
|
135
|
+
/**
|
|
136
|
+
* Height
|
|
137
|
+
*/
|
|
138
|
+
height?: string | number;
|
|
139
|
+
|
|
133
140
|
/**
|
|
134
141
|
* List items
|
|
135
142
|
*/
|
|
@@ -181,6 +188,7 @@ export function DnDList<
|
|
|
181
188
|
// Destruct
|
|
182
189
|
const {
|
|
183
190
|
keyField,
|
|
191
|
+
height = 360,
|
|
184
192
|
itemRenderer,
|
|
185
193
|
labelField,
|
|
186
194
|
mRef,
|
|
@@ -189,63 +197,36 @@ export function DnDList<
|
|
|
189
197
|
onDragEnd
|
|
190
198
|
} = props;
|
|
191
199
|
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
// Theme
|
|
195
|
-
const theme = useTheme();
|
|
196
|
-
getItemStyle = (index, isDragging) =>
|
|
197
|
-
DnDItemStyle(index, isDragging, theme);
|
|
198
|
-
}
|
|
200
|
+
// Theme
|
|
201
|
+
const theme = useTheme();
|
|
199
202
|
|
|
200
203
|
// States
|
|
201
204
|
const [items, setItems] = React.useState<D[]>([]);
|
|
202
205
|
const [activeId, setActiveId] = React.useState<UniqueIdentifier>();
|
|
203
206
|
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
};
|
|
207
|
-
|
|
208
|
-
const changeItems = (newItems: D[]) => {
|
|
209
|
-
// Possible to alter items with the handler
|
|
210
|
-
if (onChange) onChange(newItems);
|
|
211
|
-
|
|
212
|
-
doFormChange(newItems);
|
|
213
|
-
|
|
214
|
-
// Update state
|
|
215
|
-
setItems(newItems);
|
|
216
|
-
};
|
|
217
|
-
|
|
218
|
-
// Drag event handlers
|
|
219
|
-
function handleDragStart(event: DragStartEvent) {
|
|
220
|
-
const { active } = event;
|
|
221
|
-
setActiveId(active.id);
|
|
222
|
-
}
|
|
223
|
-
|
|
224
|
-
function handleDragEnd(event: DragEndEvent) {
|
|
225
|
-
const { active, over } = event;
|
|
226
|
-
|
|
227
|
-
if (over && active.id !== over.id) {
|
|
228
|
-
// Indices
|
|
229
|
-
const oldIndex = items.findIndex((item) => item.id === active.id);
|
|
230
|
-
const newIndex = items.findIndex((item) => item.id === over.id);
|
|
231
|
-
|
|
232
|
-
// Clone
|
|
233
|
-
const newItems = [...items];
|
|
234
|
-
|
|
235
|
-
// Removed item
|
|
236
|
-
const [removed] = newItems.splice(oldIndex, 1);
|
|
207
|
+
React.useEffect(() => {
|
|
208
|
+
setItems(props.items);
|
|
209
|
+
}, [props.items]);
|
|
237
210
|
|
|
238
|
-
|
|
239
|
-
|
|
211
|
+
const doFormChange = React.useCallback(
|
|
212
|
+
(newItems?: D[]) => {
|
|
213
|
+
if (onFormChange) onFormChange(newItems ?? items);
|
|
214
|
+
},
|
|
215
|
+
[items, onFormChange]
|
|
216
|
+
);
|
|
240
217
|
|
|
241
|
-
|
|
218
|
+
const changeItems = React.useCallback(
|
|
219
|
+
(newItems: D[]) => {
|
|
220
|
+
// Possible to alter items with the handler
|
|
221
|
+
if (onChange) onChange(newItems);
|
|
242
222
|
|
|
243
|
-
|
|
244
|
-
if (onDragEnd) onDragEnd(newItems);
|
|
245
|
-
}
|
|
223
|
+
doFormChange(newItems);
|
|
246
224
|
|
|
247
|
-
|
|
248
|
-
|
|
225
|
+
// Update state
|
|
226
|
+
setItems(newItems);
|
|
227
|
+
},
|
|
228
|
+
[onChange, doFormChange]
|
|
229
|
+
);
|
|
249
230
|
|
|
250
231
|
// Methods
|
|
251
232
|
React.useImperativeHandle(
|
|
@@ -327,9 +308,93 @@ export function DnDList<
|
|
|
327
308
|
}
|
|
328
309
|
};
|
|
329
310
|
},
|
|
330
|
-
[items]
|
|
311
|
+
[items, labelField, changeItems]
|
|
331
312
|
);
|
|
332
313
|
|
|
314
|
+
// Dynamic import library
|
|
315
|
+
const [dnd, setDnd] =
|
|
316
|
+
React.useState<
|
|
317
|
+
[
|
|
318
|
+
typeof DndContext,
|
|
319
|
+
typeof SortableContext,
|
|
320
|
+
typeof useSortable,
|
|
321
|
+
typeof verticalListSortingStrategy,
|
|
322
|
+
typeof CSS
|
|
323
|
+
]
|
|
324
|
+
>();
|
|
325
|
+
|
|
326
|
+
React.useEffect(() => {
|
|
327
|
+
Promise.all([
|
|
328
|
+
import("@dnd-kit/core"),
|
|
329
|
+
import("@dnd-kit/sortable"),
|
|
330
|
+
import("@dnd-kit/utilities")
|
|
331
|
+
]).then(
|
|
332
|
+
([
|
|
333
|
+
{ DndContext },
|
|
334
|
+
{ SortableContext, useSortable, verticalListSortingStrategy },
|
|
335
|
+
{ CSS }
|
|
336
|
+
]) => {
|
|
337
|
+
setDnd([
|
|
338
|
+
DndContext,
|
|
339
|
+
SortableContext,
|
|
340
|
+
useSortable,
|
|
341
|
+
verticalListSortingStrategy,
|
|
342
|
+
CSS
|
|
343
|
+
]);
|
|
344
|
+
}
|
|
345
|
+
);
|
|
346
|
+
}, []);
|
|
347
|
+
|
|
348
|
+
if (dnd == null) {
|
|
349
|
+
return <Skeleton variant="rectangular" width="100%" height={height} />;
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
const [
|
|
353
|
+
DndContextType,
|
|
354
|
+
SortableContextType,
|
|
355
|
+
useSortableType,
|
|
356
|
+
verticalListSortingStrategyType,
|
|
357
|
+
CSSType
|
|
358
|
+
] = dnd;
|
|
359
|
+
|
|
360
|
+
let getItemStyle = props.getItemStyle;
|
|
361
|
+
if (getItemStyle == null) {
|
|
362
|
+
getItemStyle = (index, isDragging) =>
|
|
363
|
+
DnDItemStyle(index, isDragging, theme);
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
// Drag event handlers
|
|
367
|
+
function handleDragStart(event: DragStartEvent) {
|
|
368
|
+
const { active } = event;
|
|
369
|
+
setActiveId(active.id);
|
|
370
|
+
}
|
|
371
|
+
|
|
372
|
+
function handleDragEnd(event: DragEndEvent) {
|
|
373
|
+
const { active, over } = event;
|
|
374
|
+
|
|
375
|
+
if (over && active.id !== over.id) {
|
|
376
|
+
// Indices
|
|
377
|
+
const oldIndex = items.findIndex((item) => item.id === active.id);
|
|
378
|
+
const newIndex = items.findIndex((item) => item.id === over.id);
|
|
379
|
+
|
|
380
|
+
// Clone
|
|
381
|
+
const newItems = [...items];
|
|
382
|
+
|
|
383
|
+
// Removed item
|
|
384
|
+
const [removed] = newItems.splice(oldIndex, 1);
|
|
385
|
+
|
|
386
|
+
// Insert to the destination index
|
|
387
|
+
newItems.splice(newIndex, 0, removed);
|
|
388
|
+
|
|
389
|
+
changeItems(newItems);
|
|
390
|
+
|
|
391
|
+
// Drag end handler
|
|
392
|
+
if (onDragEnd) onDragEnd(newItems);
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
setActiveId(undefined);
|
|
396
|
+
}
|
|
397
|
+
|
|
333
398
|
const setupDiv = (div: HTMLDivElement) => {
|
|
334
399
|
// Inputs
|
|
335
400
|
div
|
|
@@ -353,18 +418,19 @@ export function DnDList<
|
|
|
353
418
|
);
|
|
354
419
|
};
|
|
355
420
|
|
|
356
|
-
React.useEffect(() => {
|
|
357
|
-
setItems(props.items);
|
|
358
|
-
}, [props.items]);
|
|
359
|
-
|
|
360
421
|
const children = (
|
|
361
|
-
<
|
|
362
|
-
<
|
|
422
|
+
<DndContextType onDragStart={handleDragStart} onDragEnd={handleDragEnd}>
|
|
423
|
+
<SortableContextType
|
|
424
|
+
items={items}
|
|
425
|
+
strategy={verticalListSortingStrategyType}
|
|
426
|
+
>
|
|
363
427
|
{items.map((item, index) => {
|
|
364
428
|
const id = item[keyField] as unknown as UniqueIdentifier;
|
|
365
429
|
return (
|
|
366
430
|
<SortableItem
|
|
367
431
|
id={id}
|
|
432
|
+
useSortableType={useSortableType}
|
|
433
|
+
CSSType={CSSType}
|
|
368
434
|
key={id}
|
|
369
435
|
style={getItemStyle!(index, id === activeId)}
|
|
370
436
|
itemRenderer={(nodeRef, actionNodeRef) =>
|
|
@@ -373,8 +439,8 @@ export function DnDList<
|
|
|
373
439
|
/>
|
|
374
440
|
);
|
|
375
441
|
})}
|
|
376
|
-
</
|
|
377
|
-
</
|
|
442
|
+
</SortableContextType>
|
|
443
|
+
</DndContextType>
|
|
378
444
|
);
|
|
379
445
|
|
|
380
446
|
if (onFormChange) {
|