@fieldnotes/core 0.4.1 → 0.5.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/dist/index.cjs +47 -12
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +12 -2
- package/dist/index.d.ts +12 -2
- package/dist/index.js +46 -12
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -69,6 +69,7 @@ __export(index_exports, {
|
|
|
69
69
|
isBindable: () => isBindable,
|
|
70
70
|
isNearBezier: () => isNearBezier,
|
|
71
71
|
parseState: () => parseState,
|
|
72
|
+
snapPoint: () => snapPoint,
|
|
72
73
|
unbindArrow: () => unbindArrow,
|
|
73
74
|
updateBoundArrow: () => updateBoundArrow
|
|
74
75
|
});
|
|
@@ -195,6 +196,14 @@ function migrateElement(obj) {
|
|
|
195
196
|
}
|
|
196
197
|
}
|
|
197
198
|
|
|
199
|
+
// src/core/snap.ts
|
|
200
|
+
function snapPoint(point, gridSize) {
|
|
201
|
+
return {
|
|
202
|
+
x: Math.round(point.x / gridSize) * gridSize || 0,
|
|
203
|
+
y: Math.round(point.y / gridSize) * gridSize || 0
|
|
204
|
+
};
|
|
205
|
+
}
|
|
206
|
+
|
|
198
207
|
// src/core/auto-save.ts
|
|
199
208
|
var DEFAULT_KEY = "fieldnotes-autosave";
|
|
200
209
|
var DEFAULT_DEBOUNCE_MS = 1e3;
|
|
@@ -1577,6 +1586,7 @@ var Viewport = class {
|
|
|
1577
1586
|
this.container = container;
|
|
1578
1587
|
this.camera = new Camera(options.camera);
|
|
1579
1588
|
this.background = new Background(options.background);
|
|
1589
|
+
this._gridSize = options.background?.spacing ?? 24;
|
|
1580
1590
|
this.store = new ElementStore();
|
|
1581
1591
|
this.toolManager = new ToolManager();
|
|
1582
1592
|
this.renderer = new ElementRenderer();
|
|
@@ -1599,7 +1609,9 @@ var Viewport = class {
|
|
|
1599
1609
|
editElement: (id) => this.startEditingElement(id),
|
|
1600
1610
|
setCursor: (cursor) => {
|
|
1601
1611
|
this.wrapper.style.cursor = cursor;
|
|
1602
|
-
}
|
|
1612
|
+
},
|
|
1613
|
+
snapToGrid: false,
|
|
1614
|
+
gridSize: this._gridSize
|
|
1603
1615
|
};
|
|
1604
1616
|
this.inputHandler = new InputHandler(this.wrapper, this.camera, {
|
|
1605
1617
|
toolManager: this.toolManager,
|
|
@@ -1644,6 +1656,8 @@ var Viewport = class {
|
|
|
1644
1656
|
toolContext;
|
|
1645
1657
|
resizeObserver = null;
|
|
1646
1658
|
animFrameId = 0;
|
|
1659
|
+
_snapToGrid = false;
|
|
1660
|
+
_gridSize;
|
|
1647
1661
|
needsRender = true;
|
|
1648
1662
|
domNodes = /* @__PURE__ */ new Map();
|
|
1649
1663
|
htmlContent = /* @__PURE__ */ new Map();
|
|
@@ -1651,6 +1665,13 @@ var Viewport = class {
|
|
|
1651
1665
|
get ctx() {
|
|
1652
1666
|
return this.canvasEl.getContext("2d");
|
|
1653
1667
|
}
|
|
1668
|
+
get snapToGrid() {
|
|
1669
|
+
return this._snapToGrid;
|
|
1670
|
+
}
|
|
1671
|
+
setSnapToGrid(enabled) {
|
|
1672
|
+
this._snapToGrid = enabled;
|
|
1673
|
+
this.toolContext.snapToGrid = enabled;
|
|
1674
|
+
}
|
|
1654
1675
|
requestRender() {
|
|
1655
1676
|
this.needsRender = true;
|
|
1656
1677
|
}
|
|
@@ -2399,10 +2420,13 @@ var SelectTool = class {
|
|
|
2399
2420
|
this.mode = { type: "idle" };
|
|
2400
2421
|
ctx.setCursor?.("default");
|
|
2401
2422
|
}
|
|
2423
|
+
snap(point, ctx) {
|
|
2424
|
+
return ctx.snapToGrid && ctx.gridSize ? snapPoint(point, ctx.gridSize) : point;
|
|
2425
|
+
}
|
|
2402
2426
|
onPointerDown(state, ctx) {
|
|
2403
2427
|
this.ctx = ctx;
|
|
2404
2428
|
const world = ctx.camera.screenToWorld({ x: state.x, y: state.y });
|
|
2405
|
-
this.lastWorld = world;
|
|
2429
|
+
this.lastWorld = this.snap(world, ctx);
|
|
2406
2430
|
this.currentWorld = world;
|
|
2407
2431
|
const arrowHit = hitTestArrowHandles(world, this._selectedIds, ctx);
|
|
2408
2432
|
if (arrowHit) {
|
|
@@ -2455,9 +2479,10 @@ var SelectTool = class {
|
|
|
2455
2479
|
}
|
|
2456
2480
|
if (this.mode.type === "dragging" && this._selectedIds.length > 0) {
|
|
2457
2481
|
ctx.setCursor?.("move");
|
|
2458
|
-
const
|
|
2459
|
-
const
|
|
2460
|
-
this.lastWorld
|
|
2482
|
+
const snapped = this.snap(world, ctx);
|
|
2483
|
+
const dx = snapped.x - this.lastWorld.x;
|
|
2484
|
+
const dy = snapped.y - this.lastWorld.y;
|
|
2485
|
+
this.lastWorld = snapped;
|
|
2461
2486
|
for (const id of this._selectedIds) {
|
|
2462
2487
|
const el = ctx.store.getById(id);
|
|
2463
2488
|
if (!el || el.locked) continue;
|
|
@@ -2806,7 +2831,7 @@ var ArrowTool = class {
|
|
|
2806
2831
|
this.fromBinding = { elementId: target.id };
|
|
2807
2832
|
this.fromTarget = target;
|
|
2808
2833
|
} else {
|
|
2809
|
-
this.start = world;
|
|
2834
|
+
this.start = ctx.snapToGrid && ctx.gridSize ? snapPoint(world, ctx.gridSize) : world;
|
|
2810
2835
|
this.fromBinding = void 0;
|
|
2811
2836
|
this.fromTarget = null;
|
|
2812
2837
|
}
|
|
@@ -2823,7 +2848,7 @@ var ArrowTool = class {
|
|
|
2823
2848
|
this.end = getElementCenter(target);
|
|
2824
2849
|
this.toTarget = target;
|
|
2825
2850
|
} else {
|
|
2826
|
-
this.end = world;
|
|
2851
|
+
this.end = ctx.snapToGrid && ctx.gridSize ? snapPoint(world, ctx.gridSize) : world;
|
|
2827
2852
|
this.toTarget = null;
|
|
2828
2853
|
}
|
|
2829
2854
|
ctx.requestRender();
|
|
@@ -2918,7 +2943,10 @@ var NoteTool = class {
|
|
|
2918
2943
|
onPointerMove(_state, _ctx) {
|
|
2919
2944
|
}
|
|
2920
2945
|
onPointerUp(state, ctx) {
|
|
2921
|
-
|
|
2946
|
+
let world = ctx.camera.screenToWorld({ x: state.x, y: state.y });
|
|
2947
|
+
if (ctx.snapToGrid && ctx.gridSize) {
|
|
2948
|
+
world = snapPoint(world, ctx.gridSize);
|
|
2949
|
+
}
|
|
2922
2950
|
const note = createNote({
|
|
2923
2951
|
position: world,
|
|
2924
2952
|
size: { ...this.size },
|
|
@@ -2959,7 +2987,10 @@ var TextTool = class {
|
|
|
2959
2987
|
onPointerMove(_state, _ctx) {
|
|
2960
2988
|
}
|
|
2961
2989
|
onPointerUp(state, ctx) {
|
|
2962
|
-
|
|
2990
|
+
let world = ctx.camera.screenToWorld({ x: state.x, y: state.y });
|
|
2991
|
+
if (ctx.snapToGrid && ctx.gridSize) {
|
|
2992
|
+
world = snapPoint(world, ctx.gridSize);
|
|
2993
|
+
}
|
|
2963
2994
|
const textEl = createText({
|
|
2964
2995
|
position: world,
|
|
2965
2996
|
fontSize: this.fontSize,
|
|
@@ -3041,12 +3072,12 @@ var ShapeTool = class {
|
|
|
3041
3072
|
}
|
|
3042
3073
|
onPointerDown(state, ctx) {
|
|
3043
3074
|
this.drawing = true;
|
|
3044
|
-
this.start = ctx.camera.screenToWorld({ x: state.x, y: state.y });
|
|
3075
|
+
this.start = this.snap(ctx.camera.screenToWorld({ x: state.x, y: state.y }), ctx);
|
|
3045
3076
|
this.end = { ...this.start };
|
|
3046
3077
|
}
|
|
3047
3078
|
onPointerMove(state, ctx) {
|
|
3048
3079
|
if (!this.drawing) return;
|
|
3049
|
-
this.end = ctx.camera.screenToWorld({ x: state.x, y: state.y });
|
|
3080
|
+
this.end = this.snap(ctx.camera.screenToWorld({ x: state.x, y: state.y }), ctx);
|
|
3050
3081
|
ctx.requestRender();
|
|
3051
3082
|
}
|
|
3052
3083
|
onPointerUp(_state, ctx) {
|
|
@@ -3110,6 +3141,9 @@ var ShapeTool = class {
|
|
|
3110
3141
|
}
|
|
3111
3142
|
return { position: { x, y }, size: { w, h } };
|
|
3112
3143
|
}
|
|
3144
|
+
snap(point, ctx) {
|
|
3145
|
+
return ctx.snapToGrid && ctx.gridSize ? snapPoint(point, ctx.gridSize) : point;
|
|
3146
|
+
}
|
|
3113
3147
|
onKeyDown = (e) => {
|
|
3114
3148
|
if (e.key === "Shift") this.shiftHeld = true;
|
|
3115
3149
|
};
|
|
@@ -3119,7 +3153,7 @@ var ShapeTool = class {
|
|
|
3119
3153
|
};
|
|
3120
3154
|
|
|
3121
3155
|
// src/index.ts
|
|
3122
|
-
var VERSION = "0.
|
|
3156
|
+
var VERSION = "0.5.0";
|
|
3123
3157
|
// Annotate the CommonJS export names for ESM import in node:
|
|
3124
3158
|
0 && (module.exports = {
|
|
3125
3159
|
AddElementCommand,
|
|
@@ -3171,6 +3205,7 @@ var VERSION = "0.4.1";
|
|
|
3171
3205
|
isBindable,
|
|
3172
3206
|
isNearBezier,
|
|
3173
3207
|
parseState,
|
|
3208
|
+
snapPoint,
|
|
3174
3209
|
unbindArrow,
|
|
3175
3210
|
updateBoundArrow
|
|
3176
3211
|
});
|