|
@@ -3,6 +3,7 @@ import * as vec from 'utils/vec'
|
3
|
3
|
import * as svg from 'utils/svg'
|
4
|
4
|
import {
|
5
|
5
|
ArrowShape,
|
|
6
|
+ Bounds,
|
6
|
7
|
ColorStyle,
|
7
|
8
|
DashStyle,
|
8
|
9
|
ShapeHandle,
|
|
@@ -10,7 +11,13 @@ import {
|
10
|
11
|
SizeStyle,
|
11
|
12
|
} from 'types'
|
12
|
13
|
import { registerShapeUtils } from './index'
|
13
|
|
-import { circleFromThreePoints, clamp, isAngleBetween } from 'utils/utils'
|
|
14
|
+import {
|
|
15
|
+ circleFromThreePoints,
|
|
16
|
+ clamp,
|
|
17
|
+ getBoundsCenter,
|
|
18
|
+ isAngleBetween,
|
|
19
|
+ rotateBounds,
|
|
20
|
+} from 'utils/utils'
|
14
|
21
|
import { pointInBounds } from 'utils/bounds'
|
15
|
22
|
import {
|
16
|
23
|
intersectArcBounds,
|
|
@@ -170,25 +177,27 @@ const arrow = registerShapeUtils<ArrowShape>({
|
170
|
177
|
)
|
171
|
178
|
},
|
172
|
179
|
|
173
|
|
- rotateTo(shape, rotation, delta) {
|
|
180
|
+ rotateBy(shape, delta) {
|
174
|
181
|
const { start, end, bend } = shape.handles
|
175
|
|
- // const mp = vec.med(start.point, end.point)
|
176
|
|
- // start.point = vec.rotWith(start.point, mp, delta)
|
177
|
|
- // end.point = vec.rotWith(end.point, mp, delta)
|
178
|
|
- // bend.point = vec.rotWith(bend.point, mp, delta)
|
179
|
|
- // this.onHandleChange(shape, shape.handles)
|
|
182
|
+ const mp = vec.med(start.point, end.point)
|
|
183
|
+ start.point = vec.rotWith(start.point, mp, delta)
|
|
184
|
+ end.point = vec.rotWith(end.point, mp, delta)
|
|
185
|
+ bend.point = vec.rotWith(bend.point, mp, delta)
|
180
|
186
|
|
181
|
|
- // const bounds = this.getBounds(shape)
|
|
187
|
+ this.onHandleChange(shape, shape.handles)
|
182
|
188
|
|
183
|
|
- // const offset = vec.sub([bounds.minX, bounds.minY], shape.point)
|
|
189
|
+ return this
|
|
190
|
+ },
|
184
|
191
|
|
185
|
|
- // this.translateTo(shape, vec.add(shape.point, offset))
|
|
192
|
+ rotateTo(shape, rotation, delta) {
|
|
193
|
+ const { start, end, bend } = shape.handles
|
|
194
|
+ const mp = vec.med(start.point, end.point)
|
|
195
|
+ start.point = vec.rotWith(start.point, mp, delta)
|
|
196
|
+ end.point = vec.rotWith(end.point, mp, delta)
|
|
197
|
+ bend.point = vec.rotWith(bend.point, mp, delta)
|
186
|
198
|
|
187
|
|
- // start.point = vec.sub(start.point, offset)
|
188
|
|
- // end.point = vec.sub(end.point, offset)
|
189
|
|
- // bend.point = vec.sub(bend.point, offset)
|
|
199
|
+ this.onHandleChange(shape, shape.handles)
|
190
|
200
|
|
191
|
|
- shape.rotation = rotation
|
192
|
201
|
return this
|
193
|
202
|
},
|
194
|
203
|
|
|
@@ -202,11 +211,16 @@ const arrow = registerShapeUtils<ArrowShape>({
|
202
|
211
|
},
|
203
|
212
|
|
204
|
213
|
getRotatedBounds(shape) {
|
205
|
|
- if (!this.boundsCache.has(shape)) {
|
206
|
|
- this.boundsCache.set(shape, getBoundsFromPoints(shape.points))
|
207
|
|
- }
|
|
214
|
+ const { start, end } = shape.handles
|
|
215
|
+ return translateBounds(
|
|
216
|
+ getBoundsFromPoints([start.point, end.point], shape.rotation),
|
|
217
|
+ shape.point
|
|
218
|
+ )
|
|
219
|
+ },
|
208
|
220
|
|
209
|
|
- return translateBounds(this.boundsCache.get(shape), shape.point)
|
|
221
|
+ getCenter(shape) {
|
|
222
|
+ const { start, end } = shape.handles
|
|
223
|
+ return vec.add(shape.point, vec.med(start.point, end.point))
|
210
|
224
|
},
|
211
|
225
|
|
212
|
226
|
hitTest(shape, point) {
|
|
@@ -281,6 +295,9 @@ const arrow = registerShapeUtils<ArrowShape>({
|
281
|
295
|
},
|
282
|
296
|
|
283
|
297
|
onHandleChange(shape, handles) {
|
|
298
|
+ // const oldBounds = this.getRotatedBounds(shape)
|
|
299
|
+ // const prevCenter = getBoundsCenter(oldBounds)
|
|
300
|
+
|
284
|
301
|
for (let id in handles) {
|
285
|
302
|
const handle = handles[id]
|
286
|
303
|
|
|
@@ -313,6 +330,27 @@ const arrow = registerShapeUtils<ArrowShape>({
|
313
|
330
|
|
314
|
331
|
shape.handles.bend.point = getBendPoint(shape)
|
315
|
332
|
|
|
333
|
+ // const newBounds = this.getRotatedBounds(shape)
|
|
334
|
+ // const newCenter = getBoundsCenter(newBounds)
|
|
335
|
+
|
|
336
|
+ // shape.point = vec.add(shape.point, vec.neg(vec.sub(newCenter, prevCenter)))
|
|
337
|
+
|
|
338
|
+ return this
|
|
339
|
+ },
|
|
340
|
+
|
|
341
|
+ onSessionComplete(shape) {
|
|
342
|
+ const bounds = this.getBounds(shape)
|
|
343
|
+
|
|
344
|
+ const offset = vec.sub([bounds.minX, bounds.minY], shape.point)
|
|
345
|
+
|
|
346
|
+ this.translateTo(shape, vec.add(shape.point, offset))
|
|
347
|
+
|
|
348
|
+ const { start, end, bend } = shape.handles
|
|
349
|
+
|
|
350
|
+ start.point = vec.sub(start.point, offset)
|
|
351
|
+ end.point = vec.sub(end.point, offset)
|
|
352
|
+ bend.point = vec.sub(bend.point, offset)
|
|
353
|
+
|
316
|
354
|
return this
|
317
|
355
|
},
|
318
|
356
|
|
|
@@ -360,3 +398,44 @@ function getBendPoint(shape: ArrowShape) {
|
360
|
398
|
? midPoint
|
361
|
399
|
: vec.add(midPoint, vec.mul(vec.per(u), bendDist))
|
362
|
400
|
}
|
|
401
|
+
|
|
402
|
+function getResizeOffset(a: Bounds, b: Bounds) {
|
|
403
|
+ const { minX: x0, minY: y0, width: w0, height: h0 } = a
|
|
404
|
+ const { minX: x1, minY: y1, width: w1, height: h1 } = b
|
|
405
|
+
|
|
406
|
+ let delta: number[]
|
|
407
|
+
|
|
408
|
+ if (h0 === h1 && w0 !== w1) {
|
|
409
|
+ if (x0 !== x1) {
|
|
410
|
+ // moving left edge, pin right edge
|
|
411
|
+ delta = vec.sub([x1, y1 + h1 / 2], [x0, y0 + h0 / 2])
|
|
412
|
+ } else {
|
|
413
|
+ // moving right edge, pin left edge
|
|
414
|
+ delta = vec.sub([x1 + w1, y1 + h1 / 2], [x0 + w0, y0 + h0 / 2])
|
|
415
|
+ }
|
|
416
|
+ } else if (h0 !== h1 && w0 === w1) {
|
|
417
|
+ if (y0 !== y1) {
|
|
418
|
+ // moving top edge, pin bottom edge
|
|
419
|
+ delta = vec.sub([x1 + w1 / 2, y1], [x0 + w0 / 2, y0])
|
|
420
|
+ } else {
|
|
421
|
+ // moving bottom edge, pin top edge
|
|
422
|
+ delta = vec.sub([x1 + w1 / 2, y1 + h1], [x0 + w0 / 2, y0 + h0])
|
|
423
|
+ }
|
|
424
|
+ } else if (x0 !== x1) {
|
|
425
|
+ if (y0 !== y1) {
|
|
426
|
+ // moving top left, pin bottom right
|
|
427
|
+ delta = vec.sub([x1, y1], [x0, y0])
|
|
428
|
+ } else {
|
|
429
|
+ // moving bottom left, pin top right
|
|
430
|
+ delta = vec.sub([x1, y1 + h1], [x0, y0 + h0])
|
|
431
|
+ }
|
|
432
|
+ } else if (y0 !== y1) {
|
|
433
|
+ // moving top right, pin bottom left
|
|
434
|
+ delta = vec.sub([x1 + w1, y1], [x0 + w0, y0])
|
|
435
|
+ } else {
|
|
436
|
+ // moving bottom right, pin top left
|
|
437
|
+ delta = vec.sub([x1 + w1, y1 + h1], [x0 + w0, y0 + h0])
|
|
438
|
+ }
|
|
439
|
+
|
|
440
|
+ return delta
|
|
441
|
+}
|