@plait/core 0.22.0 → 0.24.0-next.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.
Files changed (98) hide show
  1. package/board/board.component.interface.d.ts +2 -2
  2. package/constants/index.d.ts +0 -1
  3. package/esm2020/board/board.component.interface.mjs +1 -1
  4. package/esm2020/board/board.component.mjs +71 -18
  5. package/esm2020/constants/index.mjs +1 -2
  6. package/esm2020/constants/keycodes.mjs +1 -1
  7. package/esm2020/constants/resize.mjs +1 -1
  8. package/esm2020/constants/selection.mjs +1 -1
  9. package/esm2020/core/children/children.component.mjs +1 -1
  10. package/esm2020/core/children/effect.mjs +1 -1
  11. package/esm2020/core/element/context-change.mjs +1 -1
  12. package/esm2020/core/element/context.mjs +1 -1
  13. package/esm2020/core/element/element.component.mjs +1 -1
  14. package/esm2020/core/element/plugin-element.mjs +1 -1
  15. package/esm2020/core/island/island-base.component.mjs +1 -1
  16. package/esm2020/interfaces/board.mjs +9 -5
  17. package/esm2020/interfaces/custom-types.mjs +1 -1
  18. package/esm2020/interfaces/element.mjs +1 -1
  19. package/esm2020/interfaces/history.mjs +1 -1
  20. package/esm2020/interfaces/index.mjs +1 -1
  21. package/esm2020/interfaces/node.mjs +1 -1
  22. package/esm2020/interfaces/operation.mjs +1 -1
  23. package/esm2020/interfaces/path-ref.mjs +1 -1
  24. package/esm2020/interfaces/path.mjs +1 -1
  25. package/esm2020/interfaces/plugin-key.mjs +1 -1
  26. package/esm2020/interfaces/plugin.mjs +1 -1
  27. package/esm2020/interfaces/point.mjs +1 -1
  28. package/esm2020/interfaces/pointer.mjs +1 -1
  29. package/esm2020/interfaces/rectangle-client.mjs +1 -1
  30. package/esm2020/interfaces/selection.mjs +1 -1
  31. package/esm2020/interfaces/theme.mjs +1 -1
  32. package/esm2020/interfaces/viewport.mjs +1 -1
  33. package/esm2020/plait-core.mjs +1 -1
  34. package/esm2020/plait.module.mjs +1 -1
  35. package/esm2020/plugins/create-board.mjs +10 -2
  36. package/esm2020/plugins/with-board.mjs +1 -1
  37. package/esm2020/plugins/with-hand.mjs +1 -1
  38. package/esm2020/plugins/with-history.mjs +1 -1
  39. package/esm2020/plugins/with-hotkey.mjs +1 -1
  40. package/esm2020/plugins/with-moving.mjs +6 -4
  41. package/esm2020/plugins/with-options.mjs +1 -1
  42. package/esm2020/plugins/with-selection.mjs +15 -18
  43. package/esm2020/plugins/with-viewport.mjs +1 -1
  44. package/esm2020/public-api.mjs +1 -1
  45. package/esm2020/services/image-context.service.mjs +1 -1
  46. package/esm2020/testing/core/create-board.mjs +1 -1
  47. package/esm2020/testing/core/fake-weak-map.mjs +1 -1
  48. package/esm2020/testing/core/index.mjs +1 -1
  49. package/esm2020/testing/fake-events/event-objects.mjs +1 -1
  50. package/esm2020/testing/fake-events/index.mjs +1 -1
  51. package/esm2020/testing/index.mjs +1 -1
  52. package/esm2020/testing/test-element.mjs +1 -1
  53. package/esm2020/transforms/board.mjs +1 -1
  54. package/esm2020/transforms/general.mjs +1 -1
  55. package/esm2020/transforms/index.mjs +1 -1
  56. package/esm2020/transforms/node.mjs +1 -1
  57. package/esm2020/transforms/selection.mjs +1 -1
  58. package/esm2020/transforms/theme.mjs +1 -1
  59. package/esm2020/transforms/viewport.mjs +1 -1
  60. package/esm2020/utils/board.mjs +1 -1
  61. package/esm2020/utils/clipboard.mjs +45 -0
  62. package/esm2020/utils/common.mjs +1 -1
  63. package/esm2020/utils/dom/common.mjs +1 -1
  64. package/esm2020/utils/dom/environment.mjs +1 -1
  65. package/esm2020/utils/dom/foreign.mjs +1 -1
  66. package/esm2020/utils/dom/index.mjs +1 -1
  67. package/esm2020/utils/draw/arrow.mjs +1 -1
  68. package/esm2020/utils/draw/circle.mjs +1 -1
  69. package/esm2020/utils/draw/line.mjs +1 -1
  70. package/esm2020/utils/draw/rectangle.mjs +1 -1
  71. package/esm2020/utils/element.mjs +1 -1
  72. package/esm2020/utils/environment.mjs +1 -1
  73. package/esm2020/utils/helper.mjs +1 -1
  74. package/esm2020/utils/history.mjs +1 -1
  75. package/esm2020/utils/hotkeys.mjs +1 -1
  76. package/esm2020/utils/id-creator.mjs +1 -1
  77. package/esm2020/utils/index.mjs +3 -1
  78. package/esm2020/utils/math.mjs +1 -1
  79. package/esm2020/utils/moving-element.mjs +1 -1
  80. package/esm2020/utils/selected-element.mjs +1 -1
  81. package/esm2020/utils/to-image.mjs +1 -1
  82. package/esm2020/utils/touch.mjs +8 -0
  83. package/esm2020/utils/tree.mjs +1 -1
  84. package/esm2020/utils/viewport.mjs +1 -1
  85. package/esm2020/utils/weak-maps.mjs +2 -1
  86. package/fesm2015/plait-core.mjs +156 -45
  87. package/fesm2015/plait-core.mjs.map +1 -1
  88. package/fesm2020/plait-core.mjs +156 -42
  89. package/fesm2020/plait-core.mjs.map +1 -1
  90. package/interfaces/board.d.ts +15 -6
  91. package/interfaces/operation.d.ts +1 -1
  92. package/package.json +1 -1
  93. package/plugins/with-selection.d.ts +0 -4
  94. package/styles/styles.scss +7 -1
  95. package/utils/clipboard.d.ts +8 -0
  96. package/utils/index.d.ts +2 -0
  97. package/utils/touch.d.ts +3 -0
  98. package/utils/weak-maps.d.ts +1 -0
@@ -27,6 +27,7 @@ const BOARD_TO_IS_SELECTION_MOVING = new WeakMap();
27
27
  // save no standard selected elements
28
28
  const BOARD_TO_TEMPORARY_ELEMENTS = new WeakMap();
29
29
  const BOARD_TO_MOVING_ELEMENT = new WeakMap();
30
+ const IS_PREVENT_TOUCH_MOVE = new WeakMap();
30
31
  const PATH_REFS = new WeakMap();
31
32
 
32
33
  function depthFirstRecursion(node, callback, recursion, isReverse) {
@@ -230,11 +231,11 @@ const PlaitBoard = {
230
231
  getElementHost(board) {
231
232
  return BOARD_TO_ELEMENT_HOST.get(board)?.host;
232
233
  },
233
- getElementHostUp(board) {
234
- return BOARD_TO_ELEMENT_HOST.get(board)?.hostUp;
234
+ getElementUpperHost(board) {
235
+ return BOARD_TO_ELEMENT_HOST.get(board)?.upperHost;
235
236
  },
236
- getElementHostActive(board) {
237
- return BOARD_TO_ELEMENT_HOST.get(board)?.hostActive;
237
+ getElementActiveHost(board) {
238
+ return BOARD_TO_ELEMENT_HOST.get(board)?.activeHost;
238
239
  },
239
240
  getRoughSVG(board) {
240
241
  return BOARD_TO_ROUGH_SVG.get(board);
@@ -266,6 +267,10 @@ const PlaitBoard = {
266
267
  isPointer(board, pointer) {
267
268
  return board.pointer === pointer;
268
269
  },
270
+ isInPointer(board, pointers) {
271
+ const point = board.pointer;
272
+ return pointers.includes(point);
273
+ },
269
274
  getMovingPointInBoard(board) {
270
275
  return BOARD_TO_MOVING_POINT_IN_BOARD.get(board);
271
276
  },
@@ -869,7 +874,6 @@ var ResizeCursorClass;
869
874
  const ATTACHED_ELEMENT_CLASS_NAME = 'plait-board-attached';
870
875
 
871
876
  const CLIP_BOARD_FORMAT_KEY = 'x-plait-fragment';
872
- const CLIP_BOARD_IMAGE_FORMAT_KEY = 'x-plait-image-fragment';
873
877
  const HOST_CLASS_NAME = 'plait-board-container';
874
878
  const SCROLL_BAR_WIDTH = 20;
875
879
  const MAX_RADIUS = 16;
@@ -1568,6 +1572,57 @@ function downloadImage(url, name) {
1568
1572
  a.remove();
1569
1573
  }
1570
1574
 
1575
+ const getClipboardByKey = (key) => {
1576
+ return `application/x-plait-${key}-fragment`;
1577
+ };
1578
+ const setClipboardData = (data, elements) => {
1579
+ const result = [...elements];
1580
+ const pluginContextResult = getDataFromClipboard(data);
1581
+ if (pluginContextResult) {
1582
+ result.push(...pluginContextResult);
1583
+ }
1584
+ const stringObj = JSON.stringify(result);
1585
+ const encoded = window.btoa(encodeURIComponent(stringObj));
1586
+ data?.setData(`application/${CLIP_BOARD_FORMAT_KEY}`, encoded);
1587
+ };
1588
+ const setClipboardDataByText = (data, text) => {
1589
+ const pluginContextResult = getTextFromClipboard(data);
1590
+ data?.setData(`text/plain`, text + '\n' + pluginContextResult);
1591
+ };
1592
+ const setClipboardDataByMedia = (data, media, key) => {
1593
+ const stringObj = JSON.stringify(media);
1594
+ const encoded = window.btoa(encodeURIComponent(stringObj));
1595
+ data?.setData(getClipboardByKey(key), encoded);
1596
+ };
1597
+ const getDataFromClipboard = (data) => {
1598
+ const encoded = data?.getData(`application/${CLIP_BOARD_FORMAT_KEY}`);
1599
+ let nodesData = [];
1600
+ if (encoded) {
1601
+ const decoded = decodeURIComponent(window.atob(encoded));
1602
+ nodesData = JSON.parse(decoded);
1603
+ }
1604
+ return nodesData;
1605
+ };
1606
+ const getTextFromClipboard = (data) => {
1607
+ return (data ? data.getData(`text/plain`) : '');
1608
+ };
1609
+ const getClipboardDataByMedia = (data, key) => {
1610
+ const encoded = data?.getData(getClipboardByKey(key));
1611
+ let imageItem = null;
1612
+ if (encoded) {
1613
+ const decoded = decodeURIComponent(window.atob(encoded));
1614
+ imageItem = JSON.parse(decoded);
1615
+ }
1616
+ return imageItem;
1617
+ };
1618
+
1619
+ const isPreventTouchMove = (board) => {
1620
+ return !!IS_PREVENT_TOUCH_MOVE.get(board);
1621
+ };
1622
+ const preventTouchMove = (board, state) => {
1623
+ IS_PREVENT_TOUCH_MOVE.set(board, state);
1624
+ };
1625
+
1571
1626
  const PlaitElement = {
1572
1627
  isRootElement(value) {
1573
1628
  const parent = NODE_TO_PARENT.get(value);
@@ -2102,7 +2157,15 @@ function createBoard(children, options) {
2102
2157
  isRecursion: element => true,
2103
2158
  isMovable: element => false,
2104
2159
  getRectangle: element => null,
2105
- applyTheme: (element) => { }
2160
+ applyTheme: (element) => { },
2161
+ pointerDown: (pointer) => { },
2162
+ pointerMove: (pointer) => { },
2163
+ pointerUp: (pointer) => { },
2164
+ pointerCancel: (pointer) => { },
2165
+ pointerOut: (pointer) => { },
2166
+ pointerLeave: (pointer) => { },
2167
+ globalPointerMove: (pointer) => { },
2168
+ globalPointerUp: (pointer) => { },
2106
2169
  };
2107
2170
  return board;
2108
2171
  }
@@ -2258,7 +2321,7 @@ function withHandPointer(board) {
2258
2321
  }
2259
2322
 
2260
2323
  function withSelection(board) {
2261
- const { mousedown, globalMousemove, globalMouseup, onChange } = board;
2324
+ const { pointerDown, globalPointerMove, globalPointerUp, onChange } = board;
2262
2325
  let start = null;
2263
2326
  let end = null;
2264
2327
  let selectionMovingG;
@@ -2266,12 +2329,12 @@ function withSelection(board) {
2266
2329
  let previousSelectedElements;
2267
2330
  // prevent text from being selected when user pressed main pointer and is moving
2268
2331
  let needPreventNativeSelectionWhenMoving = false;
2269
- board.mousedown = (event) => {
2332
+ board.pointerDown = (event) => {
2270
2333
  if (event.target instanceof Element && !event.target.closest('.plait-richtext-container')) {
2271
2334
  needPreventNativeSelectionWhenMoving = true;
2272
2335
  }
2273
2336
  if (!isMainPointer(event)) {
2274
- mousedown(event);
2337
+ pointerDown(event);
2275
2338
  return;
2276
2339
  }
2277
2340
  const options = board.getPluginOptions(PlaitPluginKey.withSelection);
@@ -2280,7 +2343,7 @@ function withSelection(board) {
2280
2343
  const hitElements = getHitElements(board, { ranges: [range] });
2281
2344
  const selectedElements = getSelectedElements(board);
2282
2345
  if (hitElements.length === 1 && selectedElements.includes(hitElements[0]) && !options.isDisabledSelect) {
2283
- mousedown(event);
2346
+ pointerDown(event);
2284
2347
  return;
2285
2348
  }
2286
2349
  if (PlaitBoard.isPointer(board, PlaitPointerType.selection) &&
@@ -2288,13 +2351,15 @@ function withSelection(board) {
2288
2351
  options.isMultiple &&
2289
2352
  !options.isDisabledSelect) {
2290
2353
  start = point;
2354
+ preventTouchMove(board, true);
2291
2355
  }
2292
2356
  Transforms.setSelection(board, { ranges: [range] });
2293
- mousedown(event);
2357
+ pointerDown(event);
2294
2358
  };
2295
- board.globalMousemove = (event) => {
2359
+ board.globalPointerMove = (event) => {
2296
2360
  if (needPreventNativeSelectionWhenMoving) {
2297
- preventNativeSelection(board, event);
2361
+ // prevent text from being selected
2362
+ event.preventDefault();
2298
2363
  }
2299
2364
  if (start) {
2300
2365
  const movedTarget = transformPoint(board, toPoint(event.x, event.y, PlaitBoard.getHost(board)));
@@ -2318,9 +2383,9 @@ function withSelection(board) {
2318
2383
  PlaitBoard.getHost(board).append(selectionMovingG);
2319
2384
  }
2320
2385
  }
2321
- globalMousemove(event);
2386
+ globalPointerMove(event);
2322
2387
  };
2323
- board.globalMouseup = (event) => {
2388
+ board.globalPointerUp = (event) => {
2324
2389
  if (start && end) {
2325
2390
  selectionMovingG?.remove();
2326
2391
  clearSelectionMoving(board);
@@ -2339,7 +2404,8 @@ function withSelection(board) {
2339
2404
  start = null;
2340
2405
  end = null;
2341
2406
  needPreventNativeSelectionWhenMoving = false;
2342
- globalMouseup(event);
2407
+ preventTouchMove(board, false);
2408
+ globalPointerUp(event);
2343
2409
  };
2344
2410
  board.onChange = () => {
2345
2411
  const options = board.getPluginOptions(PlaitPluginKey.withSelection);
@@ -2424,12 +2490,6 @@ function createSelectionOuterG(board, selectElements) {
2424
2490
  fillStyle: 'solid'
2425
2491
  });
2426
2492
  }
2427
- /**
2428
- * prevent text from being selected
2429
- */
2430
- const preventNativeSelection = (board, event) => {
2431
- event.preventDefault();
2432
- };
2433
2493
 
2434
2494
  function withViewport(board) {
2435
2495
  const { onChange } = board;
@@ -2485,7 +2545,7 @@ function withMoving(board) {
2485
2545
  mousedown(event);
2486
2546
  };
2487
2547
  board.mousemove = event => {
2488
- if (startPoint && activeElements?.length && !PlaitBoard.hasBeenTextEditing(board)) {
2548
+ if (startPoint && activeElements.length && !PlaitBoard.hasBeenTextEditing(board)) {
2489
2549
  if (!isPreventDefault) {
2490
2550
  isPreventDefault = true;
2491
2551
  }
@@ -2497,10 +2557,12 @@ function withMoving(board) {
2497
2557
  if (Math.abs(offsetX) > offsetBuffer || Math.abs(offsetY) > offsetBuffer) {
2498
2558
  throttleRAF(() => {
2499
2559
  const currentElements = activeElements.map(activeElement => {
2500
- const [x, y] = activeElement?.points[0];
2560
+ const points = activeElement.points || [];
2561
+ const [x, y] = activeElement.points[0];
2562
+ const newPoints = points.map(p => [p[0] + offsetX, p[1] + offsetY]);
2501
2563
  const index = board.children.findIndex(item => item.id === activeElement.id);
2502
2564
  Transforms.setNode(board, {
2503
- points: [[x + offsetX, y + offsetY]]
2565
+ points: newPoints
2504
2566
  }, [index]);
2505
2567
  MERGING.set(board, true);
2506
2568
  return PlaitNode.get(board, [index]);
@@ -2848,8 +2910,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.5", ngImpor
2848
2910
  }] } });
2849
2911
 
2850
2912
  const ElementHostClass = 'element-host';
2851
- const ElementHostUpClass = 'element-host-up';
2852
- const ElementHostActiveClass = 'element-host-active';
2913
+ const ElementUpperHostClass = 'element-upper-host';
2914
+ const ElementActiveHostClass = 'element-active-host';
2853
2915
  class PlaitBoardComponent {
2854
2916
  get host() {
2855
2917
  return this.svg.nativeElement;
@@ -2899,8 +2961,8 @@ class PlaitBoardComponent {
2899
2961
  }
2900
2962
  ngOnInit() {
2901
2963
  const elementHost = this.host.querySelector(`.${ElementHostClass}`);
2902
- const elementHostUp = this.host.querySelector(`.${ElementHostUpClass}`);
2903
- const elementHostActive = this.host.querySelector(`.${ElementHostActiveClass}`);
2964
+ const elementUpperHost = this.host.querySelector(`.${ElementUpperHostClass}`);
2965
+ const elementActiveHost = this.host.querySelector(`.${ElementActiveHostClass}`);
2904
2966
  const roughSVG = rough.svg(this.host, {
2905
2967
  options: { roughness: 0, strokeWidth: 1 }
2906
2968
  });
@@ -2921,8 +2983,8 @@ class PlaitBoardComponent {
2921
2983
  BOARD_TO_HOST.set(this.board, this.host);
2922
2984
  BOARD_TO_ELEMENT_HOST.set(this.board, {
2923
2985
  host: elementHost,
2924
- hostUp: elementHostUp,
2925
- hostActive: elementHostActive
2986
+ upperHost: elementUpperHost,
2987
+ activeHost: elementActiveHost
2926
2988
  });
2927
2989
  BOARD_TO_ON_CHANGE.set(this.board, () => {
2928
2990
  this.ngZone.run(() => {
@@ -2983,34 +3045,67 @@ class PlaitBoardComponent {
2983
3045
  .subscribe((event) => {
2984
3046
  this.board.mousedown(event);
2985
3047
  });
3048
+ fromEvent(this.host, 'pointerdown')
3049
+ .pipe(takeUntil(this.destroy$))
3050
+ .subscribe((event) => {
3051
+ this.board.pointerDown(event);
3052
+ });
2986
3053
  fromEvent(this.host, 'mousemove')
2987
3054
  .pipe(takeUntil(this.destroy$))
2988
3055
  .subscribe((event) => {
2989
3056
  BOARD_TO_MOVING_POINT_IN_BOARD.set(this.board, [event.x, event.y]);
2990
3057
  this.board.mousemove(event);
2991
3058
  });
3059
+ fromEvent(this.host, 'pointermove')
3060
+ .pipe(takeUntil(this.destroy$))
3061
+ .subscribe((event) => {
3062
+ BOARD_TO_MOVING_POINT_IN_BOARD.set(this.board, [event.x, event.y]);
3063
+ this.board.pointerMove(event);
3064
+ });
2992
3065
  fromEvent(this.host, 'mouseleave')
2993
3066
  .pipe(takeUntil(this.destroy$))
2994
3067
  .subscribe((event) => {
2995
3068
  BOARD_TO_MOVING_POINT_IN_BOARD.delete(this.board);
2996
3069
  this.board.mouseleave(event);
2997
3070
  });
3071
+ fromEvent(this.host, 'pointerleave')
3072
+ .pipe(takeUntil(this.destroy$))
3073
+ .subscribe((event) => {
3074
+ BOARD_TO_MOVING_POINT_IN_BOARD.delete(this.board);
3075
+ this.board.pointerLeave(event);
3076
+ });
2998
3077
  fromEvent(document, 'mousemove')
2999
3078
  .pipe(takeUntil(this.destroy$))
3000
3079
  .subscribe((event) => {
3001
3080
  BOARD_TO_MOVING_POINT.set(this.board, [event.x, event.y]);
3002
3081
  this.board.globalMousemove(event);
3003
3082
  });
3083
+ fromEvent(document, 'pointermove')
3084
+ .pipe(takeUntil(this.destroy$))
3085
+ .subscribe((event) => {
3086
+ BOARD_TO_MOVING_POINT.set(this.board, [event.x, event.y]);
3087
+ this.board.globalPointerMove(event);
3088
+ });
3004
3089
  fromEvent(this.host, 'mouseup')
3005
3090
  .pipe(takeUntil(this.destroy$))
3006
3091
  .subscribe((event) => {
3007
3092
  this.board.mouseup(event);
3008
3093
  });
3094
+ fromEvent(this.host, 'pointerup')
3095
+ .pipe(takeUntil(this.destroy$))
3096
+ .subscribe((event) => {
3097
+ this.board.pointerUp(event);
3098
+ });
3009
3099
  fromEvent(document, 'mouseup')
3010
3100
  .pipe(takeUntil(this.destroy$))
3011
3101
  .subscribe((event) => {
3012
3102
  this.board.globalMouseup(event);
3013
3103
  });
3104
+ fromEvent(document, 'pointerup')
3105
+ .pipe(takeUntil(this.destroy$))
3106
+ .subscribe((event) => {
3107
+ this.board.globalPointerUp(event);
3108
+ });
3014
3109
  fromEvent(this.host, 'dblclick')
3015
3110
  .pipe(takeUntil(this.destroy$), filter(() => this.isFocused && !PlaitBoard.hasBeenTextEditing(this.board)))
3016
3111
  .subscribe((event) => {
@@ -3021,7 +3116,11 @@ class PlaitBoardComponent {
3021
3116
  this.board.globalKeydown(event);
3022
3117
  }), filter(event => this.isFocused && !PlaitBoard.hasBeenTextEditing(this.board) && !hasInputOrTextareaTarget(event.target)))
3023
3118
  .subscribe((event) => {
3024
- this.board?.keydown(event);
3119
+ const selectedElements = getSelectedElements(this.board);
3120
+ if (selectedElements.length > 0 && (hotkeys.isDeleteBackward(event) || hotkeys.isDeleteForward(event))) {
3121
+ this.board.deleteFragment(null);
3122
+ }
3123
+ this.board.keydown(event);
3025
3124
  });
3026
3125
  fromEvent(document, 'keyup')
3027
3126
  .pipe(takeUntil(this.destroy$), filter(() => this.isFocused && !PlaitBoard.hasBeenTextEditing(this.board)))
@@ -3031,8 +3130,12 @@ class PlaitBoardComponent {
3031
3130
  fromEvent(document, 'copy')
3032
3131
  .pipe(takeUntil(this.destroy$), filter(() => this.isFocused && !PlaitBoard.hasBeenTextEditing(this.board)))
3033
3132
  .subscribe((event) => {
3034
- event.preventDefault();
3035
- this.board?.setFragment(event.clipboardData);
3133
+ const selectedElements = getSelectedElements(this.board);
3134
+ if (selectedElements.length > 0) {
3135
+ event.preventDefault();
3136
+ const rectangle = getRectangleByElements(this.board, selectedElements, false);
3137
+ this.board.setFragment(event.clipboardData, rectangle);
3138
+ }
3036
3139
  });
3037
3140
  fromEvent(document, 'paste')
3038
3141
  .pipe(takeUntil(this.destroy$), filter(() => this.isFocused && !PlaitBoard.isReadonly(this.board) && !PlaitBoard.hasBeenTextEditing(this.board)))
@@ -3046,9 +3149,13 @@ class PlaitBoardComponent {
3046
3149
  fromEvent(document, 'cut')
3047
3150
  .pipe(takeUntil(this.destroy$), filter(() => this.isFocused && !PlaitBoard.isReadonly(this.board) && !PlaitBoard.hasBeenTextEditing(this.board)))
3048
3151
  .subscribe((event) => {
3049
- event.preventDefault();
3050
- this.board?.setFragment(event.clipboardData);
3051
- this.board?.deleteFragment(event.clipboardData);
3152
+ const selectedElements = getSelectedElements(this.board);
3153
+ if (selectedElements.length > 0) {
3154
+ event.preventDefault();
3155
+ const rectangle = getRectangleByElements(this.board, selectedElements, false);
3156
+ this.board.setFragment(event.clipboardData, rectangle);
3157
+ this.board.deleteFragment(event.clipboardData);
3158
+ }
3052
3159
  });
3053
3160
  }
3054
3161
  viewportScrollListener() {
@@ -3073,6 +3180,13 @@ class PlaitBoardComponent {
3073
3180
  setIsFromScrolling(this.board, true);
3074
3181
  });
3075
3182
  });
3183
+ this.ngZone.runOutsideAngular(() => {
3184
+ fromEvent(this.viewportContainer.nativeElement, 'touchmove', { passive: false }).subscribe((event) => {
3185
+ if (isPreventTouchMove(this.board)) {
3186
+ event.preventDefault();
3187
+ }
3188
+ });
3189
+ });
3076
3190
  }
3077
3191
  elementResizeListener() {
3078
3192
  this.resizeObserver = new ResizeObserver(() => {
@@ -3118,8 +3232,8 @@ PlaitBoardComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", ve
3118
3232
  <div class="viewport-container" #viewportContainer>
3119
3233
  <svg #svg width="100%" height="100%" style="position: relative;" class="board-host-svg">
3120
3234
  <g class="element-host"></g>
3121
- <g class="element-host-up"></g>
3122
- <g class="element-host-active"></g>
3235
+ <g class="element-upper-host"></g>
3236
+ <g class="element-active-host"></g>
3123
3237
  </svg>
3124
3238
  <plait-children [board]="board" [effect]="effect"></plait-children>
3125
3239
  </div>
@@ -3133,8 +3247,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.5", ngImpor
3133
3247
  <div class="viewport-container" #viewportContainer>
3134
3248
  <svg #svg width="100%" height="100%" style="position: relative;" class="board-host-svg">
3135
3249
  <g class="element-host"></g>
3136
- <g class="element-host-up"></g>
3137
- <g class="element-host-active"></g>
3250
+ <g class="element-upper-host"></g>
3251
+ <g class="element-active-host"></g>
3138
3252
  </svg>
3139
3253
  <plait-children [board]="board" [effect]="effect"></plait-children>
3140
3254
  </div>
@@ -3363,5 +3477,5 @@ function createModModifierKeys() {
3363
3477
  * Generated bundle index. Do not edit.
3364
3478
  */
3365
3479
 
3366
- export { A, ALT, APOSTROPHE, ATTACHED_ELEMENT_CLASS_NAME, AT_SIGN, B, BACKSLASH, BACKSPACE, BOARD_TO_COMPONENT, BOARD_TO_ELEMENT_HOST, BOARD_TO_HOST, BOARD_TO_IS_SELECTION_MOVING, BOARD_TO_MOVING_ELEMENT, BOARD_TO_MOVING_POINT, BOARD_TO_MOVING_POINT_IN_BOARD, BOARD_TO_ON_CHANGE, BOARD_TO_ROUGH_SVG, BOARD_TO_SELECTED_ELEMENT, BOARD_TO_TEMPORARY_ELEMENTS, BOARD_TO_VIEWPORT_ORIGINATION, BoardTransforms, C, CAPS_LOCK, CLIP_BOARD_FORMAT_KEY, CLIP_BOARD_IMAGE_FORMAT_KEY, CLOSE_SQUARE_BRACKET, COMMA, CONTEXT_MENU, CONTROL, ColorfulThemeColor, D, DASH, DELETE, DOWN_ARROW, DarkThemeColor, DefaultThemeColor, E, EIGHT, ELEMENT_TO_COMPONENT, END, ENTER, EQUALS, ESCAPE, F, F1, F10, F11, F12, F2, F3, F4, F5, F6, F7, F8, F9, FF_EQUALS, FF_MINUS, FF_MUTE, FF_SEMICOLON, FF_VOLUME_DOWN, FF_VOLUME_UP, FIRST_MEDIA, FIVE, FLUSHING, FOUR, G, H, HOME, HOST_CLASS_NAME, I, INSERT, IS_APPLE, IS_BOARD_CACHE, IS_CHROME, IS_CHROME_LEGACY, IS_EDGE_LEGACY, IS_FIREFOX, IS_IOS, IS_MAC, IS_SAFARI, IS_TEXT_EDITABLE, J, K, L, LAST_MEDIA, LEFT_ARROW, M, MAC_ENTER, MAC_META, MAC_WK_CMD_LEFT, MAC_WK_CMD_RIGHT, MAX_RADIUS, MERGING, META, MUTE, N, NINE, NODE_TO_INDEX, NODE_TO_PARENT, NS, NUMPAD_DIVIDE, NUMPAD_EIGHT, NUMPAD_FIVE, NUMPAD_FOUR, NUMPAD_MINUS, NUMPAD_MULTIPLY, NUMPAD_NINE, NUMPAD_ONE, NUMPAD_PERIOD, NUMPAD_PLUS, NUMPAD_SEVEN, NUMPAD_SIX, NUMPAD_THREE, NUMPAD_TWO, NUMPAD_ZERO, NUM_CENTER, NUM_LOCK, O, ONE, OPEN_SQUARE_BRACKET, P, PAGE_DOWN, PAGE_UP, PATH_REFS, PAUSE, PERIOD, PLUS_SIGN, POINTER_BUTTON, PRESS_AND_MOVE_BUFFER, PRINT_SCREEN, Path, PlaitBoard, PlaitBoardComponent, PlaitChildrenElement, PlaitContextService, PlaitElement, PlaitElementComponent, PlaitHistoryBoard, PlaitIslandBaseComponent, PlaitIslandPopoverBaseComponent, PlaitModule, PlaitNode, PlaitOperation, PlaitPluginElementComponent, PlaitPluginKey, PlaitPointerType, Point, Q, QUESTION_MARK, R, RIGHT_ARROW, RectangleClient, ResizeCursorClass, RetroThemeColor, S, SAVING, SCROLL_BAR_WIDTH, SCROLL_LOCK, SELECTION_BORDER_COLOR, SELECTION_FILL_COLOR, SEMICOLON, SEVEN, SHIFT, SINGLE_QUOTE, SIX, SLASH, SPACE, Selection, SoftThemeColor, StarryThemeColor, T, TAB, THREE, TILDE, TWO, ThemeColorMode, ThemeColors, Transforms, U, UP_ARROW, V, VOLUME_DOWN, VOLUME_UP, Viewport, W, X, Y, Z, ZERO, addMovingElements, addSelectedElement, arrowPoints, cacheMovingElements, cacheSelectedElements, clampZoomLevel, clearNodeWeakMap, clearSelectedElement, clearSelectionMoving, clearViewportOrigination, createFakeEvent, createForeignObject, createG, createKeyboardEvent, createModModifierKeys, createMouseEvent, createPath, createPointerEvent, createSVG, createSelectionOuterG, createTestingBoard, createText, createTouchEvent, debounce, deleteTemporaryElements, depthFirstRecursion, distanceBetweenPointAndPoint, distanceBetweenPointAndRectangle, distanceBetweenPointAndSegment, downloadImage, drawArrow, drawBezierPath, drawCircle, drawLine, drawLinearPath, drawRoundRectangle, fakeNodeWeakMap, getBoardRectangle, getElementHostBBox, getHitElementOfRoot, getHitElements, getIsRecursionFunc, getMovingElements, getRealScrollBarWidth, getRectangleByElements, getSelectedElements, getTemporaryElements, getViewBox, getViewBoxCenterPoint, getViewportContainerRect, getViewportOrigination, hasBeforeContextChange, hasInputOrTextareaTarget, hasOnBoardChange, hasOnContextChanged, hotkeys, idCreator, initializeViewBox, initializeViewportContainer, initializeViewportOffset, inverse, isDOMElement, isDOMNode, isFromScrolling, isFromViewportChange, isHitElements, isInPlaitBoard, isMainPointer, isNullOrUndefined, isSecondaryPointer, isSelectedElement, isSelectionMoving, isSetViewportOperation, normalizePoint, preventNativeSelection, removeMovingElements, removeSelectedElement, rotate, scrollToRectangle, setIsFromScrolling, setIsFromViewportChange, setSVGViewBox, setSelectionMoving, shouldClear, shouldMerge, shouldSave, throttleRAF, toImage, toPoint, transformPoint, transformPoints, updateForeignObject, updateViewportContainerScroll, updateViewportOffset, updateViewportOrigination, withMoving, withOptions, withSelection };
3480
+ export { A, ALT, APOSTROPHE, ATTACHED_ELEMENT_CLASS_NAME, AT_SIGN, B, BACKSLASH, BACKSPACE, BOARD_TO_COMPONENT, BOARD_TO_ELEMENT_HOST, BOARD_TO_HOST, BOARD_TO_IS_SELECTION_MOVING, BOARD_TO_MOVING_ELEMENT, BOARD_TO_MOVING_POINT, BOARD_TO_MOVING_POINT_IN_BOARD, BOARD_TO_ON_CHANGE, BOARD_TO_ROUGH_SVG, BOARD_TO_SELECTED_ELEMENT, BOARD_TO_TEMPORARY_ELEMENTS, BOARD_TO_VIEWPORT_ORIGINATION, BoardTransforms, C, CAPS_LOCK, CLIP_BOARD_FORMAT_KEY, CLOSE_SQUARE_BRACKET, COMMA, CONTEXT_MENU, CONTROL, ColorfulThemeColor, D, DASH, DELETE, DOWN_ARROW, DarkThemeColor, DefaultThemeColor, E, EIGHT, ELEMENT_TO_COMPONENT, END, ENTER, EQUALS, ESCAPE, F, F1, F10, F11, F12, F2, F3, F4, F5, F6, F7, F8, F9, FF_EQUALS, FF_MINUS, FF_MUTE, FF_SEMICOLON, FF_VOLUME_DOWN, FF_VOLUME_UP, FIRST_MEDIA, FIVE, FLUSHING, FOUR, G, H, HOME, HOST_CLASS_NAME, I, INSERT, IS_APPLE, IS_BOARD_CACHE, IS_CHROME, IS_CHROME_LEGACY, IS_EDGE_LEGACY, IS_FIREFOX, IS_IOS, IS_MAC, IS_PREVENT_TOUCH_MOVE, IS_SAFARI, IS_TEXT_EDITABLE, J, K, L, LAST_MEDIA, LEFT_ARROW, M, MAC_ENTER, MAC_META, MAC_WK_CMD_LEFT, MAC_WK_CMD_RIGHT, MAX_RADIUS, MERGING, META, MUTE, N, NINE, NODE_TO_INDEX, NODE_TO_PARENT, NS, NUMPAD_DIVIDE, NUMPAD_EIGHT, NUMPAD_FIVE, NUMPAD_FOUR, NUMPAD_MINUS, NUMPAD_MULTIPLY, NUMPAD_NINE, NUMPAD_ONE, NUMPAD_PERIOD, NUMPAD_PLUS, NUMPAD_SEVEN, NUMPAD_SIX, NUMPAD_THREE, NUMPAD_TWO, NUMPAD_ZERO, NUM_CENTER, NUM_LOCK, O, ONE, OPEN_SQUARE_BRACKET, P, PAGE_DOWN, PAGE_UP, PATH_REFS, PAUSE, PERIOD, PLUS_SIGN, POINTER_BUTTON, PRESS_AND_MOVE_BUFFER, PRINT_SCREEN, Path, PlaitBoard, PlaitBoardComponent, PlaitChildrenElement, PlaitContextService, PlaitElement, PlaitElementComponent, PlaitHistoryBoard, PlaitIslandBaseComponent, PlaitIslandPopoverBaseComponent, PlaitModule, PlaitNode, PlaitOperation, PlaitPluginElementComponent, PlaitPluginKey, PlaitPointerType, Point, Q, QUESTION_MARK, R, RIGHT_ARROW, RectangleClient, ResizeCursorClass, RetroThemeColor, S, SAVING, SCROLL_BAR_WIDTH, SCROLL_LOCK, SELECTION_BORDER_COLOR, SELECTION_FILL_COLOR, SEMICOLON, SEVEN, SHIFT, SINGLE_QUOTE, SIX, SLASH, SPACE, Selection, SoftThemeColor, StarryThemeColor, T, TAB, THREE, TILDE, TWO, ThemeColorMode, ThemeColors, Transforms, U, UP_ARROW, V, VOLUME_DOWN, VOLUME_UP, Viewport, W, X, Y, Z, ZERO, addMovingElements, addSelectedElement, arrowPoints, cacheMovingElements, cacheSelectedElements, clampZoomLevel, clearNodeWeakMap, clearSelectedElement, clearSelectionMoving, clearViewportOrigination, createFakeEvent, createForeignObject, createG, createKeyboardEvent, createModModifierKeys, createMouseEvent, createPath, createPointerEvent, createSVG, createSelectionOuterG, createTestingBoard, createText, createTouchEvent, debounce, deleteTemporaryElements, depthFirstRecursion, distanceBetweenPointAndPoint, distanceBetweenPointAndRectangle, distanceBetweenPointAndSegment, downloadImage, drawArrow, drawBezierPath, drawCircle, drawLine, drawLinearPath, drawRoundRectangle, fakeNodeWeakMap, getBoardRectangle, getClipboardByKey, getClipboardDataByMedia, getDataFromClipboard, getElementHostBBox, getHitElementOfRoot, getHitElements, getIsRecursionFunc, getMovingElements, getRealScrollBarWidth, getRectangleByElements, getSelectedElements, getTemporaryElements, getTextFromClipboard, getViewBox, getViewBoxCenterPoint, getViewportContainerRect, getViewportOrigination, hasBeforeContextChange, hasInputOrTextareaTarget, hasOnBoardChange, hasOnContextChanged, hotkeys, idCreator, initializeViewBox, initializeViewportContainer, initializeViewportOffset, inverse, isDOMElement, isDOMNode, isFromScrolling, isFromViewportChange, isHitElements, isInPlaitBoard, isMainPointer, isNullOrUndefined, isPreventTouchMove, isSecondaryPointer, isSelectedElement, isSelectionMoving, isSetViewportOperation, normalizePoint, preventTouchMove, removeMovingElements, removeSelectedElement, rotate, scrollToRectangle, setClipboardData, setClipboardDataByMedia, setClipboardDataByText, setIsFromScrolling, setIsFromViewportChange, setSVGViewBox, setSelectionMoving, shouldClear, shouldMerge, shouldSave, throttleRAF, toImage, toPoint, transformPoint, transformPoints, updateForeignObject, updateViewportContainerScroll, updateViewportOffset, updateViewportOrigination, withMoving, withOptions, withSelection };
3367
3481
  //# sourceMappingURL=plait-core.mjs.map