@oh-just-another/state 0.57.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +18 -0
- package/LICENSE +21 -0
- package/README.md +60 -0
- package/dist/.tsbuildinfo +1 -0
- package/dist/actions/actionClipboard.d.ts +6 -0
- package/dist/actions/actionClipboard.d.ts.map +1 -0
- package/dist/actions/actionClipboard.js +26 -0
- package/dist/actions/actionClipboard.js.map +1 -0
- package/dist/actions/actionGrouping.d.ts +5 -0
- package/dist/actions/actionGrouping.d.ts.map +1 -0
- package/dist/actions/actionGrouping.js +26 -0
- package/dist/actions/actionGrouping.js.map +1 -0
- package/dist/actions/actionHistory.d.ts +5 -0
- package/dist/actions/actionHistory.d.ts.map +1 -0
- package/dist/actions/actionHistory.js +25 -0
- package/dist/actions/actionHistory.js.map +1 -0
- package/dist/actions/actionKeyboard.d.ts +3 -0
- package/dist/actions/actionKeyboard.d.ts.map +1 -0
- package/dist/actions/actionKeyboard.js +130 -0
- package/dist/actions/actionKeyboard.js.map +1 -0
- package/dist/actions/actionLayout.d.ts +3 -0
- package/dist/actions/actionLayout.d.ts.map +1 -0
- package/dist/actions/actionLayout.js +65 -0
- package/dist/actions/actionLayout.js.map +1 -0
- package/dist/actions/actionMode.d.ts +13 -0
- package/dist/actions/actionMode.d.ts.map +1 -0
- package/dist/actions/actionMode.js +116 -0
- package/dist/actions/actionMode.js.map +1 -0
- package/dist/actions/actionSelection.d.ts +9 -0
- package/dist/actions/actionSelection.d.ts.map +1 -0
- package/dist/actions/actionSelection.js +57 -0
- package/dist/actions/actionSelection.js.map +1 -0
- package/dist/actions/actionView.d.ts +7 -0
- package/dist/actions/actionView.d.ts.map +1 -0
- package/dist/actions/actionView.js +14 -0
- package/dist/actions/actionView.js.map +1 -0
- package/dist/actions/actionZOrder.d.ts +7 -0
- package/dist/actions/actionZOrder.d.ts.map +1 -0
- package/dist/actions/actionZOrder.js +42 -0
- package/dist/actions/actionZOrder.js.map +1 -0
- package/dist/actions/actionZoom.d.ts +8 -0
- package/dist/actions/actionZoom.d.ts.map +1 -0
- package/dist/actions/actionZoom.js +61 -0
- package/dist/actions/actionZoom.js.map +1 -0
- package/dist/actions/index.d.ts +12 -0
- package/dist/actions/index.d.ts.map +1 -0
- package/dist/actions/index.js +11 -0
- package/dist/actions/index.js.map +1 -0
- package/dist/actions/registry.d.ts +68 -0
- package/dist/actions/registry.d.ts.map +1 -0
- package/dist/actions/registry.js +300 -0
- package/dist/actions/registry.js.map +1 -0
- package/dist/actions/types.d.ts +103 -0
- package/dist/actions/types.d.ts.map +1 -0
- package/dist/actions/types.js +10 -0
- package/dist/actions/types.js.map +1 -0
- package/dist/animation-tick.d.ts +28 -0
- package/dist/animation-tick.d.ts.map +1 -0
- package/dist/animation-tick.js +50 -0
- package/dist/animation-tick.js.map +1 -0
- package/dist/auto-compact.d.ts +27 -0
- package/dist/auto-compact.d.ts.map +1 -0
- package/dist/auto-compact.js +46 -0
- package/dist/auto-compact.js.map +1 -0
- package/dist/auto-layout-scheduler.d.ts +50 -0
- package/dist/auto-layout-scheduler.d.ts.map +1 -0
- package/dist/auto-layout-scheduler.js +94 -0
- package/dist/auto-layout-scheduler.js.map +1 -0
- package/dist/built-in-handlers.d.ts +24 -0
- package/dist/built-in-handlers.d.ts.map +1 -0
- package/dist/built-in-handlers.js +210 -0
- package/dist/built-in-handlers.js.map +1 -0
- package/dist/clipboard.d.ts +51 -0
- package/dist/clipboard.d.ts.map +1 -0
- package/dist/clipboard.js +105 -0
- package/dist/clipboard.js.map +1 -0
- package/dist/constants.d.ts +544 -0
- package/dist/constants.d.ts.map +1 -0
- package/dist/constants.js +537 -0
- package/dist/constants.js.map +1 -0
- package/dist/dom-events.d.ts +13 -0
- package/dist/dom-events.d.ts.map +1 -0
- package/dist/dom-events.js +70 -0
- package/dist/dom-events.js.map +1 -0
- package/dist/editor/anchor-points.d.ts +22 -0
- package/dist/editor/anchor-points.d.ts.map +1 -0
- package/dist/editor/anchor-points.js +28 -0
- package/dist/editor/anchor-points.js.map +1 -0
- package/dist/editor/applies/create.d.ts +60 -0
- package/dist/editor/applies/create.d.ts.map +1 -0
- package/dist/editor/applies/create.js +107 -0
- package/dist/editor/applies/create.js.map +1 -0
- package/dist/editor/applies/edge.d.ts +32 -0
- package/dist/editor/applies/edge.d.ts.map +1 -0
- package/dist/editor/applies/edge.js +44 -0
- package/dist/editor/applies/edge.js.map +1 -0
- package/dist/editor/applies/link-move.d.ts +53 -0
- package/dist/editor/applies/link-move.d.ts.map +1 -0
- package/dist/editor/applies/link-move.js +160 -0
- package/dist/editor/applies/link-move.js.map +1 -0
- package/dist/editor/applies/move.d.ts +38 -0
- package/dist/editor/applies/move.d.ts.map +1 -0
- package/dist/editor/applies/move.js +83 -0
- package/dist/editor/applies/move.js.map +1 -0
- package/dist/editor/applies/resize.d.ts +68 -0
- package/dist/editor/applies/resize.d.ts.map +1 -0
- package/dist/editor/applies/resize.js +199 -0
- package/dist/editor/applies/resize.js.map +1 -0
- package/dist/editor/applies/selection.d.ts +34 -0
- package/dist/editor/applies/selection.d.ts.map +1 -0
- package/dist/editor/applies/selection.js +65 -0
- package/dist/editor/applies/selection.js.map +1 -0
- package/dist/editor/applies/snap-grid.d.ts +45 -0
- package/dist/editor/applies/snap-grid.d.ts.map +1 -0
- package/dist/editor/applies/snap-grid.js +90 -0
- package/dist/editor/applies/snap-grid.js.map +1 -0
- package/dist/editor/container-ops.d.ts +74 -0
- package/dist/editor/container-ops.d.ts.map +1 -0
- package/dist/editor/container-ops.js +262 -0
- package/dist/editor/container-ops.js.map +1 -0
- package/dist/editor/event-fanout.d.ts +48 -0
- package/dist/editor/event-fanout.d.ts.map +1 -0
- package/dist/editor/event-fanout.js +53 -0
- package/dist/editor/event-fanout.js.map +1 -0
- package/dist/editor/gesture-tx.d.ts +77 -0
- package/dist/editor/gesture-tx.d.ts.map +1 -0
- package/dist/editor/gesture-tx.js +93 -0
- package/dist/editor/gesture-tx.js.map +1 -0
- package/dist/editor/hit-test.d.ts +178 -0
- package/dist/editor/hit-test.d.ts.map +1 -0
- package/dist/editor/hit-test.js +460 -0
- package/dist/editor/hit-test.js.map +1 -0
- package/dist/editor/long-press.d.ts +34 -0
- package/dist/editor/long-press.d.ts.map +1 -0
- package/dist/editor/long-press.js +58 -0
- package/dist/editor/long-press.js.map +1 -0
- package/dist/editor/pinch.d.ts +37 -0
- package/dist/editor/pinch.d.ts.map +1 -0
- package/dist/editor/pinch.js +90 -0
- package/dist/editor/pinch.js.map +1 -0
- package/dist/editor/pointer-binding.d.ts +18 -0
- package/dist/editor/pointer-binding.d.ts.map +1 -0
- package/dist/editor/pointer-binding.js +1087 -0
- package/dist/editor/pointer-binding.js.map +1 -0
- package/dist/editor/public/annotations.d.ts +54 -0
- package/dist/editor/public/annotations.d.ts.map +1 -0
- package/dist/editor/public/annotations.js +106 -0
- package/dist/editor/public/annotations.js.map +1 -0
- package/dist/editor/public/arrange-group.d.ts +81 -0
- package/dist/editor/public/arrange-group.d.ts.map +1 -0
- package/dist/editor/public/arrange-group.js +193 -0
- package/dist/editor/public/arrange-group.js.map +1 -0
- package/dist/editor/public/brush.d.ts +33 -0
- package/dist/editor/public/brush.d.ts.map +1 -0
- package/dist/editor/public/brush.js +54 -0
- package/dist/editor/public/brush.js.map +1 -0
- package/dist/editor/public/clipboard.d.ts +31 -0
- package/dist/editor/public/clipboard.d.ts.map +1 -0
- package/dist/editor/public/clipboard.js +35 -0
- package/dist/editor/public/clipboard.js.map +1 -0
- package/dist/editor/public/image-insert.d.ts +30 -0
- package/dist/editor/public/image-insert.d.ts.map +1 -0
- package/dist/editor/public/image-insert.js +57 -0
- package/dist/editor/public/image-insert.js.map +1 -0
- package/dist/editor/public/layers.d.ts +56 -0
- package/dist/editor/public/layers.d.ts.map +1 -0
- package/dist/editor/public/layers.js +104 -0
- package/dist/editor/public/layers.js.map +1 -0
- package/dist/editor/public/link.d.ts +25 -0
- package/dist/editor/public/link.d.ts.map +1 -0
- package/dist/editor/public/link.js +74 -0
- package/dist/editor/public/link.js.map +1 -0
- package/dist/editor/public/placement.d.ts +60 -0
- package/dist/editor/public/placement.d.ts.map +1 -0
- package/dist/editor/public/placement.js +111 -0
- package/dist/editor/public/placement.js.map +1 -0
- package/dist/editor/public/selection-ops.d.ts +78 -0
- package/dist/editor/public/selection-ops.d.ts.map +1 -0
- package/dist/editor/public/selection-ops.js +226 -0
- package/dist/editor/public/selection-ops.js.map +1 -0
- package/dist/editor/public/text-edit.d.ts +17 -0
- package/dist/editor/public/text-edit.d.ts.map +1 -0
- package/dist/editor/public/text-edit.js +28 -0
- package/dist/editor/public/text-edit.js.map +1 -0
- package/dist/editor/public/z-order.d.ts +47 -0
- package/dist/editor/public/z-order.d.ts.map +1 -0
- package/dist/editor/public/z-order.js +151 -0
- package/dist/editor/public/z-order.js.map +1 -0
- package/dist/editor/public/zoom-pan.d.ts +44 -0
- package/dist/editor/public/zoom-pan.d.ts.map +1 -0
- package/dist/editor/public/zoom-pan.js +116 -0
- package/dist/editor/public/zoom-pan.js.map +1 -0
- package/dist/editor/render-orchestrator.d.ts +11 -0
- package/dist/editor/render-orchestrator.d.ts.map +1 -0
- package/dist/editor/render-orchestrator.js +473 -0
- package/dist/editor/render-orchestrator.js.map +1 -0
- package/dist/editor/resize-helpers.d.ts +30 -0
- package/dist/editor/resize-helpers.d.ts.map +1 -0
- package/dist/editor/resize-helpers.js +121 -0
- package/dist/editor/resize-helpers.js.map +1 -0
- package/dist/editor/shape-filters.d.ts +11 -0
- package/dist/editor/shape-filters.d.ts.map +1 -0
- package/dist/editor/shape-filters.js +19 -0
- package/dist/editor/shape-filters.js.map +1 -0
- package/dist/editor/shape-traits.d.ts +16 -0
- package/dist/editor/shape-traits.d.ts.map +1 -0
- package/dist/editor/shape-traits.js +29 -0
- package/dist/editor/shape-traits.js.map +1 -0
- package/dist/editor/viewport-helpers.d.ts +24 -0
- package/dist/editor/viewport-helpers.d.ts.map +1 -0
- package/dist/editor/viewport-helpers.js +63 -0
- package/dist/editor/viewport-helpers.js.map +1 -0
- package/dist/editor-events.d.ts +33 -0
- package/dist/editor-events.d.ts.map +1 -0
- package/dist/editor-events.js +2 -0
- package/dist/editor-events.js.map +1 -0
- package/dist/editor.d.ts +1841 -0
- package/dist/editor.d.ts.map +1 -0
- package/dist/editor.js +4803 -0
- package/dist/editor.js.map +1 -0
- package/dist/file-drop.d.ts +99 -0
- package/dist/file-drop.d.ts.map +1 -0
- package/dist/file-drop.js +198 -0
- package/dist/file-drop.js.map +1 -0
- package/dist/frame-helpers.d.ts +30 -0
- package/dist/frame-helpers.d.ts.map +1 -0
- package/dist/frame-helpers.js +105 -0
- package/dist/frame-helpers.js.map +1 -0
- package/dist/group-helpers.d.ts +39 -0
- package/dist/group-helpers.d.ts.map +1 -0
- package/dist/group-helpers.js +116 -0
- package/dist/group-helpers.js.map +1 -0
- package/dist/handle.d.ts +73 -0
- package/dist/handle.d.ts.map +1 -0
- package/dist/handle.js +184 -0
- package/dist/handle.js.map +1 -0
- package/dist/index.d.ts +26 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +16 -0
- package/dist/index.js.map +1 -0
- package/dist/interactive.d.ts +21 -0
- package/dist/interactive.d.ts.map +1 -0
- package/dist/interactive.js +11 -0
- package/dist/interactive.js.map +1 -0
- package/dist/link-selection.d.ts +21 -0
- package/dist/link-selection.d.ts.map +1 -0
- package/dist/link-selection.js +37 -0
- package/dist/link-selection.js.map +1 -0
- package/dist/machine.d.ts +322 -0
- package/dist/machine.d.ts.map +1 -0
- package/dist/machine.js +568 -0
- package/dist/machine.js.map +1 -0
- package/dist/modes.d.ts +24 -0
- package/dist/modes.d.ts.map +1 -0
- package/dist/modes.js +2 -0
- package/dist/modes.js.map +1 -0
- package/dist/overlay.d.ts +262 -0
- package/dist/overlay.d.ts.map +1 -0
- package/dist/overlay.js +673 -0
- package/dist/overlay.js.map +1 -0
- package/dist/platform.d.ts +70 -0
- package/dist/platform.d.ts.map +1 -0
- package/dist/platform.js +115 -0
- package/dist/platform.js.map +1 -0
- package/dist/selection.d.ts +18 -0
- package/dist/selection.d.ts.map +1 -0
- package/dist/selection.js +31 -0
- package/dist/selection.js.map +1 -0
- package/package.json +59 -0
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import type { Bounds, ElementId } from "@oh-just-another/types";
|
|
2
|
+
import { type Scene } from "@oh-just-another/scene";
|
|
3
|
+
import type { HistoryProvider } from "@oh-just-another/history";
|
|
4
|
+
/**
|
|
5
|
+
* Next free `Frame N` auto-name — finds the highest existing `Frame <number>`
|
|
6
|
+
* in the scene and returns the increment. New frames default to this when the
|
|
7
|
+
* host doesn't supply a name.
|
|
8
|
+
*/
|
|
9
|
+
export declare const nextFrameName: (scene: Scene) => string;
|
|
10
|
+
/**
|
|
11
|
+
* Assign `frameId` to every shape (except the frame itself) whose centre
|
|
12
|
+
* falls inside `frameBounds`. Already-owned shapes are left alone; the user
|
|
13
|
+
* has to drag them in explicitly to reassign.
|
|
14
|
+
*
|
|
15
|
+
* Mutates `history` (push per change) and returns the new scene. Caller
|
|
16
|
+
* decides whether to wrap in a single transaction (Editor already does for
|
|
17
|
+
* the gesture).
|
|
18
|
+
*/
|
|
19
|
+
export declare const assignFrameMembers: (scene: Scene, history: HistoryProvider, frameId: ElementId, frameBounds: Bounds) => Scene;
|
|
20
|
+
/**
|
|
21
|
+
* Re-evaluate frame membership for EVERY non-frame element against the
|
|
22
|
+
* current frames — run at the end of a move / resize gesture. An element
|
|
23
|
+
* joins the top-most frame whose world bounds contain its centre, and is
|
|
24
|
+
* released (`frameId` cleared) when its centre is over no frame. Idempotent:
|
|
25
|
+
* pushes a patch only when an element's owning frame actually changed, so a
|
|
26
|
+
* plain click / no-op drag costs nothing. Mutates `history`; returns the new
|
|
27
|
+
* scene.
|
|
28
|
+
*/
|
|
29
|
+
export declare const reconcileFrameMembership: (scene: Scene, history: HistoryProvider) => Scene;
|
|
30
|
+
//# sourceMappingURL=frame-helpers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"frame-helpers.d.ts","sourceRoot":"","sources":["../src/frame-helpers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AAChE,OAAO,EAGL,KAAK,KAAK,EACX,MAAM,wBAAwB,CAAC;AAChC,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAWhE;;;;GAIG;AACH,eAAO,MAAM,aAAa,GAAI,OAAO,KAAK,KAAG,MAQ5C,CAAC;AAEF;;;;;;;;GAQG;AACH,eAAO,MAAM,kBAAkB,GAC7B,OAAO,KAAK,EACZ,SAAS,eAAe,EACxB,SAAS,SAAS,EAClB,aAAa,MAAM,KAClB,KAmBF,CAAC;AAEF;;;;;;;;GAQG;AACH,eAAO,MAAM,wBAAwB,GAAI,OAAO,KAAK,EAAE,SAAS,eAAe,KAAG,KAkCjF,CAAC"}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
import { getElementWorldBounds, updateElement, } from "@oh-just-another/scene";
|
|
2
|
+
/**
|
|
3
|
+
* Frame helpers. Two distinct concerns: choosing a free auto-name
|
|
4
|
+
* (`Frame N+1`) and assigning ownership when a frame is freshly drawn over
|
|
5
|
+
* existing shapes. Both are bounded by scene contents; the second threads
|
|
6
|
+
* scene + history mutations the same way Editor does internally.
|
|
7
|
+
*/
|
|
8
|
+
const FRAME_NAME_PATTERN = /^Frame (\d+)$/;
|
|
9
|
+
/**
|
|
10
|
+
* Next free `Frame N` auto-name — finds the highest existing `Frame <number>`
|
|
11
|
+
* in the scene and returns the increment. New frames default to this when the
|
|
12
|
+
* host doesn't supply a name.
|
|
13
|
+
*/
|
|
14
|
+
export const nextFrameName = (scene) => {
|
|
15
|
+
let max = 0;
|
|
16
|
+
for (const s of scene.elements.values()) {
|
|
17
|
+
if (s.type !== "frame")
|
|
18
|
+
continue;
|
|
19
|
+
const m = FRAME_NAME_PATTERN.exec(s.name ?? "");
|
|
20
|
+
if (m)
|
|
21
|
+
max = Math.max(max, Number(m[1]));
|
|
22
|
+
}
|
|
23
|
+
return `Frame ${max + 1}`;
|
|
24
|
+
};
|
|
25
|
+
/**
|
|
26
|
+
* Assign `frameId` to every shape (except the frame itself) whose centre
|
|
27
|
+
* falls inside `frameBounds`. Already-owned shapes are left alone; the user
|
|
28
|
+
* has to drag them in explicitly to reassign.
|
|
29
|
+
*
|
|
30
|
+
* Mutates `history` (push per change) and returns the new scene. Caller
|
|
31
|
+
* decides whether to wrap in a single transaction (Editor already does for
|
|
32
|
+
* the gesture).
|
|
33
|
+
*/
|
|
34
|
+
export const assignFrameMembers = (scene, history, frameId, frameBounds) => {
|
|
35
|
+
const left = frameBounds.x;
|
|
36
|
+
const top = frameBounds.y;
|
|
37
|
+
const right = frameBounds.x + frameBounds.width;
|
|
38
|
+
const bottom = frameBounds.y + frameBounds.height;
|
|
39
|
+
let next = scene;
|
|
40
|
+
for (const shape of scene.elements.values()) {
|
|
41
|
+
if (shape.id === frameId)
|
|
42
|
+
continue;
|
|
43
|
+
if (shape.type === "frame")
|
|
44
|
+
continue;
|
|
45
|
+
if (shape.frameId !== undefined)
|
|
46
|
+
continue;
|
|
47
|
+
const b = getElementWorldBounds(shape);
|
|
48
|
+
const cx = b.x + b.width / 2;
|
|
49
|
+
const cy = b.y + b.height / 2;
|
|
50
|
+
if (cx < left || cx > right || cy < top || cy > bottom)
|
|
51
|
+
continue;
|
|
52
|
+
const r = updateElement(next, shape.id, (s) => ({ ...s, frameId }));
|
|
53
|
+
next = r.scene;
|
|
54
|
+
history.push(r.patch);
|
|
55
|
+
}
|
|
56
|
+
return next;
|
|
57
|
+
};
|
|
58
|
+
/**
|
|
59
|
+
* Re-evaluate frame membership for EVERY non-frame element against the
|
|
60
|
+
* current frames — run at the end of a move / resize gesture. An element
|
|
61
|
+
* joins the top-most frame whose world bounds contain its centre, and is
|
|
62
|
+
* released (`frameId` cleared) when its centre is over no frame. Idempotent:
|
|
63
|
+
* pushes a patch only when an element's owning frame actually changed, so a
|
|
64
|
+
* plain click / no-op drag costs nothing. Mutates `history`; returns the new
|
|
65
|
+
* scene.
|
|
66
|
+
*/
|
|
67
|
+
export const reconcileFrameMembership = (scene, history) => {
|
|
68
|
+
// Frames top-most first — highest z-order (fractional-index string) wins
|
|
69
|
+
// when frames overlap.
|
|
70
|
+
const frames = [...scene.elements.values()]
|
|
71
|
+
.filter((s) => s.type === "frame")
|
|
72
|
+
.sort((a, b) => (a.order < b.order ? 1 : a.order > b.order ? -1 : 0))
|
|
73
|
+
.map((f) => ({ id: f.id, b: getElementWorldBounds(f) }));
|
|
74
|
+
let next = scene;
|
|
75
|
+
for (const shape of scene.elements.values()) {
|
|
76
|
+
if (shape.type === "frame")
|
|
77
|
+
continue;
|
|
78
|
+
const b = getElementWorldBounds(shape);
|
|
79
|
+
const cx = b.x + b.width / 2;
|
|
80
|
+
const cy = b.y + b.height / 2;
|
|
81
|
+
let owner;
|
|
82
|
+
for (const f of frames) {
|
|
83
|
+
if (cx >= f.b.x && cx <= f.b.x + f.b.width && cy >= f.b.y && cy <= f.b.y + f.b.height) {
|
|
84
|
+
owner = f.id;
|
|
85
|
+
break;
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
if (shape.frameId === owner)
|
|
89
|
+
continue;
|
|
90
|
+
const r = updateElement(next, shape.id, (s) => {
|
|
91
|
+
const copy = { ...s };
|
|
92
|
+
// `exactOptionalPropertyTypes`: omit the key on release rather than
|
|
93
|
+
// setting it to `undefined`.
|
|
94
|
+
if (owner === undefined)
|
|
95
|
+
delete copy.frameId;
|
|
96
|
+
else
|
|
97
|
+
copy.frameId = owner;
|
|
98
|
+
return copy;
|
|
99
|
+
});
|
|
100
|
+
next = r.scene;
|
|
101
|
+
history.push(r.patch);
|
|
102
|
+
}
|
|
103
|
+
return next;
|
|
104
|
+
};
|
|
105
|
+
//# sourceMappingURL=frame-helpers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"frame-helpers.js","sourceRoot":"","sources":["../src/frame-helpers.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import type { ElementId } from "@oh-just-another/types";
|
|
2
|
+
import { type Scene, type Element } from "@oh-just-another/scene";
|
|
3
|
+
/**
|
|
4
|
+
* Topmost group ancestor of `shape` — walks the `parentId` chain and
|
|
5
|
+
* remembers the last parent typed `"group"`. Returns `null` when no ancestor
|
|
6
|
+
* is a group.
|
|
7
|
+
*/
|
|
8
|
+
export declare const topGroupAncestor: (scene: Scene, shape: Element) => Element | null;
|
|
9
|
+
/**
|
|
10
|
+
* `true` when `elementId`'s parent chain contains `groupId` (or
|
|
11
|
+
* `elementId === groupId`). Bounded walk so a corrupted scene with a parentId
|
|
12
|
+
* cycle returns false instead of looping forever.
|
|
13
|
+
*/
|
|
14
|
+
export declare const isDescendantOfGroup: (scene: Scene, elementId: ElementId, groupId: ElementId) => boolean;
|
|
15
|
+
/**
|
|
16
|
+
* Walk the parent chain of `shape` upward, promoting through groups until
|
|
17
|
+
* either:
|
|
18
|
+
* • the next parent is the editor's currently-entered group (drill-in mode
|
|
19
|
+
* lets the user pick the group's children);
|
|
20
|
+
* • the parent is no longer a group (containers / templates intentionally
|
|
21
|
+
* let click hits land on their children).
|
|
22
|
+
*/
|
|
23
|
+
export declare const promoteToGroupRoot: (scene: Scene, shape: Element, enteredGroup: ElementId | null) => Element;
|
|
24
|
+
/**
|
|
25
|
+
* Compute the dim set for isolation rendering — every shape whose parent chain
|
|
26
|
+
* does NOT pass through `enteredGroupId`. Selection always stays opaque even
|
|
27
|
+
* when somehow not in the descendant set.
|
|
28
|
+
*/
|
|
29
|
+
export declare const computeDimElements: (scene: Scene, selection: Iterable<ElementId>, enteredGroupId: ElementId) => ReadonlySet<ElementId>;
|
|
30
|
+
/**
|
|
31
|
+
* Decide which group `raw` should drill into on a double-click.
|
|
32
|
+
*
|
|
33
|
+
* • No group ancestor → null (drill doesn't apply).
|
|
34
|
+
* • Top group not yet entered → enter top.
|
|
35
|
+
* • Top group already entered → walk down the chain and pick the next inner
|
|
36
|
+
* group (drill one level deeper).
|
|
37
|
+
*/
|
|
38
|
+
export declare const pickDrillTarget: (scene: Scene, raw: Element, top: Element | null, enteredGroup: ElementId | null) => Element | null;
|
|
39
|
+
//# sourceMappingURL=group-helpers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"group-helpers.d.ts","sourceRoot":"","sources":["../src/group-helpers.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AACxD,OAAO,EAAc,KAAK,KAAK,EAAE,KAAK,OAAO,EAAE,MAAM,wBAAwB,CAAC;AAU9E;;;;GAIG;AACH,eAAO,MAAM,gBAAgB,GAAI,OAAO,KAAK,EAAE,OAAO,OAAO,KAAG,OAAO,GAAG,IAYzE,CAAC;AAEF;;;;GAIG;AACH,eAAO,MAAM,mBAAmB,GAC9B,OAAO,KAAK,EACZ,WAAW,SAAS,EACpB,SAAS,SAAS,KACjB,OAUF,CAAC;AAEF;;;;;;;GAOG;AACH,eAAO,MAAM,kBAAkB,GAC7B,OAAO,KAAK,EACZ,OAAO,OAAO,EACd,cAAc,SAAS,GAAG,IAAI,KAC7B,OAYF,CAAC;AAEF;;;;GAIG;AACH,eAAO,MAAM,kBAAkB,GAC7B,OAAO,KAAK,EACZ,WAAW,QAAQ,CAAC,SAAS,CAAC,EAC9B,gBAAgB,SAAS,KACxB,WAAW,CAAC,SAAS,CAUvB,CAAC;AAEF;;;;;;;GAOG;AACH,eAAO,MAAM,eAAe,GAC1B,OAAO,KAAK,EACZ,KAAK,OAAO,EACZ,KAAK,OAAO,GAAG,IAAI,EACnB,cAAc,SAAS,GAAG,IAAI,KAC7B,OAAO,GAAG,IAeZ,CAAC"}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import { getElement } from "@oh-just-another/scene";
|
|
2
|
+
/**
|
|
3
|
+
* Group / isolation helpers — pure functions over Scene + ElementId with no
|
|
4
|
+
* Editor back-reference, so the test suite can drive them directly. Editor
|
|
5
|
+
* keeps wrapper methods that forward to these.
|
|
6
|
+
*/
|
|
7
|
+
const MAX_PARENT_DEPTH = 64;
|
|
8
|
+
/**
|
|
9
|
+
* Topmost group ancestor of `shape` — walks the `parentId` chain and
|
|
10
|
+
* remembers the last parent typed `"group"`. Returns `null` when no ancestor
|
|
11
|
+
* is a group.
|
|
12
|
+
*/
|
|
13
|
+
export const topGroupAncestor = (scene, shape) => {
|
|
14
|
+
let topGroup = null;
|
|
15
|
+
let cursor = shape;
|
|
16
|
+
let depth = 0;
|
|
17
|
+
while (cursor.parentId && depth < MAX_PARENT_DEPTH) {
|
|
18
|
+
const parent = getElement(scene, cursor.parentId);
|
|
19
|
+
if (!parent)
|
|
20
|
+
break;
|
|
21
|
+
if (parent.type === "group")
|
|
22
|
+
topGroup = parent;
|
|
23
|
+
cursor = parent;
|
|
24
|
+
depth++;
|
|
25
|
+
}
|
|
26
|
+
return topGroup;
|
|
27
|
+
};
|
|
28
|
+
/**
|
|
29
|
+
* `true` when `elementId`'s parent chain contains `groupId` (or
|
|
30
|
+
* `elementId === groupId`). Bounded walk so a corrupted scene with a parentId
|
|
31
|
+
* cycle returns false instead of looping forever.
|
|
32
|
+
*/
|
|
33
|
+
export const isDescendantOfGroup = (scene, elementId, groupId) => {
|
|
34
|
+
let cursor = getElement(scene, elementId);
|
|
35
|
+
let depth = 0;
|
|
36
|
+
while (cursor && depth < MAX_PARENT_DEPTH) {
|
|
37
|
+
if (cursor.id === groupId)
|
|
38
|
+
return true;
|
|
39
|
+
if (!cursor.parentId)
|
|
40
|
+
return false;
|
|
41
|
+
cursor = getElement(scene, cursor.parentId);
|
|
42
|
+
depth++;
|
|
43
|
+
}
|
|
44
|
+
return false;
|
|
45
|
+
};
|
|
46
|
+
/**
|
|
47
|
+
* Walk the parent chain of `shape` upward, promoting through groups until
|
|
48
|
+
* either:
|
|
49
|
+
* • the next parent is the editor's currently-entered group (drill-in mode
|
|
50
|
+
* lets the user pick the group's children);
|
|
51
|
+
* • the parent is no longer a group (containers / templates intentionally
|
|
52
|
+
* let click hits land on their children).
|
|
53
|
+
*/
|
|
54
|
+
export const promoteToGroupRoot = (scene, shape, enteredGroup) => {
|
|
55
|
+
let current = shape;
|
|
56
|
+
let depth = 0;
|
|
57
|
+
while (current.parentId && depth < MAX_PARENT_DEPTH) {
|
|
58
|
+
if (enteredGroup === current.parentId)
|
|
59
|
+
break;
|
|
60
|
+
const parent = getElement(scene, current.parentId);
|
|
61
|
+
if (!parent)
|
|
62
|
+
break;
|
|
63
|
+
if (parent.type !== "group")
|
|
64
|
+
break;
|
|
65
|
+
current = parent;
|
|
66
|
+
depth++;
|
|
67
|
+
}
|
|
68
|
+
return current;
|
|
69
|
+
};
|
|
70
|
+
/**
|
|
71
|
+
* Compute the dim set for isolation rendering — every shape whose parent chain
|
|
72
|
+
* does NOT pass through `enteredGroupId`. Selection always stays opaque even
|
|
73
|
+
* when somehow not in the descendant set.
|
|
74
|
+
*/
|
|
75
|
+
export const computeDimElements = (scene, selection, enteredGroupId) => {
|
|
76
|
+
const dim = new Set();
|
|
77
|
+
const selectionSet = new Set(selection);
|
|
78
|
+
for (const s of scene.elements.values()) {
|
|
79
|
+
if (selectionSet.has(s.id))
|
|
80
|
+
continue;
|
|
81
|
+
if (!isDescendantOfGroup(scene, s.id, enteredGroupId)) {
|
|
82
|
+
dim.add(s.id);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
return dim;
|
|
86
|
+
};
|
|
87
|
+
/**
|
|
88
|
+
* Decide which group `raw` should drill into on a double-click.
|
|
89
|
+
*
|
|
90
|
+
* • No group ancestor → null (drill doesn't apply).
|
|
91
|
+
* • Top group not yet entered → enter top.
|
|
92
|
+
* • Top group already entered → walk down the chain and pick the next inner
|
|
93
|
+
* group (drill one level deeper).
|
|
94
|
+
*/
|
|
95
|
+
export const pickDrillTarget = (scene, raw, top, enteredGroup) => {
|
|
96
|
+
if (!top)
|
|
97
|
+
return null;
|
|
98
|
+
if (enteredGroup !== top.id)
|
|
99
|
+
return top;
|
|
100
|
+
let cursor = raw;
|
|
101
|
+
let next = null;
|
|
102
|
+
let depth = 0;
|
|
103
|
+
while (cursor.parentId && depth < MAX_PARENT_DEPTH) {
|
|
104
|
+
const parent = getElement(scene, cursor.parentId);
|
|
105
|
+
if (!parent)
|
|
106
|
+
break;
|
|
107
|
+
if (parent.id === top.id)
|
|
108
|
+
break;
|
|
109
|
+
if (parent.type === "group")
|
|
110
|
+
next = parent;
|
|
111
|
+
cursor = parent;
|
|
112
|
+
depth++;
|
|
113
|
+
}
|
|
114
|
+
return next;
|
|
115
|
+
};
|
|
116
|
+
//# sourceMappingURL=group-helpers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"group-helpers.js","sourceRoot":"","sources":["../src/group-helpers.ts"],"names":[],"mappings":"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"}
|
package/dist/handle.d.ts
ADDED
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
import type { Bounds, Vec2 } from "@oh-just-another/types";
|
|
2
|
+
import { HANDLE_HIT_SLOP, HANDLE_OUTSET, HANDLE_SIZE } from "./constants.js";
|
|
3
|
+
/**
|
|
4
|
+
* Eight resize-handle positions arranged around the shape's AABB. `nw` is
|
|
5
|
+
* top-left, `ne` top-right, etc. `n`/`s`/`e`/`w` are edge midpoints.
|
|
6
|
+
*/
|
|
7
|
+
export type HandleId = "nw" | "n" | "ne" | "e" | "se" | "s" | "sw" | "w";
|
|
8
|
+
export declare const ALL_HANDLES: readonly HandleId[];
|
|
9
|
+
/**
|
|
10
|
+
* Subset of `ALL_HANDLES` containing only the four corner positions. Used for
|
|
11
|
+
* aspect-locked resize (groups, fixed-ratio media) — only corner drags carry
|
|
12
|
+
* the diagonal that the resize math projects onto a single scale factor.
|
|
13
|
+
*/
|
|
14
|
+
export declare const CORNER_HANDLES: readonly HandleId[];
|
|
15
|
+
/**
|
|
16
|
+
* CSS `cursor` for a resize handle — the bidirectional arrow aligned with the
|
|
17
|
+
* handle's resize axis. Opposite handles share a cursor (e.g. `nw`/`se` →
|
|
18
|
+
* `nwse-resize`). Used by the editor's context-cursor logic.
|
|
19
|
+
*
|
|
20
|
+
* Ignores element rotation — a rotated shape's handles technically want a
|
|
21
|
+
* rotated cursor, but CSS only offers the 8 fixed arrows; we map by handle id.
|
|
22
|
+
*/
|
|
23
|
+
export declare const cursorForHandle: (handle: HandleId) => string;
|
|
24
|
+
/**
|
|
25
|
+
* Re-exports handle geometry/hit-target constants from `constants.ts`.
|
|
26
|
+
* `HANDLE_HIT_SLOP` is decoupled from `HANDLE_SIZE`/`HANDLE_OUTSET` — the grab
|
|
27
|
+
* area grows independently of the drawn square. Re-exported so consumers
|
|
28
|
+
* (`overlay`, `editor`, `index`, tests) keep importing from `./handle.js`.
|
|
29
|
+
*/
|
|
30
|
+
export { HANDLE_HIT_SLOP, HANDLE_OUTSET, HANDLE_SIZE };
|
|
31
|
+
/**
|
|
32
|
+
* Position (in world coordinates) of a handle on the given bounds. The
|
|
33
|
+
* position is offset outward by `HANDLE_OUTSET` screen pixels so the handle
|
|
34
|
+
* sits outside the shape's bbox — the hit area never overlaps the shape body,
|
|
35
|
+
* making the handle reliably grabable even when the shape covers most of the
|
|
36
|
+
* click target.
|
|
37
|
+
*
|
|
38
|
+
* `zoom` defaults to 1 for callers that need world-coordinate positions
|
|
39
|
+
* (resize math), but the rendering / hit-test path should pass the current
|
|
40
|
+
* viewport zoom so the outset stays constant on screen across zoom levels.
|
|
41
|
+
*/
|
|
42
|
+
export declare const handlePosition: (handle: HandleId, b: Bounds, zoom?: number) => Vec2;
|
|
43
|
+
/**
|
|
44
|
+
* Find which resize handle the point is over, given the shape's world bounds
|
|
45
|
+
* and the current view zoom (hit area stays constant in screen pixels).
|
|
46
|
+
* Returns `null` if nothing is hit.
|
|
47
|
+
*
|
|
48
|
+
* Two grab shapes, so the edge-midpoint dots can be removed from the chrome
|
|
49
|
+
* while edge resize stays available (drag the selection-box side itself):
|
|
50
|
+
*
|
|
51
|
+
* • Corners (`nw/ne/se/sw`) — a square grab at the drawn corner dot (offset
|
|
52
|
+
* outward by `HANDLE_OUTSET`). Checked first so a near-corner point
|
|
53
|
+
* resolves to the diagonal, not an edge.
|
|
54
|
+
* • Edges (`n/s/e/w`) — the WHOLE side of the box: a slop band along the
|
|
55
|
+
* corresponding bounds edge, spanning between the corners. No dot is drawn
|
|
56
|
+
* for these; the side line is the target.
|
|
57
|
+
*
|
|
58
|
+
* Edges only participate when present in `handleSet` (e.g. aspect-locked
|
|
59
|
+
* resize passes `CORNER_HANDLES`, so only corners hit). The returned id feeds
|
|
60
|
+
* the same `resizeBounds` / resize dispatch.
|
|
61
|
+
*
|
|
62
|
+
* `screenHalfSize` defaults to `HANDLE_HIT_SLOP` (mouse); touch hosts pass
|
|
63
|
+
* `TOUCH_HANDLE_HIT_SLOP` so a finger can grab without precision-pointing.
|
|
64
|
+
*/
|
|
65
|
+
export declare const hitHandle: (point: Vec2, b: Bounds, zoom: number, screenHalfSize?: number, handleSet?: readonly HandleId[]) => HandleId | null;
|
|
66
|
+
/**
|
|
67
|
+
* Apply a delta in world coordinates to bounds, using the given handle as the
|
|
68
|
+
* grab point. Anchor (opposite corner) stays fixed. The result may have
|
|
69
|
+
* negative width/height while dragging — `bounds.normalize` in `@math` flips
|
|
70
|
+
* it on commit.
|
|
71
|
+
*/
|
|
72
|
+
export declare const resizeBounds: (b: Bounds, handle: HandleId, delta: Vec2) => Bounds;
|
|
73
|
+
//# sourceMappingURL=handle.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"handle.d.ts","sourceRoot":"","sources":["../src/handle.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAE7E;;;GAGG;AACH,MAAM,MAAM,QAAQ,GAAG,IAAI,GAAG,GAAG,GAAG,IAAI,GAAG,GAAG,GAAG,IAAI,GAAG,GAAG,GAAG,IAAI,GAAG,GAAG,CAAC;AAEzE,eAAO,MAAM,WAAW,EAAE,SAAS,QAAQ,EAAiD,CAAC;AAE7F;;;;GAIG;AACH,eAAO,MAAM,cAAc,EAAE,SAAS,QAAQ,EAA6B,CAAC;AAE5E;;;;;;;GAOG;AACH,eAAO,MAAM,eAAe,GAAI,QAAQ,QAAQ,KAAG,MAelD,CAAC;AAEF;;;;;GAKG;AACH,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,WAAW,EAAE,CAAC;AAEvD;;;;;;;;;;GAUG;AACH,eAAO,MAAM,cAAc,GAAI,QAAQ,QAAQ,EAAE,GAAG,MAAM,EAAE,aAAQ,KAAG,IAwBtE,CAAC;AAEF;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,eAAO,MAAM,SAAS,GACpB,OAAO,IAAI,EACX,GAAG,MAAM,EACT,MAAM,MAAM,EACZ,iBAAgB,MAAwB,EACxC,YAAW,SAAS,QAAQ,EAAgB,KAC3C,QAAQ,GAAG,IAkCb,CAAC;AAEF;;;;;GAKG;AACH,eAAO,MAAM,YAAY,GAAI,GAAG,MAAM,EAAE,QAAQ,QAAQ,EAAE,OAAO,IAAI,KAAG,MAuCvE,CAAC"}
|
package/dist/handle.js
ADDED
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
import { HANDLE_HIT_SLOP, HANDLE_OUTSET, HANDLE_SIZE } from "./constants.js";
|
|
2
|
+
export const ALL_HANDLES = ["nw", "n", "ne", "e", "se", "s", "sw", "w"];
|
|
3
|
+
/**
|
|
4
|
+
* Subset of `ALL_HANDLES` containing only the four corner positions. Used for
|
|
5
|
+
* aspect-locked resize (groups, fixed-ratio media) — only corner drags carry
|
|
6
|
+
* the diagonal that the resize math projects onto a single scale factor.
|
|
7
|
+
*/
|
|
8
|
+
export const CORNER_HANDLES = ["nw", "ne", "se", "sw"];
|
|
9
|
+
/**
|
|
10
|
+
* CSS `cursor` for a resize handle — the bidirectional arrow aligned with the
|
|
11
|
+
* handle's resize axis. Opposite handles share a cursor (e.g. `nw`/`se` →
|
|
12
|
+
* `nwse-resize`). Used by the editor's context-cursor logic.
|
|
13
|
+
*
|
|
14
|
+
* Ignores element rotation — a rotated shape's handles technically want a
|
|
15
|
+
* rotated cursor, but CSS only offers the 8 fixed arrows; we map by handle id.
|
|
16
|
+
*/
|
|
17
|
+
export const cursorForHandle = (handle) => {
|
|
18
|
+
switch (handle) {
|
|
19
|
+
case "nw":
|
|
20
|
+
case "se":
|
|
21
|
+
return "nwse-resize";
|
|
22
|
+
case "ne":
|
|
23
|
+
case "sw":
|
|
24
|
+
return "nesw-resize";
|
|
25
|
+
case "n":
|
|
26
|
+
case "s":
|
|
27
|
+
return "ns-resize";
|
|
28
|
+
case "e":
|
|
29
|
+
case "w":
|
|
30
|
+
return "ew-resize";
|
|
31
|
+
}
|
|
32
|
+
};
|
|
33
|
+
/**
|
|
34
|
+
* Re-exports handle geometry/hit-target constants from `constants.ts`.
|
|
35
|
+
* `HANDLE_HIT_SLOP` is decoupled from `HANDLE_SIZE`/`HANDLE_OUTSET` — the grab
|
|
36
|
+
* area grows independently of the drawn square. Re-exported so consumers
|
|
37
|
+
* (`overlay`, `editor`, `index`, tests) keep importing from `./handle.js`.
|
|
38
|
+
*/
|
|
39
|
+
export { HANDLE_HIT_SLOP, HANDLE_OUTSET, HANDLE_SIZE };
|
|
40
|
+
/**
|
|
41
|
+
* Position (in world coordinates) of a handle on the given bounds. The
|
|
42
|
+
* position is offset outward by `HANDLE_OUTSET` screen pixels so the handle
|
|
43
|
+
* sits outside the shape's bbox — the hit area never overlaps the shape body,
|
|
44
|
+
* making the handle reliably grabable even when the shape covers most of the
|
|
45
|
+
* click target.
|
|
46
|
+
*
|
|
47
|
+
* `zoom` defaults to 1 for callers that need world-coordinate positions
|
|
48
|
+
* (resize math), but the rendering / hit-test path should pass the current
|
|
49
|
+
* viewport zoom so the outset stays constant on screen across zoom levels.
|
|
50
|
+
*/
|
|
51
|
+
export const handlePosition = (handle, b, zoom = 1) => {
|
|
52
|
+
const cx = b.x + b.width / 2;
|
|
53
|
+
const cy = b.y + b.height / 2;
|
|
54
|
+
const maxX = b.x + b.width;
|
|
55
|
+
const maxY = b.y + b.height;
|
|
56
|
+
const o = HANDLE_OUTSET / zoom;
|
|
57
|
+
switch (handle) {
|
|
58
|
+
case "nw":
|
|
59
|
+
return { x: b.x - o, y: b.y - o };
|
|
60
|
+
case "n":
|
|
61
|
+
return { x: cx, y: b.y - o };
|
|
62
|
+
case "ne":
|
|
63
|
+
return { x: maxX + o, y: b.y - o };
|
|
64
|
+
case "e":
|
|
65
|
+
return { x: maxX + o, y: cy };
|
|
66
|
+
case "se":
|
|
67
|
+
return { x: maxX + o, y: maxY + o };
|
|
68
|
+
case "s":
|
|
69
|
+
return { x: cx, y: maxY + o };
|
|
70
|
+
case "sw":
|
|
71
|
+
return { x: b.x - o, y: maxY + o };
|
|
72
|
+
case "w":
|
|
73
|
+
return { x: b.x - o, y: cy };
|
|
74
|
+
}
|
|
75
|
+
};
|
|
76
|
+
/**
|
|
77
|
+
* Find which resize handle the point is over, given the shape's world bounds
|
|
78
|
+
* and the current view zoom (hit area stays constant in screen pixels).
|
|
79
|
+
* Returns `null` if nothing is hit.
|
|
80
|
+
*
|
|
81
|
+
* Two grab shapes, so the edge-midpoint dots can be removed from the chrome
|
|
82
|
+
* while edge resize stays available (drag the selection-box side itself):
|
|
83
|
+
*
|
|
84
|
+
* • Corners (`nw/ne/se/sw`) — a square grab at the drawn corner dot (offset
|
|
85
|
+
* outward by `HANDLE_OUTSET`). Checked first so a near-corner point
|
|
86
|
+
* resolves to the diagonal, not an edge.
|
|
87
|
+
* • Edges (`n/s/e/w`) — the WHOLE side of the box: a slop band along the
|
|
88
|
+
* corresponding bounds edge, spanning between the corners. No dot is drawn
|
|
89
|
+
* for these; the side line is the target.
|
|
90
|
+
*
|
|
91
|
+
* Edges only participate when present in `handleSet` (e.g. aspect-locked
|
|
92
|
+
* resize passes `CORNER_HANDLES`, so only corners hit). The returned id feeds
|
|
93
|
+
* the same `resizeBounds` / resize dispatch.
|
|
94
|
+
*
|
|
95
|
+
* `screenHalfSize` defaults to `HANDLE_HIT_SLOP` (mouse); touch hosts pass
|
|
96
|
+
* `TOUCH_HANDLE_HIT_SLOP` so a finger can grab without precision-pointing.
|
|
97
|
+
*/
|
|
98
|
+
export const hitHandle = (point, b, zoom, screenHalfSize = HANDLE_HIT_SLOP, handleSet = ALL_HANDLES) => {
|
|
99
|
+
const slop = screenHalfSize / zoom;
|
|
100
|
+
// Corners — point-grab at each drawn dot.
|
|
101
|
+
for (const id of handleSet) {
|
|
102
|
+
if (id.length !== 2)
|
|
103
|
+
continue; // skip edges this pass
|
|
104
|
+
const p = handlePosition(id, b, zoom);
|
|
105
|
+
if (Math.abs(point.x - p.x) <= slop && Math.abs(point.y - p.y) <= slop) {
|
|
106
|
+
return id;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
// Edges — slop band along the selection-box side, between the corners.
|
|
110
|
+
const minX = b.x;
|
|
111
|
+
const maxX = b.x + b.width;
|
|
112
|
+
const minY = b.y;
|
|
113
|
+
const maxY = b.y + b.height;
|
|
114
|
+
const onX = point.x >= minX - slop && point.x <= maxX + slop;
|
|
115
|
+
const onY = point.y >= minY - slop && point.y <= maxY + slop;
|
|
116
|
+
for (const id of handleSet) {
|
|
117
|
+
switch (id) {
|
|
118
|
+
case "n":
|
|
119
|
+
if (onX && Math.abs(point.y - minY) <= slop)
|
|
120
|
+
return "n";
|
|
121
|
+
break;
|
|
122
|
+
case "s":
|
|
123
|
+
if (onX && Math.abs(point.y - maxY) <= slop)
|
|
124
|
+
return "s";
|
|
125
|
+
break;
|
|
126
|
+
case "w":
|
|
127
|
+
if (onY && Math.abs(point.x - minX) <= slop)
|
|
128
|
+
return "w";
|
|
129
|
+
break;
|
|
130
|
+
case "e":
|
|
131
|
+
if (onY && Math.abs(point.x - maxX) <= slop)
|
|
132
|
+
return "e";
|
|
133
|
+
break;
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
return null;
|
|
137
|
+
};
|
|
138
|
+
/**
|
|
139
|
+
* Apply a delta in world coordinates to bounds, using the given handle as the
|
|
140
|
+
* grab point. Anchor (opposite corner) stays fixed. The result may have
|
|
141
|
+
* negative width/height while dragging — `bounds.normalize` in `@math` flips
|
|
142
|
+
* it on commit.
|
|
143
|
+
*/
|
|
144
|
+
export const resizeBounds = (b, handle, delta) => {
|
|
145
|
+
let { x, y, width, height } = b;
|
|
146
|
+
switch (handle) {
|
|
147
|
+
case "nw":
|
|
148
|
+
x += delta.x;
|
|
149
|
+
y += delta.y;
|
|
150
|
+
width -= delta.x;
|
|
151
|
+
height -= delta.y;
|
|
152
|
+
break;
|
|
153
|
+
case "n":
|
|
154
|
+
y += delta.y;
|
|
155
|
+
height -= delta.y;
|
|
156
|
+
break;
|
|
157
|
+
case "ne":
|
|
158
|
+
y += delta.y;
|
|
159
|
+
width += delta.x;
|
|
160
|
+
height -= delta.y;
|
|
161
|
+
break;
|
|
162
|
+
case "e":
|
|
163
|
+
width += delta.x;
|
|
164
|
+
break;
|
|
165
|
+
case "se":
|
|
166
|
+
width += delta.x;
|
|
167
|
+
height += delta.y;
|
|
168
|
+
break;
|
|
169
|
+
case "s":
|
|
170
|
+
height += delta.y;
|
|
171
|
+
break;
|
|
172
|
+
case "sw":
|
|
173
|
+
x += delta.x;
|
|
174
|
+
width -= delta.x;
|
|
175
|
+
height += delta.y;
|
|
176
|
+
break;
|
|
177
|
+
case "w":
|
|
178
|
+
x += delta.x;
|
|
179
|
+
width -= delta.x;
|
|
180
|
+
break;
|
|
181
|
+
}
|
|
182
|
+
return { x, y, width, height };
|
|
183
|
+
};
|
|
184
|
+
//# sourceMappingURL=handle.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"handle.js","sourceRoot":"","sources":["../src/handle.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
export type { Mode } from "./modes.js";
|
|
2
|
+
export { DEFAULT_MODE } from "./modes.js";
|
|
3
|
+
export type { Selection } from "./selection.js";
|
|
4
|
+
export * as selection from "./selection.js";
|
|
5
|
+
export type { HandleId } from "./handle.js";
|
|
6
|
+
export { ALL_HANDLES, HANDLE_SIZE, handlePosition, hitHandle, resizeBounds } from "./handle.js";
|
|
7
|
+
export type { InteractionContext, InteractionEvent, InteractionEmit, PressTarget, PointerDownEvent, PointerMoveEvent, PointerUpEvent, PointerCancelEvent, SetModeEvent, } from "./machine.js";
|
|
8
|
+
export { interactionMachine, interpretPressEnd, DRAG_THRESHOLD, boundsFromPoints, } from "./machine.js";
|
|
9
|
+
export type { OverlayStyle, PeerCursor, PeerSelection } from "./overlay.js";
|
|
10
|
+
export { renderOverlay, DEFAULT_OVERLAY_STYLE } from "./overlay.js";
|
|
11
|
+
export { PEER_CURSOR_BROADCAST_INTERVAL_MS } from "./constants.js";
|
|
12
|
+
export { fromPointerEvent, fromKeyboardEvent, fromWheelEvent } from "./dom-events.js";
|
|
13
|
+
export type { InteractiveHitTester } from "./interactive.js";
|
|
14
|
+
export { registerInteractiveHitTester, getInteractiveHitTester } from "./interactive.js";
|
|
15
|
+
export type { EditorOptions, LoadSceneOptions, CursorRole, CursorSpec } from "./editor.js";
|
|
16
|
+
export { Editor } from "./editor.js";
|
|
17
|
+
export type { EditorEvents } from "./editor-events.js";
|
|
18
|
+
export { normalizeHref, safeHref } from "./editor/public/link.js";
|
|
19
|
+
export type { FileDropHandler, FileDropContext, WalkOptions } from "./file-drop.js";
|
|
20
|
+
export { FileDropRegistry, IMAGE_MIME_TYPES, VIDEO_MIME_TYPES, isImageFile, isVideoFile, isSceneJsonFile, readFileAsDataURL, readFileAsText, walkDataTransfer, } from "./file-drop.js";
|
|
21
|
+
export type { Action, ActionCategory, ActionContext, HotkeyMatcher } from "./actions/index.js";
|
|
22
|
+
export { ActionRegistry, defaultActionRegistry, registerBuiltinActions, hasSelection, hasSelectionOrLink, actionUndo, actionRedo, historyActions, actionSelectAll, actionDeleteSelection, actionDuplicateSelection, selectionActions, actionCopy, actionCut, actionPaste, clipboardActions, actionBringToFront, actionSendToBack, zOrderActions, actionGroupSelection, actionUngroupSelection, groupingActions, actionZoomIn, actionZoomOut, actionZoomReset, actionZoomToFit, zoomActions, actionModeSelect, actionModeHand, actionModeRect, actionModeEllipse, actionModeText, actionModeLink, actionModeBrush, actionModeFrame, actionToggleToolLock, actionCancel, modeActions, } from "./actions/index.js";
|
|
23
|
+
export type { PrettyHotkeyDesc } from "./platform.js";
|
|
24
|
+
export { isMac, isWindows, isAndroid, isIOS, isLinux, isFirefox, isSafari, CTRL_OR_CMD_KEY, getDevicePixelRatio, formatHotkey, formatHotkeyParts, } from "./platform.js";
|
|
25
|
+
export type { Annotation, Comment } from "@oh-just-another/scene";
|
|
26
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export { DEFAULT_MODE } from "./modes.js";
|
|
2
|
+
export * as selection from "./selection.js";
|
|
3
|
+
export { ALL_HANDLES, HANDLE_SIZE, handlePosition, hitHandle, resizeBounds } from "./handle.js";
|
|
4
|
+
export { interactionMachine, interpretPressEnd, DRAG_THRESHOLD, boundsFromPoints, } from "./machine.js";
|
|
5
|
+
export { renderOverlay, DEFAULT_OVERLAY_STYLE } from "./overlay.js";
|
|
6
|
+
export { PEER_CURSOR_BROADCAST_INTERVAL_MS } from "./constants.js";
|
|
7
|
+
export { fromPointerEvent, fromKeyboardEvent, fromWheelEvent } from "./dom-events.js";
|
|
8
|
+
export { registerInteractiveHitTester, getInteractiveHitTester } from "./interactive.js";
|
|
9
|
+
export { Editor } from "./editor.js";
|
|
10
|
+
export { normalizeHref, safeHref } from "./editor/public/link.js";
|
|
11
|
+
export { FileDropRegistry, IMAGE_MIME_TYPES, VIDEO_MIME_TYPES, isImageFile, isVideoFile, isSceneJsonFile, readFileAsDataURL, readFileAsText, walkDataTransfer, } from "./file-drop.js";
|
|
12
|
+
export { ActionRegistry, defaultActionRegistry, registerBuiltinActions, hasSelection, hasSelectionOrLink,
|
|
13
|
+
// Re-export individual built-ins so hosts can replace / compose.
|
|
14
|
+
actionUndo, actionRedo, historyActions, actionSelectAll, actionDeleteSelection, actionDuplicateSelection, selectionActions, actionCopy, actionCut, actionPaste, clipboardActions, actionBringToFront, actionSendToBack, zOrderActions, actionGroupSelection, actionUngroupSelection, groupingActions, actionZoomIn, actionZoomOut, actionZoomReset, actionZoomToFit, zoomActions, actionModeSelect, actionModeHand, actionModeRect, actionModeEllipse, actionModeText, actionModeLink, actionModeBrush, actionModeFrame, actionToggleToolLock, actionCancel, modeActions, } from "./actions/index.js";
|
|
15
|
+
export { isMac, isWindows, isAndroid, isIOS, isLinux, isFirefox, isSafari, CTRL_OR_CMD_KEY, getDevicePixelRatio, formatHotkey, formatHotkeyParts, } from "./platform.js";
|
|
16
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAG1C,OAAO,KAAK,SAAS,MAAM,gBAAgB,CAAC;AAG5C,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,cAAc,EAAE,SAAS,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAahG,OAAO,EACL,kBAAkB,EAClB,iBAAiB,EACjB,cAAc,EACd,gBAAgB,GACjB,MAAM,cAAc,CAAC;AAGtB,OAAO,EAAE,aAAa,EAAE,qBAAqB,EAAE,MAAM,cAAc,CAAC;AAEpE,OAAO,EAAE,iCAAiC,EAAE,MAAM,gBAAgB,CAAC;AAEnE,OAAO,EAAE,gBAAgB,EAAE,iBAAiB,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAGtF,OAAO,EAAE,4BAA4B,EAAE,uBAAuB,EAAE,MAAM,kBAAkB,CAAC;AAGzF,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAErC,OAAO,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,yBAAyB,CAAC;AAIlE,OAAO,EACL,gBAAgB,EAChB,gBAAgB,EAChB,gBAAgB,EAChB,WAAW,EACX,WAAW,EACX,eAAe,EACf,iBAAiB,EACjB,cAAc,EACd,gBAAgB,GACjB,MAAM,gBAAgB,CAAC;AAIxB,OAAO,EACL,cAAc,EACd,qBAAqB,EACrB,sBAAsB,EACtB,YAAY,EACZ,kBAAkB;AAClB,iEAAiE;AACjE,UAAU,EACV,UAAU,EACV,cAAc,EACd,eAAe,EACf,qBAAqB,EACrB,wBAAwB,EACxB,gBAAgB,EAChB,UAAU,EACV,SAAS,EACT,WAAW,EACX,gBAAgB,EAChB,kBAAkB,EAClB,gBAAgB,EAChB,aAAa,EACb,oBAAoB,EACpB,sBAAsB,EACtB,eAAe,EACf,YAAY,EACZ,aAAa,EACb,eAAe,EACf,eAAe,EACf,WAAW,EACX,gBAAgB,EAChB,cAAc,EACd,cAAc,EACd,iBAAiB,EACjB,cAAc,EACd,cAAc,EACd,eAAe,EACf,eAAe,EACf,oBAAoB,EACpB,YAAY,EACZ,WAAW,GACZ,MAAM,oBAAoB,CAAC;AAI5B,OAAO,EACL,KAAK,EACL,SAAS,EACT,SAAS,EACT,KAAK,EACL,OAAO,EACP,SAAS,EACT,QAAQ,EACR,eAAe,EACf,mBAAmB,EACnB,YAAY,EACZ,iBAAiB,GAClB,MAAM,eAAe,CAAC"}
|