vgapp 1.1.6 → 1.1.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.
Files changed (54) hide show
  1. package/CHANGELOG.md +10 -1
  2. package/README.md +48 -48
  3. package/app/langs/en/buttons.json +17 -17
  4. package/app/langs/en/messages.json +36 -36
  5. package/app/langs/ru/buttons.json +17 -17
  6. package/app/langs/ru/messages.json +36 -36
  7. package/app/modules/vgfilepreview/js/i18n.js +56 -56
  8. package/app/modules/vgfilepreview/js/renderers/image-modal.js +145 -145
  9. package/app/modules/vgfilepreview/js/renderers/image.js +92 -92
  10. package/app/modules/vgfilepreview/js/renderers/index.js +19 -19
  11. package/app/modules/vgfilepreview/js/renderers/office-modal.js +168 -168
  12. package/app/modules/vgfilepreview/js/renderers/office.js +79 -79
  13. package/app/modules/vgfilepreview/js/renderers/pdf-modal.js +260 -260
  14. package/app/modules/vgfilepreview/js/renderers/pdf.js +76 -76
  15. package/app/modules/vgfilepreview/js/renderers/playlist.js +71 -71
  16. package/app/modules/vgfilepreview/js/renderers/text-modal.js +343 -343
  17. package/app/modules/vgfilepreview/js/renderers/text.js +83 -83
  18. package/app/modules/vgfilepreview/js/renderers/video-modal.js +272 -272
  19. package/app/modules/vgfilepreview/js/renderers/video.js +80 -80
  20. package/app/modules/vgfilepreview/js/renderers/zip-modal.js +522 -522
  21. package/app/modules/vgfilepreview/js/renderers/zip.js +89 -89
  22. package/app/modules/vgfilepreview/js/vgfilepreview.js +7 -7
  23. package/app/modules/vgfilepreview/readme.md +68 -68
  24. package/app/modules/vgfilepreview/scss/_variables.scss +113 -113
  25. package/app/modules/vgfilepreview/scss/vgfilepreview.scss +464 -464
  26. package/app/modules/vgfiles/js/base.js +26 -26
  27. package/app/modules/vgfiles/js/droppable.js +260 -260
  28. package/app/modules/vgfiles/js/render.js +153 -153
  29. package/app/modules/vgfiles/js/vgfiles.js +41 -41
  30. package/app/modules/vgfiles/readme.md +123 -123
  31. package/app/modules/vgfiles/scss/_variables.scss +18 -18
  32. package/app/modules/vgfiles/scss/vgfiles.scss +148 -148
  33. package/app/modules/vgformsender/js/vgformsender.js +1 -1
  34. package/app/modules/vgmodal/js/vgmodal.drag.js +332 -332
  35. package/app/modules/vgmodal/js/vgmodal.js +33 -33
  36. package/app/modules/vgmodal/js/vgmodal.resize.js +435 -435
  37. package/app/modules/vgnav/js/vgnav.js +135 -135
  38. package/app/modules/vgnav/readme.md +67 -67
  39. package/app/modules/vgnestable/README.md +307 -307
  40. package/app/modules/vgnestable/scss/_variables.scss +60 -60
  41. package/app/modules/vgnestable/scss/vgnestable.scss +163 -163
  42. package/app/modules/vgselect/js/vgselect.js +39 -39
  43. package/app/modules/vgselect/scss/vgselect.scss +22 -22
  44. package/app/modules/vgspy/readme.md +28 -28
  45. package/app/utils/js/components/audio-metadata.js +240 -240
  46. package/app/utils/js/components/file-icon.js +109 -109
  47. package/app/utils/js/components/file-preview.js +304 -304
  48. package/app/utils/js/components/sanitize.js +150 -150
  49. package/app/utils/js/components/video-metadata.js +140 -140
  50. package/build/vgapp.css +1 -1
  51. package/build/vgapp.css.map +1 -1
  52. package/build/vgapp.js.map +1 -1
  53. package/index.scss +9 -9
  54. package/package.json +1 -1
@@ -1,332 +1,332 @@
1
- const DEFAULT_OPTIONS = {
2
- enable: false,
3
- selector: '.vg-modal-content',
4
- threshold: 4,
5
- resizeEdgeSize: 8,
6
- debug: false,
7
- };
8
-
9
- class VGModalDrag {
10
- constructor(modalElement, dialogElement, options = {}) {
11
- this._modalElement = modalElement;
12
- this._dialogElement = dialogElement;
13
- this._options = this._normalizeOptions(options);
14
- this._pointerId = null;
15
- this._dragTarget = null;
16
- this._isDragging = false;
17
- this._startX = 0;
18
- this._startY = 0;
19
- this._currentX = 0;
20
- this._currentY = 0;
21
- this._dialogStartLeft = 0;
22
- this._dialogStartTop = 0;
23
- this._dialogWidth = 0;
24
- this._dialogHeight = 0;
25
- this._isEnabled = false;
26
- this._previousUserSelect = '';
27
- this._previousTransition = '';
28
- this._previousWillChange = '';
29
- this._initialRect = null;
30
- this._lockedIframes = [];
31
- this._debugElement = null;
32
-
33
- this._onPointerMove = this._onPointerMove.bind(this);
34
- this._onPointerUp = this._onPointerUp.bind(this);
35
- this._onPointerDown = this._onPointerDown.bind(this);
36
- this._onNativeDragStart = this._onNativeDragStart.bind(this);
37
- }
38
-
39
- setOptions(options = {}) {
40
- this._options = this._normalizeOptions(options, this._options);
41
- this._updateDebugOverlay();
42
- }
43
-
44
- enable() {
45
- if (!this._dialogElement || this._isEnabled) return;
46
-
47
- this._updateDebugOverlay();
48
- this._dialogElement.addEventListener('pointerdown', this._onPointerDown);
49
- this._isEnabled = true;
50
- }
51
-
52
- disable() {
53
- if (!this._dialogElement || !this._isEnabled) return;
54
-
55
- this._dialogElement.removeEventListener('pointerdown', this._onPointerDown);
56
- document.removeEventListener('pointermove', this._onPointerMove);
57
- document.removeEventListener('pointerup', this._onPointerUp);
58
- document.removeEventListener('pointercancel', this._onPointerUp);
59
- document.removeEventListener('dragstart', this._onNativeDragStart, true);
60
- this._dialogElement.style.touchAction = '';
61
- document.body.style.userSelect = this._previousUserSelect;
62
- this._pointerId = null;
63
- this._dragTarget = null;
64
- this._isDragging = false;
65
- this._initialRect = null;
66
- this._unlockEmbeddedFrames();
67
- this._restoreDragStyles();
68
- delete this._modalElement.dataset.vgModalDragging;
69
- this._setDebugVisibility(false);
70
- this._isEnabled = false;
71
- }
72
-
73
- syncPosition() {
74
- if (!this._isEnabled) return;
75
- if (!this._isPreparedForInteraction()) return;
76
-
77
- const rect = this._dialogElement.getBoundingClientRect();
78
- const width = this._dialogElement.offsetWidth || rect.width;
79
- const height = this._dialogElement.offsetHeight || rect.height;
80
- const currentLeft = Number.parseFloat(this._dialogElement.style.left);
81
- const currentTop = Number.parseFloat(this._dialogElement.style.top);
82
- const left = Number.isFinite(currentLeft) ? currentLeft : rect.left;
83
- const top = Number.isFinite(currentTop) ? currentTop : rect.top;
84
- const maxLeft = Math.max(0, window.innerWidth - width);
85
- const maxTop = Math.max(0, window.innerHeight - height);
86
- const nextLeft = Math.min(maxLeft, Math.max(0, left));
87
- const nextTop = Math.min(maxTop, Math.max(0, top));
88
-
89
- this._dialogElement.style.left = `${nextLeft}px`;
90
- this._dialogElement.style.top = `${nextTop}px`;
91
- this._updateDebugValues('synced');
92
- }
93
-
94
- _onPointerDown(event) {
95
- if (event.button !== 0) return;
96
-
97
- const dragArea = this._resolveDragArea(event.target);
98
- if (!dragArea || !this._dialogElement.contains(dragArea)) return;
99
- if (this._isPointerOnResizeEdge(event)) return;
100
- if (event.target.closest('input, textarea, select, button, a, [contenteditable="true"]')) return;
101
- if (dragArea && dragArea.closest('[data-vg-dismiss="modal"]')) return;
102
-
103
- this._pointerId = event.pointerId;
104
- this._dragTarget = event.target;
105
- this._isDragging = false;
106
- event.preventDefault();
107
- this._previousUserSelect = document.body.style.userSelect;
108
- document.body.style.userSelect = 'none';
109
- this._initialRect = this._dialogElement.getBoundingClientRect();
110
- this._dialogStartLeft = this._initialRect.left;
111
- this._dialogStartTop = this._initialRect.top;
112
- this._dialogWidth = this._initialRect.width;
113
- this._dialogHeight = this._initialRect.height;
114
- this._startX = event.clientX;
115
- this._startY = event.clientY;
116
- this._currentX = event.clientX;
117
- this._currentY = event.clientY;
118
- this._lockEmbeddedFrames();
119
- this._modalElement.dataset.vgModalDragging = 'true';
120
- this._setDebugVisibility(true);
121
- this._updateDebugValues('armed');
122
-
123
- document.addEventListener('dragstart', this._onNativeDragStart, true);
124
-
125
- if (this._dialogElement && this._dialogElement.setPointerCapture) {
126
- this._dialogElement.setPointerCapture(event.pointerId);
127
- }
128
-
129
- document.addEventListener('pointermove', this._onPointerMove);
130
- document.addEventListener('pointerup', this._onPointerUp);
131
- document.addEventListener('pointercancel', this._onPointerUp);
132
- }
133
-
134
- _onPointerMove(event) {
135
- if (event.pointerId !== this._pointerId) return;
136
-
137
- this._currentX = event.clientX;
138
- this._currentY = event.clientY;
139
- if (!this._isDragging) {
140
- const deltaX = this._currentX - this._startX;
141
- const deltaY = this._currentY - this._startY;
142
- const distance = Math.hypot(deltaX, deltaY);
143
- if (distance < this._options.threshold) return;
144
-
145
- this._isDragging = true;
146
- this._dialogElement.style.touchAction = 'none';
147
- this._applyDragStyles();
148
- this._preparePosition(this._initialRect);
149
- event.preventDefault();
150
- this._updateDebugValues('dragging');
151
- }
152
- this._applyDragPosition();
153
- }
154
-
155
- _onPointerUp(event) {
156
- if (event.pointerId !== this._pointerId) return;
157
-
158
- document.removeEventListener('pointermove', this._onPointerMove);
159
- document.removeEventListener('pointerup', this._onPointerUp);
160
- document.removeEventListener('pointercancel', this._onPointerUp);
161
- document.removeEventListener('dragstart', this._onNativeDragStart, true);
162
- if (this._isDragging) {
163
- this._applyDragPosition();
164
- }
165
- this._dialogElement.style.touchAction = '';
166
- document.body.style.userSelect = this._previousUserSelect;
167
-
168
- if (this._dialogElement && this._dialogElement.releasePointerCapture) {
169
- this._dialogElement.releasePointerCapture(event.pointerId);
170
- }
171
-
172
- this._pointerId = null;
173
- this._dragTarget = null;
174
- this._isDragging = false;
175
- this._initialRect = null;
176
- this._unlockEmbeddedFrames();
177
- this._restoreDragStyles();
178
- delete this._modalElement.dataset.vgModalDragging;
179
- this._setDebugVisibility(this._options.debug);
180
- this._updateDebugValues('idle');
181
- }
182
-
183
- _preparePosition(rect = null) {
184
- if (!this._dialogElement) return;
185
-
186
- const currentRect = rect || this._dialogElement.getBoundingClientRect();
187
- this._dialogElement.style.position = 'fixed';
188
- this._dialogElement.style.margin = '0';
189
- this._dialogElement.style.left = `${currentRect.left}px`;
190
- this._dialogElement.style.top = `${currentRect.top}px`;
191
- this._dialogElement.style.width = `${currentRect.width}px`;
192
- this._dialogElement.style.height = `${currentRect.height}px`;
193
- this._dialogElement.style.transform = 'none';
194
- }
195
-
196
- _isPreparedForInteraction() {
197
- return this._dialogElement.style.position === 'fixed' && this._dialogElement.style.transform === 'none';
198
- }
199
-
200
- _isPointerOnResizeEdge(event) {
201
- const rect = this._dialogElement.getBoundingClientRect();
202
- const offsetX = event.clientX - rect.left;
203
- const offsetY = event.clientY - rect.top;
204
- const edgeSize = this._options.resizeEdgeSize;
205
-
206
- const nearTop = offsetY >= 0 && offsetY <= edgeSize;
207
- const nearBottom = offsetY <= rect.height && offsetY >= rect.height - edgeSize;
208
- const nearLeft = offsetX >= 0 && offsetX <= edgeSize;
209
- const nearRight = offsetX <= rect.width && offsetX >= rect.width - edgeSize;
210
-
211
- return nearTop || nearBottom || nearLeft || nearRight;
212
- }
213
-
214
- _applyDragPosition() {
215
- if (this._pointerId === null || !this._isDragging) return;
216
-
217
- const deltaX = this._currentX - this._startX;
218
- const deltaY = this._currentY - this._startY;
219
- const maxLeft = Math.max(0, window.innerWidth - this._dialogWidth);
220
- const maxTop = Math.max(0, window.innerHeight - this._dialogHeight);
221
- const nextLeft = Math.min(maxLeft, Math.max(0, this._dialogStartLeft + deltaX));
222
- const nextTop = Math.min(maxTop, Math.max(0, this._dialogStartTop + deltaY));
223
-
224
- this._dialogElement.style.left = `${nextLeft}px`;
225
- this._dialogElement.style.top = `${nextTop}px`;
226
- this._updateDebugValues('dragging');
227
- }
228
-
229
- _onNativeDragStart(event) {
230
- if (this._pointerId === null) return;
231
- event.preventDefault();
232
- }
233
-
234
- _applyDragStyles() {
235
- this._previousTransition = this._dialogElement.style.transition;
236
- this._previousWillChange = this._dialogElement.style.willChange;
237
- this._dialogElement.style.transition = 'none';
238
- this._dialogElement.style.willChange = 'left, top';
239
- }
240
-
241
- _restoreDragStyles() {
242
- this._dialogElement.style.transition = this._previousTransition;
243
- this._dialogElement.style.willChange = this._previousWillChange;
244
- }
245
-
246
- _lockEmbeddedFrames() {
247
- if (!this._dialogElement || this._lockedIframes.length) return;
248
-
249
- const iframes = this._dialogElement.querySelectorAll('iframe');
250
- for (const frame of iframes) {
251
- this._lockedIframes.push({
252
- element: frame,
253
- pointerEvents: frame.style.pointerEvents,
254
- });
255
- frame.style.pointerEvents = 'none';
256
- }
257
- }
258
-
259
- _unlockEmbeddedFrames() {
260
- if (!this._lockedIframes.length) return;
261
-
262
- for (const item of this._lockedIframes) {
263
- item.element.style.pointerEvents = item.pointerEvents;
264
- }
265
- this._lockedIframes = [];
266
- }
267
-
268
- _normalizeOptions(options, base = DEFAULT_OPTIONS) {
269
- const merged = {...base, ...options};
270
- const threshold = Number(merged.threshold);
271
- const resizeEdgeSize = Number(merged.resizeEdgeSize);
272
- const selector = typeof merged.selector === 'string' && merged.selector.trim()
273
- ? merged.selector
274
- : DEFAULT_OPTIONS.selector;
275
-
276
- return {
277
- ...merged,
278
- selector,
279
- threshold: Number.isFinite(threshold) && threshold >= 0 ? threshold : DEFAULT_OPTIONS.threshold,
280
- resizeEdgeSize: Number.isFinite(resizeEdgeSize) && resizeEdgeSize > 0 ? resizeEdgeSize : DEFAULT_OPTIONS.resizeEdgeSize,
281
- debug: Boolean(merged.debug),
282
- };
283
- }
284
-
285
- _resolveDragArea(target) {
286
- try {
287
- return target.closest(this._options.selector);
288
- } catch (error) {
289
- return target.closest(DEFAULT_OPTIONS.selector);
290
- }
291
- }
292
-
293
- _updateDebugOverlay() {
294
- if (!this._options.debug) {
295
- this._setDebugVisibility(false);
296
- return;
297
- }
298
-
299
- if (!this._debugElement) {
300
- this._debugElement = document.createElement('div');
301
- this._debugElement.style.position = 'absolute';
302
- this._debugElement.style.left = '170px';
303
- this._debugElement.style.bottom = '8px';
304
- this._debugElement.style.zIndex = '7';
305
- this._debugElement.style.padding = '4px 6px';
306
- this._debugElement.style.borderRadius = '4px';
307
- this._debugElement.style.background = 'rgba(0, 0, 0, 0.72)';
308
- this._debugElement.style.color = '#fff';
309
- this._debugElement.style.fontSize = '11px';
310
- this._debugElement.style.lineHeight = '1.3';
311
- this._debugElement.style.pointerEvents = 'none';
312
- this._dialogElement.append(this._debugElement);
313
- }
314
-
315
- this._setDebugVisibility(true);
316
- this._updateDebugValues(this._isDragging ? 'dragging' : 'idle');
317
- }
318
-
319
- _setDebugVisibility(visible) {
320
- if (!this._debugElement) return;
321
- this._debugElement.style.display = visible ? 'block' : 'none';
322
- }
323
-
324
- _updateDebugValues(state = 'idle') {
325
- if (!this._debugElement || !this._options.debug) return;
326
-
327
- const rect = this._dialogElement.getBoundingClientRect();
328
- this._debugElement.textContent = `drag:${state} x:${Math.round(rect.left)} y:${Math.round(rect.top)} w:${Math.round(rect.width)} h:${Math.round(rect.height)}`;
329
- }
330
- }
331
-
332
- export default VGModalDrag;
1
+ const DEFAULT_OPTIONS = {
2
+ enable: false,
3
+ selector: '.vg-modal-content',
4
+ threshold: 4,
5
+ resizeEdgeSize: 8,
6
+ debug: false,
7
+ };
8
+
9
+ class VGModalDrag {
10
+ constructor(modalElement, dialogElement, options = {}) {
11
+ this._modalElement = modalElement;
12
+ this._dialogElement = dialogElement;
13
+ this._options = this._normalizeOptions(options);
14
+ this._pointerId = null;
15
+ this._dragTarget = null;
16
+ this._isDragging = false;
17
+ this._startX = 0;
18
+ this._startY = 0;
19
+ this._currentX = 0;
20
+ this._currentY = 0;
21
+ this._dialogStartLeft = 0;
22
+ this._dialogStartTop = 0;
23
+ this._dialogWidth = 0;
24
+ this._dialogHeight = 0;
25
+ this._isEnabled = false;
26
+ this._previousUserSelect = '';
27
+ this._previousTransition = '';
28
+ this._previousWillChange = '';
29
+ this._initialRect = null;
30
+ this._lockedIframes = [];
31
+ this._debugElement = null;
32
+
33
+ this._onPointerMove = this._onPointerMove.bind(this);
34
+ this._onPointerUp = this._onPointerUp.bind(this);
35
+ this._onPointerDown = this._onPointerDown.bind(this);
36
+ this._onNativeDragStart = this._onNativeDragStart.bind(this);
37
+ }
38
+
39
+ setOptions(options = {}) {
40
+ this._options = this._normalizeOptions(options, this._options);
41
+ this._updateDebugOverlay();
42
+ }
43
+
44
+ enable() {
45
+ if (!this._dialogElement || this._isEnabled) return;
46
+
47
+ this._updateDebugOverlay();
48
+ this._dialogElement.addEventListener('pointerdown', this._onPointerDown);
49
+ this._isEnabled = true;
50
+ }
51
+
52
+ disable() {
53
+ if (!this._dialogElement || !this._isEnabled) return;
54
+
55
+ this._dialogElement.removeEventListener('pointerdown', this._onPointerDown);
56
+ document.removeEventListener('pointermove', this._onPointerMove);
57
+ document.removeEventListener('pointerup', this._onPointerUp);
58
+ document.removeEventListener('pointercancel', this._onPointerUp);
59
+ document.removeEventListener('dragstart', this._onNativeDragStart, true);
60
+ this._dialogElement.style.touchAction = '';
61
+ document.body.style.userSelect = this._previousUserSelect;
62
+ this._pointerId = null;
63
+ this._dragTarget = null;
64
+ this._isDragging = false;
65
+ this._initialRect = null;
66
+ this._unlockEmbeddedFrames();
67
+ this._restoreDragStyles();
68
+ delete this._modalElement.dataset.vgModalDragging;
69
+ this._setDebugVisibility(false);
70
+ this._isEnabled = false;
71
+ }
72
+
73
+ syncPosition() {
74
+ if (!this._isEnabled) return;
75
+ if (!this._isPreparedForInteraction()) return;
76
+
77
+ const rect = this._dialogElement.getBoundingClientRect();
78
+ const width = this._dialogElement.offsetWidth || rect.width;
79
+ const height = this._dialogElement.offsetHeight || rect.height;
80
+ const currentLeft = Number.parseFloat(this._dialogElement.style.left);
81
+ const currentTop = Number.parseFloat(this._dialogElement.style.top);
82
+ const left = Number.isFinite(currentLeft) ? currentLeft : rect.left;
83
+ const top = Number.isFinite(currentTop) ? currentTop : rect.top;
84
+ const maxLeft = Math.max(0, window.innerWidth - width);
85
+ const maxTop = Math.max(0, window.innerHeight - height);
86
+ const nextLeft = Math.min(maxLeft, Math.max(0, left));
87
+ const nextTop = Math.min(maxTop, Math.max(0, top));
88
+
89
+ this._dialogElement.style.left = `${nextLeft}px`;
90
+ this._dialogElement.style.top = `${nextTop}px`;
91
+ this._updateDebugValues('synced');
92
+ }
93
+
94
+ _onPointerDown(event) {
95
+ if (event.button !== 0) return;
96
+
97
+ const dragArea = this._resolveDragArea(event.target);
98
+ if (!dragArea || !this._dialogElement.contains(dragArea)) return;
99
+ if (this._isPointerOnResizeEdge(event)) return;
100
+ if (event.target.closest('input, textarea, select, button, a, [contenteditable="true"]')) return;
101
+ if (dragArea && dragArea.closest('[data-vg-dismiss="modal"]')) return;
102
+
103
+ this._pointerId = event.pointerId;
104
+ this._dragTarget = event.target;
105
+ this._isDragging = false;
106
+ event.preventDefault();
107
+ this._previousUserSelect = document.body.style.userSelect;
108
+ document.body.style.userSelect = 'none';
109
+ this._initialRect = this._dialogElement.getBoundingClientRect();
110
+ this._dialogStartLeft = this._initialRect.left;
111
+ this._dialogStartTop = this._initialRect.top;
112
+ this._dialogWidth = this._initialRect.width;
113
+ this._dialogHeight = this._initialRect.height;
114
+ this._startX = event.clientX;
115
+ this._startY = event.clientY;
116
+ this._currentX = event.clientX;
117
+ this._currentY = event.clientY;
118
+ this._lockEmbeddedFrames();
119
+ this._modalElement.dataset.vgModalDragging = 'true';
120
+ this._setDebugVisibility(true);
121
+ this._updateDebugValues('armed');
122
+
123
+ document.addEventListener('dragstart', this._onNativeDragStart, true);
124
+
125
+ if (this._dialogElement && this._dialogElement.setPointerCapture) {
126
+ this._dialogElement.setPointerCapture(event.pointerId);
127
+ }
128
+
129
+ document.addEventListener('pointermove', this._onPointerMove);
130
+ document.addEventListener('pointerup', this._onPointerUp);
131
+ document.addEventListener('pointercancel', this._onPointerUp);
132
+ }
133
+
134
+ _onPointerMove(event) {
135
+ if (event.pointerId !== this._pointerId) return;
136
+
137
+ this._currentX = event.clientX;
138
+ this._currentY = event.clientY;
139
+ if (!this._isDragging) {
140
+ const deltaX = this._currentX - this._startX;
141
+ const deltaY = this._currentY - this._startY;
142
+ const distance = Math.hypot(deltaX, deltaY);
143
+ if (distance < this._options.threshold) return;
144
+
145
+ this._isDragging = true;
146
+ this._dialogElement.style.touchAction = 'none';
147
+ this._applyDragStyles();
148
+ this._preparePosition(this._initialRect);
149
+ event.preventDefault();
150
+ this._updateDebugValues('dragging');
151
+ }
152
+ this._applyDragPosition();
153
+ }
154
+
155
+ _onPointerUp(event) {
156
+ if (event.pointerId !== this._pointerId) return;
157
+
158
+ document.removeEventListener('pointermove', this._onPointerMove);
159
+ document.removeEventListener('pointerup', this._onPointerUp);
160
+ document.removeEventListener('pointercancel', this._onPointerUp);
161
+ document.removeEventListener('dragstart', this._onNativeDragStart, true);
162
+ if (this._isDragging) {
163
+ this._applyDragPosition();
164
+ }
165
+ this._dialogElement.style.touchAction = '';
166
+ document.body.style.userSelect = this._previousUserSelect;
167
+
168
+ if (this._dialogElement && this._dialogElement.releasePointerCapture) {
169
+ this._dialogElement.releasePointerCapture(event.pointerId);
170
+ }
171
+
172
+ this._pointerId = null;
173
+ this._dragTarget = null;
174
+ this._isDragging = false;
175
+ this._initialRect = null;
176
+ this._unlockEmbeddedFrames();
177
+ this._restoreDragStyles();
178
+ delete this._modalElement.dataset.vgModalDragging;
179
+ this._setDebugVisibility(this._options.debug);
180
+ this._updateDebugValues('idle');
181
+ }
182
+
183
+ _preparePosition(rect = null) {
184
+ if (!this._dialogElement) return;
185
+
186
+ const currentRect = rect || this._dialogElement.getBoundingClientRect();
187
+ this._dialogElement.style.position = 'fixed';
188
+ this._dialogElement.style.margin = '0';
189
+ this._dialogElement.style.left = `${currentRect.left}px`;
190
+ this._dialogElement.style.top = `${currentRect.top}px`;
191
+ this._dialogElement.style.width = `${currentRect.width}px`;
192
+ this._dialogElement.style.height = `${currentRect.height}px`;
193
+ this._dialogElement.style.transform = 'none';
194
+ }
195
+
196
+ _isPreparedForInteraction() {
197
+ return this._dialogElement.style.position === 'fixed' && this._dialogElement.style.transform === 'none';
198
+ }
199
+
200
+ _isPointerOnResizeEdge(event) {
201
+ const rect = this._dialogElement.getBoundingClientRect();
202
+ const offsetX = event.clientX - rect.left;
203
+ const offsetY = event.clientY - rect.top;
204
+ const edgeSize = this._options.resizeEdgeSize;
205
+
206
+ const nearTop = offsetY >= 0 && offsetY <= edgeSize;
207
+ const nearBottom = offsetY <= rect.height && offsetY >= rect.height - edgeSize;
208
+ const nearLeft = offsetX >= 0 && offsetX <= edgeSize;
209
+ const nearRight = offsetX <= rect.width && offsetX >= rect.width - edgeSize;
210
+
211
+ return nearTop || nearBottom || nearLeft || nearRight;
212
+ }
213
+
214
+ _applyDragPosition() {
215
+ if (this._pointerId === null || !this._isDragging) return;
216
+
217
+ const deltaX = this._currentX - this._startX;
218
+ const deltaY = this._currentY - this._startY;
219
+ const maxLeft = Math.max(0, window.innerWidth - this._dialogWidth);
220
+ const maxTop = Math.max(0, window.innerHeight - this._dialogHeight);
221
+ const nextLeft = Math.min(maxLeft, Math.max(0, this._dialogStartLeft + deltaX));
222
+ const nextTop = Math.min(maxTop, Math.max(0, this._dialogStartTop + deltaY));
223
+
224
+ this._dialogElement.style.left = `${nextLeft}px`;
225
+ this._dialogElement.style.top = `${nextTop}px`;
226
+ this._updateDebugValues('dragging');
227
+ }
228
+
229
+ _onNativeDragStart(event) {
230
+ if (this._pointerId === null) return;
231
+ event.preventDefault();
232
+ }
233
+
234
+ _applyDragStyles() {
235
+ this._previousTransition = this._dialogElement.style.transition;
236
+ this._previousWillChange = this._dialogElement.style.willChange;
237
+ this._dialogElement.style.transition = 'none';
238
+ this._dialogElement.style.willChange = 'left, top';
239
+ }
240
+
241
+ _restoreDragStyles() {
242
+ this._dialogElement.style.transition = this._previousTransition;
243
+ this._dialogElement.style.willChange = this._previousWillChange;
244
+ }
245
+
246
+ _lockEmbeddedFrames() {
247
+ if (!this._dialogElement || this._lockedIframes.length) return;
248
+
249
+ const iframes = this._dialogElement.querySelectorAll('iframe');
250
+ for (const frame of iframes) {
251
+ this._lockedIframes.push({
252
+ element: frame,
253
+ pointerEvents: frame.style.pointerEvents,
254
+ });
255
+ frame.style.pointerEvents = 'none';
256
+ }
257
+ }
258
+
259
+ _unlockEmbeddedFrames() {
260
+ if (!this._lockedIframes.length) return;
261
+
262
+ for (const item of this._lockedIframes) {
263
+ item.element.style.pointerEvents = item.pointerEvents;
264
+ }
265
+ this._lockedIframes = [];
266
+ }
267
+
268
+ _normalizeOptions(options, base = DEFAULT_OPTIONS) {
269
+ const merged = {...base, ...options};
270
+ const threshold = Number(merged.threshold);
271
+ const resizeEdgeSize = Number(merged.resizeEdgeSize);
272
+ const selector = typeof merged.selector === 'string' && merged.selector.trim()
273
+ ? merged.selector
274
+ : DEFAULT_OPTIONS.selector;
275
+
276
+ return {
277
+ ...merged,
278
+ selector,
279
+ threshold: Number.isFinite(threshold) && threshold >= 0 ? threshold : DEFAULT_OPTIONS.threshold,
280
+ resizeEdgeSize: Number.isFinite(resizeEdgeSize) && resizeEdgeSize > 0 ? resizeEdgeSize : DEFAULT_OPTIONS.resizeEdgeSize,
281
+ debug: Boolean(merged.debug),
282
+ };
283
+ }
284
+
285
+ _resolveDragArea(target) {
286
+ try {
287
+ return target.closest(this._options.selector);
288
+ } catch (error) {
289
+ return target.closest(DEFAULT_OPTIONS.selector);
290
+ }
291
+ }
292
+
293
+ _updateDebugOverlay() {
294
+ if (!this._options.debug) {
295
+ this._setDebugVisibility(false);
296
+ return;
297
+ }
298
+
299
+ if (!this._debugElement) {
300
+ this._debugElement = document.createElement('div');
301
+ this._debugElement.style.position = 'absolute';
302
+ this._debugElement.style.left = '170px';
303
+ this._debugElement.style.bottom = '8px';
304
+ this._debugElement.style.zIndex = '7';
305
+ this._debugElement.style.padding = '4px 6px';
306
+ this._debugElement.style.borderRadius = '4px';
307
+ this._debugElement.style.background = 'rgba(0, 0, 0, 0.72)';
308
+ this._debugElement.style.color = '#fff';
309
+ this._debugElement.style.fontSize = '11px';
310
+ this._debugElement.style.lineHeight = '1.3';
311
+ this._debugElement.style.pointerEvents = 'none';
312
+ this._dialogElement.append(this._debugElement);
313
+ }
314
+
315
+ this._setDebugVisibility(true);
316
+ this._updateDebugValues(this._isDragging ? 'dragging' : 'idle');
317
+ }
318
+
319
+ _setDebugVisibility(visible) {
320
+ if (!this._debugElement) return;
321
+ this._debugElement.style.display = visible ? 'block' : 'none';
322
+ }
323
+
324
+ _updateDebugValues(state = 'idle') {
325
+ if (!this._debugElement || !this._options.debug) return;
326
+
327
+ const rect = this._dialogElement.getBoundingClientRect();
328
+ this._debugElement.textContent = `drag:${state} x:${Math.round(rect.left)} y:${Math.round(rect.top)} w:${Math.round(rect.width)} h:${Math.round(rect.height)}`;
329
+ }
330
+ }
331
+
332
+ export default VGModalDrag;