@hkdigital/lib-sveltekit 0.2.10 → 0.2.11
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.
@@ -12,7 +12,6 @@
|
|
12
12
|
DROPPING
|
13
13
|
} from '../../constants/state-labels/drag-states.js';
|
14
14
|
|
15
|
-
|
16
15
|
/** @typedef {import('../../typedef').SimulatedDragEvent} SimulatedDragEvent */
|
17
16
|
|
18
17
|
/**
|
@@ -26,7 +25,8 @@
|
|
26
25
|
* classes?: string,
|
27
26
|
* children: import('svelte').Snippet<[{
|
28
27
|
* element: HTMLElement,
|
29
|
-
* rect: DOMRect
|
28
|
+
* rect: DOMRect,
|
29
|
+
* isDragging: boolean
|
30
30
|
* }]>,
|
31
31
|
* draggingSnippet?: import('svelte').Snippet<[{
|
32
32
|
* element: HTMLElement,
|
@@ -102,24 +102,27 @@
|
|
102
102
|
let customPreviewSet = $state(false);
|
103
103
|
let elementRect = $state(null);
|
104
104
|
|
105
|
-
// Track if current draggable can drop in the active zone
|
106
|
-
let canDropInActiveZone = $derived.by(() => {
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
});
|
112
|
-
|
113
|
-
// Computed state object for CSS classes
|
114
|
-
let stateObject = $derived({
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
122
|
-
|
105
|
+
// Track if current draggable can drop in the active zone
|
106
|
+
let canDropInActiveZone = $derived.by(() => {
|
107
|
+
if (currentState !== DRAGGING || !dragState.activeDropZone) return false;
|
108
|
+
|
109
|
+
const activeZone = dragState.dropZones.get(dragState.activeDropZone);
|
110
|
+
return activeZone?.canDrop || false;
|
111
|
+
});
|
112
|
+
|
113
|
+
// Computed state object for CSS classes
|
114
|
+
let stateObject = $derived({
|
115
|
+
idle: currentState === IDLE,
|
116
|
+
dragging: currentState === DRAGGING,
|
117
|
+
'drag-preview': currentState === DRAG_PREVIEW,
|
118
|
+
dropping: currentState === DROPPING,
|
119
|
+
'drag-disabled': disabled || !canDrag(item),
|
120
|
+
'can-drop': currentState === DRAGGING && canDropInActiveZone,
|
121
|
+
'cannot-drop':
|
122
|
+
currentState === DRAGGING &&
|
123
|
+
dragState.activeDropZone &&
|
124
|
+
!canDropInActiveZone
|
125
|
+
});
|
123
126
|
|
124
127
|
let stateClasses = $derived(toStateClasses(stateObject));
|
125
128
|
|
@@ -180,10 +183,10 @@ let stateObject = $derived({
|
|
180
183
|
|
181
184
|
let transparentPixel;
|
182
185
|
|
183
|
-
if(
|
184
|
-
{
|
186
|
+
if (browser) {
|
185
187
|
transparentPixel = new Image();
|
186
|
-
transparentPixel.src =
|
188
|
+
transparentPixel.src =
|
189
|
+
'data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7';
|
187
190
|
}
|
188
191
|
|
189
192
|
/**
|
@@ -191,7 +194,6 @@ let stateObject = $derived({
|
|
191
194
|
* @param {DragEvent} event - The drag event
|
192
195
|
*/
|
193
196
|
function startDrag(event) {
|
194
|
-
|
195
197
|
// Set a transparent 1x1 pixel image to hide browser's default preview
|
196
198
|
event.dataTransfer.setDragImage(transparentPixel, 0, 0);
|
197
199
|
|
@@ -363,10 +365,10 @@ let stateObject = $derived({
|
|
363
365
|
|
364
366
|
// Show preview
|
365
367
|
// if (draggingSnippet) {
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
368
|
+
elementRect = rect;
|
369
|
+
previewX = rect.left;
|
370
|
+
previewY = rect.top;
|
371
|
+
showPreview = true;
|
370
372
|
// }
|
371
373
|
|
372
374
|
// Prevent scrolling while dragging
|
@@ -385,79 +387,83 @@ let stateObject = $derived({
|
|
385
387
|
* Handle touch move
|
386
388
|
* @param {TouchEvent} event
|
387
389
|
*/
|
388
|
-
function handleTouchMove(event) {
|
389
|
-
|
390
|
+
function handleTouchMove(event) {
|
391
|
+
if (!touchDragging) return;
|
390
392
|
|
391
|
-
|
392
|
-
|
393
|
+
event.preventDefault();
|
394
|
+
const touch = event.touches[0];
|
393
395
|
|
394
|
-
|
395
|
-
|
396
|
-
|
397
|
-
|
398
|
-
|
396
|
+
// Update preview position
|
397
|
+
if (showPreview) {
|
398
|
+
previewX = touch.clientX - dragOffsetX;
|
399
|
+
previewY = touch.clientY - dragOffsetY;
|
400
|
+
}
|
399
401
|
|
400
|
-
|
401
|
-
|
402
|
-
|
403
|
-
|
404
|
-
|
405
|
-
|
406
|
-
|
407
|
-
|
408
|
-
|
409
|
-
|
410
|
-
|
411
|
-
|
412
|
-
|
413
|
-
|
414
|
-
|
415
|
-
|
416
|
-
|
417
|
-
|
418
|
-
|
419
|
-
|
402
|
+
/** @type {SimulatedDragEvent} */
|
403
|
+
const simulatedEvent = {
|
404
|
+
type: 'dragover',
|
405
|
+
clientX: touch.clientX,
|
406
|
+
clientY: touch.clientY,
|
407
|
+
dataTransfer: {
|
408
|
+
types: [`application/x-draggable-${draggableId}`, 'text/plain'],
|
409
|
+
getData: () => 1,
|
410
|
+
dropEffect: 'move',
|
411
|
+
effectAllowed: 'move',
|
412
|
+
files: []
|
413
|
+
},
|
414
|
+
|
415
|
+
preventDefault: () => {},
|
416
|
+
stopPropagation: () => {}
|
417
|
+
};
|
418
|
+
|
419
|
+
// Update active dropzone in drag state
|
420
|
+
dragState.updateActiveDropZone(
|
421
|
+
touch.clientX,
|
422
|
+
touch.clientY,
|
423
|
+
simulatedEvent
|
424
|
+
);
|
425
|
+
}
|
420
426
|
|
421
427
|
/**
|
422
428
|
* Handle touch end
|
423
429
|
* @param {TouchEvent} event
|
424
430
|
*/
|
425
431
|
function handleTouchEnd(event) {
|
426
|
-
|
427
|
-
|
428
|
-
|
429
|
-
|
430
|
-
|
431
|
-
|
432
|
-
|
433
|
-
|
434
|
-
|
435
|
-
|
436
|
-
|
437
|
-
|
438
|
-
|
439
|
-
|
440
|
-
|
441
|
-
|
442
|
-
|
443
|
-
|
444
|
-
|
445
|
-
|
446
|
-
|
447
|
-
|
448
|
-
|
449
|
-
|
450
|
-
|
451
|
-
|
452
|
-
|
453
|
-
|
454
|
-
|
455
|
-
|
456
|
-
|
457
|
-
|
458
|
-
|
459
|
-
|
460
|
-
}
|
432
|
+
clearTimeout(dragTimeout);
|
433
|
+
|
434
|
+
if (!touchDragging) return;
|
435
|
+
|
436
|
+
const touch = event.changedTouches[0];
|
437
|
+
|
438
|
+
/** @type {SimulatedDragEvent} */
|
439
|
+
const simulatedEvent = {
|
440
|
+
type: 'drop',
|
441
|
+
clientX: touch.clientX,
|
442
|
+
clientY: touch.clientY,
|
443
|
+
dataTransfer: {
|
444
|
+
types: [`application/x-draggable-${draggableId}`, 'text/plain'],
|
445
|
+
getData: () => 1,
|
446
|
+
dropEffect: 'move',
|
447
|
+
effectAllowed: 'move',
|
448
|
+
files: []
|
449
|
+
},
|
450
|
+
preventDefault: () => {}, // Add this!
|
451
|
+
stopPropagation: () => {} // And this!
|
452
|
+
};
|
453
|
+
|
454
|
+
// Trigger drop at final touch position
|
455
|
+
dragState.handleDropAtPoint(touch.clientX, touch.clientY, simulatedEvent);
|
456
|
+
|
457
|
+
// Clean up
|
458
|
+
touchDragging = false;
|
459
|
+
currentState = IDLE;
|
460
|
+
showPreview = false;
|
461
|
+
dragState.end(draggableId);
|
462
|
+
|
463
|
+
// Remove document handlers
|
464
|
+
document.removeEventListener('touchmove', handleTouchMove);
|
465
|
+
document.removeEventListener('touchend', handleTouchEnd);
|
466
|
+
}
|
461
467
|
</script>
|
462
468
|
|
463
469
|
<div
|
@@ -474,7 +480,11 @@ function handleTouchMove(event) {
|
|
474
480
|
style="touch-action: none;"
|
475
481
|
{...attrs}
|
476
482
|
>
|
477
|
-
{@render children({
|
483
|
+
{@render children({
|
484
|
+
element: draggableElement,
|
485
|
+
rect: elementRect,
|
486
|
+
isDragging: false
|
487
|
+
})}
|
478
488
|
</div>
|
479
489
|
|
480
490
|
{#if showPreview && elementRect}
|
@@ -485,11 +495,18 @@ function handleTouchMove(event) {
|
|
485
495
|
style:left="{previewX}px"
|
486
496
|
style:top="{previewY}px"
|
487
497
|
>
|
488
|
-
|
489
|
-
|
490
|
-
|
491
|
-
|
492
|
-
|
498
|
+
{#if draggingSnippet}
|
499
|
+
{@render draggingSnippet({
|
500
|
+
element: draggableElement,
|
501
|
+
rect: elementRect
|
502
|
+
})}
|
503
|
+
{:else}
|
504
|
+
{@render children({
|
505
|
+
element: draggableElement,
|
506
|
+
rect: elementRect,
|
507
|
+
isDragging: true
|
508
|
+
})}
|
509
|
+
{/if}
|
493
510
|
</div>
|
494
511
|
{/if}
|
495
512
|
|
@@ -13,6 +13,7 @@ type Draggable = {
|
|
13
13
|
children: Snippet<[{
|
14
14
|
element: HTMLElement;
|
15
15
|
rect: DOMRect;
|
16
|
+
isDragging: boolean;
|
16
17
|
}]>;
|
17
18
|
draggingSnippet?: Snippet<[{
|
18
19
|
element: HTMLElement;
|
@@ -58,6 +59,7 @@ declare const Draggable: import("svelte").Component<{
|
|
58
59
|
children: import("svelte").Snippet<[{
|
59
60
|
element: HTMLElement;
|
60
61
|
rect: DOMRect;
|
62
|
+
isDragging: boolean;
|
61
63
|
}]>;
|
62
64
|
draggingSnippet?: import("svelte").Snippet<[{
|
63
65
|
element: HTMLElement;
|
package/package.json
CHANGED
@@ -1,319 +0,0 @@
|
|
1
|
-
// drag-state.svelte.js
|
2
|
-
import { defineStateContext } from '$lib/util/svelte/state-context/index.js';
|
3
|
-
|
4
|
-
/** @typedef {import('$lib/typedef').SimulatedDragEvent} SimulatedDragEvent */
|
5
|
-
|
6
|
-
class DragState {
|
7
|
-
// Existing draggables map
|
8
|
-
draggables = $state(new Map());
|
9
|
-
|
10
|
-
// New: Registry for dropzones
|
11
|
-
dropZones = $state(new Map());
|
12
|
-
|
13
|
-
// Track which dropzone is currently active
|
14
|
-
activeDropZone = $state(null);
|
15
|
-
|
16
|
-
// Track the last active drop zone
|
17
|
-
// - activeDropZone gets cleared by dragLeavr
|
18
|
-
// - but we need it in 'end'
|
19
|
-
lastActiveDropZone = null;
|
20
|
-
|
21
|
-
/**
|
22
|
-
* Register a dropzone
|
23
|
-
* @param {string} zoneId
|
24
|
-
* @param {Object} config
|
25
|
-
* @param {string} config.zone
|
26
|
-
* @param {string} config.group
|
27
|
-
* @param {Function} config.accepts
|
28
|
-
* @param {Function} config.onDragEnter
|
29
|
-
* @param {Function} config.onDragOver
|
30
|
-
* @param {Function} config.onDragLeave
|
31
|
-
* @param {(DropData) => void} config.onDrop
|
32
|
-
* @param {HTMLElement} config.element
|
33
|
-
*/
|
34
|
-
registerDropZone(zoneId, config) {
|
35
|
-
if (this.dropZones.has(zoneId)) {
|
36
|
-
throw new Error(`Zone [${zoneId}] is already registered`);
|
37
|
-
}
|
38
|
-
|
39
|
-
this.dropZones.set(zoneId, {
|
40
|
-
...config,
|
41
|
-
isOver: false,
|
42
|
-
canDrop: false
|
43
|
-
});
|
44
|
-
}
|
45
|
-
|
46
|
-
/**
|
47
|
-
* Unregister a dropzone
|
48
|
-
* @param {string} zoneId
|
49
|
-
*/
|
50
|
-
unregisterDropZone(zoneId) {
|
51
|
-
if (this.activeDropZone === zoneId) {
|
52
|
-
this.activeDropZone = null;
|
53
|
-
}
|
54
|
-
this.dropZones.delete(zoneId);
|
55
|
-
}
|
56
|
-
|
57
|
-
/**
|
58
|
-
* Get dropzone at coordinates
|
59
|
-
* @param {number} x
|
60
|
-
* @param {number} y
|
61
|
-
* @returns {Object|null}
|
62
|
-
*/
|
63
|
-
getDropZoneAtPoint(x, y) {
|
64
|
-
// Check all registered dropzones
|
65
|
-
for (const [zoneId, config] of this.dropZones) {
|
66
|
-
const rect = config.element.getBoundingClientRect();
|
67
|
-
|
68
|
-
if (
|
69
|
-
x >= rect.left &&
|
70
|
-
x <= rect.right &&
|
71
|
-
y >= rect.top &&
|
72
|
-
y <= rect.bottom
|
73
|
-
) {
|
74
|
-
// Found a dropzone at this point
|
75
|
-
// Check if it's the deepest one (for nested zones)
|
76
|
-
let deepestZone = { zoneId, config, depth: 0 };
|
77
|
-
|
78
|
-
// Check for nested dropzones
|
79
|
-
for (const [otherId, otherConfig] of this.dropZones) {
|
80
|
-
if (otherId === zoneId) continue;
|
81
|
-
|
82
|
-
const otherRect = otherConfig.element.getBoundingClientRect();
|
83
|
-
if (
|
84
|
-
x >= otherRect.left &&
|
85
|
-
x <= otherRect.right &&
|
86
|
-
y >= otherRect.top &&
|
87
|
-
y <= otherRect.bottom
|
88
|
-
) {
|
89
|
-
// Check if this zone is nested inside our current zone
|
90
|
-
if (config.element.contains(otherConfig.element)) {
|
91
|
-
deepestZone = {
|
92
|
-
zoneId: otherId,
|
93
|
-
config: otherConfig,
|
94
|
-
depth: deepestZone.depth + 1
|
95
|
-
};
|
96
|
-
}
|
97
|
-
}
|
98
|
-
}
|
99
|
-
|
100
|
-
return { zoneId: deepestZone.zoneId, config: deepestZone.config };
|
101
|
-
}
|
102
|
-
}
|
103
|
-
|
104
|
-
return null;
|
105
|
-
}
|
106
|
-
|
107
|
-
/**
|
108
|
-
* Update active dropzone based on coordinates
|
109
|
-
*
|
110
|
-
* @param {number} x
|
111
|
-
* @param {number} y
|
112
|
-
* @param {DragEvent|SimulatedDragEvent} event
|
113
|
-
*/
|
114
|
-
updateActiveDropZone(x, y, event) {
|
115
|
-
const dropZone = this.getDropZoneAtPoint(x, y);
|
116
|
-
const newActiveId = dropZone?.zoneId || null;
|
117
|
-
|
118
|
-
// Handle leave/enter transitions
|
119
|
-
if (this.activeDropZone !== newActiveId) {
|
120
|
-
// Leave previous zone
|
121
|
-
if (this.activeDropZone) {
|
122
|
-
this.lastActiveDropZone = this.activeDropZone;
|
123
|
-
|
124
|
-
const prevConfig = this.dropZones.get(this.activeDropZone);
|
125
|
-
if (prevConfig) {
|
126
|
-
prevConfig.isOver = false;
|
127
|
-
prevConfig.canDrop = false;
|
128
|
-
prevConfig.onDragLeave?.({ event, zone: prevConfig.zone });
|
129
|
-
}
|
130
|
-
}
|
131
|
-
|
132
|
-
// Enter new zone
|
133
|
-
if (newActiveId && dropZone) {
|
134
|
-
const dragData = this.getDraggable(event);
|
135
|
-
const canDrop = dragData && dropZone.config.accepts(dragData);
|
136
|
-
|
137
|
-
dropZone.config.isOver = true;
|
138
|
-
dropZone.config.canDrop = canDrop;
|
139
|
-
dropZone.config.onDragEnter?.({
|
140
|
-
event,
|
141
|
-
zone: dropZone.config.zone,
|
142
|
-
canDrop
|
143
|
-
});
|
144
|
-
}
|
145
|
-
|
146
|
-
this.activeDropZone = newActiveId;
|
147
|
-
} else if (newActiveId) {
|
148
|
-
// Still in the same zone, just send dragOver
|
149
|
-
dropZone.config.onDragOver?.({ event, zone: dropZone.config.zone });
|
150
|
-
}
|
151
|
-
}
|
152
|
-
|
153
|
-
/**
|
154
|
-
* Handle drop at coordinates
|
155
|
-
* @param {number} x
|
156
|
-
* @param {number} y
|
157
|
-
* @param {DragEvent|SimulatedDragEvent} event
|
158
|
-
*/
|
159
|
-
handleDropAtPoint(x, y, event) {
|
160
|
-
const dropZone = this.getDropZoneAtPoint(x, y);
|
161
|
-
|
162
|
-
if (dropZone && dropZone.config.canDrop) {
|
163
|
-
const dragData = this.getDraggable(event);
|
164
|
-
|
165
|
-
if (dragData && dropZone.config.element) {
|
166
|
-
// Calculate drop position relative to dropzone
|
167
|
-
const rect = dropZone.config.element.getBoundingClientRect();
|
168
|
-
|
169
|
-
const style = window.getComputedStyle(dropZone.config.element);
|
170
|
-
|
171
|
-
const borderLeftWidth = parseInt(style.borderLeftWidth, 10) || 0;
|
172
|
-
const borderTopWidth = parseInt(style.borderTopWidth, 10) || 0;
|
173
|
-
|
174
|
-
const dropOffsetX = x - rect.left - borderLeftWidth;
|
175
|
-
const dropOffsetY = y - rect.top - borderTopWidth;
|
176
|
-
|
177
|
-
const dropX = dropOffsetX - (dragData.offsetX ?? 0);
|
178
|
-
const dropY = dropOffsetY - (dragData.offsetY ?? 0);
|
179
|
-
|
180
|
-
// Call the dropzone's drop handler
|
181
|
-
dropZone.config.onDrop?.({
|
182
|
-
zone: dropZone.config.zone,
|
183
|
-
source: dragData.source,
|
184
|
-
item: dragData.item,
|
185
|
-
x: dropX,
|
186
|
-
y: dropY,
|
187
|
-
drag: dragData,
|
188
|
-
drop: {
|
189
|
-
offsetX: dropOffsetX,
|
190
|
-
offsetY: dropOffsetY,
|
191
|
-
target: dropZone.config.element
|
192
|
-
}
|
193
|
-
});
|
194
|
-
}
|
195
|
-
}
|
196
|
-
|
197
|
-
// Ensure we notify the active dropzone that drag ended
|
198
|
-
if (this.activeDropZone) {
|
199
|
-
const config = this.dropZones.get(this.activeDropZone);
|
200
|
-
if (config) {
|
201
|
-
config.isOver = false;
|
202
|
-
config.canDrop = false;
|
203
|
-
config.onDragLeave?.({ event, zone: config.zone });
|
204
|
-
}
|
205
|
-
}
|
206
|
-
|
207
|
-
// Reset active dropzone
|
208
|
-
this.activeDropZone = null;
|
209
|
-
}
|
210
|
-
|
211
|
-
/**
|
212
|
-
* @param {string} draggableId
|
213
|
-
* @param {import('$lib/typedef/drag.js').DragData} dragData
|
214
|
-
*/
|
215
|
-
start(draggableId, dragData) {
|
216
|
-
this.draggables.set(draggableId, dragData);
|
217
|
-
}
|
218
|
-
|
219
|
-
/**
|
220
|
-
* @param {string} draggableId
|
221
|
-
*/
|
222
|
-
end(draggableId) {
|
223
|
-
this.draggables.delete(draggableId);
|
224
|
-
|
225
|
-
// Check both current AND last active dropzone
|
226
|
-
const zoneToNotify = this.activeDropZone || this.lastActiveDropZone;
|
227
|
-
|
228
|
-
if (zoneToNotify) {
|
229
|
-
const config = this.dropZones.get(zoneToNotify);
|
230
|
-
if (config && (config.isOver || config.canDrop)) {
|
231
|
-
config.isOver = false;
|
232
|
-
config.canDrop = false;
|
233
|
-
config.onDragLeave?.({
|
234
|
-
event: new DragEvent('dragend'),
|
235
|
-
zone: config.zone
|
236
|
-
});
|
237
|
-
}
|
238
|
-
}
|
239
|
-
|
240
|
-
this.activeDropZone = null;
|
241
|
-
this.lastActiveDropZone = null;
|
242
|
-
}
|
243
|
-
|
244
|
-
/**
|
245
|
-
* Get a drag data by draggable id
|
246
|
-
*
|
247
|
-
* @param {string} draggableId
|
248
|
-
* @returns {import('$lib/typedef/drag.js').DragData|undefined}
|
249
|
-
*/
|
250
|
-
getDraggableById(draggableId) {
|
251
|
-
return this.draggables.get(draggableId);
|
252
|
-
}
|
253
|
-
|
254
|
-
/**
|
255
|
-
* Get a drag data. Extracts draggable id from the supplied DragEvent
|
256
|
-
*
|
257
|
-
* @param {DragEvent|SimulatedDragEvent} event
|
258
|
-
*
|
259
|
-
* @returns {Object|null} The drag data, or null for file drops
|
260
|
-
*/
|
261
|
-
getDraggable(event) {
|
262
|
-
// Check if this is a file drop first
|
263
|
-
if (event.dataTransfer && event.dataTransfer.types) {
|
264
|
-
// Check if types is an array or DOMStringList
|
265
|
-
const types = Array.from(event.dataTransfer.types);
|
266
|
-
if (types.includes('Files')) {
|
267
|
-
return null; // This is a file drop, not an internal drag
|
268
|
-
}
|
269
|
-
}
|
270
|
-
|
271
|
-
// For dragover events, we can't read dataTransfer.getData in Chrome
|
272
|
-
// Instead, check if we have an active drag operation
|
273
|
-
if (event.type === 'dragover'|| event.type === 'dragenter') {
|
274
|
-
if (this.draggables.size > 0) {
|
275
|
-
// Return the most recent drag operation
|
276
|
-
return this.current;
|
277
|
-
}
|
278
|
-
}
|
279
|
-
|
280
|
-
// For drop events, we can read the data
|
281
|
-
if (event.type === 'drop' && event.dataTransfer) {
|
282
|
-
try {
|
283
|
-
const jsonData = event.dataTransfer.getData('application/json');
|
284
|
-
if (jsonData) {
|
285
|
-
const transferData = JSON.parse(jsonData);
|
286
|
-
const draggableId = transferData.draggableId;
|
287
|
-
|
288
|
-
if (draggableId) {
|
289
|
-
return this.getDraggableById(draggableId);
|
290
|
-
}
|
291
|
-
}
|
292
|
-
} catch (error) {
|
293
|
-
console.error('Error getting drag data from drop:', error);
|
294
|
-
}
|
295
|
-
}
|
296
|
-
|
297
|
-
// Fallback to checking active drags
|
298
|
-
return this.current;
|
299
|
-
}
|
300
|
-
|
301
|
-
/**
|
302
|
-
* Get the most recently started drag operation (convenience method)
|
303
|
-
* @returns {import('$lib/typedef/drag.js').DragData|undefined}
|
304
|
-
*/
|
305
|
-
get current() {
|
306
|
-
const entries = Array.from(this.draggables.entries());
|
307
|
-
return entries.length > 0 ? entries[entries.length - 1][1] : undefined;
|
308
|
-
}
|
309
|
-
|
310
|
-
/**
|
311
|
-
* @returns {boolean}
|
312
|
-
*/
|
313
|
-
isDragging() {
|
314
|
-
return this.draggables.size > 0;
|
315
|
-
}
|
316
|
-
}
|
317
|
-
|
318
|
-
export const [createOrGetDragState, createDragState, getDragState] =
|
319
|
-
defineStateContext(DragState);
|