@embedpdf/utils 2.0.1 → 2.0.2
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/dist/preact/index.cjs +1 -1
- package/dist/preact/index.cjs.map +1 -1
- package/dist/preact/index.js +143 -123
- package/dist/preact/index.js.map +1 -1
- package/dist/react/index.cjs +1 -1
- package/dist/react/index.cjs.map +1 -1
- package/dist/react/index.js +143 -123
- package/dist/react/index.js.map +1 -1
- package/dist/shared/plugin-interaction-primitives/drag-resize-controller.d.ts +18 -0
- package/dist/shared-preact/plugin-interaction-primitives/drag-resize-controller.d.ts +18 -0
- package/dist/shared-react/plugin-interaction-primitives/drag-resize-controller.d.ts +18 -0
- package/dist/shared-svelte/plugin-interaction-primitives/drag-resize-controller.d.ts +18 -0
- package/dist/shared-vue/plugin-interaction-primitives/drag-resize-controller.d.ts +18 -0
- package/dist/svelte/index.cjs +1 -1
- package/dist/svelte/index.cjs.map +1 -1
- package/dist/svelte/index.js +143 -123
- package/dist/svelte/index.js.map +1 -1
- package/dist/vue/index.cjs +1 -1
- package/dist/vue/index.cjs.map +1 -1
- package/dist/vue/index.js +143 -123
- package/dist/vue/index.js.map +1 -1
- package/package.json +2 -2
package/dist/svelte/index.js
CHANGED
|
@@ -1,6 +1,12 @@
|
|
|
1
1
|
import * as $ from "svelte/internal/client";
|
|
2
2
|
import "svelte/internal/disclose-version";
|
|
3
3
|
import { getCounterRotation } from "@embedpdf/utils";
|
|
4
|
+
function getAnchor(handle) {
|
|
5
|
+
return {
|
|
6
|
+
x: handle.includes("e") ? "left" : handle.includes("w") ? "right" : "center",
|
|
7
|
+
y: handle.includes("s") ? "top" : handle.includes("n") ? "bottom" : "center"
|
|
8
|
+
};
|
|
9
|
+
}
|
|
4
10
|
class DragResizeController {
|
|
5
11
|
constructor(config, onUpdate) {
|
|
6
12
|
this.config = config;
|
|
@@ -258,134 +264,124 @@ class DragResizeController {
|
|
|
258
264
|
};
|
|
259
265
|
return this.applyConstraints(position);
|
|
260
266
|
}
|
|
267
|
+
/**
|
|
268
|
+
* Calculate the new rect after a resize operation.
|
|
269
|
+
* Pipeline: applyDelta → enforceAspectRatio → clampToBounds → applyConstraints
|
|
270
|
+
*/
|
|
261
271
|
calculateResizePosition(delta, handle) {
|
|
262
|
-
var _a;
|
|
263
272
|
if (!this.startElement) return this.config.element;
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
case "se":
|
|
270
|
-
width += delta.x;
|
|
271
|
-
height += delta.y;
|
|
272
|
-
break;
|
|
273
|
-
case "sw":
|
|
274
|
-
x += delta.x;
|
|
275
|
-
width -= delta.x;
|
|
276
|
-
height += delta.y;
|
|
277
|
-
break;
|
|
278
|
-
case "ne":
|
|
279
|
-
width += delta.x;
|
|
280
|
-
y += delta.y;
|
|
281
|
-
height -= delta.y;
|
|
282
|
-
break;
|
|
283
|
-
case "nw":
|
|
284
|
-
x += delta.x;
|
|
285
|
-
width -= delta.x;
|
|
286
|
-
y += delta.y;
|
|
287
|
-
height -= delta.y;
|
|
288
|
-
break;
|
|
289
|
-
case "n":
|
|
290
|
-
y += delta.y;
|
|
291
|
-
height -= delta.y;
|
|
292
|
-
break;
|
|
293
|
-
case "s":
|
|
294
|
-
height += delta.y;
|
|
295
|
-
break;
|
|
296
|
-
case "e":
|
|
297
|
-
width += delta.x;
|
|
298
|
-
break;
|
|
299
|
-
case "w":
|
|
300
|
-
x += delta.x;
|
|
301
|
-
width -= delta.x;
|
|
302
|
-
break;
|
|
273
|
+
const anchor = getAnchor(handle);
|
|
274
|
+
const aspectRatio = this.startElement.size.width / this.startElement.size.height || 1;
|
|
275
|
+
let rect = this.applyResizeDelta(delta, anchor);
|
|
276
|
+
if (this.config.maintainAspectRatio) {
|
|
277
|
+
rect = this.enforceAspectRatio(rect, anchor, aspectRatio);
|
|
303
278
|
}
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
279
|
+
rect = this.clampToBounds(rect, anchor, aspectRatio);
|
|
280
|
+
return this.applyConstraints(rect);
|
|
281
|
+
}
|
|
282
|
+
/**
|
|
283
|
+
* Apply the mouse delta to produce a raw (unconstrained) resized rect.
|
|
284
|
+
*/
|
|
285
|
+
applyResizeDelta(delta, anchor) {
|
|
286
|
+
const start = this.startElement;
|
|
287
|
+
let x = start.origin.x;
|
|
288
|
+
let y = start.origin.y;
|
|
289
|
+
let width = start.size.width;
|
|
290
|
+
let height = start.size.height;
|
|
291
|
+
if (anchor.x === "left") {
|
|
292
|
+
width += delta.x;
|
|
293
|
+
} else if (anchor.x === "right") {
|
|
294
|
+
x += delta.x;
|
|
295
|
+
width -= delta.x;
|
|
296
|
+
}
|
|
297
|
+
if (anchor.y === "top") {
|
|
298
|
+
height += delta.y;
|
|
299
|
+
} else if (anchor.y === "bottom") {
|
|
300
|
+
y += delta.y;
|
|
301
|
+
height -= delta.y;
|
|
302
|
+
}
|
|
303
|
+
return { origin: { x, y }, size: { width, height } };
|
|
304
|
+
}
|
|
305
|
+
/**
|
|
306
|
+
* Enforce aspect ratio while respecting the anchor.
|
|
307
|
+
* For edge handles (center anchor on one axis), the rect expands symmetrically on that axis.
|
|
308
|
+
* For corner handles, the anchor corner stays fixed.
|
|
309
|
+
*/
|
|
310
|
+
enforceAspectRatio(rect, anchor, aspectRatio) {
|
|
311
|
+
const start = this.startElement;
|
|
312
|
+
let { x, y } = rect.origin;
|
|
313
|
+
let { width, height } = rect.size;
|
|
314
|
+
const isEdgeHandle = anchor.x === "center" || anchor.y === "center";
|
|
315
|
+
if (isEdgeHandle) {
|
|
316
|
+
if (anchor.y === "center") {
|
|
317
|
+
height = width / aspectRatio;
|
|
318
|
+
y = start.origin.y + (start.size.height - height) / 2;
|
|
321
319
|
} else {
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
if (widthChange > heightChange) {
|
|
325
|
-
height = width / aspectRatio;
|
|
326
|
-
} else {
|
|
327
|
-
width = height * aspectRatio;
|
|
328
|
-
}
|
|
329
|
-
if (handle.includes("w")) {
|
|
330
|
-
x = this.startElement.origin.x + this.startElement.size.width - width;
|
|
331
|
-
}
|
|
332
|
-
if (handle.includes("n")) {
|
|
333
|
-
y = this.startElement.origin.y + this.startElement.size.height - height;
|
|
334
|
-
}
|
|
320
|
+
width = height * aspectRatio;
|
|
321
|
+
x = start.origin.x + (start.size.width - width) / 2;
|
|
335
322
|
}
|
|
323
|
+
} else {
|
|
324
|
+
const dw = Math.abs(width - start.size.width);
|
|
325
|
+
const dh = Math.abs(height - start.size.height);
|
|
326
|
+
if (dw >= dh) {
|
|
327
|
+
height = width / aspectRatio;
|
|
328
|
+
} else {
|
|
329
|
+
width = height * aspectRatio;
|
|
330
|
+
}
|
|
331
|
+
}
|
|
332
|
+
if (anchor.x === "right") {
|
|
333
|
+
x = start.origin.x + start.size.width - width;
|
|
334
|
+
}
|
|
335
|
+
if (anchor.y === "bottom") {
|
|
336
|
+
y = start.origin.y + start.size.height - height;
|
|
336
337
|
}
|
|
338
|
+
return { origin: { x, y }, size: { width, height } };
|
|
339
|
+
}
|
|
340
|
+
/**
|
|
341
|
+
* Clamp rect to bounding box while respecting anchor and aspect ratio.
|
|
342
|
+
*/
|
|
343
|
+
clampToBounds(rect, anchor, aspectRatio) {
|
|
344
|
+
var _a;
|
|
337
345
|
const bbox = (_a = this.config.constraints) == null ? void 0 : _a.boundingBox;
|
|
338
|
-
if (bbox)
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
break;
|
|
356
|
-
case "n":
|
|
357
|
-
if (y < 0) {
|
|
358
|
-
height += y;
|
|
359
|
-
y = 0;
|
|
360
|
-
}
|
|
361
|
-
break;
|
|
362
|
-
case "sw":
|
|
363
|
-
if (x < 0) {
|
|
364
|
-
width += x;
|
|
365
|
-
x = 0;
|
|
366
|
-
}
|
|
367
|
-
height = Math.min(height, bbox.height - y);
|
|
368
|
-
break;
|
|
369
|
-
case "nw":
|
|
370
|
-
if (x < 0) {
|
|
371
|
-
width += x;
|
|
372
|
-
x = 0;
|
|
373
|
-
}
|
|
374
|
-
if (y < 0) {
|
|
375
|
-
height += y;
|
|
376
|
-
y = 0;
|
|
377
|
-
}
|
|
378
|
-
break;
|
|
379
|
-
case "ne":
|
|
380
|
-
width = Math.min(width, bbox.width - x);
|
|
381
|
-
if (y < 0) {
|
|
382
|
-
height += y;
|
|
383
|
-
y = 0;
|
|
384
|
-
}
|
|
385
|
-
break;
|
|
346
|
+
if (!bbox) return rect;
|
|
347
|
+
const start = this.startElement;
|
|
348
|
+
let { x, y } = rect.origin;
|
|
349
|
+
let { width, height } = rect.size;
|
|
350
|
+
width = Math.max(1, width);
|
|
351
|
+
height = Math.max(1, height);
|
|
352
|
+
const anchorX = anchor.x === "left" ? start.origin.x : start.origin.x + start.size.width;
|
|
353
|
+
const anchorY = anchor.y === "top" ? start.origin.y : start.origin.y + start.size.height;
|
|
354
|
+
const maxW = anchor.x === "left" ? bbox.width - anchorX : anchor.x === "right" ? anchorX : Math.min(start.origin.x, bbox.width - start.origin.x - start.size.width) * 2 + start.size.width;
|
|
355
|
+
const maxH = anchor.y === "top" ? bbox.height - anchorY : anchor.y === "bottom" ? anchorY : Math.min(start.origin.y, bbox.height - start.origin.y - start.size.height) * 2 + start.size.height;
|
|
356
|
+
if (this.config.maintainAspectRatio) {
|
|
357
|
+
const scaleW = width > maxW ? maxW / width : 1;
|
|
358
|
+
const scaleH = height > maxH ? maxH / height : 1;
|
|
359
|
+
const scale = Math.min(scaleW, scaleH);
|
|
360
|
+
if (scale < 1) {
|
|
361
|
+
width *= scale;
|
|
362
|
+
height *= scale;
|
|
386
363
|
}
|
|
364
|
+
} else {
|
|
365
|
+
width = Math.min(width, maxW);
|
|
366
|
+
height = Math.min(height, maxH);
|
|
387
367
|
}
|
|
388
|
-
|
|
368
|
+
if (anchor.x === "left") {
|
|
369
|
+
x = anchorX;
|
|
370
|
+
} else if (anchor.x === "right") {
|
|
371
|
+
x = anchorX - width;
|
|
372
|
+
} else {
|
|
373
|
+
x = start.origin.x + (start.size.width - width) / 2;
|
|
374
|
+
}
|
|
375
|
+
if (anchor.y === "top") {
|
|
376
|
+
y = anchorY;
|
|
377
|
+
} else if (anchor.y === "bottom") {
|
|
378
|
+
y = anchorY - height;
|
|
379
|
+
} else {
|
|
380
|
+
y = start.origin.y + (start.size.height - height) / 2;
|
|
381
|
+
}
|
|
382
|
+
x = Math.max(0, Math.min(x, bbox.width - width));
|
|
383
|
+
y = Math.max(0, Math.min(y, bbox.height - height));
|
|
384
|
+
return { origin: { x, y }, size: { width, height } };
|
|
389
385
|
}
|
|
390
386
|
applyConstraints(position) {
|
|
391
387
|
const { constraints } = this.config;
|
|
@@ -394,10 +390,34 @@ class DragResizeController {
|
|
|
394
390
|
origin: { x, y },
|
|
395
391
|
size: { width, height }
|
|
396
392
|
} = position;
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
393
|
+
const minW = constraints.minWidth ?? 1;
|
|
394
|
+
const minH = constraints.minHeight ?? 1;
|
|
395
|
+
const maxW = constraints.maxWidth;
|
|
396
|
+
const maxH = constraints.maxHeight;
|
|
397
|
+
if (this.config.maintainAspectRatio && width > 0 && height > 0) {
|
|
398
|
+
const ratio = width / height;
|
|
399
|
+
if (width < minW) {
|
|
400
|
+
width = minW;
|
|
401
|
+
height = width / ratio;
|
|
402
|
+
}
|
|
403
|
+
if (height < minH) {
|
|
404
|
+
height = minH;
|
|
405
|
+
width = height * ratio;
|
|
406
|
+
}
|
|
407
|
+
if (maxW !== void 0 && width > maxW) {
|
|
408
|
+
width = maxW;
|
|
409
|
+
height = width / ratio;
|
|
410
|
+
}
|
|
411
|
+
if (maxH !== void 0 && height > maxH) {
|
|
412
|
+
height = maxH;
|
|
413
|
+
width = height * ratio;
|
|
414
|
+
}
|
|
415
|
+
} else {
|
|
416
|
+
width = Math.max(minW, width);
|
|
417
|
+
height = Math.max(minH, height);
|
|
418
|
+
if (maxW !== void 0) width = Math.min(maxW, width);
|
|
419
|
+
if (maxH !== void 0) height = Math.min(maxH, height);
|
|
420
|
+
}
|
|
401
421
|
if (constraints.boundingBox) {
|
|
402
422
|
x = Math.max(0, Math.min(x, constraints.boundingBox.width - width));
|
|
403
423
|
y = Math.max(0, Math.min(y, constraints.boundingBox.height - height));
|
package/dist/svelte/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sources":["../../src/shared/plugin-interaction-primitives/drag-resize-controller.ts","../../src/shared/plugin-interaction-primitives/utils.ts","../../src/svelte/hooks/use-drag-resize.svelte.ts","../../src/svelte/utils/styles-to-string.ts","../../src/svelte/hooks/use-interaction-handles.svelte.ts","../../src/svelte/actions/doublePress.ts","../../src/svelte/components/CounterRotateContainer.svelte","../../src/svelte/utils/deep-to-raw.ts"],"sourcesContent":["import { Position, Rect } from '@embedpdf/models';\n\nexport interface DragResizeConfig {\n element: Rect;\n vertices?: Position[];\n constraints?: {\n minWidth?: number;\n minHeight?: number;\n maxWidth?: number;\n maxHeight?: number;\n boundingBox?: { width: number; height: number }; // page bounds\n };\n maintainAspectRatio?: boolean;\n pageRotation?: number;\n scale?: number;\n}\n\nexport type InteractionState = 'idle' | 'dragging' | 'resizing' | 'vertex-editing';\nexport type ResizeHandle = 'nw' | 'ne' | 'sw' | 'se' | 'n' | 'e' | 's' | 'w';\n\nexport interface TransformData {\n type: 'move' | 'resize' | 'vertex-edit';\n changes: {\n rect?: Rect;\n vertices?: Position[];\n };\n metadata?: {\n handle?: ResizeHandle;\n vertexIndex?: number;\n maintainAspectRatio?: boolean;\n };\n}\n\nexport interface InteractionEvent {\n state: 'start' | 'move' | 'end';\n transformData?: TransformData;\n}\n\n/**\n * Pure geometric controller that manages drag/resize/vertex-edit logic.\n */\nexport class DragResizeController {\n private state: InteractionState = 'idle';\n private startPoint: Position | null = null;\n private startElement: Rect | null = null;\n private activeHandle: ResizeHandle | null = null;\n private currentPosition: Rect | null = null;\n\n // Vertex editing state - pure geometric\n private activeVertexIndex: number | null = null;\n private startVertices: Position[] = [];\n private currentVertices: Position[] = [];\n\n constructor(\n private config: DragResizeConfig,\n private onUpdate: (event: InteractionEvent) => void,\n ) {\n this.currentVertices = config.vertices || [];\n }\n\n updateConfig(config: Partial<DragResizeConfig>) {\n this.config = { ...this.config, ...config };\n this.currentVertices = config.vertices || [];\n }\n\n startDrag(clientX: number, clientY: number) {\n this.state = 'dragging';\n this.startPoint = { x: clientX, y: clientY };\n this.startElement = { ...this.config.element };\n this.currentPosition = { ...this.config.element };\n\n this.onUpdate({\n state: 'start',\n transformData: {\n type: 'move',\n changes: {\n rect: this.startElement,\n },\n },\n });\n }\n\n startResize(handle: ResizeHandle, clientX: number, clientY: number) {\n this.state = 'resizing';\n this.activeHandle = handle;\n this.startPoint = { x: clientX, y: clientY };\n this.startElement = { ...this.config.element };\n this.currentPosition = { ...this.config.element };\n\n this.onUpdate({\n state: 'start',\n transformData: {\n type: 'resize',\n changes: {\n rect: this.startElement,\n },\n metadata: {\n handle: this.activeHandle,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n }\n\n startVertexEdit(vertexIndex: number, clientX: number, clientY: number) {\n // Refresh vertices from latest config before validating index\n this.currentVertices = [...(this.config.vertices ?? this.currentVertices)];\n if (vertexIndex < 0 || vertexIndex >= this.currentVertices.length) return;\n\n this.state = 'vertex-editing';\n this.activeVertexIndex = vertexIndex;\n this.startPoint = { x: clientX, y: clientY };\n this.startVertices = [...this.currentVertices];\n\n this.onUpdate({\n state: 'start',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices: this.startVertices,\n },\n metadata: {\n vertexIndex,\n },\n },\n });\n }\n\n move(clientX: number, clientY: number) {\n if (this.state === 'idle' || !this.startPoint) return;\n\n if (this.state === 'dragging' && this.startElement) {\n const delta = this.calculateDelta(clientX, clientY);\n const position = this.calculateDragPosition(delta);\n this.currentPosition = position;\n\n this.onUpdate({\n state: 'move',\n transformData: {\n type: 'move',\n changes: {\n rect: position,\n },\n },\n });\n } else if (this.state === 'resizing' && this.activeHandle && this.startElement) {\n const delta = this.calculateDelta(clientX, clientY);\n const position = this.calculateResizePosition(delta, this.activeHandle);\n this.currentPosition = position;\n\n this.onUpdate({\n state: 'move',\n transformData: {\n type: 'resize',\n changes: {\n rect: position,\n },\n metadata: {\n handle: this.activeHandle,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n } else if (this.state === 'vertex-editing' && this.activeVertexIndex !== null) {\n const vertices = this.calculateVertexPosition(clientX, clientY);\n this.currentVertices = vertices;\n\n this.onUpdate({\n state: 'move',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices,\n },\n metadata: {\n vertexIndex: this.activeVertexIndex,\n },\n },\n });\n }\n }\n\n end() {\n if (this.state === 'idle') return;\n\n const wasState = this.state;\n const handle = this.activeHandle;\n const vertexIndex = this.activeVertexIndex;\n\n if (wasState === 'vertex-editing') {\n this.onUpdate({\n state: 'end',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices: this.currentVertices,\n },\n metadata: {\n vertexIndex: vertexIndex || undefined,\n },\n },\n });\n } else {\n const finalPosition = this.getCurrentPosition();\n this.onUpdate({\n state: 'end',\n transformData: {\n type: wasState === 'dragging' ? 'move' : 'resize',\n changes: {\n rect: finalPosition,\n },\n metadata:\n wasState === 'dragging'\n ? undefined\n : {\n handle: handle || undefined,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n }\n\n this.reset();\n }\n\n cancel() {\n if (this.state === 'idle') return;\n\n if (this.state === 'vertex-editing') {\n this.onUpdate({\n state: 'end',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices: this.startVertices,\n },\n metadata: {\n vertexIndex: this.activeVertexIndex || undefined,\n },\n },\n });\n } else if (this.startElement) {\n this.onUpdate({\n state: 'end',\n transformData: {\n type: this.state === 'dragging' ? 'move' : 'resize',\n changes: {\n rect: this.startElement,\n },\n metadata:\n this.state === 'dragging'\n ? undefined\n : {\n handle: this.activeHandle || undefined,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n }\n\n this.reset();\n }\n\n private reset() {\n this.state = 'idle';\n this.startPoint = null;\n this.startElement = null;\n this.activeHandle = null;\n this.currentPosition = null;\n this.activeVertexIndex = null;\n this.startVertices = [];\n }\n\n private getCurrentPosition() {\n return this.currentPosition || this.config.element;\n }\n\n private calculateDelta(clientX: number, clientY: number): Position {\n if (!this.startPoint) return { x: 0, y: 0 };\n\n const rawDelta: Position = {\n x: clientX - this.startPoint.x,\n y: clientY - this.startPoint.y,\n };\n\n return this.transformDelta(rawDelta);\n }\n\n private transformDelta(delta: Position): Position {\n const { pageRotation = 0, scale = 1 } = this.config;\n\n const rad = (pageRotation * Math.PI) / 2;\n const cos = Math.cos(rad);\n const sin = Math.sin(rad);\n\n const scaledX = delta.x / scale;\n const scaledY = delta.y / scale;\n\n return {\n x: cos * scaledX + sin * scaledY,\n y: -sin * scaledX + cos * scaledY,\n };\n }\n\n private clampPoint(p: Position): Position {\n const bbox = this.config.constraints?.boundingBox;\n if (!bbox) return p;\n return {\n x: Math.max(0, Math.min(p.x, bbox.width)),\n y: Math.max(0, Math.min(p.y, bbox.height)),\n };\n }\n\n private calculateVertexPosition(clientX: number, clientY: number): Position[] {\n if (this.activeVertexIndex === null) return this.startVertices;\n\n const delta = this.calculateDelta(clientX, clientY);\n const newVertices = [...this.startVertices];\n const currentVertex = newVertices[this.activeVertexIndex];\n\n const moved = {\n x: currentVertex.x + delta.x,\n y: currentVertex.y + delta.y,\n };\n newVertices[this.activeVertexIndex] = this.clampPoint(moved);\n\n return newVertices;\n }\n\n private calculateDragPosition(delta: Position): Rect {\n if (!this.startElement) return this.config.element;\n\n const position: Rect = {\n origin: {\n x: this.startElement.origin.x + delta.x,\n y: this.startElement.origin.y + delta.y,\n },\n size: {\n width: this.startElement.size.width,\n height: this.startElement.size.height,\n },\n };\n\n return this.applyConstraints(position);\n }\n\n private calculateResizePosition(delta: Position, handle: ResizeHandle): Rect {\n if (!this.startElement) return this.config.element;\n\n let {\n origin: { x, y },\n size: { width, height },\n } = this.startElement;\n\n switch (handle) {\n case 'se':\n width += delta.x;\n height += delta.y;\n break;\n case 'sw':\n x += delta.x;\n width -= delta.x;\n height += delta.y;\n break;\n case 'ne':\n width += delta.x;\n y += delta.y;\n height -= delta.y;\n break;\n case 'nw':\n x += delta.x;\n width -= delta.x;\n y += delta.y;\n height -= delta.y;\n break;\n case 'n':\n y += delta.y;\n height -= delta.y;\n break;\n case 's':\n height += delta.y;\n break;\n case 'e':\n width += delta.x;\n break;\n case 'w':\n x += delta.x;\n width -= delta.x;\n break;\n }\n\n // Maintain aspect ratio if needed\n if (this.config.maintainAspectRatio && this.startElement) {\n const aspectRatio = this.startElement.size.width / this.startElement.size.height;\n\n if (['n', 's', 'e', 'w'].includes(handle)) {\n if (handle === 'n' || handle === 's') {\n const newWidth = height * aspectRatio;\n const widthDiff = newWidth - width;\n width = newWidth;\n x -= widthDiff / 2;\n } else {\n const newHeight = width / aspectRatio;\n const heightDiff = newHeight - height;\n height = newHeight;\n if (handle === 'w') {\n x = this.startElement.origin.x + this.startElement.size.width - width;\n }\n y -= heightDiff / 2;\n }\n } else {\n const widthChange = Math.abs(width - this.startElement.size.width);\n const heightChange = Math.abs(height - this.startElement.size.height);\n if (widthChange > heightChange) {\n height = width / aspectRatio;\n } else {\n width = height * aspectRatio;\n }\n if (handle.includes('w')) {\n x = this.startElement.origin.x + this.startElement.size.width - width;\n }\n if (handle.includes('n')) {\n y = this.startElement.origin.y + this.startElement.size.height - height;\n }\n }\n }\n\n // Handle-aware bounding box clamping to avoid shifting opposite edge\n const bbox = this.config.constraints?.boundingBox;\n if (bbox) {\n switch (handle) {\n case 'e':\n width = Math.min(width, bbox.width - x);\n break;\n case 's':\n height = Math.min(height, bbox.height - y);\n break;\n case 'se':\n width = Math.min(width, bbox.width - x);\n height = Math.min(height, bbox.height - y);\n break;\n case 'w':\n if (x < 0) {\n width += x;\n x = 0;\n }\n break;\n case 'n':\n if (y < 0) {\n height += y;\n y = 0;\n }\n break;\n case 'sw':\n if (x < 0) {\n width += x;\n x = 0;\n }\n height = Math.min(height, bbox.height - y);\n break;\n case 'nw':\n if (x < 0) {\n width += x;\n x = 0;\n }\n if (y < 0) {\n height += y;\n y = 0;\n }\n break;\n case 'ne':\n width = Math.min(width, bbox.width - x);\n if (y < 0) {\n height += y;\n y = 0;\n }\n break;\n }\n }\n\n return this.applyConstraints({ origin: { x, y }, size: { width, height } });\n }\n\n private applyConstraints(position: Rect): Rect {\n const { constraints } = this.config;\n if (!constraints) return position;\n\n let {\n origin: { x, y },\n size: { width, height },\n } = position;\n\n // Apply size constraints\n width = Math.max(constraints.minWidth || 1, width);\n height = Math.max(constraints.minHeight || 1, height);\n\n if (constraints.maxWidth) width = Math.min(constraints.maxWidth, width);\n if (constraints.maxHeight) height = Math.min(constraints.maxHeight, height);\n\n // Apply bounding box constraints\n if (constraints.boundingBox) {\n x = Math.max(0, Math.min(x, constraints.boundingBox.width - width));\n y = Math.max(0, Math.min(y, constraints.boundingBox.height - height));\n }\n\n return { origin: { x, y }, size: { width, height } };\n }\n}\n","import type { Position, Rect } from '@embedpdf/models';\nimport type { ResizeHandle, DragResizeConfig } from './drag-resize-controller';\n\nexport type QuarterTurns = 0 | 1 | 2 | 3;\n\nexport interface ResizeUI {\n handleSize?: number; // px (default 8)\n spacing?: number; // px distance from the box edge (default 1)\n offsetMode?: 'outside' | 'inside' | 'center'; // default 'outside'\n includeSides?: boolean; // default false\n zIndex?: number; // default 3\n rotationAwareCursor?: boolean; // default true\n}\n\nexport interface VertexUI {\n vertexSize?: number; // px (default 12)\n zIndex?: number; // default 4\n}\n\nexport interface HandleDescriptor {\n handle: ResizeHandle;\n style: Record<string, number | string>;\n attrs?: Record<string, any>;\n}\n\nfunction diagonalCursor(handle: ResizeHandle, rot: QuarterTurns): string {\n // Standard cursors; diagonals flip on odd quarter-turns\n const diag0: Record<'nw' | 'ne' | 'sw' | 'se', string> = {\n nw: 'nwse-resize',\n ne: 'nesw-resize',\n sw: 'nesw-resize',\n se: 'nwse-resize',\n };\n if (handle === 'n' || handle === 's') return 'ns-resize';\n if (handle === 'e' || handle === 'w') return 'ew-resize';\n if (rot % 2 === 0) return diag0[handle as 'nw' | 'ne' | 'sw' | 'se'];\n return { nw: 'nesw-resize', ne: 'nwse-resize', sw: 'nwse-resize', se: 'nesw-resize' }[\n handle as 'nw' | 'ne' | 'sw' | 'se'\n ]!;\n}\n\nfunction edgeOffset(k: number, spacing: number, mode: 'outside' | 'inside' | 'center') {\n // Base puts the handle centered on the edge\n const base = -k / 2;\n if (mode === 'center') return base;\n // outside moves further out (more negative), inside moves in (less negative)\n return mode === 'outside' ? base - spacing : base + spacing;\n}\n\nexport function describeResizeFromConfig(\n cfg: DragResizeConfig,\n ui: ResizeUI = {},\n): HandleDescriptor[] {\n const {\n handleSize = 8,\n spacing = 1,\n offsetMode = 'outside',\n includeSides = false,\n zIndex = 3,\n rotationAwareCursor = true,\n } = ui;\n\n const rotation = ((cfg.pageRotation ?? 0) % 4) as QuarterTurns;\n\n const off = (edge: 'top' | 'right' | 'bottom' | 'left') => ({\n [edge]: edgeOffset(handleSize, spacing, offsetMode) + 'px',\n });\n\n const corners: Array<[ResizeHandle, Record<string, number | string>]> = [\n ['nw', { ...off('top'), ...off('left') }],\n ['ne', { ...off('top'), ...off('right') }],\n ['sw', { ...off('bottom'), ...off('left') }],\n ['se', { ...off('bottom'), ...off('right') }],\n ];\n const sides: Array<[ResizeHandle, Record<string, number | string>]> = includeSides\n ? [\n ['n', { ...off('top'), left: `calc(50% - ${handleSize / 2}px)` }],\n ['s', { ...off('bottom'), left: `calc(50% - ${handleSize / 2}px)` }],\n ['w', { ...off('left'), top: `calc(50% - ${handleSize / 2}px)` }],\n ['e', { ...off('right'), top: `calc(50% - ${handleSize / 2}px)` }],\n ]\n : [];\n\n const all = [...corners, ...sides];\n\n return all.map(([handle, pos]) => ({\n handle,\n style: {\n position: 'absolute',\n width: handleSize + 'px',\n height: handleSize + 'px',\n borderRadius: '50%',\n zIndex,\n cursor: rotationAwareCursor ? diagonalCursor(handle, rotation) : 'default',\n touchAction: 'none',\n ...(pos as any),\n },\n attrs: { 'data-epdf-handle': handle },\n }));\n}\n\nexport function describeVerticesFromConfig(\n cfg: DragResizeConfig,\n ui: VertexUI = {},\n liveVertices?: Position[],\n): HandleDescriptor[] {\n const { vertexSize = 12, zIndex = 4 } = ui;\n const rect: Rect = cfg.element;\n const scale = cfg.scale ?? 1;\n const verts = liveVertices ?? cfg.vertices ?? [];\n\n return verts.map((v, i) => {\n const left = (v.x - rect.origin.x) * scale - vertexSize / 2;\n const top = (v.y - rect.origin.y) * scale - vertexSize / 2;\n return {\n handle: 'nw', // not used; kept for type\n style: {\n position: 'absolute',\n left: left + 'px',\n top: top + 'px',\n width: vertexSize + 'px',\n height: vertexSize + 'px',\n borderRadius: '50%',\n cursor: 'pointer',\n zIndex,\n touchAction: 'none',\n },\n attrs: { 'data-epdf-vertex': i },\n };\n });\n}\n","import {\n type DragResizeConfig,\n DragResizeController,\n type InteractionEvent,\n type ResizeHandle,\n} from '../../shared/plugin-interaction-primitives';\n\nexport interface UseDragResizeOptions extends DragResizeConfig {\n onUpdate?: (event: InteractionEvent) => void;\n enabled?: boolean;\n}\n\nexport interface ResizeHandleEventProps {\n onpointerdown: (e: PointerEvent) => void;\n onpointermove: (e: PointerEvent) => void;\n onpointerup: (e: PointerEvent) => void;\n onpointercancel: (e: PointerEvent) => void;\n}\n\nexport function useDragResize(getOptions: () => UseDragResizeOptions) {\n // Use getter function to maintain reactivity\n const config = $derived.by(() => {\n const opts = getOptions();\n const { onUpdate, enabled, ...rest } = opts;\n return rest;\n });\n\n const enabled = $derived(getOptions().enabled ?? true);\n const onUpdate = $derived(getOptions().onUpdate);\n\n let controller = $state<DragResizeController | null>(null);\n\n // Initialize or update controller\n $effect(() => {\n if (!controller) {\n controller = new DragResizeController(config, (event) => onUpdate?.(event));\n } else {\n controller.updateConfig(config);\n }\n });\n\n const handleDragStart = (e: PointerEvent) => {\n if (!enabled) return;\n e.preventDefault();\n e.stopPropagation();\n controller?.startDrag(e.clientX, e.clientY);\n (e.currentTarget as HTMLElement).setPointerCapture(e.pointerId);\n };\n\n const handleMove = (e: PointerEvent) => {\n e.preventDefault();\n e.stopPropagation();\n controller?.move(e.clientX, e.clientY);\n };\n\n const handleEnd = (e: PointerEvent) => {\n e.preventDefault();\n e.stopPropagation();\n controller?.end();\n (e.currentTarget as HTMLElement).releasePointerCapture?.(e.pointerId);\n };\n\n const createResizeHandler = (handle: ResizeHandle): ResizeHandleEventProps => ({\n onpointerdown: (e: PointerEvent) => {\n if (!enabled) return;\n e.preventDefault();\n e.stopPropagation();\n controller?.startResize(handle, e.clientX, e.clientY);\n (e.currentTarget as HTMLElement).setPointerCapture(e.pointerId);\n },\n onpointermove: handleMove,\n onpointerup: handleEnd,\n onpointercancel: handleEnd,\n });\n\n const createVertexHandler = (vertexIndex: number): ResizeHandleEventProps => ({\n onpointerdown: (e: PointerEvent) => {\n if (!enabled) return;\n e.preventDefault();\n e.stopPropagation();\n controller?.startVertexEdit(vertexIndex, e.clientX, e.clientY);\n (e.currentTarget as HTMLElement).setPointerCapture(e.pointerId);\n },\n onpointermove: handleMove,\n onpointerup: handleEnd,\n onpointercancel: handleEnd,\n });\n\n const dragProps = $derived(\n enabled\n ? {\n onpointerdown: handleDragStart,\n onpointermove: handleMove,\n onpointerup: handleEnd,\n onpointercancel: handleEnd,\n }\n : {},\n );\n\n return {\n get dragProps() {\n return dragProps;\n },\n createResizeProps: createResizeHandler,\n createVertexProps: createVertexHandler,\n };\n}\n","/**\n * Converts a style object with camelCase properties to a CSS string with kebab-case properties.\n *\n * This is useful in Svelte 5 where spreading style objects doesn't work with the `style:` directive.\n * Instead, you can convert the entire style object to a string and apply it to the `style` attribute.\n *\n * @param style - An object containing CSS properties in camelCase format with string or number values\n * @returns A CSS string with kebab-case properties suitable for the HTML style attribute\n *\n * @example\n * ```ts\n * const styles = {\n * position: 'absolute',\n * zIndex: 10,\n * borderRadius: '50%',\n * backgroundColor: '#007ACC'\n * };\n *\n * const cssString = stylesToString(styles);\n * // Returns: \"position: absolute; z-index: 10; border-radius: 50%; background-color: #007ACC\"\n * ```\n *\n * @example\n * Usage in Svelte templates:\n * ```svelte\n * <div style=\"{stylesToString(myStyles)}; color: red;\"></div>\n * ```\n */\nexport function stylesToString(style: Record<string, string | number>): string {\n return Object.entries(style)\n .map(([key, value]) => {\n const cssKey = key.replace(/[A-Z]/g, (m) => `-${m.toLowerCase()}`);\n return `${cssKey}: ${value}`;\n })\n .join('; ');\n}\n","import { useDragResize, type UseDragResizeOptions } from './use-drag-resize.svelte';\nimport {\n describeResizeFromConfig,\n describeVerticesFromConfig,\n type ResizeUI,\n type VertexUI,\n} from '../../shared/plugin-interaction-primitives';\nimport { stylesToString } from '../utils/styles-to-string';\n\nexport type HandleElementProps = {\n key: string | number;\n style: string;\n onpointerdown: (e: PointerEvent) => void;\n onpointermove: (e: PointerEvent) => void;\n onpointerup: (e: PointerEvent) => void;\n onpointercancel: (e: PointerEvent) => void;\n} & Record<string, any>;\n\nexport function useInteractionHandles(\n getOpts: () => {\n controller: UseDragResizeOptions;\n resizeUI?: ResizeUI;\n vertexUI?: VertexUI;\n includeVertices?: boolean;\n handleAttrs?: (\n h: 'nw' | 'ne' | 'sw' | 'se' | 'n' | 'e' | 's' | 'w',\n ) => Record<string, any> | void;\n vertexAttrs?: (i: number) => Record<string, any> | void;\n },\n) {\n // Use getter function and $derived to maintain reactivity\n const controller = $derived(getOpts().controller);\n const resizeUI = $derived(getOpts().resizeUI);\n const vertexUI = $derived(getOpts().vertexUI);\n const includeVertices = $derived(getOpts().includeVertices ?? false);\n const handleAttrs = $derived(getOpts().handleAttrs);\n const vertexAttrs = $derived(getOpts().vertexAttrs);\n\n const dragResize = useDragResize(() => controller);\n\n // Resize handles: computed from controller config\n const resize = $derived.by((): HandleElementProps[] => {\n const desc = describeResizeFromConfig(controller, resizeUI);\n return desc.map((d) => ({\n key: d.attrs?.['data-epdf-handle'] as string,\n style: stylesToString(d.style),\n ...dragResize.createResizeProps(d.handle),\n ...(d.attrs ?? {}),\n ...(handleAttrs?.(d.handle) ?? {}),\n }));\n });\n\n // Vertex handles: computed from controller config and vertices\n const vertices = $derived.by((): HandleElementProps[] => {\n if (!includeVertices) return [];\n const desc = describeVerticesFromConfig(controller, vertexUI, controller.vertices);\n return desc.map((d, i) => ({\n key: i,\n style: stylesToString(d.style),\n ...dragResize.createVertexProps(i),\n ...(d.attrs ?? {}),\n ...(vertexAttrs?.(i) ?? {}),\n }));\n });\n\n // Return getters to maintain reactivity when accessed from outside\n return {\n get dragProps() {\n return dragResize.dragProps;\n },\n get resize() {\n return resize;\n },\n get vertices() {\n return vertices;\n },\n };\n}\n","export type DoublePressOptions = {\n delay?: number; // ms between taps\n tolerancePx?: number; // spatial tolerance\n onDouble?: (e: PointerEvent | MouseEvent) => void;\n};\n\nexport function doublePress<T extends Element = Element>(\n node: T,\n options: DoublePressOptions = {},\n) {\n let { onDouble, delay = 300, tolerancePx = 18 } = options;\n\n // last pointerup (time & position)\n const last = { t: 0, x: 0, y: 0 };\n\n const handlePointerUp = (e: Event) => {\n const ev = e as PointerEvent;\n if (!onDouble) return;\n\n // ignore mouse (mouse uses native dblclick)\n // ignore non-primary pointers (multi-touch, etc.)\n if (ev.pointerType === 'mouse' || ev.isPrimary === false) return;\n\n const now = performance.now();\n const x = ev.clientX;\n const y = ev.clientY;\n\n const withinTime = now - last.t <= delay;\n const dx = x - last.x;\n const dy = y - last.y;\n const withinDist = dx * dx + dy * dy <= tolerancePx * tolerancePx;\n\n if (withinTime && withinDist) onDouble?.(ev);\n\n last.t = now;\n last.x = x;\n last.y = y;\n };\n\n const handleDblClick = (e: Event) => {\n onDouble?.(e as MouseEvent);\n };\n\n node.addEventListener('pointerup', handlePointerUp, { capture: true });\n node.addEventListener('dblclick', handleDblClick);\n\n return {\n update(next?: DoublePressOptions) {\n if (!next) return;\n onDouble = next.onDouble;\n // use nullish coalescing so 0 isn't swallowed accidentally (even though 0 isn't useful here)\n delay = next.delay ?? delay;\n tolerancePx = next.tolerancePx ?? tolerancePx;\n },\n destroy() {\n node.removeEventListener('pointerup', handlePointerUp, { capture: true } as any);\n node.removeEventListener('dblclick', handleDblClick);\n },\n };\n}\n","<script lang=\"ts\">\n import type { Snippet } from 'svelte';\n import type { Action } from 'svelte/action';\n import { getCounterRotation } from '@embedpdf/utils';\n import type { Rect, Rotation } from '@embedpdf/models';\n import type { MenuWrapperProps } from './types';\n\n interface CounterRotateProps {\n rect: Rect;\n rotation: Rotation;\n }\n\n interface CounterRotateChildrenProps {\n matrix: string;\n rect: Rect;\n menuWrapperProps: MenuWrapperProps;\n }\n\n interface Props extends CounterRotateProps {\n children?: Snippet<[CounterRotateChildrenProps]>;\n }\n\n let { rect, rotation, children }: Props = $props();\n const counterRotation = $derived(getCounterRotation(rect, rotation));\n\n // Svelte action for capture-phase event handling\n // This is the idiomatic way to attach lifecycle-managed behavior to DOM elements\n const menuWrapperAction: Action<HTMLElement> = (node) => {\n const handlePointerDown = (e: Event) => {\n // Stop propagation to prevent underlying layers from receiving the event\n e.stopPropagation();\n // DO NOT use e.preventDefault() here - it breaks click events on mobile/tablet!\n // preventDefault() stops the browser from generating click events from touch,\n // which makes buttons inside this container non-functional on touch devices.\n };\n\n const handleTouchStart = (e: Event) => {\n // Stop propagation to prevent underlying layers from receiving the event\n e.stopPropagation();\n // DO NOT use e.preventDefault() here - it breaks click events on mobile/tablet!\n };\n\n // Use capture phase to intercept before synthetic events\n node.addEventListener('pointerdown', handlePointerDown, { capture: true });\n node.addEventListener('touchstart', handleTouchStart, { capture: true });\n\n return {\n destroy() {\n node.removeEventListener('pointerdown', handlePointerDown, { capture: true });\n node.removeEventListener('touchstart', handleTouchStart, { capture: true });\n },\n };\n };\n\n const menuWrapperStyle = $derived(\n `position: absolute; ` +\n `left: ${rect.origin.x}px; ` +\n `top: ${rect.origin.y}px; ` +\n `transform: ${counterRotation.matrix}; ` +\n `transform-origin: 0 0; ` +\n `width: ${counterRotation.width}px; ` +\n `height: ${counterRotation.height}px; ` +\n `pointer-events: none; ` +\n `z-index: 3`,\n );\n\n const menuWrapperProps: MenuWrapperProps = $derived({\n style: menuWrapperStyle,\n action: menuWrapperAction,\n });\n</script>\n\n{#if children}\n {@render children({\n menuWrapperProps,\n matrix: counterRotation.matrix,\n rect: {\n origin: { x: rect.origin.x, y: rect.origin.y },\n size: { width: counterRotation.width, height: counterRotation.height },\n },\n })}\n{/if}\n","/**\n * Converts Svelte proxy objects to plain JavaScript objects.\n * This is useful when passing data to Web Workers or other contexts\n * that cannot handle Svelte's reactive proxies.\n *\n * Inspired by the Vue implementation, this recursively traverses the object\n * and handles primitives, arrays, and plain objects while stripping reactive proxies.\n */\nexport function deepToRaw<T extends Record<string, any>>(sourceObj: T): T {\n const objectIterator = (input: any): any => {\n // Handle null and undefined\n if (input === null || input === undefined) {\n return input;\n }\n\n // Handle primitives (string, number, boolean, bigint, symbol)\n if (typeof input !== 'object') {\n return input;\n }\n\n // Handle Arrays\n if (Array.isArray(input)) {\n return input.map((item) => objectIterator(item));\n }\n\n // Handle Date objects\n if (input instanceof Date) {\n return new Date(input.getTime());\n }\n\n // Handle RegExp\n if (input instanceof RegExp) {\n return new RegExp(input.source, input.flags);\n }\n\n // Handle plain objects (including Svelte proxies)\n // For Svelte proxies, we recursively extract plain values\n if (Object.prototype.toString.call(input) === '[object Object]') {\n return Object.keys(input).reduce((acc, key) => {\n // Skip non-enumerable properties and functions\n const value = input[key];\n if (typeof value !== 'function') {\n acc[key as keyof typeof acc] = objectIterator(value);\n }\n return acc;\n }, {} as T);\n }\n\n // For other object types (Map, Set, etc.), use JSON roundtrip as fallback\n // This will convert them to plain objects/arrays\n try {\n return JSON.parse(JSON.stringify(input));\n } catch {\n // If JSON serialization fails, return undefined\n return undefined;\n }\n };\n\n return objectIterator(sourceObj);\n}\n"],"names":["onUpdate","enabled"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.js","sources":["../../src/shared/plugin-interaction-primitives/drag-resize-controller.ts","../../src/shared/plugin-interaction-primitives/utils.ts","../../src/svelte/hooks/use-drag-resize.svelte.ts","../../src/svelte/utils/styles-to-string.ts","../../src/svelte/hooks/use-interaction-handles.svelte.ts","../../src/svelte/actions/doublePress.ts","../../src/svelte/components/CounterRotateContainer.svelte","../../src/svelte/utils/deep-to-raw.ts"],"sourcesContent":["import { Position, Rect } from '@embedpdf/models';\n\nexport interface DragResizeConfig {\n element: Rect;\n vertices?: Position[];\n constraints?: {\n minWidth?: number;\n minHeight?: number;\n maxWidth?: number;\n maxHeight?: number;\n boundingBox?: { width: number; height: number }; // page bounds\n };\n maintainAspectRatio?: boolean;\n pageRotation?: number;\n scale?: number;\n}\n\nexport type InteractionState = 'idle' | 'dragging' | 'resizing' | 'vertex-editing';\nexport type ResizeHandle = 'nw' | 'ne' | 'sw' | 'se' | 'n' | 'e' | 's' | 'w';\n\nexport interface TransformData {\n type: 'move' | 'resize' | 'vertex-edit';\n changes: {\n rect?: Rect;\n vertices?: Position[];\n };\n metadata?: {\n handle?: ResizeHandle;\n vertexIndex?: number;\n maintainAspectRatio?: boolean;\n };\n}\n\nexport interface InteractionEvent {\n state: 'start' | 'move' | 'end';\n transformData?: TransformData;\n}\n\n/** Anchor describes which edges stay fixed when resizing. */\ntype Anchor = {\n x: 'left' | 'right' | 'center';\n y: 'top' | 'bottom' | 'center';\n};\n\n/**\n * Derive anchor from handle.\n * - 'e' means we're dragging east → left edge is anchored\n * - 'nw' means we're dragging north-west → bottom-right corner is anchored\n */\nfunction getAnchor(handle: ResizeHandle): Anchor {\n return {\n x: handle.includes('e') ? 'left' : handle.includes('w') ? 'right' : 'center',\n y: handle.includes('s') ? 'top' : handle.includes('n') ? 'bottom' : 'center',\n };\n}\n\n/**\n * Pure geometric controller that manages drag/resize/vertex-edit logic.\n */\nexport class DragResizeController {\n private state: InteractionState = 'idle';\n private startPoint: Position | null = null;\n private startElement: Rect | null = null;\n private activeHandle: ResizeHandle | null = null;\n private currentPosition: Rect | null = null;\n\n // Vertex editing state - pure geometric\n private activeVertexIndex: number | null = null;\n private startVertices: Position[] = [];\n private currentVertices: Position[] = [];\n\n constructor(\n private config: DragResizeConfig,\n private onUpdate: (event: InteractionEvent) => void,\n ) {\n this.currentVertices = config.vertices || [];\n }\n\n updateConfig(config: Partial<DragResizeConfig>) {\n this.config = { ...this.config, ...config };\n this.currentVertices = config.vertices || [];\n }\n\n startDrag(clientX: number, clientY: number) {\n this.state = 'dragging';\n this.startPoint = { x: clientX, y: clientY };\n this.startElement = { ...this.config.element };\n this.currentPosition = { ...this.config.element };\n\n this.onUpdate({\n state: 'start',\n transformData: {\n type: 'move',\n changes: {\n rect: this.startElement,\n },\n },\n });\n }\n\n startResize(handle: ResizeHandle, clientX: number, clientY: number) {\n this.state = 'resizing';\n this.activeHandle = handle;\n this.startPoint = { x: clientX, y: clientY };\n this.startElement = { ...this.config.element };\n this.currentPosition = { ...this.config.element };\n\n this.onUpdate({\n state: 'start',\n transformData: {\n type: 'resize',\n changes: {\n rect: this.startElement,\n },\n metadata: {\n handle: this.activeHandle,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n }\n\n startVertexEdit(vertexIndex: number, clientX: number, clientY: number) {\n // Refresh vertices from latest config before validating index\n this.currentVertices = [...(this.config.vertices ?? this.currentVertices)];\n if (vertexIndex < 0 || vertexIndex >= this.currentVertices.length) return;\n\n this.state = 'vertex-editing';\n this.activeVertexIndex = vertexIndex;\n this.startPoint = { x: clientX, y: clientY };\n this.startVertices = [...this.currentVertices];\n\n this.onUpdate({\n state: 'start',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices: this.startVertices,\n },\n metadata: {\n vertexIndex,\n },\n },\n });\n }\n\n move(clientX: number, clientY: number) {\n if (this.state === 'idle' || !this.startPoint) return;\n\n if (this.state === 'dragging' && this.startElement) {\n const delta = this.calculateDelta(clientX, clientY);\n const position = this.calculateDragPosition(delta);\n this.currentPosition = position;\n\n this.onUpdate({\n state: 'move',\n transformData: {\n type: 'move',\n changes: {\n rect: position,\n },\n },\n });\n } else if (this.state === 'resizing' && this.activeHandle && this.startElement) {\n const delta = this.calculateDelta(clientX, clientY);\n const position = this.calculateResizePosition(delta, this.activeHandle);\n this.currentPosition = position;\n\n this.onUpdate({\n state: 'move',\n transformData: {\n type: 'resize',\n changes: {\n rect: position,\n },\n metadata: {\n handle: this.activeHandle,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n } else if (this.state === 'vertex-editing' && this.activeVertexIndex !== null) {\n const vertices = this.calculateVertexPosition(clientX, clientY);\n this.currentVertices = vertices;\n\n this.onUpdate({\n state: 'move',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices,\n },\n metadata: {\n vertexIndex: this.activeVertexIndex,\n },\n },\n });\n }\n }\n\n end() {\n if (this.state === 'idle') return;\n\n const wasState = this.state;\n const handle = this.activeHandle;\n const vertexIndex = this.activeVertexIndex;\n\n if (wasState === 'vertex-editing') {\n this.onUpdate({\n state: 'end',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices: this.currentVertices,\n },\n metadata: {\n vertexIndex: vertexIndex || undefined,\n },\n },\n });\n } else {\n const finalPosition = this.getCurrentPosition();\n this.onUpdate({\n state: 'end',\n transformData: {\n type: wasState === 'dragging' ? 'move' : 'resize',\n changes: {\n rect: finalPosition,\n },\n metadata:\n wasState === 'dragging'\n ? undefined\n : {\n handle: handle || undefined,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n }\n\n this.reset();\n }\n\n cancel() {\n if (this.state === 'idle') return;\n\n if (this.state === 'vertex-editing') {\n this.onUpdate({\n state: 'end',\n transformData: {\n type: 'vertex-edit',\n changes: {\n vertices: this.startVertices,\n },\n metadata: {\n vertexIndex: this.activeVertexIndex || undefined,\n },\n },\n });\n } else if (this.startElement) {\n this.onUpdate({\n state: 'end',\n transformData: {\n type: this.state === 'dragging' ? 'move' : 'resize',\n changes: {\n rect: this.startElement,\n },\n metadata:\n this.state === 'dragging'\n ? undefined\n : {\n handle: this.activeHandle || undefined,\n maintainAspectRatio: this.config.maintainAspectRatio,\n },\n },\n });\n }\n\n this.reset();\n }\n\n private reset() {\n this.state = 'idle';\n this.startPoint = null;\n this.startElement = null;\n this.activeHandle = null;\n this.currentPosition = null;\n this.activeVertexIndex = null;\n this.startVertices = [];\n }\n\n private getCurrentPosition() {\n return this.currentPosition || this.config.element;\n }\n\n private calculateDelta(clientX: number, clientY: number): Position {\n if (!this.startPoint) return { x: 0, y: 0 };\n\n const rawDelta: Position = {\n x: clientX - this.startPoint.x,\n y: clientY - this.startPoint.y,\n };\n\n return this.transformDelta(rawDelta);\n }\n\n private transformDelta(delta: Position): Position {\n const { pageRotation = 0, scale = 1 } = this.config;\n\n const rad = (pageRotation * Math.PI) / 2;\n const cos = Math.cos(rad);\n const sin = Math.sin(rad);\n\n const scaledX = delta.x / scale;\n const scaledY = delta.y / scale;\n\n return {\n x: cos * scaledX + sin * scaledY,\n y: -sin * scaledX + cos * scaledY,\n };\n }\n\n private clampPoint(p: Position): Position {\n const bbox = this.config.constraints?.boundingBox;\n if (!bbox) return p;\n return {\n x: Math.max(0, Math.min(p.x, bbox.width)),\n y: Math.max(0, Math.min(p.y, bbox.height)),\n };\n }\n\n private calculateVertexPosition(clientX: number, clientY: number): Position[] {\n if (this.activeVertexIndex === null) return this.startVertices;\n\n const delta = this.calculateDelta(clientX, clientY);\n const newVertices = [...this.startVertices];\n const currentVertex = newVertices[this.activeVertexIndex];\n\n const moved = {\n x: currentVertex.x + delta.x,\n y: currentVertex.y + delta.y,\n };\n newVertices[this.activeVertexIndex] = this.clampPoint(moved);\n\n return newVertices;\n }\n\n private calculateDragPosition(delta: Position): Rect {\n if (!this.startElement) return this.config.element;\n\n const position: Rect = {\n origin: {\n x: this.startElement.origin.x + delta.x,\n y: this.startElement.origin.y + delta.y,\n },\n size: {\n width: this.startElement.size.width,\n height: this.startElement.size.height,\n },\n };\n\n return this.applyConstraints(position);\n }\n\n /**\n * Calculate the new rect after a resize operation.\n * Pipeline: applyDelta → enforceAspectRatio → clampToBounds → applyConstraints\n */\n private calculateResizePosition(delta: Position, handle: ResizeHandle): Rect {\n if (!this.startElement) return this.config.element;\n\n const anchor = getAnchor(handle);\n const aspectRatio = this.startElement.size.width / this.startElement.size.height || 1;\n\n // Step 1: Apply delta to get raw resize\n let rect = this.applyResizeDelta(delta, anchor);\n\n // Step 2: Enforce aspect ratio if enabled\n if (this.config.maintainAspectRatio) {\n rect = this.enforceAspectRatio(rect, anchor, aspectRatio);\n }\n\n // Step 3: Clamp to bounding box\n rect = this.clampToBounds(rect, anchor, aspectRatio);\n\n // Step 4: Apply min/max constraints\n return this.applyConstraints(rect);\n }\n\n /**\n * Apply the mouse delta to produce a raw (unconstrained) resized rect.\n */\n private applyResizeDelta(delta: Position, anchor: Anchor): Rect {\n const start = this.startElement!;\n let x = start.origin.x;\n let y = start.origin.y;\n let width = start.size.width;\n let height = start.size.height;\n\n // Horizontal: if anchor is left, right edge moves; if anchor is right, left edge moves\n if (anchor.x === 'left') {\n width += delta.x;\n } else if (anchor.x === 'right') {\n x += delta.x;\n width -= delta.x;\n }\n // anchor.x === 'center' means no horizontal resize from this handle\n\n // Vertical: if anchor is top, bottom edge moves; if anchor is bottom, top edge moves\n if (anchor.y === 'top') {\n height += delta.y;\n } else if (anchor.y === 'bottom') {\n y += delta.y;\n height -= delta.y;\n }\n\n return { origin: { x, y }, size: { width, height } };\n }\n\n /**\n * Enforce aspect ratio while respecting the anchor.\n * For edge handles (center anchor on one axis), the rect expands symmetrically on that axis.\n * For corner handles, the anchor corner stays fixed.\n */\n private enforceAspectRatio(rect: Rect, anchor: Anchor, aspectRatio: number): Rect {\n const start = this.startElement!;\n let { x, y } = rect.origin;\n let { width, height } = rect.size;\n\n const isEdgeHandle = anchor.x === 'center' || anchor.y === 'center';\n\n if (isEdgeHandle) {\n // Edge handle: one dimension drives, the other follows, centered on the non-moving axis\n if (anchor.y === 'center') {\n // Horizontal edge (e/w): width is primary\n height = width / aspectRatio;\n // Center vertically relative to original\n y = start.origin.y + (start.size.height - height) / 2;\n } else {\n // Vertical edge (n/s): height is primary\n width = height * aspectRatio;\n // Center horizontally relative to original\n x = start.origin.x + (start.size.width - width) / 2;\n }\n } else {\n // Corner handle: pick the dominant axis based on which changed more\n const dw = Math.abs(width - start.size.width);\n const dh = Math.abs(height - start.size.height);\n\n if (dw >= dh) {\n height = width / aspectRatio;\n } else {\n width = height * aspectRatio;\n }\n }\n\n // Reposition based on anchor\n if (anchor.x === 'right') {\n x = start.origin.x + start.size.width - width;\n }\n if (anchor.y === 'bottom') {\n y = start.origin.y + start.size.height - height;\n }\n\n return { origin: { x, y }, size: { width, height } };\n }\n\n /**\n * Clamp rect to bounding box while respecting anchor and aspect ratio.\n */\n private clampToBounds(rect: Rect, anchor: Anchor, aspectRatio: number): Rect {\n const bbox = this.config.constraints?.boundingBox;\n if (!bbox) return rect;\n\n const start = this.startElement!;\n let { x, y } = rect.origin;\n let { width, height } = rect.size;\n\n // Ensure positive dimensions\n width = Math.max(1, width);\n height = Math.max(1, height);\n\n // Calculate anchor points (the edges/corners that must stay fixed)\n const anchorX = anchor.x === 'left' ? start.origin.x : start.origin.x + start.size.width;\n const anchorY = anchor.y === 'top' ? start.origin.y : start.origin.y + start.size.height;\n\n // Calculate max available space from anchor\n const maxW =\n anchor.x === 'left'\n ? bbox.width - anchorX\n : anchor.x === 'right'\n ? anchorX\n : Math.min(start.origin.x, bbox.width - start.origin.x - start.size.width) * 2 +\n start.size.width;\n\n const maxH =\n anchor.y === 'top'\n ? bbox.height - anchorY\n : anchor.y === 'bottom'\n ? anchorY\n : Math.min(start.origin.y, bbox.height - start.origin.y - start.size.height) * 2 +\n start.size.height;\n\n if (this.config.maintainAspectRatio) {\n // Find the scaling factor that fits both constraints\n const scaleW = width > maxW ? maxW / width : 1;\n const scaleH = height > maxH ? maxH / height : 1;\n const scale = Math.min(scaleW, scaleH);\n\n if (scale < 1) {\n width *= scale;\n height *= scale;\n }\n } else {\n // Clamp independently\n width = Math.min(width, maxW);\n height = Math.min(height, maxH);\n }\n\n // Recompute position based on anchor\n if (anchor.x === 'left') {\n x = anchorX;\n } else if (anchor.x === 'right') {\n x = anchorX - width;\n } else {\n x = start.origin.x + (start.size.width - width) / 2;\n }\n\n if (anchor.y === 'top') {\n y = anchorY;\n } else if (anchor.y === 'bottom') {\n y = anchorY - height;\n } else {\n y = start.origin.y + (start.size.height - height) / 2;\n }\n\n // Final clamp to ensure we're within bounds (handles center anchor edge cases)\n x = Math.max(0, Math.min(x, bbox.width - width));\n y = Math.max(0, Math.min(y, bbox.height - height));\n\n return { origin: { x, y }, size: { width, height } };\n }\n\n private applyConstraints(position: Rect): Rect {\n const { constraints } = this.config;\n if (!constraints) return position;\n\n let {\n origin: { x, y },\n size: { width, height },\n } = position;\n\n const minW = constraints.minWidth ?? 1;\n const minH = constraints.minHeight ?? 1;\n const maxW = constraints.maxWidth;\n const maxH = constraints.maxHeight;\n\n if (this.config.maintainAspectRatio && width > 0 && height > 0) {\n const ratio = width / height;\n\n // Enforce mins (scale up)\n if (width < minW) {\n width = minW;\n height = width / ratio;\n }\n if (height < minH) {\n height = minH;\n width = height * ratio;\n }\n\n // Enforce maxes (scale down)\n if (maxW !== undefined && width > maxW) {\n width = maxW;\n height = width / ratio;\n }\n if (maxH !== undefined && height > maxH) {\n height = maxH;\n width = height * ratio;\n }\n } else {\n width = Math.max(minW, width);\n height = Math.max(minH, height);\n if (maxW !== undefined) width = Math.min(maxW, width);\n if (maxH !== undefined) height = Math.min(maxH, height);\n }\n\n // Clamp position to bounding box\n if (constraints.boundingBox) {\n x = Math.max(0, Math.min(x, constraints.boundingBox.width - width));\n y = Math.max(0, Math.min(y, constraints.boundingBox.height - height));\n }\n\n return { origin: { x, y }, size: { width, height } };\n }\n}\n","import type { Position, Rect } from '@embedpdf/models';\nimport type { ResizeHandle, DragResizeConfig } from './drag-resize-controller';\n\nexport type QuarterTurns = 0 | 1 | 2 | 3;\n\nexport interface ResizeUI {\n handleSize?: number; // px (default 8)\n spacing?: number; // px distance from the box edge (default 1)\n offsetMode?: 'outside' | 'inside' | 'center'; // default 'outside'\n includeSides?: boolean; // default false\n zIndex?: number; // default 3\n rotationAwareCursor?: boolean; // default true\n}\n\nexport interface VertexUI {\n vertexSize?: number; // px (default 12)\n zIndex?: number; // default 4\n}\n\nexport interface HandleDescriptor {\n handle: ResizeHandle;\n style: Record<string, number | string>;\n attrs?: Record<string, any>;\n}\n\nfunction diagonalCursor(handle: ResizeHandle, rot: QuarterTurns): string {\n // Standard cursors; diagonals flip on odd quarter-turns\n const diag0: Record<'nw' | 'ne' | 'sw' | 'se', string> = {\n nw: 'nwse-resize',\n ne: 'nesw-resize',\n sw: 'nesw-resize',\n se: 'nwse-resize',\n };\n if (handle === 'n' || handle === 's') return 'ns-resize';\n if (handle === 'e' || handle === 'w') return 'ew-resize';\n if (rot % 2 === 0) return diag0[handle as 'nw' | 'ne' | 'sw' | 'se'];\n return { nw: 'nesw-resize', ne: 'nwse-resize', sw: 'nwse-resize', se: 'nesw-resize' }[\n handle as 'nw' | 'ne' | 'sw' | 'se'\n ]!;\n}\n\nfunction edgeOffset(k: number, spacing: number, mode: 'outside' | 'inside' | 'center') {\n // Base puts the handle centered on the edge\n const base = -k / 2;\n if (mode === 'center') return base;\n // outside moves further out (more negative), inside moves in (less negative)\n return mode === 'outside' ? base - spacing : base + spacing;\n}\n\nexport function describeResizeFromConfig(\n cfg: DragResizeConfig,\n ui: ResizeUI = {},\n): HandleDescriptor[] {\n const {\n handleSize = 8,\n spacing = 1,\n offsetMode = 'outside',\n includeSides = false,\n zIndex = 3,\n rotationAwareCursor = true,\n } = ui;\n\n const rotation = ((cfg.pageRotation ?? 0) % 4) as QuarterTurns;\n\n const off = (edge: 'top' | 'right' | 'bottom' | 'left') => ({\n [edge]: edgeOffset(handleSize, spacing, offsetMode) + 'px',\n });\n\n const corners: Array<[ResizeHandle, Record<string, number | string>]> = [\n ['nw', { ...off('top'), ...off('left') }],\n ['ne', { ...off('top'), ...off('right') }],\n ['sw', { ...off('bottom'), ...off('left') }],\n ['se', { ...off('bottom'), ...off('right') }],\n ];\n const sides: Array<[ResizeHandle, Record<string, number | string>]> = includeSides\n ? [\n ['n', { ...off('top'), left: `calc(50% - ${handleSize / 2}px)` }],\n ['s', { ...off('bottom'), left: `calc(50% - ${handleSize / 2}px)` }],\n ['w', { ...off('left'), top: `calc(50% - ${handleSize / 2}px)` }],\n ['e', { ...off('right'), top: `calc(50% - ${handleSize / 2}px)` }],\n ]\n : [];\n\n const all = [...corners, ...sides];\n\n return all.map(([handle, pos]) => ({\n handle,\n style: {\n position: 'absolute',\n width: handleSize + 'px',\n height: handleSize + 'px',\n borderRadius: '50%',\n zIndex,\n cursor: rotationAwareCursor ? diagonalCursor(handle, rotation) : 'default',\n touchAction: 'none',\n ...(pos as any),\n },\n attrs: { 'data-epdf-handle': handle },\n }));\n}\n\nexport function describeVerticesFromConfig(\n cfg: DragResizeConfig,\n ui: VertexUI = {},\n liveVertices?: Position[],\n): HandleDescriptor[] {\n const { vertexSize = 12, zIndex = 4 } = ui;\n const rect: Rect = cfg.element;\n const scale = cfg.scale ?? 1;\n const verts = liveVertices ?? cfg.vertices ?? [];\n\n return verts.map((v, i) => {\n const left = (v.x - rect.origin.x) * scale - vertexSize / 2;\n const top = (v.y - rect.origin.y) * scale - vertexSize / 2;\n return {\n handle: 'nw', // not used; kept for type\n style: {\n position: 'absolute',\n left: left + 'px',\n top: top + 'px',\n width: vertexSize + 'px',\n height: vertexSize + 'px',\n borderRadius: '50%',\n cursor: 'pointer',\n zIndex,\n touchAction: 'none',\n },\n attrs: { 'data-epdf-vertex': i },\n };\n });\n}\n","import {\n type DragResizeConfig,\n DragResizeController,\n type InteractionEvent,\n type ResizeHandle,\n} from '../../shared/plugin-interaction-primitives';\n\nexport interface UseDragResizeOptions extends DragResizeConfig {\n onUpdate?: (event: InteractionEvent) => void;\n enabled?: boolean;\n}\n\nexport interface ResizeHandleEventProps {\n onpointerdown: (e: PointerEvent) => void;\n onpointermove: (e: PointerEvent) => void;\n onpointerup: (e: PointerEvent) => void;\n onpointercancel: (e: PointerEvent) => void;\n}\n\nexport function useDragResize(getOptions: () => UseDragResizeOptions) {\n // Use getter function to maintain reactivity\n const config = $derived.by(() => {\n const opts = getOptions();\n const { onUpdate, enabled, ...rest } = opts;\n return rest;\n });\n\n const enabled = $derived(getOptions().enabled ?? true);\n const onUpdate = $derived(getOptions().onUpdate);\n\n let controller = $state<DragResizeController | null>(null);\n\n // Initialize or update controller\n $effect(() => {\n if (!controller) {\n controller = new DragResizeController(config, (event) => onUpdate?.(event));\n } else {\n controller.updateConfig(config);\n }\n });\n\n const handleDragStart = (e: PointerEvent) => {\n if (!enabled) return;\n e.preventDefault();\n e.stopPropagation();\n controller?.startDrag(e.clientX, e.clientY);\n (e.currentTarget as HTMLElement).setPointerCapture(e.pointerId);\n };\n\n const handleMove = (e: PointerEvent) => {\n e.preventDefault();\n e.stopPropagation();\n controller?.move(e.clientX, e.clientY);\n };\n\n const handleEnd = (e: PointerEvent) => {\n e.preventDefault();\n e.stopPropagation();\n controller?.end();\n (e.currentTarget as HTMLElement).releasePointerCapture?.(e.pointerId);\n };\n\n const createResizeHandler = (handle: ResizeHandle): ResizeHandleEventProps => ({\n onpointerdown: (e: PointerEvent) => {\n if (!enabled) return;\n e.preventDefault();\n e.stopPropagation();\n controller?.startResize(handle, e.clientX, e.clientY);\n (e.currentTarget as HTMLElement).setPointerCapture(e.pointerId);\n },\n onpointermove: handleMove,\n onpointerup: handleEnd,\n onpointercancel: handleEnd,\n });\n\n const createVertexHandler = (vertexIndex: number): ResizeHandleEventProps => ({\n onpointerdown: (e: PointerEvent) => {\n if (!enabled) return;\n e.preventDefault();\n e.stopPropagation();\n controller?.startVertexEdit(vertexIndex, e.clientX, e.clientY);\n (e.currentTarget as HTMLElement).setPointerCapture(e.pointerId);\n },\n onpointermove: handleMove,\n onpointerup: handleEnd,\n onpointercancel: handleEnd,\n });\n\n const dragProps = $derived(\n enabled\n ? {\n onpointerdown: handleDragStart,\n onpointermove: handleMove,\n onpointerup: handleEnd,\n onpointercancel: handleEnd,\n }\n : {},\n );\n\n return {\n get dragProps() {\n return dragProps;\n },\n createResizeProps: createResizeHandler,\n createVertexProps: createVertexHandler,\n };\n}\n","/**\n * Converts a style object with camelCase properties to a CSS string with kebab-case properties.\n *\n * This is useful in Svelte 5 where spreading style objects doesn't work with the `style:` directive.\n * Instead, you can convert the entire style object to a string and apply it to the `style` attribute.\n *\n * @param style - An object containing CSS properties in camelCase format with string or number values\n * @returns A CSS string with kebab-case properties suitable for the HTML style attribute\n *\n * @example\n * ```ts\n * const styles = {\n * position: 'absolute',\n * zIndex: 10,\n * borderRadius: '50%',\n * backgroundColor: '#007ACC'\n * };\n *\n * const cssString = stylesToString(styles);\n * // Returns: \"position: absolute; z-index: 10; border-radius: 50%; background-color: #007ACC\"\n * ```\n *\n * @example\n * Usage in Svelte templates:\n * ```svelte\n * <div style=\"{stylesToString(myStyles)}; color: red;\"></div>\n * ```\n */\nexport function stylesToString(style: Record<string, string | number>): string {\n return Object.entries(style)\n .map(([key, value]) => {\n const cssKey = key.replace(/[A-Z]/g, (m) => `-${m.toLowerCase()}`);\n return `${cssKey}: ${value}`;\n })\n .join('; ');\n}\n","import { useDragResize, type UseDragResizeOptions } from './use-drag-resize.svelte';\nimport {\n describeResizeFromConfig,\n describeVerticesFromConfig,\n type ResizeUI,\n type VertexUI,\n} from '../../shared/plugin-interaction-primitives';\nimport { stylesToString } from '../utils/styles-to-string';\n\nexport type HandleElementProps = {\n key: string | number;\n style: string;\n onpointerdown: (e: PointerEvent) => void;\n onpointermove: (e: PointerEvent) => void;\n onpointerup: (e: PointerEvent) => void;\n onpointercancel: (e: PointerEvent) => void;\n} & Record<string, any>;\n\nexport function useInteractionHandles(\n getOpts: () => {\n controller: UseDragResizeOptions;\n resizeUI?: ResizeUI;\n vertexUI?: VertexUI;\n includeVertices?: boolean;\n handleAttrs?: (\n h: 'nw' | 'ne' | 'sw' | 'se' | 'n' | 'e' | 's' | 'w',\n ) => Record<string, any> | void;\n vertexAttrs?: (i: number) => Record<string, any> | void;\n },\n) {\n // Use getter function and $derived to maintain reactivity\n const controller = $derived(getOpts().controller);\n const resizeUI = $derived(getOpts().resizeUI);\n const vertexUI = $derived(getOpts().vertexUI);\n const includeVertices = $derived(getOpts().includeVertices ?? false);\n const handleAttrs = $derived(getOpts().handleAttrs);\n const vertexAttrs = $derived(getOpts().vertexAttrs);\n\n const dragResize = useDragResize(() => controller);\n\n // Resize handles: computed from controller config\n const resize = $derived.by((): HandleElementProps[] => {\n const desc = describeResizeFromConfig(controller, resizeUI);\n return desc.map((d) => ({\n key: d.attrs?.['data-epdf-handle'] as string,\n style: stylesToString(d.style),\n ...dragResize.createResizeProps(d.handle),\n ...(d.attrs ?? {}),\n ...(handleAttrs?.(d.handle) ?? {}),\n }));\n });\n\n // Vertex handles: computed from controller config and vertices\n const vertices = $derived.by((): HandleElementProps[] => {\n if (!includeVertices) return [];\n const desc = describeVerticesFromConfig(controller, vertexUI, controller.vertices);\n return desc.map((d, i) => ({\n key: i,\n style: stylesToString(d.style),\n ...dragResize.createVertexProps(i),\n ...(d.attrs ?? {}),\n ...(vertexAttrs?.(i) ?? {}),\n }));\n });\n\n // Return getters to maintain reactivity when accessed from outside\n return {\n get dragProps() {\n return dragResize.dragProps;\n },\n get resize() {\n return resize;\n },\n get vertices() {\n return vertices;\n },\n };\n}\n","export type DoublePressOptions = {\n delay?: number; // ms between taps\n tolerancePx?: number; // spatial tolerance\n onDouble?: (e: PointerEvent | MouseEvent) => void;\n};\n\nexport function doublePress<T extends Element = Element>(\n node: T,\n options: DoublePressOptions = {},\n) {\n let { onDouble, delay = 300, tolerancePx = 18 } = options;\n\n // last pointerup (time & position)\n const last = { t: 0, x: 0, y: 0 };\n\n const handlePointerUp = (e: Event) => {\n const ev = e as PointerEvent;\n if (!onDouble) return;\n\n // ignore mouse (mouse uses native dblclick)\n // ignore non-primary pointers (multi-touch, etc.)\n if (ev.pointerType === 'mouse' || ev.isPrimary === false) return;\n\n const now = performance.now();\n const x = ev.clientX;\n const y = ev.clientY;\n\n const withinTime = now - last.t <= delay;\n const dx = x - last.x;\n const dy = y - last.y;\n const withinDist = dx * dx + dy * dy <= tolerancePx * tolerancePx;\n\n if (withinTime && withinDist) onDouble?.(ev);\n\n last.t = now;\n last.x = x;\n last.y = y;\n };\n\n const handleDblClick = (e: Event) => {\n onDouble?.(e as MouseEvent);\n };\n\n node.addEventListener('pointerup', handlePointerUp, { capture: true });\n node.addEventListener('dblclick', handleDblClick);\n\n return {\n update(next?: DoublePressOptions) {\n if (!next) return;\n onDouble = next.onDouble;\n // use nullish coalescing so 0 isn't swallowed accidentally (even though 0 isn't useful here)\n delay = next.delay ?? delay;\n tolerancePx = next.tolerancePx ?? tolerancePx;\n },\n destroy() {\n node.removeEventListener('pointerup', handlePointerUp, { capture: true } as any);\n node.removeEventListener('dblclick', handleDblClick);\n },\n };\n}\n","<script lang=\"ts\">\n import type { Snippet } from 'svelte';\n import type { Action } from 'svelte/action';\n import { getCounterRotation } from '@embedpdf/utils';\n import type { Rect, Rotation } from '@embedpdf/models';\n import type { MenuWrapperProps } from './types';\n\n interface CounterRotateProps {\n rect: Rect;\n rotation: Rotation;\n }\n\n interface CounterRotateChildrenProps {\n matrix: string;\n rect: Rect;\n menuWrapperProps: MenuWrapperProps;\n }\n\n interface Props extends CounterRotateProps {\n children?: Snippet<[CounterRotateChildrenProps]>;\n }\n\n let { rect, rotation, children }: Props = $props();\n const counterRotation = $derived(getCounterRotation(rect, rotation));\n\n // Svelte action for capture-phase event handling\n // This is the idiomatic way to attach lifecycle-managed behavior to DOM elements\n const menuWrapperAction: Action<HTMLElement> = (node) => {\n const handlePointerDown = (e: Event) => {\n // Stop propagation to prevent underlying layers from receiving the event\n e.stopPropagation();\n // DO NOT use e.preventDefault() here - it breaks click events on mobile/tablet!\n // preventDefault() stops the browser from generating click events from touch,\n // which makes buttons inside this container non-functional on touch devices.\n };\n\n const handleTouchStart = (e: Event) => {\n // Stop propagation to prevent underlying layers from receiving the event\n e.stopPropagation();\n // DO NOT use e.preventDefault() here - it breaks click events on mobile/tablet!\n };\n\n // Use capture phase to intercept before synthetic events\n node.addEventListener('pointerdown', handlePointerDown, { capture: true });\n node.addEventListener('touchstart', handleTouchStart, { capture: true });\n\n return {\n destroy() {\n node.removeEventListener('pointerdown', handlePointerDown, { capture: true });\n node.removeEventListener('touchstart', handleTouchStart, { capture: true });\n },\n };\n };\n\n const menuWrapperStyle = $derived(\n `position: absolute; ` +\n `left: ${rect.origin.x}px; ` +\n `top: ${rect.origin.y}px; ` +\n `transform: ${counterRotation.matrix}; ` +\n `transform-origin: 0 0; ` +\n `width: ${counterRotation.width}px; ` +\n `height: ${counterRotation.height}px; ` +\n `pointer-events: none; ` +\n `z-index: 3`,\n );\n\n const menuWrapperProps: MenuWrapperProps = $derived({\n style: menuWrapperStyle,\n action: menuWrapperAction,\n });\n</script>\n\n{#if children}\n {@render children({\n menuWrapperProps,\n matrix: counterRotation.matrix,\n rect: {\n origin: { x: rect.origin.x, y: rect.origin.y },\n size: { width: counterRotation.width, height: counterRotation.height },\n },\n })}\n{/if}\n","/**\n * Converts Svelte proxy objects to plain JavaScript objects.\n * This is useful when passing data to Web Workers or other contexts\n * that cannot handle Svelte's reactive proxies.\n *\n * Inspired by the Vue implementation, this recursively traverses the object\n * and handles primitives, arrays, and plain objects while stripping reactive proxies.\n */\nexport function deepToRaw<T extends Record<string, any>>(sourceObj: T): T {\n const objectIterator = (input: any): any => {\n // Handle null and undefined\n if (input === null || input === undefined) {\n return input;\n }\n\n // Handle primitives (string, number, boolean, bigint, symbol)\n if (typeof input !== 'object') {\n return input;\n }\n\n // Handle Arrays\n if (Array.isArray(input)) {\n return input.map((item) => objectIterator(item));\n }\n\n // Handle Date objects\n if (input instanceof Date) {\n return new Date(input.getTime());\n }\n\n // Handle RegExp\n if (input instanceof RegExp) {\n return new RegExp(input.source, input.flags);\n }\n\n // Handle plain objects (including Svelte proxies)\n // For Svelte proxies, we recursively extract plain values\n if (Object.prototype.toString.call(input) === '[object Object]') {\n return Object.keys(input).reduce((acc, key) => {\n // Skip non-enumerable properties and functions\n const value = input[key];\n if (typeof value !== 'function') {\n acc[key as keyof typeof acc] = objectIterator(value);\n }\n return acc;\n }, {} as T);\n }\n\n // For other object types (Map, Set, etc.), use JSON roundtrip as fallback\n // This will convert them to plain objects/arrays\n try {\n return JSON.parse(JSON.stringify(input));\n } catch {\n // If JSON serialization fails, return undefined\n return undefined;\n }\n };\n\n return objectIterator(sourceObj);\n}\n"],"names":["onUpdate","enabled"],"mappings":"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"}
|
package/dist/vue/index.cjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const t=require("vue"),e=require("@embedpdf/utils"),i=t.defineComponent({__name:"counter-rotate-container",props:{rect:{},rotation:{}},setup(i){const n=i,a=t.computed(()=>e.getCounterRotation(n.rect,n.rotation)),s=t.computed(()=>({style:{position:"absolute",left:`${n.rect.origin.x}px`,top:`${n.rect.origin.y}px`,transform:a.value.matrix,transformOrigin:"0 0",width:`${a.value.width}px`,height:`${a.value.height}px`,pointerEvents:"none",zIndex:3},onPointerdown:t=>{t.stopPropagation(),t.preventDefault()},onTouchstart:t=>{t.stopPropagation(),t.preventDefault()}})),r=t.computed(()=>({origin:{x:n.rect.origin.x,y:n.rect.origin.y},size:{width:a.value.width,height:a.value.height}}));return(e,i)=>t.renderSlot(e.$slots,"default",{menuWrapperProps:s.value,matrix:a.value.matrix,rect:r.value})}});class n{constructor(t,e){this.config=t,this.onUpdate=e,this.state="idle",this.startPoint=null,this.startElement=null,this.activeHandle=null,this.currentPosition=null,this.activeVertexIndex=null,this.startVertices=[],this.currentVertices=[],this.currentVertices=t.vertices||[]}updateConfig(t){this.config={...this.config,...t},this.currentVertices=t.vertices||[]}startDrag(t,e){this.state="dragging",this.startPoint={x:t,y:e},this.startElement={...this.config.element},this.currentPosition={...this.config.element},this.onUpdate({state:"start",transformData:{type:"move",changes:{rect:this.startElement}}})}startResize(t,e,i){this.state="resizing",this.activeHandle=t,this.startPoint={x:e,y:i},this.startElement={...this.config.element},this.currentPosition={...this.config.element},this.onUpdate({state:"start",transformData:{type:"resize",changes:{rect:this.startElement},metadata:{handle:this.activeHandle,maintainAspectRatio:this.config.maintainAspectRatio}}})}startVertexEdit(t,e,i){this.currentVertices=[...this.config.vertices??this.currentVertices],t<0||t>=this.currentVertices.length||(this.state="vertex-editing",this.activeVertexIndex=t,this.startPoint={x:e,y:i},this.startVertices=[...this.currentVertices],this.onUpdate({state:"start",transformData:{type:"vertex-edit",changes:{vertices:this.startVertices},metadata:{vertexIndex:t}}}))}move(t,e){if("idle"!==this.state&&this.startPoint)if("dragging"===this.state&&this.startElement){const i=this.calculateDelta(t,e),n=this.calculateDragPosition(i);this.currentPosition=n,this.onUpdate({state:"move",transformData:{type:"move",changes:{rect:n}}})}else if("resizing"===this.state&&this.activeHandle&&this.startElement){const i=this.calculateDelta(t,e),n=this.calculateResizePosition(i,this.activeHandle);this.currentPosition=n,this.onUpdate({state:"move",transformData:{type:"resize",changes:{rect:n},metadata:{handle:this.activeHandle,maintainAspectRatio:this.config.maintainAspectRatio}}})}else if("vertex-editing"===this.state&&null!==this.activeVertexIndex){const i=this.calculateVertexPosition(t,e);this.currentVertices=i,this.onUpdate({state:"move",transformData:{type:"vertex-edit",changes:{vertices:i},metadata:{vertexIndex:this.activeVertexIndex}}})}}end(){if("idle"===this.state)return;const t=this.state,e=this.activeHandle,i=this.activeVertexIndex;if("vertex-editing"===t)this.onUpdate({state:"end",transformData:{type:"vertex-edit",changes:{vertices:this.currentVertices},metadata:{vertexIndex:i||void 0}}});else{const i=this.getCurrentPosition();this.onUpdate({state:"end",transformData:{type:"dragging"===t?"move":"resize",changes:{rect:i},metadata:"dragging"===t?void 0:{handle:e||void 0,maintainAspectRatio:this.config.maintainAspectRatio}}})}this.reset()}cancel(){"idle"!==this.state&&("vertex-editing"===this.state?this.onUpdate({state:"end",transformData:{type:"vertex-edit",changes:{vertices:this.startVertices},metadata:{vertexIndex:this.activeVertexIndex||void 0}}}):this.startElement&&this.onUpdate({state:"end",transformData:{type:"dragging"===this.state?"move":"resize",changes:{rect:this.startElement},metadata:"dragging"===this.state?void 0:{handle:this.activeHandle||void 0,maintainAspectRatio:this.config.maintainAspectRatio}}}),this.reset())}reset(){this.state="idle",this.startPoint=null,this.startElement=null,this.activeHandle=null,this.currentPosition=null,this.activeVertexIndex=null,this.startVertices=[]}getCurrentPosition(){return this.currentPosition||this.config.element}calculateDelta(t,e){if(!this.startPoint)return{x:0,y:0};const i={x:t-this.startPoint.x,y:e-this.startPoint.y};return this.transformDelta(i)}transformDelta(t){const{pageRotation:e=0,scale:i=1}=this.config,n=e*Math.PI/2,a=Math.cos(n),s=Math.sin(n),r=t.x/i,o=t.y/i;return{x:a*r+s*o,y:-s*r+a*o}}clampPoint(t){var e;const i=null==(e=this.config.constraints)?void 0:e.boundingBox;return i?{x:Math.max(0,Math.min(t.x,i.width)),y:Math.max(0,Math.min(t.y,i.height))}:t}calculateVertexPosition(t,e){if(null===this.activeVertexIndex)return this.startVertices;const i=this.calculateDelta(t,e),n=[...this.startVertices],a=n[this.activeVertexIndex],s={x:a.x+i.x,y:a.y+i.y};return n[this.activeVertexIndex]=this.clampPoint(s),n}calculateDragPosition(t){if(!this.startElement)return this.config.element;const e={origin:{x:this.startElement.origin.x+t.x,y:this.startElement.origin.y+t.y},size:{width:this.startElement.size.width,height:this.startElement.size.height}};return this.applyConstraints(e)}calculateResizePosition(t,e){var i;if(!this.startElement)return this.config.element;let{origin:{x:n,y:a},size:{width:s,height:r}}=this.startElement;switch(e){case"se":s+=t.x,r+=t.y;break;case"sw":n+=t.x,s-=t.x,r+=t.y;break;case"ne":s+=t.x,a+=t.y,r-=t.y;break;case"nw":n+=t.x,s-=t.x,a+=t.y,r-=t.y;break;case"n":a+=t.y,r-=t.y;break;case"s":r+=t.y;break;case"e":s+=t.x;break;case"w":n+=t.x,s-=t.x}if(this.config.maintainAspectRatio&&this.startElement){const t=this.startElement.size.width/this.startElement.size.height;if(["n","s","e","w"].includes(e))if("n"===e||"s"===e){const e=r*t,i=e-s;s=e,n-=i/2}else{const i=s/t,o=i-r;r=i,"w"===e&&(n=this.startElement.origin.x+this.startElement.size.width-s),a-=o/2}else{Math.abs(s-this.startElement.size.width)>Math.abs(r-this.startElement.size.height)?r=s/t:s=r*t,e.includes("w")&&(n=this.startElement.origin.x+this.startElement.size.width-s),e.includes("n")&&(a=this.startElement.origin.y+this.startElement.size.height-r)}}const o=null==(i=this.config.constraints)?void 0:i.boundingBox;if(o)switch(e){case"e":s=Math.min(s,o.width-n);break;case"s":r=Math.min(r,o.height-a);break;case"se":s=Math.min(s,o.width-n),r=Math.min(r,o.height-a);break;case"w":n<0&&(s+=n,n=0);break;case"n":a<0&&(r+=a,a=0);break;case"sw":n<0&&(s+=n,n=0),r=Math.min(r,o.height-a);break;case"nw":n<0&&(s+=n,n=0),a<0&&(r+=a,a=0);break;case"ne":s=Math.min(s,o.width-n),a<0&&(r+=a,a=0)}return this.applyConstraints({origin:{x:n,y:a},size:{width:s,height:r}})}applyConstraints(t){const{constraints:e}=this.config;if(!e)return t;let{origin:{x:i,y:n},size:{width:a,height:s}}=t;return a=Math.max(e.minWidth||1,a),s=Math.max(e.minHeight||1,s),e.maxWidth&&(a=Math.min(e.maxWidth,a)),e.maxHeight&&(s=Math.min(e.maxHeight,s)),e.boundingBox&&(i=Math.max(0,Math.min(i,e.boundingBox.width-a)),n=Math.max(0,Math.min(n,e.boundingBox.height-s))),{origin:{x:i,y:n},size:{width:a,height:s}}}}function a(t,e){return"n"===t||"s"===t?"ns-resize":"e"===t||"w"===t?"ew-resize":e%2==0?{nw:"nwse-resize",ne:"nesw-resize",sw:"nesw-resize",se:"nwse-resize"}[t]:{nw:"nesw-resize",ne:"nwse-resize",sw:"nwse-resize",se:"nesw-resize"}[t]}function s(t,e,i){const n=-t/2;return"center"===i?n:"outside"===i?n-e:n+e}const r=e=>t.toRaw(t.isRef(e)?t.unref(e):e),o=(t,e=0)=>{const i=Number(t);return Number.isFinite(i)?i:e},l=t=>{var e,i,n,a;return{origin:{x:o(null==(e=null==t?void 0:t.origin)?void 0:e.x),y:o(null==(i=null==t?void 0:t.origin)?void 0:i.y)},size:{width:o(null==(n=null==t?void 0:t.size)?void 0:n.width),height:o(null==(a=null==t?void 0:t.size)?void 0:a.height)}}},c=(t=[])=>t.map(t=>({x:o(null==t?void 0:t.x),y:o(null==t?void 0:t.y)})),h=t=>void 0===t?void 0:Boolean(t),d=t=>void 0===t?void 0:o(t),u=t=>t?r(t):void 0;function p(e){const i=t.ref(null),{onUpdate:a,element:s,vertices:o,constraints:p,maintainAspectRatio:v,pageRotation:m,scale:g,enabled:x}=e,f={element:l(r(s)),vertices:o?c(r(o)):void 0,constraints:u(p),maintainAspectRatio:h(void 0===x?void 0:r(v)),pageRotation:d(void 0===m?void 0:r(m)),scale:d(void 0===g?void 0:r(g))};i.value||(i.value=t.markRaw(new n(f,t=>null==a?void 0:a(t)))),t.watch(()=>({element:s,vertices:o,constraints:p,maintainAspectRatio:v,pageRotation:m,scale:g}),t=>{var e;null==(e=i.value)||e.updateConfig({element:l(r(t.element)),vertices:t.vertices?c(r(t.vertices)):void 0,constraints:u(t.constraints),maintainAspectRatio:h(void 0===t.maintainAspectRatio?void 0:r(t.maintainAspectRatio)),pageRotation:d(void 0===t.pageRotation?void 0:r(t.pageRotation)),scale:d(void 0===t.scale?void 0:r(t.scale))})},{deep:!0}),t.onUnmounted(()=>{i.value=null});const y=()=>Boolean(void 0===x||r(x)),P=t=>{var e,n,a;y()&&(t.preventDefault(),t.stopPropagation(),null==(e=i.value)||e.startDrag(t.clientX,t.clientY),null==(a=(n=t.currentTarget).setPointerCapture)||a.call(n,t.pointerId))},w=t=>{var e;return null==(e=i.value)?void 0:e.move(t.clientX,t.clientY)},z=t=>{var e,n,a;null==(e=i.value)||e.end(),null==(a=(n=t.currentTarget).releasePointerCapture)||a.call(n,t.pointerId)},R=t=>{var e,n,a;null==(e=i.value)||e.cancel(),null==(a=(n=t.currentTarget).releasePointerCapture)||a.call(n,t.pointerId)};return{dragProps:t.computed(()=>y()?{onPointerdown:P,onPointermove:w,onPointerup:z,onPointercancel:R}:{}),createResizeProps:t=>({onPointerdown:e=>{var n,a,s;y()&&(e.preventDefault(),e.stopPropagation(),null==(n=i.value)||n.startResize(t,e.clientX,e.clientY),null==(s=(a=e.currentTarget).setPointerCapture)||s.call(a,e.pointerId))},onPointermove:w,onPointerup:z,onPointercancel:R}),createVertexProps:t=>({onPointerdown:e=>{var n,a,s;y()&&(e.preventDefault(),e.stopPropagation(),null==(n=i.value)||n.startVertexEdit(t,e.clientX,e.clientY),null==(s=(a=e.currentTarget).setPointerCapture)||s.call(a,e.pointerId))},onPointermove:w,onPointerup:z,onPointercancel:R})}}exports.CounterRotate=i,exports.deepToRaw=function(e){const i=e=>Array.isArray(e)?e.map(t=>i(t)):t.isRef(e)||t.isReactive(e)||t.isProxy(e)?i(t.toRaw(e)):e&&"object"==typeof e?Object.keys(e).reduce((t,n)=>(t[n]=i(e[n]),t),{}):e;return i(e)},exports.useDoublePressProps=function(e,{delay:i=300,tolerancePx:n=18}={}){const a=t.ref({t:0,x:0,y:0});return e?{onDblclick:t=>{null==e||e(t)},onPointerupCapture:t=>{if(!e)return;if("mouse"===t.pointerType||!1===t.isPrimary)return;const s=performance.now(),r=t.clientX,o=t.clientY,l=s-a.value.t<=i,c=r-a.value.x,h=o-a.value.y;l&&c*c+h*h<=n*n&&(null==e||e(t)),a.value={t:s,x:r,y:o}}}:{}},exports.useDragResize=p,exports.useInteractionHandles=function(e){const{controller:i,resizeUI:n,vertexUI:o,includeVertices:h=!1,handleAttrs:d,vertexAttrs:u}=e,{dragProps:v,createResizeProps:m,createVertexProps:g}=p(i),x=t.computed(()=>l(r(i.element))),f=t.computed(()=>i.vertices?c(r(i.vertices)):void 0),y=t.computed(()=>Number(r(i.scale??1))),P=t.computed(()=>Number(r(i.pageRotation??0))),w=t.computed(()=>void 0===i.maintainAspectRatio?void 0:Boolean(r(i.maintainAspectRatio))),z=t.computed(()=>r(i.constraints??void 0));return{dragProps:v,resize:t.computed(()=>function(t,e={}){const{handleSize:i=8,spacing:n=1,offsetMode:r="outside",includeSides:o=!1,zIndex:l=3,rotationAwareCursor:c=!0}=e,h=(t.pageRotation??0)%4,d=t=>({[t]:s(i,n,r)+"px"});return[["nw",{...d("top"),...d("left")}],["ne",{...d("top"),...d("right")}],["sw",{...d("bottom"),...d("left")}],["se",{...d("bottom"),...d("right")}],...o?[["n",{...d("top"),left:`calc(50% - ${i/2}px)`}],["s",{...d("bottom"),left:`calc(50% - ${i/2}px)`}],["w",{...d("left"),top:`calc(50% - ${i/2}px)`}],["e",{...d("right"),top:`calc(50% - ${i/2}px)`}]]:[]].map(([t,e])=>({handle:t,style:{position:"absolute",width:i+"px",height:i+"px",borderRadius:"50%",zIndex:l,cursor:c?a(t,h):"default",touchAction:"none",...e},attrs:{"data-epdf-handle":t}}))}({element:x.value,scale:y.value,pageRotation:P.value,maintainAspectRatio:w.value,constraints:z.value},n).map(t=>{var e;return{key:(null==(e=t.attrs)?void 0:e["data-epdf-handle"])??t.handle,style:t.style,...m(t.handle),...t.attrs??{},...(null==d?void 0:d(t.handle))??{}}})),vertices:t.computed(()=>{if(!h)return[];const t=f.value??[];return function(t,e={},i){const{vertexSize:n=12,zIndex:a=4}=e,s=t.element,r=t.scale??1;return(i??t.vertices??[]).map((t,e)=>({handle:"nw",style:{position:"absolute",left:(t.x-s.origin.x)*r-n/2+"px",top:(t.y-s.origin.y)*r-n/2+"px",width:n+"px",height:n+"px",borderRadius:"50%",cursor:"pointer",zIndex:a,touchAction:"none"},attrs:{"data-epdf-vertex":e}}))}({element:x.value,scale:y.value,vertices:t},o,t).map((t,e)=>({key:e,style:t.style,...g(e),...t.attrs??{},...(null==u?void 0:u(e))??{}}))})}};
|
|
1
|
+
"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const t=require("vue"),e=require("@embedpdf/utils"),i=t.defineComponent({__name:"counter-rotate-container",props:{rect:{},rotation:{}},setup(i){const n=i,s=t.computed(()=>e.getCounterRotation(n.rect,n.rotation)),a=t.computed(()=>({style:{position:"absolute",left:`${n.rect.origin.x}px`,top:`${n.rect.origin.y}px`,transform:s.value.matrix,transformOrigin:"0 0",width:`${s.value.width}px`,height:`${s.value.height}px`,pointerEvents:"none",zIndex:3},onPointerdown:t=>{t.stopPropagation(),t.preventDefault()},onTouchstart:t=>{t.stopPropagation(),t.preventDefault()}})),r=t.computed(()=>({origin:{x:n.rect.origin.x,y:n.rect.origin.y},size:{width:s.value.width,height:s.value.height}}));return(e,i)=>t.renderSlot(e.$slots,"default",{menuWrapperProps:a.value,matrix:s.value.matrix,rect:r.value})}});class n{constructor(t,e){this.config=t,this.onUpdate=e,this.state="idle",this.startPoint=null,this.startElement=null,this.activeHandle=null,this.currentPosition=null,this.activeVertexIndex=null,this.startVertices=[],this.currentVertices=[],this.currentVertices=t.vertices||[]}updateConfig(t){this.config={...this.config,...t},this.currentVertices=t.vertices||[]}startDrag(t,e){this.state="dragging",this.startPoint={x:t,y:e},this.startElement={...this.config.element},this.currentPosition={...this.config.element},this.onUpdate({state:"start",transformData:{type:"move",changes:{rect:this.startElement}}})}startResize(t,e,i){this.state="resizing",this.activeHandle=t,this.startPoint={x:e,y:i},this.startElement={...this.config.element},this.currentPosition={...this.config.element},this.onUpdate({state:"start",transformData:{type:"resize",changes:{rect:this.startElement},metadata:{handle:this.activeHandle,maintainAspectRatio:this.config.maintainAspectRatio}}})}startVertexEdit(t,e,i){this.currentVertices=[...this.config.vertices??this.currentVertices],t<0||t>=this.currentVertices.length||(this.state="vertex-editing",this.activeVertexIndex=t,this.startPoint={x:e,y:i},this.startVertices=[...this.currentVertices],this.onUpdate({state:"start",transformData:{type:"vertex-edit",changes:{vertices:this.startVertices},metadata:{vertexIndex:t}}}))}move(t,e){if("idle"!==this.state&&this.startPoint)if("dragging"===this.state&&this.startElement){const i=this.calculateDelta(t,e),n=this.calculateDragPosition(i);this.currentPosition=n,this.onUpdate({state:"move",transformData:{type:"move",changes:{rect:n}}})}else if("resizing"===this.state&&this.activeHandle&&this.startElement){const i=this.calculateDelta(t,e),n=this.calculateResizePosition(i,this.activeHandle);this.currentPosition=n,this.onUpdate({state:"move",transformData:{type:"resize",changes:{rect:n},metadata:{handle:this.activeHandle,maintainAspectRatio:this.config.maintainAspectRatio}}})}else if("vertex-editing"===this.state&&null!==this.activeVertexIndex){const i=this.calculateVertexPosition(t,e);this.currentVertices=i,this.onUpdate({state:"move",transformData:{type:"vertex-edit",changes:{vertices:i},metadata:{vertexIndex:this.activeVertexIndex}}})}}end(){if("idle"===this.state)return;const t=this.state,e=this.activeHandle,i=this.activeVertexIndex;if("vertex-editing"===t)this.onUpdate({state:"end",transformData:{type:"vertex-edit",changes:{vertices:this.currentVertices},metadata:{vertexIndex:i||void 0}}});else{const i=this.getCurrentPosition();this.onUpdate({state:"end",transformData:{type:"dragging"===t?"move":"resize",changes:{rect:i},metadata:"dragging"===t?void 0:{handle:e||void 0,maintainAspectRatio:this.config.maintainAspectRatio}}})}this.reset()}cancel(){"idle"!==this.state&&("vertex-editing"===this.state?this.onUpdate({state:"end",transformData:{type:"vertex-edit",changes:{vertices:this.startVertices},metadata:{vertexIndex:this.activeVertexIndex||void 0}}}):this.startElement&&this.onUpdate({state:"end",transformData:{type:"dragging"===this.state?"move":"resize",changes:{rect:this.startElement},metadata:"dragging"===this.state?void 0:{handle:this.activeHandle||void 0,maintainAspectRatio:this.config.maintainAspectRatio}}}),this.reset())}reset(){this.state="idle",this.startPoint=null,this.startElement=null,this.activeHandle=null,this.currentPosition=null,this.activeVertexIndex=null,this.startVertices=[]}getCurrentPosition(){return this.currentPosition||this.config.element}calculateDelta(t,e){if(!this.startPoint)return{x:0,y:0};const i={x:t-this.startPoint.x,y:e-this.startPoint.y};return this.transformDelta(i)}transformDelta(t){const{pageRotation:e=0,scale:i=1}=this.config,n=e*Math.PI/2,s=Math.cos(n),a=Math.sin(n),r=t.x/i,o=t.y/i;return{x:s*r+a*o,y:-a*r+s*o}}clampPoint(t){var e;const i=null==(e=this.config.constraints)?void 0:e.boundingBox;return i?{x:Math.max(0,Math.min(t.x,i.width)),y:Math.max(0,Math.min(t.y,i.height))}:t}calculateVertexPosition(t,e){if(null===this.activeVertexIndex)return this.startVertices;const i=this.calculateDelta(t,e),n=[...this.startVertices],s=n[this.activeVertexIndex],a={x:s.x+i.x,y:s.y+i.y};return n[this.activeVertexIndex]=this.clampPoint(a),n}calculateDragPosition(t){if(!this.startElement)return this.config.element;const e={origin:{x:this.startElement.origin.x+t.x,y:this.startElement.origin.y+t.y},size:{width:this.startElement.size.width,height:this.startElement.size.height}};return this.applyConstraints(e)}calculateResizePosition(t,e){if(!this.startElement)return this.config.element;const i=function(t){return{x:t.includes("e")?"left":t.includes("w")?"right":"center",y:t.includes("s")?"top":t.includes("n")?"bottom":"center"}}(e),n=this.startElement.size.width/this.startElement.size.height||1;let s=this.applyResizeDelta(t,i);return this.config.maintainAspectRatio&&(s=this.enforceAspectRatio(s,i,n)),s=this.clampToBounds(s,i,n),this.applyConstraints(s)}applyResizeDelta(t,e){const i=this.startElement;let n=i.origin.x,s=i.origin.y,a=i.size.width,r=i.size.height;return"left"===e.x?a+=t.x:"right"===e.x&&(n+=t.x,a-=t.x),"top"===e.y?r+=t.y:"bottom"===e.y&&(s+=t.y,r-=t.y),{origin:{x:n,y:s},size:{width:a,height:r}}}enforceAspectRatio(t,e,i){const n=this.startElement;let{x:s,y:a}=t.origin,{width:r,height:o}=t.size;if("center"===e.x||"center"===e.y)"center"===e.y?(o=r/i,a=n.origin.y+(n.size.height-o)/2):(r=o*i,s=n.origin.x+(n.size.width-r)/2);else{Math.abs(r-n.size.width)>=Math.abs(o-n.size.height)?o=r/i:r=o*i}return"right"===e.x&&(s=n.origin.x+n.size.width-r),"bottom"===e.y&&(a=n.origin.y+n.size.height-o),{origin:{x:s,y:a},size:{width:r,height:o}}}clampToBounds(t,e,i){var n;const s=null==(n=this.config.constraints)?void 0:n.boundingBox;if(!s)return t;const a=this.startElement;let{x:r,y:o}=t.origin,{width:l,height:c}=t.size;l=Math.max(1,l),c=Math.max(1,c);const h="left"===e.x?a.origin.x:a.origin.x+a.size.width,d="top"===e.y?a.origin.y:a.origin.y+a.size.height,u="left"===e.x?s.width-h:"right"===e.x?h:2*Math.min(a.origin.x,s.width-a.origin.x-a.size.width)+a.size.width,p="top"===e.y?s.height-d:"bottom"===e.y?d:2*Math.min(a.origin.y,s.height-a.origin.y-a.size.height)+a.size.height;if(this.config.maintainAspectRatio){const t=l>u?u/l:1,e=c>p?p/c:1,i=Math.min(t,e);i<1&&(l*=i,c*=i)}else l=Math.min(l,u),c=Math.min(c,p);return r="left"===e.x?h:"right"===e.x?h-l:a.origin.x+(a.size.width-l)/2,o="top"===e.y?d:"bottom"===e.y?d-c:a.origin.y+(a.size.height-c)/2,r=Math.max(0,Math.min(r,s.width-l)),o=Math.max(0,Math.min(o,s.height-c)),{origin:{x:r,y:o},size:{width:l,height:c}}}applyConstraints(t){const{constraints:e}=this.config;if(!e)return t;let{origin:{x:i,y:n},size:{width:s,height:a}}=t;const r=e.minWidth??1,o=e.minHeight??1,l=e.maxWidth,c=e.maxHeight;if(this.config.maintainAspectRatio&&s>0&&a>0){const t=s/a;s<r&&(s=r,a=s/t),a<o&&(a=o,s=a*t),void 0!==l&&s>l&&(s=l,a=s/t),void 0!==c&&a>c&&(a=c,s=a*t)}else s=Math.max(r,s),a=Math.max(o,a),void 0!==l&&(s=Math.min(l,s)),void 0!==c&&(a=Math.min(c,a));return e.boundingBox&&(i=Math.max(0,Math.min(i,e.boundingBox.width-s)),n=Math.max(0,Math.min(n,e.boundingBox.height-a))),{origin:{x:i,y:n},size:{width:s,height:a}}}}function s(t,e){return"n"===t||"s"===t?"ns-resize":"e"===t||"w"===t?"ew-resize":e%2==0?{nw:"nwse-resize",ne:"nesw-resize",sw:"nesw-resize",se:"nwse-resize"}[t]:{nw:"nesw-resize",ne:"nwse-resize",sw:"nwse-resize",se:"nesw-resize"}[t]}function a(t,e,i){const n=-t/2;return"center"===i?n:"outside"===i?n-e:n+e}const r=e=>t.toRaw(t.isRef(e)?t.unref(e):e),o=(t,e=0)=>{const i=Number(t);return Number.isFinite(i)?i:e},l=t=>{var e,i,n,s;return{origin:{x:o(null==(e=null==t?void 0:t.origin)?void 0:e.x),y:o(null==(i=null==t?void 0:t.origin)?void 0:i.y)},size:{width:o(null==(n=null==t?void 0:t.size)?void 0:n.width),height:o(null==(s=null==t?void 0:t.size)?void 0:s.height)}}},c=(t=[])=>t.map(t=>({x:o(null==t?void 0:t.x),y:o(null==t?void 0:t.y)})),h=t=>void 0===t?void 0:Boolean(t),d=t=>void 0===t?void 0:o(t),u=t=>t?r(t):void 0;function p(e){const i=t.ref(null),{onUpdate:s,element:a,vertices:o,constraints:p,maintainAspectRatio:g,pageRotation:v,scale:m,enabled:x}=e,f={element:l(r(a)),vertices:o?c(r(o)):void 0,constraints:u(p),maintainAspectRatio:h(void 0===x?void 0:r(g)),pageRotation:d(void 0===v?void 0:r(v)),scale:d(void 0===m?void 0:r(m))};i.value||(i.value=t.markRaw(new n(f,t=>null==s?void 0:s(t)))),t.watch(()=>({element:a,vertices:o,constraints:p,maintainAspectRatio:g,pageRotation:v,scale:m}),t=>{var e;null==(e=i.value)||e.updateConfig({element:l(r(t.element)),vertices:t.vertices?c(r(t.vertices)):void 0,constraints:u(t.constraints),maintainAspectRatio:h(void 0===t.maintainAspectRatio?void 0:r(t.maintainAspectRatio)),pageRotation:d(void 0===t.pageRotation?void 0:r(t.pageRotation)),scale:d(void 0===t.scale?void 0:r(t.scale))})},{deep:!0}),t.onUnmounted(()=>{i.value=null});const y=()=>Boolean(void 0===x||r(x)),z=t=>{var e,n,s;y()&&(t.preventDefault(),t.stopPropagation(),null==(e=i.value)||e.startDrag(t.clientX,t.clientY),null==(s=(n=t.currentTarget).setPointerCapture)||s.call(n,t.pointerId))},P=t=>{var e;return null==(e=i.value)?void 0:e.move(t.clientX,t.clientY)},w=t=>{var e,n,s;null==(e=i.value)||e.end(),null==(s=(n=t.currentTarget).releasePointerCapture)||s.call(n,t.pointerId)},R=t=>{var e,n,s;null==(e=i.value)||e.cancel(),null==(s=(n=t.currentTarget).releasePointerCapture)||s.call(n,t.pointerId)};return{dragProps:t.computed(()=>y()?{onPointerdown:z,onPointermove:P,onPointerup:w,onPointercancel:R}:{}),createResizeProps:t=>({onPointerdown:e=>{var n,s,a;y()&&(e.preventDefault(),e.stopPropagation(),null==(n=i.value)||n.startResize(t,e.clientX,e.clientY),null==(a=(s=e.currentTarget).setPointerCapture)||a.call(s,e.pointerId))},onPointermove:P,onPointerup:w,onPointercancel:R}),createVertexProps:t=>({onPointerdown:e=>{var n,s,a;y()&&(e.preventDefault(),e.stopPropagation(),null==(n=i.value)||n.startVertexEdit(t,e.clientX,e.clientY),null==(a=(s=e.currentTarget).setPointerCapture)||a.call(s,e.pointerId))},onPointermove:P,onPointerup:w,onPointercancel:R})}}exports.CounterRotate=i,exports.deepToRaw=function(e){const i=e=>Array.isArray(e)?e.map(t=>i(t)):t.isRef(e)||t.isReactive(e)||t.isProxy(e)?i(t.toRaw(e)):e&&"object"==typeof e?Object.keys(e).reduce((t,n)=>(t[n]=i(e[n]),t),{}):e;return i(e)},exports.useDoublePressProps=function(e,{delay:i=300,tolerancePx:n=18}={}){const s=t.ref({t:0,x:0,y:0});return e?{onDblclick:t=>{null==e||e(t)},onPointerupCapture:t=>{if(!e)return;if("mouse"===t.pointerType||!1===t.isPrimary)return;const a=performance.now(),r=t.clientX,o=t.clientY,l=a-s.value.t<=i,c=r-s.value.x,h=o-s.value.y;l&&c*c+h*h<=n*n&&(null==e||e(t)),s.value={t:a,x:r,y:o}}}:{}},exports.useDragResize=p,exports.useInteractionHandles=function(e){const{controller:i,resizeUI:n,vertexUI:o,includeVertices:h=!1,handleAttrs:d,vertexAttrs:u}=e,{dragProps:g,createResizeProps:v,createVertexProps:m}=p(i),x=t.computed(()=>l(r(i.element))),f=t.computed(()=>i.vertices?c(r(i.vertices)):void 0),y=t.computed(()=>Number(r(i.scale??1))),z=t.computed(()=>Number(r(i.pageRotation??0))),P=t.computed(()=>void 0===i.maintainAspectRatio?void 0:Boolean(r(i.maintainAspectRatio))),w=t.computed(()=>r(i.constraints??void 0));return{dragProps:g,resize:t.computed(()=>function(t,e={}){const{handleSize:i=8,spacing:n=1,offsetMode:r="outside",includeSides:o=!1,zIndex:l=3,rotationAwareCursor:c=!0}=e,h=(t.pageRotation??0)%4,d=t=>({[t]:a(i,n,r)+"px"});return[["nw",{...d("top"),...d("left")}],["ne",{...d("top"),...d("right")}],["sw",{...d("bottom"),...d("left")}],["se",{...d("bottom"),...d("right")}],...o?[["n",{...d("top"),left:`calc(50% - ${i/2}px)`}],["s",{...d("bottom"),left:`calc(50% - ${i/2}px)`}],["w",{...d("left"),top:`calc(50% - ${i/2}px)`}],["e",{...d("right"),top:`calc(50% - ${i/2}px)`}]]:[]].map(([t,e])=>({handle:t,style:{position:"absolute",width:i+"px",height:i+"px",borderRadius:"50%",zIndex:l,cursor:c?s(t,h):"default",touchAction:"none",...e},attrs:{"data-epdf-handle":t}}))}({element:x.value,scale:y.value,pageRotation:z.value,maintainAspectRatio:P.value,constraints:w.value},n).map(t=>{var e;return{key:(null==(e=t.attrs)?void 0:e["data-epdf-handle"])??t.handle,style:t.style,...v(t.handle),...t.attrs??{},...(null==d?void 0:d(t.handle))??{}}})),vertices:t.computed(()=>{if(!h)return[];const t=f.value??[];return function(t,e={},i){const{vertexSize:n=12,zIndex:s=4}=e,a=t.element,r=t.scale??1;return(i??t.vertices??[]).map((t,e)=>({handle:"nw",style:{position:"absolute",left:(t.x-a.origin.x)*r-n/2+"px",top:(t.y-a.origin.y)*r-n/2+"px",width:n+"px",height:n+"px",borderRadius:"50%",cursor:"pointer",zIndex:s,touchAction:"none"},attrs:{"data-epdf-vertex":e}}))}({element:x.value,scale:y.value,vertices:t},o,t).map((t,e)=>({key:e,style:t.style,...m(e),...t.attrs??{},...(null==u?void 0:u(e))??{}}))})}};
|
|
2
2
|
//# sourceMappingURL=index.cjs.map
|