@plait/mind 0.2.2 → 0.3.1

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 (130) hide show
  1. package/{drawer/base/base.d.ts → base/base.drawer.d.ts} +1 -1
  2. package/{plugins/emoji → base}/emoji-base.component.d.ts +2 -2
  3. package/{plugins/emoji → base}/index.d.ts +1 -1
  4. package/draw/abstract.d.ts +2 -1
  5. package/draw/indented-link.d.ts +1 -1
  6. package/draw/link/logic-link.d.ts +1 -1
  7. package/draw/node.d.ts +5 -0
  8. package/draw/topic.d.ts +16 -0
  9. package/{plugins/emoji → drawer}/emoji.drawer.d.ts +3 -3
  10. package/drawer/quick-insert.drawer.d.ts +1 -1
  11. package/esm2020/base/base.drawer.mjs +17 -0
  12. package/esm2020/base/emoji-base.component.mjs +33 -0
  13. package/esm2020/base/index.mjs +3 -0
  14. package/esm2020/draw/abstract.mjs +8 -7
  15. package/esm2020/draw/indented-link.mjs +3 -3
  16. package/esm2020/draw/link/abstract-link.mjs +9 -15
  17. package/esm2020/draw/link/logic-link.mjs +9 -9
  18. package/esm2020/draw/node.mjs +21 -0
  19. package/esm2020/draw/topic.mjs +32 -0
  20. package/esm2020/drawer/emoji.drawer.mjs +73 -0
  21. package/esm2020/drawer/quick-insert.drawer.mjs +3 -3
  22. package/esm2020/interfaces/index.mjs +2 -2
  23. package/esm2020/interfaces/pointer.mjs +5 -0
  24. package/esm2020/mind.component.mjs +2 -2
  25. package/esm2020/mind.module.mjs +5 -5
  26. package/esm2020/node.component.mjs +11 -10
  27. package/esm2020/plugins/with-abstract-resize.board.mjs +12 -0
  28. package/esm2020/plugins/with-abstract-resize.mjs +107 -0
  29. package/esm2020/plugins/with-mind-create.mjs +85 -0
  30. package/esm2020/plugins/with-mind-extend.mjs +11 -0
  31. package/esm2020/plugins/with-mind.board.mjs +2 -0
  32. package/esm2020/plugins/with-mind.mjs +30 -16
  33. package/esm2020/plugins/with-node-dnd.mjs +162 -0
  34. package/esm2020/public-api.mjs +5 -3
  35. package/esm2020/transforms/abstract-node.mjs +3 -2
  36. package/esm2020/transforms/emoji.mjs +37 -0
  37. package/esm2020/transforms/index.mjs +7 -3
  38. package/esm2020/transforms/node.mjs +40 -33
  39. package/esm2020/utils/abstract/common.mjs +64 -31
  40. package/esm2020/utils/abstract/resize.mjs +3 -2
  41. package/esm2020/utils/clipboard.mjs +16 -18
  42. package/esm2020/utils/dnd/common.mjs +35 -0
  43. package/esm2020/utils/dnd/detector.mjs +268 -0
  44. package/esm2020/utils/dnd/draw.mjs +161 -0
  45. package/esm2020/utils/index.mjs +6 -6
  46. package/esm2020/utils/mind.mjs +6 -129
  47. package/esm2020/utils/node/adjust-node.mjs +49 -0
  48. package/esm2020/utils/node/common.mjs +6 -0
  49. package/esm2020/utils/node/create-node.mjs +61 -0
  50. package/esm2020/utils/node/index.mjs +4 -0
  51. package/esm2020/utils/point-placement.mjs +22 -2
  52. package/esm2020/utils/position/emoji.mjs +31 -0
  53. package/esm2020/utils/position/index.mjs +4 -0
  54. package/esm2020/utils/position/node.mjs +34 -0
  55. package/esm2020/utils/position/topic.mjs +14 -0
  56. package/esm2020/utils/space/emoji.mjs +19 -0
  57. package/esm2020/utils/space/layout-options.mjs +72 -0
  58. package/esm2020/utils/space/node-space.mjs +77 -0
  59. package/fesm2015/plait-mind.mjs +1464 -1631
  60. package/fesm2015/plait-mind.mjs.map +1 -1
  61. package/fesm2020/plait-mind.mjs +1486 -1642
  62. package/fesm2020/plait-mind.mjs.map +1 -1
  63. package/interfaces/index.d.ts +1 -1
  64. package/interfaces/pointer.d.ts +3 -0
  65. package/mind.module.d.ts +2 -2
  66. package/node.component.d.ts +3 -3
  67. package/package.json +3 -3
  68. package/{interfaces/abstract.d.ts → plugins/with-abstract-resize.board.d.ts} +2 -2
  69. package/plugins/with-mind-create.d.ts +11 -0
  70. package/plugins/with-mind-extend.d.ts +3 -0
  71. package/plugins/{with-extend-mind.d.ts → with-mind.board.d.ts} +4 -4
  72. package/plugins/with-mind.d.ts +1 -1
  73. package/public-api.d.ts +4 -2
  74. package/styles/styles.scss +5 -2
  75. package/transforms/abstract-node.d.ts +1 -1
  76. package/transforms/emoji.d.ts +6 -0
  77. package/transforms/index.d.ts +3 -0
  78. package/transforms/node.d.ts +5 -5
  79. package/utils/abstract/common.d.ts +19 -4
  80. package/utils/abstract/resize.d.ts +2 -1
  81. package/utils/dnd/common.d.ts +7 -0
  82. package/utils/dnd/detector.d.ts +31 -0
  83. package/utils/dnd/draw.d.ts +9 -0
  84. package/utils/index.d.ts +5 -5
  85. package/utils/mind.d.ts +3 -22
  86. package/utils/node/adjust-node.d.ts +5 -0
  87. package/utils/{node.d.ts → node/common.d.ts} +1 -1
  88. package/utils/node/create-node.d.ts +14 -0
  89. package/utils/node/index.d.ts +3 -0
  90. package/utils/point-placement.d.ts +8 -1
  91. package/utils/position/emoji.d.ts +7 -0
  92. package/utils/position/index.d.ts +3 -0
  93. package/utils/position/node.d.ts +12 -0
  94. package/utils/position/topic.d.ts +16 -0
  95. package/utils/space/emoji.d.ts +7 -0
  96. package/{layout-option.d.ts → utils/space/layout-options.d.ts} +1 -1
  97. package/utils/{node-space.d.ts → space/node-space.d.ts} +4 -4
  98. package/draw/link.d.ts +0 -3
  99. package/draw/richtext.d.ts +0 -15
  100. package/draw/shape.d.ts +0 -3
  101. package/esm2020/draw/link.mjs +0 -160
  102. package/esm2020/draw/richtext.mjs +0 -39
  103. package/esm2020/draw/shape.mjs +0 -18
  104. package/esm2020/drawer/base/base.mjs +0 -17
  105. package/esm2020/interfaces/abstract.mjs +0 -12
  106. package/esm2020/layout-option.mjs +0 -72
  107. package/esm2020/plugins/emoji/emoji-base.component.mjs +0 -33
  108. package/esm2020/plugins/emoji/emoji.drawer.mjs +0 -72
  109. package/esm2020/plugins/emoji/emoji.mjs +0 -47
  110. package/esm2020/plugins/emoji/index.mjs +0 -3
  111. package/esm2020/plugins/with-abstract.mjs +0 -106
  112. package/esm2020/plugins/with-dnd.mjs +0 -179
  113. package/esm2020/plugins/with-extend-mind.mjs +0 -11
  114. package/esm2020/utils/direction-corrector.mjs +0 -54
  115. package/esm2020/utils/direction-detector.mjs +0 -56
  116. package/esm2020/utils/dnd.mjs +0 -122
  117. package/esm2020/utils/draw-placeholder.mjs +0 -313
  118. package/esm2020/utils/drop-target-corrector.mjs +0 -87
  119. package/esm2020/utils/graph.mjs +0 -24
  120. package/esm2020/utils/node-space.mjs +0 -77
  121. package/esm2020/utils/node.mjs +0 -6
  122. package/plugins/emoji/emoji.d.ts +0 -11
  123. package/utils/direction-corrector.d.ts +0 -4
  124. package/utils/direction-detector.d.ts +0 -9
  125. package/utils/dnd.d.ts +0 -16
  126. package/utils/draw-placeholder.d.ts +0 -42
  127. package/utils/drop-target-corrector.d.ts +0 -9
  128. package/utils/graph.d.ts +0 -5
  129. /package/plugins/{with-abstract.d.ts → with-abstract-resize.d.ts} +0 -0
  130. /package/plugins/{with-dnd.d.ts → with-node-dnd.d.ts} +0 -0
@@ -1,122 +0,0 @@
1
- import { MindElement } from '../interfaces/element';
2
- import { isChildElement } from './mind';
3
- import { Path, PlaitBoard, Transforms, ELEMENT_TO_COMPONENT, PlaitElement } from '@plait/core';
4
- import { isHorizontalLogicLayout, isIndentedLayout, isLeftLayout, isRightLayout, isTopLayout, isBottomLayout, isVerticalLogicLayout } from '@plait/layouts';
5
- import { deleteElementHandleAbstract, findUpElement, insertElementHandleAbstract } from '../utils';
6
- import { MindTransforms } from '../transforms';
7
- export const isValidTarget = (origin, target) => {
8
- return origin !== target && !isChildElement(origin, target);
9
- };
10
- export const addActiveOnDragOrigin = (activeElement, isOrigin = true) => {
11
- const activeComponent = PlaitElement.getComponent(activeElement);
12
- if (isOrigin) {
13
- activeComponent.g.classList.add('dragging-origin');
14
- }
15
- else {
16
- activeComponent.g.classList.add('dragging-child');
17
- }
18
- !activeElement.isCollapsed &&
19
- activeElement.children.forEach(child => {
20
- addActiveOnDragOrigin(child, false);
21
- });
22
- };
23
- export const removeActiveOnDragOrigin = (activeElement, isOrigin = true) => {
24
- const activeComponent = PlaitElement.getComponent(activeElement);
25
- if (isOrigin) {
26
- activeComponent.g.classList.remove('dragging-origin');
27
- }
28
- else {
29
- activeComponent.g.classList.remove('dragging-child');
30
- }
31
- !activeElement.isCollapsed &&
32
- activeElement.children.forEach(child => {
33
- removeActiveOnDragOrigin(child, false);
34
- });
35
- };
36
- export const updatePathByLayoutAndDropTarget = (targetPath, layout, dropTarget) => {
37
- // 上下布局:左右是兄弟节点,上下是子节点
38
- if (isVerticalLogicLayout(layout)) {
39
- if (isTopLayout(layout) && dropTarget.detectResult === 'top') {
40
- targetPath.push(dropTarget.target.children.length);
41
- }
42
- if (isBottomLayout(layout) && dropTarget.detectResult === 'bottom') {
43
- targetPath.push(dropTarget.target.children.length);
44
- }
45
- // 如果是左,位置不变,右则插入到下一个兄弟节点
46
- if (dropTarget.detectResult === 'right') {
47
- targetPath = Path.next(targetPath);
48
- }
49
- }
50
- // 水平布局/标准布局:上下是兄弟节点,左右是子节点
51
- if (isHorizontalLogicLayout(layout)) {
52
- if (dropTarget.detectResult === 'right') {
53
- targetPath.push(dropTarget.target.children.length);
54
- }
55
- if (dropTarget.detectResult === 'left') {
56
- targetPath.push(dropTarget.target.children.length);
57
- }
58
- // 如果是上,位置不变,下插入到下一个兄弟节点
59
- if (dropTarget.detectResult === 'bottom') {
60
- targetPath = Path.next(targetPath);
61
- }
62
- }
63
- // 缩进布局:上下是兄弟节点,左右是子节点,但上(左上/右上),探测到上是子节点,下则位置不变,反之同理。
64
- if (isIndentedLayout(layout)) {
65
- if (isTopLayout(layout) && dropTarget.detectResult === 'top') {
66
- targetPath = Path.next(targetPath);
67
- }
68
- if (isBottomLayout(layout) && dropTarget.detectResult === 'bottom') {
69
- targetPath = Path.next(targetPath);
70
- }
71
- if (isLeftLayout(layout) && dropTarget.detectResult === 'left') {
72
- targetPath.push(dropTarget.target.children.length);
73
- }
74
- if (isRightLayout(layout) && dropTarget.detectResult === 'right') {
75
- targetPath.push(dropTarget.target.children.length);
76
- }
77
- }
78
- return targetPath;
79
- };
80
- export const updateRightNodeCount = (board, activeComponent, targetComponent, detectResult) => {
81
- let rightNodeCount;
82
- const mindElement = findUpElement(targetComponent.node.origin).root;
83
- const mindComponent = ELEMENT_TO_COMPONENT.get(mindElement);
84
- const activeIndex = mindComponent?.root.children.indexOf(activeComponent.node);
85
- const targetIndex = mindComponent?.root.children.indexOf(targetComponent.node);
86
- const activeParent = MindElement.getParent(activeComponent.element);
87
- const targetParent = MindElement.findParent(targetComponent.element);
88
- const isActiveOnRight = activeIndex !== -1 && activeIndex <= activeParent.rightNodeCount - 1;
89
- const isTargetOnRight = targetParent && targetIndex !== -1 && targetIndex <= targetParent.rightNodeCount - 1;
90
- const isBothOnRight = isActiveOnRight && isTargetOnRight;
91
- const rootChildCount = mindComponent.root.children?.length;
92
- const rootRightNodeCount = mindComponent?.root.origin.rightNodeCount;
93
- if (!isBothOnRight) {
94
- if (isActiveOnRight) {
95
- rightNodeCount = rootChildCount < rootRightNodeCount ? rootChildCount - 1 : rootRightNodeCount - 1;
96
- Transforms.setNode(board, { rightNodeCount }, PlaitBoard.findPath(board, activeParent));
97
- }
98
- if (isTargetOnRight && detectResult !== 'right') {
99
- rightNodeCount = rootChildCount < rootRightNodeCount ? rootRightNodeCount : rootRightNodeCount + 1;
100
- const parent = MindElement.getParent(targetComponent.element);
101
- Transforms.setNode(board, { rightNodeCount }, PlaitBoard.findPath(board, parent));
102
- }
103
- //二级子节点拖动到根节点左侧
104
- if (targetComponent.node.origin.isRoot && detectResult === 'left' && activeIndex === -1) {
105
- rightNodeCount = rootChildCount;
106
- Transforms.setNode(board, { rightNodeCount }, PlaitBoard.findPath(board, targetComponent.element));
107
- }
108
- }
109
- };
110
- const IS_DRAGGING = new WeakMap();
111
- export const isDragging = (board) => {
112
- return !!IS_DRAGGING.get(board);
113
- };
114
- export const setIsDragging = (board, state) => {
115
- IS_DRAGGING.set(board, state);
116
- };
117
- export const updateAbstractInDnd = (board, deletableElements, originPath) => {
118
- const refs = insertElementHandleAbstract(board, originPath, false);
119
- deleteElementHandleAbstract(board, deletableElements, refs);
120
- MindTransforms.setAbstractsByRefs(board, refs);
121
- };
122
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZG5kLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vcGFja2FnZXMvbWluZC9zcmMvdXRpbHMvZG5kLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxXQUFXLEVBQUUsTUFBTSx1QkFBdUIsQ0FBQztBQUVwRCxPQUFPLEVBQUUsY0FBYyxFQUFFLE1BQU0sUUFBUSxDQUFDO0FBQ3hDLE9BQU8sRUFBRSxJQUFJLEVBQUUsVUFBVSxFQUFFLFVBQVUsRUFBRSxvQkFBb0IsRUFBRSxZQUFZLEVBQUUsTUFBTSxhQUFhLENBQUM7QUFDL0YsT0FBTyxFQUNILHVCQUF1QixFQUN2QixnQkFBZ0IsRUFDaEIsWUFBWSxFQUNaLGFBQWEsRUFDYixXQUFXLEVBRVgsY0FBYyxFQUNkLHFCQUFxQixFQUN4QixNQUFNLGdCQUFnQixDQUFDO0FBR3hCLE9BQU8sRUFBRSwyQkFBMkIsRUFBRSxhQUFhLEVBQUUsMkJBQTJCLEVBQUUsTUFBTSxVQUFVLENBQUM7QUFFbkcsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUUvQyxNQUFNLENBQUMsTUFBTSxhQUFhLEdBQUcsQ0FBQyxNQUFtQixFQUFFLE1BQW1CLEVBQUUsRUFBRTtJQUN0RSxPQUFPLE1BQU0sS0FBSyxNQUFNLElBQUksQ0FBQyxjQUFjLENBQUMsTUFBTSxFQUFFLE1BQU0sQ0FBQyxDQUFDO0FBQ2hFLENBQUMsQ0FBQztBQUVGLE1BQU0sQ0FBQyxNQUFNLHFCQUFxQixHQUFHLENBQUMsYUFBMEIsRUFBRSxRQUFRLEdBQUcsSUFBSSxFQUFFLEVBQUU7SUFDakYsTUFBTSxlQUFlLEdBQUcsWUFBWSxDQUFDLFlBQVksQ0FBQyxhQUFhLENBQXNCLENBQUM7SUFDdEYsSUFBSSxRQUFRLEVBQUU7UUFDVixlQUFlLENBQUMsQ0FBQyxDQUFDLFNBQVMsQ0FBQyxHQUFHLENBQUMsaUJBQWlCLENBQUMsQ0FBQztLQUN0RDtTQUFNO1FBQ0gsZUFBZSxDQUFDLENB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QyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgTWluZEVsZW1lbnQgfSBmcm9tICcuLi9pbnRlcmZhY2VzL2VsZW1lbnQnO1xuaW1wb3J0IHsgTWluZE5vZGVDb21wb25lbnQgfSBmcm9tICcuLi9ub2RlLmNvbXBvbmVudCc7XG5pbXBvcnQgeyBpc0NoaWxkRWxlbWVudCB9IGZyb20gJy4vbWluZCc7XG5pbXBvcnQgeyBQYXRoLCBQbGFpdEJvYXJkLCBUcmFuc2Zvcm1zLCBFTEVNRU5UX1RPX0NPTVBPTkVOVCwgUGxhaXRFbGVtZW50IH0gZnJvbSAnQHBsYWl0L2NvcmUnO1xuaW1wb3J0IHtcbiAgICBpc0hvcml6b250YWxMb2dpY0xheW91dCxcbiAgICBpc0luZGVudGVkTGF5b3V0LFxuICAgIGlzTGVmdExheW91dCxcbiAgICBpc1JpZ2h0TGF5b3V0LFxuICAgIGlzVG9wTGF5b3V0LFxuICAgIE1pbmRMYXlvdXRUeXBlLFxuICAgIGlzQm90dG9tTGF5b3V0LFxuICAgIGlzVmVydGljYWxMb2dpY0xheW91dFxufSBmcm9tICdAcGxhaXQvbGF5b3V0cyc7XG5pbXBvcnQgeyBQbGFpdE1pbmQgfSBmcm9tICcuLi9pbnRlcmZhY2VzL2VsZW1lbnQnO1xuaW1wb3J0IHsgRGV0ZWN0UmVzdWx0LCBNaW5kTm9kZSB9IGZyb20gJy4uL2ludGVyZmFjZXMvbm9kZSc7XG5pbXBvcnQgeyBkZWxldGVFbGVtZW50SGFuZGxlQWJzdHJhY3QsIGZpbmRVcEVsZW1lbnQsIGluc2VydEVsZW1lbnRIYW5kbGVBYnN0cmFjdCB9IGZyb20gJy4uL3V0aWxzJztcbmltcG9ydCB7IFBsYWl0TWluZENvbXBvbmVudCB9IGZyb20gJy4uL21pbmQuY29tcG9uZW50JztcbmltcG9ydCB7IE1pbmRUcmFuc2Zvcm1zIH0gZnJvbSAnLi4vdHJhbnNmb3Jtcyc7XG5cbmV4cG9ydCBjb25zdCBpc1ZhbGlkVGFyZ2V0ID0gKG9yaWdpbjogTWluZEVsZW1lbnQsIHRhcmdldDogTWluZEVsZW1lbnQpID0+IHtcbiAgICByZXR1cm4gb3JpZ2luICE9PSB0YXJnZXQgJiYgIWlzQ2hpbGRFbGVtZW50KG9yaWdpbiwgdGFyZ2V0KTtcbn07XG5cbmV4cG9ydCBjb25zdCBhZGRBY3RpdmVPbkRyYWdPcmlnaW4gPSAoYWN0aXZlRWxlbWVudDogTWluZEVsZW1lbnQsIGlzT3JpZ2luID0gdHJ1ZSkgPT4ge1xuICAgIGNvbnN0IGFjdGl2ZUNvbXBvbmVudCA9IFBsYWl0RWxlbWVudC5nZXRDb21wb25lbnQoYWN0aXZlRWxlbWVudCkgYXMgTWluZE5vZGVDb21wb25lbnQ7XG4gICAgaWYgKGlzT3JpZ2luKSB7XG4gICAgICAgIGFjdGl2ZUNvbXBvbmVudC5nLmNsYXNzTGlzdC5hZGQoJ2RyYWdnaW5nLW9yaWdpbicpO1xuICAgIH0gZWxzZSB7XG4gICAgICAgIGFjdGl2ZUNvbXBvbmVudC5nLmNsYXNzTGlzdC5hZGQoJ2RyYWdnaW5nLWNoaWxkJyk7XG4gICAgfVxuICAgICFhY3RpdmVFbGVtZW50LmlzQ29sbGFwc2VkICYmXG4gICAgICAgIGFjdGl2ZUVsZW1lbnQuY2hpbGRyZW4uZm9yRWFjaChjaGlsZCA9PiB7XG4gICAgICAgICAgICBhZGRBY3RpdmVPbkRyYWdPcmlnaW4oY2hpbGQsIGZhbHNlKTtcbiAgICAgICAgfSk7XG59O1xuXG5leHBvcnQgY29uc3QgcmVtb3ZlQWN0aXZlT25EcmFnT3JpZ2luID0gKGFjdGl2ZUVsZW1lbnQ6IE1pbmRFbGVtZW50LCBpc09yaWdpbiA9IHRydWUpID0+IHtcbiAgICBjb25zdCBhY3RpdmVDb21wb25lbnQgPSBQbGFpdEVsZW1lbnQuZ2V0Q29tcG9uZW50KGFjdGl2ZUVsZW1lbnQpIGFzIE1pbmROb2RlQ29tcG9uZW50O1xuICAgIGlmIChpc09yaWdpbikge1xuICAgICAgICBhY3RpdmVDb21wb25lbnQuZy5jbGFzc0xpc3QucmVtb3ZlKCdkcmFnZ2luZy1vcmlnaW4nKTtcbiAgICB9IGVsc2Uge1xuICAgICAgICBhY3RpdmVDb21wb25lbnQuZy5jbGFzc0xpc3QucmVtb3ZlKCdkcmFnZ2luZy1jaGlsZCcpO1xuICAgIH1cbiAgICAhYWN0aXZlRWxlbWVudC5pc0NvbGxhcHNlZCAmJlxuICAgICAgICBhY3RpdmVFbGVtZW50LmNoaWxkcmVuLmZvckVhY2goY2hpbGQgPT4ge1xuICAgICAgICAgICAgcmVtb3ZlQWN0aXZlT25EcmFnT3JpZ2luKGNoaWxkLCBmYWxzZSk7XG4gICAgICAgIH0pO1xufTtcblxuZXhwb3J0IGNvbnN0IHVwZGF0ZVBhdGhCeUxheW91dEFuZERyb3BUYXJnZXQgPSAoXG4gICAgdGFyZ2V0UGF0aDogUGF0aCxcbiAgICBsYXlvdXQ6IE1pbmRMYXlvdXRUeXBlLFxuICAgIGRyb3BUYXJnZXQ6IHsgdGFyZ2V0OiBNaW5kRWxlbWVudDsgZGV0ZWN0UmVzdWx0OiBEZXRlY3RSZXN1bHQgfVxuKSA9PiB7XG4gICAgLy8g5LiK5LiL5biD5bGA77ya5bem5Y+z5piv5YWE5byf6IqC54K577yM5LiK5LiL5piv5a2Q6IqC54K5XG4gICAgaWYgKGlzVmVydGljYWxMb2dpY0xheW91dChsYXlvdXQpKSB7XG4gICAgICAgIGlmIChpc1RvcExheW91dChsYXlvdXQpICYmIGRyb3BUYXJnZXQuZGV0ZWN0UmVzdWx0ID09PSAndG9wJykge1xuICAgICAgICAgICAgdGFyZ2V0UGF0aC5wdXNoKGRyb3BUYXJnZXQudGFyZ2V0LmNoaWxkcmVuLmxlbmd0aCk7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGlzQm90dG9tTGF5b3V0KGxheW91dCkgJiYgZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQgPT09ICdib3R0b20nKSB7XG4gICAgICAgICAgICB0YXJnZXRQYXRoLnB1c2goZHJvcFRhcmdldC50YXJnZXQuY2hpbGRyZW4ubGVuZ3RoKTtcbiAgICAgICAgfVxuICAgICAgICAvLyDlpoLmnpzmmK/lt6bvvIzkvY3nva7kuI3lj5jvvIzlj7PliJnmj5LlhaXliLDkuIvkuIDkuKrlhYTlvJ/oioLngrlcbiAgICAgICAgaWYgKGRyb3BUYXJnZXQuZGV0ZWN0UmVzdWx0ID09PSAncmlnaHQnKSB7XG4gICAgICAgICAgICB0YXJnZXRQYXRoID0gUGF0aC5uZXh0KHRhcmdldFBhdGgpO1xuICAgICAgICB9XG4gICAgfVxuICAgIC8vIOawtOW5s+W4g+WxgC/moIflh4bluIPlsYDvvJrkuIrkuIvmmK/lhYTlvJ/oioLngrnvvIzlt6blj7PmmK/lrZDoioLngrlcbiAgICBpZiAoaXNIb3Jpem9udGFsTG9naWNMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICBpZiAoZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQgPT09ICdyaWdodCcpIHtcbiAgICAgICAgICAgIHRhcmdldFBhdGgucHVzaChkcm9wVGFyZ2V0LnRhcmdldC5jaGlsZHJlbi5sZW5ndGgpO1xuICAgICAgICB9XG4gICAgICAgIGlmIChkcm9wVGFyZ2V0LmRldGVjdFJlc3VsdCA9PT0gJ2xlZnQnKSB7XG4gICAgICAgICAgICB0YXJnZXRQYXRoLnB1c2goZHJvcFRhcmdldC50YXJnZXQuY2hpbGRyZW4ubGVuZ3RoKTtcbiAgICAgICAgfVxuICAgICAgICAvLyDlpoLmnpzmmK/kuIrvvIzkvY3nva7kuI3lj5jvvIzkuIvmj5LlhaXliLDkuIvkuIDkuKrlhYTlvJ/oioLngrlcbiAgICAgICAgaWYgKGRyb3BUYXJnZXQuZGV0ZWN0UmVzdWx0ID09PSAnYm90dG9tJykge1xuICAgICAgICAgICAgdGFyZ2V0UGF0aCA9IFBhdGgubmV4dCh0YXJnZXRQYXRoKTtcbiAgICAgICAgfVxuICAgIH1cbiAgICAvLyDnvKnov5vluIPlsYDvvJrkuIrkuIvmmK/lhYTlvJ/oioLngrnvvIzlt6blj7PmmK/lrZDoioLngrnvvIzkvYbkuIrvvIjlt6bkuIov5Y+z5LiK77yJ77yM5o6i5rWL5Yiw5LiK5piv5a2Q6IqC54K577yM5LiL5YiZ5L2N572u5LiN5Y+Y77yM5Y+N5LmL5ZCM55CG44CCXG4gICAgaWYgKGlzSW5kZW50ZWRMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICBpZiAoaXNUb3BMYXlvdXQobGF5b3V0KSAmJiBkcm9wVGFyZ2V0LmRldGVjdFJlc3VsdCA9PT0gJ3RvcCcpIHtcbiAgICAgICAgICAgIHRhcmdldFBhdGggPSBQYXRoLm5leHQodGFyZ2V0UGF0aCk7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGlzQm90dG9tTGF5b3V0KGxheW91dCkgJiYgZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQgPT09ICdib3R0b20nKSB7XG4gICAgICAgICAgICB0YXJnZXRQYXRoID0gUGF0aC5uZXh0KHRhcmdldFBhdGgpO1xuICAgICAgICB9XG4gICAgICAgIGlmIChpc0xlZnRMYXlvdXQobGF5b3V0KSAmJiBkcm9wVGFyZ2V0LmRldGVjdFJlc3VsdCA9PT0gJ2xlZnQnKSB7XG4gICAgICAgICAgICB0YXJnZXRQYXRoLnB1c2goZHJvcFRhcmdldC50YXJnZXQuY2hpbGRyZW4ubGVuZ3RoKTtcbiAgICAgICAgfVxuICAgICAgICBpZiAoaXNSaWdodExheW91dChsYXlvdXQpICYmIGRyb3BUYXJnZXQuZGV0ZWN0UmVzdWx0ID09PSAncmlnaHQnKSB7XG4gICAgICAgICAgICB0YXJnZXRQYXRoLnB1c2goZHJvcFRhcmdldC50YXJnZXQuY2hpbGRyZW4ubGVuZ3RoKTtcbiAgICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gdGFyZ2V0UGF0aDtcbn07XG5cbmV4cG9ydCBjb25zdCB1cGRhdGVSaWdodE5vZGVDb3VudCA9IChcbiAgICBib2FyZDogUGxhaXRCb2FyZCxcbiAgICBhY3RpdmVDb21wb25lbnQ6IE1pbmROb2RlQ29tcG9uZW50LFxuICAgIHRhcmdldENvbXBvbmVudDogTWluZE5vZGVDb21wb25lbnQsXG4gICAgZGV0ZWN0UmVzdWx0OiBEZXRlY3RSZXN1bHRcbikgPT4ge1xuICAgIGxldCByaWdodE5vZGVDb3VudDtcbiAgICBjb25zdCBtaW5kRWxlbWVudCA9IGZpbmRVcEVsZW1lbnQodGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luKS5yb290O1xuICAgIGNvbnN0IG1pbmRDb21wb25lbnQgPSBFTEVNRU5UX1RPX0NPTVBPTkVOVC5nZXQobWluZEVsZW1lbnQgYXMgUGxhaXRNaW5kKSBhcyBQbGFpdE1pbmRDb21wb25lbnQ7XG4gICAgY29uc3QgYWN0aXZlSW5kZXggPSBtaW5kQ29tcG9uZW50Py5yb290LmNoaWxkcmVuLmluZGV4T2YoYWN0aXZlQ29tcG9uZW50Lm5vZGUpIGFzIG51bWJlcjtcbiAgICBjb25zdCB0YXJnZXRJbmRleCA9IG1pbmRDb21wb25lbnQ/LnJvb3QuY2hpbGRyZW4uaW5kZXhPZih0YXJnZXRDb21wb25lbnQubm9kZSkgYXMgbnVtYmVyO1xuICAgIGNvbnN0IGFjdGl2ZVBhcmVudCA9IE1pbmRFbGVtZW50LmdldFBhcmVudChhY3RpdmVDb21wb25lbnQuZWxlbWVudCk7XG4gICAgY29uc3QgdGFyZ2V0UGFyZW50ID0gTWluZEVsZW1lbnQuZmluZFBhcmVudCh0YXJnZXRDb21wb25lbnQuZWxlbWVudCk7XG4gICAgY29uc3QgaXNBY3RpdmVPblJpZ2h0ID0gYWN0aXZlSW5kZXggIT09IC0xICYmIGFjdGl2ZUluZGV4IDw9IChhY3RpdmVQYXJlbnQucmlnaHROb2RlQ291bnQgYXMgbnVtYmVyKSAtIDE7XG4gICAgY29uc3QgaXNUYXJnZXRPblJpZ2h0ID0gdGFyZ2V0UGFyZW50ICYmIHRhcmdldEluZGV4ICE9PSAtMSAmJiB0YXJnZXRJbmRleCA8PSAodGFyZ2V0UGFyZW50LnJpZ2h0Tm9kZUNvdW50IGFzIG51bWJlcikgLSAxO1xuICAgIGNvbnN0IGlzQm90aE9uUmlnaHQgPSBpc0FjdGl2ZU9uUmlnaHQgJiYgaXNUYXJnZXRPblJpZ2h0O1xuICAgIGNvbnN0IHJvb3RDaGlsZENvdW50ID0gbWluZENvbXBvbmVudC5yb290LmNoaWxkcmVuPy5sZW5ndGggYXMgbnVtYmVyO1xuICAgIGNvbnN0IHJvb3RSaWdodE5vZGVDb3VudCA9IG1pbmRDb21wb25lbnQ/LnJvb3Qub3JpZ2luLnJpZ2h0Tm9kZUNvdW50IGFzIG51bWJlcjtcblxuICAgIGlmICghaXNCb3RoT25SaWdodCkge1xuICAgICAgICBpZiAoaXNBY3RpdmVPblJpZ2h0KSB7XG4gICAgICAgICAgICByaWdodE5vZGVDb3VudCA9IHJvb3RDaGlsZENvdW50IDwgcm9vdFJpZ2h0Tm9kZUNvdW50ID8gcm9vdENoaWxkQ291bnQgLSAxIDogcm9vdFJpZ2h0Tm9kZUNvdW50IC0gMTtcbiAgICAgICAgICAgIFRyYW5zZm9ybXMuc2V0Tm9kZShib2FyZCwgeyByaWdodE5vZGVDb3VudCB9LCBQbGFpdEJvYXJkLmZpbmRQYXRoKGJvYXJkLCBhY3RpdmVQYXJlbnQpKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChpc1RhcmdldE9uUmlnaHQgJiYgZGV0ZWN0UmVzdWx0ICE9PSAncmlnaHQnKSB7XG4gICAgICAgICAgICByaWdodE5vZGVDb3VudCA9IHJvb3RDaGlsZENvdW50IDwgcm9vdFJpZ2h0Tm9kZUNvdW50ID8gcm9vdFJpZ2h0Tm9kZUNvdW50IDogcm9vdFJpZ2h0Tm9kZUNvdW50ICsgMTtcbiAgICAgICAgICAgIGNvbnN0IHBhcmVudCA9IE1pbmRFbGVtZW50LmdldFBhcmVudCh0YXJnZXRDb21wb25lbnQuZWxlbWVudCk7XG4gICAgICAgICAgICBUcmFuc2Zvcm1zLnNldE5vZGUoYm9hcmQsIHsgcmlnaHROb2RlQ291bnQgfSwgUGxhaXRCb2FyZC5maW5kUGF0aChib2FyZCwgcGFyZW50KSk7XG4gICAgICAgIH1cblxuICAgICAgICAvL+S6jOe6p+WtkOiKgueCueaLluWKqOWIsOagueiKgueCueW3puS+p1xuICAgICAgICBpZiAodGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luLmlzUm9vdCAmJiBkZXRlY3RSZXN1bHQgPT09ICdsZWZ0JyAmJiBhY3RpdmVJbmRleCA9PT0gLTEpIHtcbiAgICAgICAgICAgIHJpZ2h0Tm9kZUNvdW50ID0gcm9vdENoaWxkQ291bnQ7XG4gICAgICAgICAgICBUcmFuc2Zvcm1zLnNldE5vZGUoYm9hcmQsIHsgcmlnaHROb2RlQ291bnQgfSwgUGxhaXRCb2FyZC5maW5kUGF0aChib2FyZCwgdGFyZ2V0Q29tcG9uZW50LmVsZW1lbnQpKTtcbiAgICAgICAgfVxuICAgIH1cbn07XG5cbmNvbnN0IElTX0RSQUdHSU5HID0gbmV3IFdlYWtNYXA8UGxhaXRCb2FyZCwgYm9vbGVhbj4oKTtcblxuZXhwb3J0IGNvbnN0IGlzRHJhZ2dpbmcgPSAoYm9hcmQ6IFBsYWl0Qm9hcmQpID0+IHtcbiAgICByZXR1cm4gISFJU19EUkFHR0lORy5nZXQoYm9hcmQpO1xufTtcblxuZXhwb3J0IGNvbnN0IHNldElzRHJhZ2dpbmcgPSAoYm9hcmQ6IFBsYWl0Qm9hcmQsIHN0YXRlOiBib29sZWFuKSA9PiB7XG4gICAgSVNfRFJBR0dJTkcuc2V0KGJvYXJkLCBzdGF0ZSk7XG59O1xuXG5leHBvcnQgY29uc3QgdXBkYXRlQWJzdHJhY3RJbkRuZCA9IChib2FyZDogUGxhaXRCb2FyZCwgZGVsZXRhYmxlRWxlbWVudHM6IE1pbmRFbGVtZW50W10sIG9yaWdpblBhdGg6IFBhdGgpID0+IHtcbiAgICBjb25zdCByZWZzID0gaW5zZXJ0RWxlbWVudEhhbmRsZUFic3RyYWN0KGJvYXJkLCBvcmlnaW5QYXRoLCBmYWxzZSk7XG4gICAgZGVsZXRlRWxlbWVudEhhbmRsZUFic3RyYWN0KGJvYXJkLCBkZWxldGFibGVFbGVtZW50cywgcmVmcyk7XG4gICAgTWluZFRyYW5zZm9ybXMuc2V0QWJzdHJhY3RzQnlSZWZzKGJvYXJkLCByZWZzKTtcbn07XG4iXX0=
@@ -1,313 +0,0 @@
1
- import { BASE, PRIMARY_COLOR, STROKE_WIDTH } from '../constants';
2
- import { drawLink } from '../draw/link';
3
- import { MindElement } from '../interfaces';
4
- import { getRectangleByNode } from './graph';
5
- import { PlaitBoard, PlaitElement, drawRoundRectangle } from '@plait/core';
6
- import { MindQueries } from '../queries';
7
- import { getNonAbstractChildren, isBottomLayout, isHorizontalLayout, isHorizontalLogicLayout, isIndentedLayout, isRightLayout, isVerticalLogicLayout } from '@plait/layouts';
8
- import { drawIndentedLink } from '../draw/indented-link';
9
- import { isLeftLayout, isTopLayout } from '@plait/layouts';
10
- import { isStandardLayout } from '@plait/layouts';
11
- import { isMixedLayout } from './layout';
12
- export const drawPlaceholderDropNodeG = (board, dropTarget, fakeDropNodeG) => {
13
- const targetComponent = PlaitElement.getComponent(dropTarget.target);
14
- const targetRect = getRectangleByNode(targetComponent.node);
15
- if (dropTarget.detectResult && ['right', 'left'].includes(dropTarget.detectResult)) {
16
- drawStraightDropNodeG(board, targetRect, dropTarget.detectResult, targetComponent, fakeDropNodeG);
17
- }
18
- const targetParent = MindElement.findParent(targetComponent.element);
19
- if (targetParent && dropTarget.detectResult && ['top', 'bottom'].includes(dropTarget.detectResult)) {
20
- const parentComponent = PlaitElement.getComponent(targetParent);
21
- const targetIndex = parentComponent.node.origin.children.indexOf(targetComponent.node.origin);
22
- drawCurvePlaceholderDropNodeG(board, targetRect, dropTarget.detectResult, targetIndex, targetComponent, parentComponent, fakeDropNodeG);
23
- }
24
- };
25
- export const drawCurvePlaceholderDropNodeG = (board, targetRect, detectResult, targetIndex, targetComponent, parentComponent, fakeDropNodeG) => {
26
- const parentNodeLayout = MindQueries.getCorrectLayoutByElement(board, parentComponent.node.origin);
27
- const layout = MindQueries.getCorrectLayoutByElement(board, targetComponent.node.parent.origin);
28
- const strokeWidth = targetComponent.node.origin.branchWidth ? targetComponent.node.origin.branchWidth : STROKE_WIDTH;
29
- let fakeX = targetComponent.node.x, fakeY = targetRect.y - 30, fakeRectangleStartX = targetRect.x, fakeRectangleEndX = targetRect.x + 30, fakeRectangleStartY = fakeY, fakeRectangleEndY = fakeRectangleStartY + 12, width = 30;
30
- if (isLeftLayout(layout)) {
31
- fakeX = targetComponent.node.x + targetComponent.node.width - 30;
32
- fakeRectangleStartX = targetRect.x + targetRect.width - 30;
33
- fakeRectangleEndX = targetRect.x + targetRect.width;
34
- }
35
- if (isHorizontalLogicLayout(parentNodeLayout)) {
36
- fakeY = getHorizontalFakeY(detectResult, targetIndex, parentComponent.node, targetRect, layout, fakeY);
37
- if (isStandardLayout(parentNodeLayout)) {
38
- const rightNodeCount = parentComponent.node.origin.rightNodeCount || 0;
39
- const idx = parentComponent.node.children.findIndex(x => x === targetComponent.node);
40
- const isLeft = idx >= rightNodeCount;
41
- // 标准布局的左,需要调整 x
42
- if (isLeft) {
43
- fakeX = targetComponent.node.x + targetComponent.node.width - 30;
44
- fakeRectangleStartX = targetRect.x + targetRect.width - 30;
45
- fakeRectangleEndX = targetRect.x + targetRect.width;
46
- }
47
- const isLeftFirst = idx === rightNodeCount;
48
- const isRightLast = idx === rightNodeCount - 1;
49
- // 拖拽至左第一个节点的情况
50
- if (detectResult === 'top' && isLeftFirst) {
51
- fakeY = targetRect.y - targetRect.height;
52
- }
53
- if (detectResult === 'bottom' && isRightLast) {
54
- fakeY = targetRect.y + targetRect.height + 30;
55
- }
56
- }
57
- fakeRectangleStartY = fakeY;
58
- fakeRectangleEndY = fakeRectangleStartY + 12;
59
- }
60
- if (isVerticalLogicLayout(layout)) {
61
- parentComponent = targetComponent;
62
- targetComponent = PlaitElement.getComponent(MindElement.getParent(targetComponent.element));
63
- fakeX = parentComponent.node.x;
64
- width = parentComponent.node.width;
65
- const vGap = BASE * 6 + strokeWidth;
66
- if (isTopLayout(layout) && detectResult === 'top') {
67
- fakeY = targetRect.y - vGap;
68
- fakeRectangleStartY = fakeY - vGap + strokeWidth;
69
- }
70
- if (isBottomLayout(layout) && detectResult === 'bottom') {
71
- fakeY = targetRect.y + targetRect.height + vGap;
72
- fakeRectangleStartY = fakeY + vGap - strokeWidth;
73
- }
74
- fakeRectangleStartX = fakeX + Math.ceil(parentComponent.node.width / 2) - parentComponent.node.hGap - Math.ceil(strokeWidth / 2);
75
- fakeRectangleEndX = fakeRectangleStartX + 30;
76
- fakeRectangleEndY = fakeRectangleStartY + 12;
77
- }
78
- if (isIndentedLayout(layout)) {
79
- // 偏移一个 Gap
80
- if (isLeftLayout(layout)) {
81
- fakeX -= BASE * 4;
82
- }
83
- if (isRightLayout(layout)) {
84
- fakeX += BASE * 4;
85
- }
86
- if (isTopLayout(layout)) {
87
- if (detectResult === 'top') {
88
- const isLastNode = targetIndex === parentComponent.node.origin.children.length - 1;
89
- if (isLastNode) {
90
- fakeY = targetRect.y - targetRect.height - BASE;
91
- }
92
- else {
93
- const nextComponent = PlaitElement.getComponent(parentComponent.node.origin.children[targetIndex + 1]);
94
- const nextRect = getRectangleByNode(nextComponent.node);
95
- fakeY = targetRect.y - Math.abs((nextRect.y + nextRect.height - targetRect.y) / 2);
96
- }
97
- }
98
- if (detectResult === 'bottom') {
99
- const isFirstNode = targetIndex === 0;
100
- if (isFirstNode) {
101
- const parentRect = getRectangleByNode(parentComponent.node);
102
- fakeY = parentRect.y - parentRect.height / 2 - BASE;
103
- }
104
- else {
105
- const previousComponent = PlaitElement.getComponent(parentComponent.node.origin.children[targetIndex + 1]);
106
- const previousRect = getRectangleByNode(previousComponent.node);
107
- fakeY = previousRect.y - Math.abs((targetRect.y + targetRect.height - previousRect.y) / 2);
108
- }
109
- }
110
- }
111
- fakeRectangleStartX = fakeX;
112
- fakeRectangleEndX = fakeRectangleStartX + 30;
113
- fakeRectangleStartY = fakeY;
114
- fakeRectangleEndY = fakeRectangleStartY + 12;
115
- }
116
- // 构造一条曲线
117
- const fakeNode = { ...targetComponent.node, x: fakeX, y: fakeY, width, height: 12 };
118
- const linkSVGG = isIndentedLayout(layout)
119
- ? drawIndentedLink(board, parentComponent.node, fakeNode, PRIMARY_COLOR, false)
120
- : drawLink(board, parentComponent.node, fakeNode, PRIMARY_COLOR, isHorizontalLayout(layout), false);
121
- // 构造一个矩形框坐标
122
- const fakeRectangleG = drawRoundRectangle(PlaitBoard.getRoughSVG(board), fakeRectangleStartX, fakeRectangleStartY, fakeRectangleEndX, fakeRectangleEndY, {
123
- stroke: PRIMARY_COLOR,
124
- strokeWidth: 2,
125
- fill: PRIMARY_COLOR,
126
- fillStyle: 'solid'
127
- });
128
- fakeDropNodeG?.appendChild(linkSVGG);
129
- fakeDropNodeG?.appendChild(fakeRectangleG);
130
- };
131
- export const drawStraightDropNodeG = (board, targetRect, detectResult, targetComponent, fakeDropNodeG) => {
132
- const { x, y, width, height } = targetRect;
133
- const lineLength = 40;
134
- let startLinePoint = x + width;
135
- let endLinePoint = x + width + lineLength;
136
- let startRectanglePointX = x + width + lineLength;
137
- let endRectanglePointX = x + lineLength + width + 30;
138
- let startRectanglePointY = y + height / 2 - 6;
139
- let endRectanglePointY = y + height / 2 - 6 + 12;
140
- if (detectResult === 'left') {
141
- startLinePoint = x - lineLength;
142
- endLinePoint = x;
143
- startRectanglePointX = x - lineLength - 30;
144
- endRectanglePointX = x - lineLength;
145
- }
146
- let fakeY = targetComponent.node.y;
147
- let fakeX = targetRect.x;
148
- const strokeWidth = targetComponent.node.origin.branchWidth ? targetComponent.node.origin.branchWidth : STROKE_WIDTH;
149
- const pointOptions = {
150
- fakeX,
151
- fakeY,
152
- x,
153
- y,
154
- width,
155
- height,
156
- strokeWidth
157
- };
158
- const parentLayout = MindQueries.getCorrectLayoutByElement(board, targetComponent.node.origin.isRoot ? targetComponent.node.origin : targetComponent.node.parent.origin);
159
- const layout = MindQueries.getCorrectLayoutByElement(board, targetComponent.node.origin);
160
- if (!isMixedLayout(parentLayout, layout)) {
161
- // 构造一条直线
162
- let linePoints = [
163
- [startLinePoint, y + height / 2],
164
- [endLinePoint, y + height / 2]
165
- ];
166
- if (isIndentedLayout(parentLayout)) {
167
- const fakePoint = getIndentedFakePoint(parentLayout, pointOptions);
168
- drawIndentNodeG(board, fakeDropNodeG, fakePoint, targetComponent.node);
169
- return;
170
- }
171
- else if (isVerticalLogicLayout(parentLayout)) {
172
- if (!targetComponent.node.origin.isRoot) {
173
- /**
174
- * 计算逻辑:
175
- * 1. 移动到左侧:当前节点 startX - 偏移值,偏移值计算如下:
176
- * a. 第一个节点: 固定值(来源于 getMainAxle,第二级节点:BASE * 8,其他 BASE * 3 + strokeWidth / 2);
177
- * b. 第二个节点到最后一个节点之间:上一个节点到当前节点间距的一半((当前节点 startX - 上一个节点的 endX) / 2),endX = 当前节点的 startX + width;
178
- * 2. 移动到右侧:当前节点 x + width + 偏移值,偏移值计算如下:
179
- * a. 第二个节点到最后一个节点之间的右侧:当前节点到下一个节点间距的一半((下一个节点 startX - 当前节点的 endX) / 2),endX = 当前节点的 startX + width;
180
- * b. 最后一个节点的右侧:固定值(来源于 getMainAxle,第二级节点:BASE * 8,其他 BASE * 3 + strokeWidth / 2);
181
- */
182
- fakeY = targetComponent.node.y;
183
- const parentComponent = PlaitElement.getComponent(MindElement.getParent(targetComponent.element));
184
- const targetIndex = parentComponent.node.origin.children.indexOf(targetComponent.node.origin);
185
- if (detectResult === 'left') {
186
- let offsetX = 0;
187
- const isFirstNode = targetIndex === 0;
188
- if (isFirstNode) {
189
- offsetX = parentComponent.node.origin.isRoot ? BASE * 8 : BASE * 3 + strokeWidth / 2;
190
- }
191
- else {
192
- const previousComponent = PlaitElement.getComponent(parentComponent.node.origin.children[targetIndex - 1]);
193
- const previousRect = getRectangleByNode(previousComponent.node);
194
- const space = targetRect.x - (previousRect.x + previousRect.width);
195
- offsetX = space / 2;
196
- }
197
- fakeX = targetRect.x - offsetX - width / 2 - Math.ceil(strokeWidth / 2);
198
- }
199
- if (detectResult === 'right') {
200
- let offsetX = 0;
201
- const isLastNode = targetIndex === parentComponent.node.origin.children.length - 1;
202
- if (isLastNode) {
203
- offsetX = parentComponent.node.origin.isRoot ? BASE * 8 : BASE * 3 + strokeWidth / 2;
204
- }
205
- else {
206
- const nextComponent = PlaitElement.getComponent(parentComponent.node.origin.children[targetIndex + 1]);
207
- const nextRect = getRectangleByNode(nextComponent.node);
208
- const space = nextRect.x - (targetRect.x + targetRect.width);
209
- offsetX = space / 2;
210
- }
211
- fakeX = targetRect.x + width + offsetX - width / 2 - Math.ceil(strokeWidth / 2);
212
- }
213
- startRectanglePointX = fakeX;
214
- if (isTopLayout(parentLayout)) {
215
- // 因为矩形是从左上角为起点向下画的,所以需要向上偏移一个矩形的高度(-12)
216
- startRectanglePointY = fakeY + height + targetComponent.node.vGap - 12;
217
- }
218
- if (isBottomLayout(parentLayout)) {
219
- startRectanglePointY = fakeY + targetComponent.node.vGap;
220
- }
221
- endRectanglePointX = startRectanglePointX + 30;
222
- endRectanglePointY = startRectanglePointY + 12;
223
- const fakeNode = { ...targetComponent.node, x: fakeX, y: fakeY, width: 30 };
224
- const linkSVGG = drawLink(board, parentComponent.node, fakeNode, PRIMARY_COLOR, false, false);
225
- fakeDropNodeG?.appendChild(linkSVGG);
226
- }
227
- }
228
- else {
229
- let linkSVGG = PlaitBoard.getRoughSVG(board).linearPath(linePoints, { stroke: PRIMARY_COLOR, strokeWidth });
230
- fakeDropNodeG?.appendChild(linkSVGG);
231
- }
232
- // 构造一个矩形框坐标
233
- let fakeRectangleG = drawRoundRectangle(PlaitBoard.getRoughSVG(board), startRectanglePointX, startRectanglePointY, endRectanglePointX, endRectanglePointY, {
234
- stroke: PRIMARY_COLOR,
235
- strokeWidth: 2,
236
- fill: PRIMARY_COLOR,
237
- fillStyle: 'solid'
238
- });
239
- fakeDropNodeG?.appendChild(fakeRectangleG);
240
- }
241
- else {
242
- // 混合布局画线逻辑
243
- if (isHorizontalLogicLayout(parentLayout)) {
244
- if (isIndentedLayout(layout)) {
245
- const fakePoint = getIndentedFakePoint(layout, pointOptions);
246
- drawIndentNodeG(board, fakeDropNodeG, fakePoint, targetComponent.node);
247
- return;
248
- }
249
- }
250
- }
251
- };
252
- export const getHorizontalFakeY = (detectResult, targetIndex, parentNode, targetRect, layout, fakeY) => {
253
- const childrenLength = getNonAbstractChildren(parentNode).length;
254
- if (detectResult === 'top') {
255
- if (targetIndex === 0 && isTopLayout(layout)) {
256
- fakeY = targetRect.y + targetRect.height;
257
- }
258
- if (targetIndex > 0) {
259
- const previousComponent = PlaitElement.getComponent(parentNode.origin.children[targetIndex - 1]);
260
- const previousRect = getRectangleByNode(previousComponent.node);
261
- const topY = previousRect.y + previousRect.height;
262
- fakeY = topY + (targetRect.y - topY) / 5;
263
- }
264
- }
265
- if (detectResult === 'bottom') {
266
- fakeY = targetRect.y + targetRect.height + 30;
267
- if (targetIndex < childrenLength - 1) {
268
- const nextComponent = PlaitElement.getComponent(parentNode.origin.children[targetIndex + 1]);
269
- const nextRect = getRectangleByNode(nextComponent.node);
270
- const topY = targetRect.y + targetRect.height;
271
- fakeY = topY + (nextRect.y - topY) / 5;
272
- }
273
- if (targetIndex === childrenLength - 1) {
274
- fakeY = targetRect.y + targetRect.height + 30;
275
- }
276
- }
277
- return fakeY;
278
- };
279
- export const getIndentedFakePoint = (layout, pointOptions) => {
280
- let { fakeX, fakeY, x, y, width, height, strokeWidth } = pointOptions;
281
- const hGap = BASE * 4;
282
- const vGap = BASE * 6;
283
- const offsetX = hGap + width / 2 + strokeWidth;
284
- const offsetY = vGap + height / 2 + strokeWidth;
285
- if (isLeftLayout(layout)) {
286
- fakeX = x - offsetX;
287
- }
288
- if (isRightLayout(layout)) {
289
- fakeX = x + offsetX;
290
- }
291
- if (isTopLayout(layout)) {
292
- fakeY = y - offsetY;
293
- }
294
- if (isBottomLayout(layout)) {
295
- fakeY = y + height + offsetY;
296
- }
297
- return { fakeX, fakeY };
298
- };
299
- export const drawIndentNodeG = (board, fakeDropNodeG, fakePoint, node) => {
300
- const { fakeX, fakeY } = fakePoint;
301
- const fakeNode = { ...node, x: fakeX, y: fakeY, width: 30, height: 12 };
302
- const linkSVGG = drawIndentedLink(board, node, fakeNode, PRIMARY_COLOR, false);
303
- const startRectanglePointX = fakeX, startRectanglePointY = fakeY, endRectanglePointX = fakeX + 30, endRectanglePointY = fakeY + 12;
304
- const fakeRectangleG = drawRoundRectangle(PlaitBoard.getRoughSVG(board), startRectanglePointX, startRectanglePointY, endRectanglePointX, endRectanglePointY, {
305
- stroke: PRIMARY_COLOR,
306
- strokeWidth: 2,
307
- fill: PRIMARY_COLOR,
308
- fillStyle: 'solid'
309
- });
310
- fakeDropNodeG?.appendChild(linkSVGG);
311
- fakeDropNodeG?.appendChild(fakeRectangleG);
312
- };
313
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZHJhdy1wbGFjZWhvbGRlci5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3BhY2thZ2VzL21pbmQvc3JjL3V0aWxzL2RyYXctcGxhY2Vob2xkZXIudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLElBQUksRUFBRSxhQUFhLEVBQUUsWUFBWSxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBQ2pFLE9BQU8sRUFBRSxRQUFRLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFDeEMsT0FBTyxFQUFnQixXQUFXLEVBQVksTUFBTSxlQUFlLENBQUM7QUFFcEUsT0FBTyxFQUFFLGtCQUFrQixFQUFFLE1BQU0sU0FBUyxDQUFDO0FBQzdDLE9BQU8sRUFBRSxVQUFVLEVBQUUsWUFBWSxFQUFTLGtCQUFrQixFQUFFLE1BQU0sYUFBYSxDQUFDO0FBQ2xGLE9BQU8sRUFBRSxXQUFXLEVBQUUsTUFBTSxZQUFZLENBQUM7QUFDekMsT0FBTyxFQUNILHNCQUFzQixFQUN0QixjQUFjLEVBQ2Qsa0JBQWtCLEVBQ2xCLHVCQUF1QixFQUN2QixnQkFBZ0IsRUFDaEIsYUFBYSxFQUNiLHFCQUFxQixFQUV4QixNQUFNLGdCQUFnQixDQUFDO0FBQ3hCLE9BQU8sRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLHVCQUF1QixDQUFDO0FBQ3pELE9BQU8sRUFBRSxZQUFZLEVBQUUsV0FBVyxFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFDM0QsT0FBTyxFQUFFLGdCQUFnQixFQUFFLE1BQU0sZ0JBQWdCLENBQUM7QUFDbEQsT0FBTyxFQUFFLGFBQWEsRUFBRSxNQUFNLFVBQVUsQ0FBQztBQUV6QyxNQUFNLENBQUMsTUFBTSx3QkFBd0IsR0FBRyxDQUNwQyxLQUFpQixFQUNqQixVQUErRCxFQUMvRCxhQUFzQyxFQUN4QyxFQUFFO0lBQ0EsTUFBTSxlQUFlLEdBQUcsWUFBWSxDQUFDLFlBQVksQ0FBQyxVQUFVLENBQUMsTUFBTSxDQUFzQixDQUFDO0lBQzFGLE1BQU0s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Uk9LRV9XSURUSCB9IGZyb20gJy4uL2NvbnN0YW50cyc7XG5pbXBvcnQgeyBkcmF3TGluayB9IGZyb20gJy4uL2RyYXcvbGluayc7XG5pbXBvcnQgeyBEZXRlY3RSZXN1bHQsIE1pbmRFbGVtZW50LCBNaW5kTm9kZSB9IGZyb20gJy4uL2ludGVyZmFjZXMnO1xuaW1wb3J0IHsgTWluZE5vZGVDb21wb25lbnQgfSBmcm9tICcuLi9ub2RlLmNvbXBvbmVudCc7XG5pbXBvcnQgeyBnZXRSZWN0YW5nbGVCeU5vZGUgfSBmcm9tICcuL2dyYXBoJztcbmltcG9ydCB7IFBsYWl0Qm9hcmQsIFBsYWl0RWxlbWVudCwgUG9pbnQsIGRyYXdSb3VuZFJlY3RhbmdsZSB9IGZyb20gJ0BwbGFpdC9jb3JlJztcbmltcG9ydCB7IE1pbmRRdWVyaWVzIH0gZnJvbSAnLi4vcXVlcmllcyc7XG5pbXBvcnQge1xuICAgIGdldE5vbkFic3RyYWN0Q2hpbGRyZW4sXG4gICAgaXNCb3R0b21MYXlvdXQsXG4gICAgaXNIb3Jpem9udGFsTGF5b3V0LFxuICAgIGlzSG9yaXpvbnRhbExvZ2ljTGF5b3V0LFxuICAgIGlzSW5kZW50ZWRMYXlvdXQsXG4gICAgaXNSaWdodExheW91dCxcbiAgICBpc1ZlcnRpY2FsTG9naWNMYXlvdXQsXG4gICAgTWluZExheW91dFR5cGVcbn0gZnJvbSAnQHBsYWl0L2xheW91dHMnO1xuaW1wb3J0IHsgZHJhd0luZGVudGVkTGluayB9IGZyb20gJy4uL2RyYXcvaW5kZW50ZWQtbGluayc7XG5pbXBvcnQgeyBpc0xlZnRMYXlvdXQsIGlzVG9wTGF5b3V0IH0gZnJvbSAnQHBsYWl0L2xheW91dHMnO1xuaW1wb3J0IHsgaXNTdGFuZGFyZExheW91dCB9IGZyb20gJ0BwbGFpdC9sYXlvdXRzJztcbmltcG9ydCB7IGlzTWl4ZWRMYXlvdXQgfSBmcm9tICcuL2xheW91dCc7XG5cbmV4cG9ydCBjb25zdCBkcmF3UGxhY2Vob2xkZXJEcm9wTm9kZUcgPSAoXG4gICAgYm9hcmQ6IFBsYWl0Qm9hcmQsXG4gICAgZHJvcFRhcmdldDogeyB0YXJnZXQ6IE1pbmRFbGVtZW50OyBkZXRlY3RSZXN1bHQ6IERldGVjdFJlc3VsdCB9LFxuICAgIGZha2VEcm9wTm9kZUc6IFNWR0dFbGVtZW50IHwgdW5kZWZpbmVkXG4pID0+IHtcbiAgICBjb25zdCB0YXJnZXRDb21wb25lbnQgPSBQbGFpdEVsZW1lbnQuZ2V0Q29tcG9uZW50KGRyb3BUYXJnZXQudGFyZ2V0KSBhcyBNaW5kTm9kZUNvbXBvbmVudDtcbiAgICBjb25zdCB0YXJnZXRSZWN0ID0gZ2V0UmVjdGFuZ2xlQnlOb2RlKHRhcmdldENvbXBvbmVudC5ub2RlKTtcbiAgICBpZiAoZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQgJiYgWydyaWdodCcsICdsZWZ0J10uaW5jbHVkZXMoZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQpKSB7XG4gICAgICAgIGRyYXdTdHJhaWdodERyb3BOb2RlRyhib2FyZCwgdGFyZ2V0UmVjdCwgZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQsIHRhcmdldENvbXBvbmVudCwgZmFrZURyb3BOb2RlRyk7XG4gICAgfVxuICAgIGNvbnN0IHRhcmdldFBhcmVudCA9IE1pbmRFbGVtZW50LmZpbmRQYXJlbnQodGFyZ2V0Q29tcG9uZW50LmVsZW1lbnQpO1xuICAgIGlmICh0YXJnZXRQYXJlbnQgJiYgZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQgJiYgWyd0b3AnLCAnYm90dG9tJ10uaW5jbHVkZXMoZHJvcFRhcmdldC5kZXRlY3RSZXN1bHQpKSB7XG4gICAgICAgIGNvbnN0IHBhcmVudENvbXBvbmVudCA9IFBsYWl0RWxlbWVudC5nZXRDb21wb25lbnQodGFyZ2V0UGFyZW50KSBhcyBNaW5kTm9kZUNvbXBvbmVudDtcbiAgICAgICAgY29uc3QgdGFyZ2V0SW5kZXggPSBwYXJlbnRDb21wb25lbnQubm9kZS5vcmlnaW4uY2hpbGRyZW4uaW5kZXhPZih0YXJnZXRDb21wb25lbnQubm9kZS5vcmlnaW4pO1xuICAgICAgICBkcmF3Q3VydmVQbGFjZWhvbGRlckRyb3BOb2RlRyhcbiAgICAgICAgICAgIGJvYXJkLFxuICAgICAgICAgICAgdGFyZ2V0UmVjdCxcbiAgICAgICAgICAgIGRyb3BUYXJnZXQuZGV0ZWN0UmVzdWx0LFxuICAgICAgICAgICAgdGFyZ2V0SW5kZXgsXG4gICAgICAgICAgICB0YXJnZXRDb21wb25lbnQsXG4gICAgICAgICAgICBwYXJlbnRDb21wb25lbnQsXG4gICAgICAgICAgICBmYWtlRHJvcE5vZGVHXG4gICAgICAgICk7XG4gICAgfVxufTtcblxuZXhwb3J0IGNvbnN0IGRyYXdDdXJ2ZVBsYWNlaG9sZGVyRHJvcE5vZGVHID0gKFxuICAgIGJvYXJkOiBQbGFpdEJvYXJkLFxuICAgIHRhcmdldFJlY3Q6IHtcbiAgICAgICAgeDogbnVtYmVyO1xuICAgICAgICB5OiBudW1iZXI7XG4gICAgICAgIHdpZHRoOiBudW1iZXI7XG4gICAgICAgIGhlaWdodDogbnVtYmVyO1xuICAgIH0sXG4gICAgZGV0ZWN0UmVzdWx0OiBEZXRlY3RSZXN1bHQsXG4gICAgdGFyZ2V0SW5kZXg6IG51bWJlcixcbiAgICB0YXJnZXRDb21wb25lbnQ6IE1pbmROb2RlQ29tcG9uZW50LFxuICAgIHBhcmVudENvbXBvbmVudDogTWluZE5vZGVDb21wb25lbnQsXG4gICAgZmFrZURyb3BOb2RlRzogU1ZHR0VsZW1lbnQgfCB1bmRlZmluZWRcbikgPT4ge1xuICAgIGNvbnN0IHBhcmVudE5vZGVMYXlvdXQgPSBNaW5kUXVlcmllcy5nZXRDb3JyZWN0TGF5b3V0QnlFbGVtZW50KGJvYXJkLCBwYXJlbnRDb21wb25lbnQubm9kZS5vcmlnaW4pO1xuICAgIGNvbnN0IGxheW91dCA9IE1pbmRRdWVyaWVzLmdldENvcnJlY3RMYXlvdXRCeUVsZW1lbnQoYm9hcmQsIHRhcmdldENvbXBvbmVudC5ub2RlLnBhcmVudC5vcmlnaW4pO1xuICAgIGNvbnN0IHN0cm9rZVdpZHRoID0gdGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luLmJyYW5jaFdpZHRoID8gdGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luLmJyYW5jaFdpZHRoIDogU1RST0tFX1dJRFRIO1xuICAgIGxldCBmYWtlWCA9IHRhcmdldENvbXBvbmVudC5ub2RlLngsXG4gICAgICAgIGZha2VZID0gdGFyZ2V0UmVjdC55IC0gMzAsXG4gICAgICAgIGZha2VSZWN0YW5nbGVTdGFydFggPSB0YXJnZXRSZWN0LngsXG4gICAgICAgIGZha2VSZWN0YW5nbGVFbmRYID0gdGFyZ2V0UmVjdC54ICsgMzAsXG4gICAgICAgIGZha2VSZWN0YW5nbGVTdGFydFkgPSBmYWtlWSxcbiAgICAgICAgZmFrZVJlY3RhbmdsZUVuZFkgPSBmYWtlUmVjdGFuZ2xlU3RhcnRZICsgMTIsXG4gICAgICAgIHdpZHRoID0gMzA7XG5cbiAgICBpZiAoaXNMZWZ0TGF5b3V0KGxheW91dCkpIHtcbiAgICAgICAgZmFrZVggPSB0YXJnZXRDb21wb25lbnQubm9kZS54ICsgdGFyZ2V0Q29tcG9uZW50Lm5vZGUud2lkdGggLSAzMDtcbiAgICAgICAgZmFrZVJlY3RhbmdsZVN0YXJ0WCA9IHRhcmdldFJlY3QueCArIHRhcmdldFJlY3Qud2lkdGggLSAzMDtcbiAgICAgICAgZmFrZVJlY3RhbmdsZUVuZFggPSB0YXJnZXRSZWN0LnggKyB0YXJnZXRSZWN0LndpZHRoO1xuICAgIH1cbiAgICBpZiAoaXNIb3Jpem9udGFsTG9naWNMYXlvdXQocGFyZW50Tm9kZUxheW91dCkpIHtcbiAgICAgICAgZmFrZVkgPSBnZXRIb3Jpem9udGFsRmFrZVkoZGV0ZWN0UmVzdWx0IGFzICd0b3AnIHwgJ2JvdHRvbScsIHRhcmdldEluZGV4LCBwYXJlbnRDb21wb25lbnQubm9kZSwgdGFyZ2V0UmVjdCwgbGF5b3V0LCBmYWtlWSk7XG4gICAgICAgIGlmIChpc1N0YW5kYXJkTGF5b3V0KHBhcmVudE5vZGVMYXlvdXQpKSB7XG4gICAgICAgICAgICBjb25zdCByaWdodE5vZGVDb3VudCA9IHBhcmVudENvbXBvbmVudC5ub2RlLm9yaWdpbi5yaWdodE5vZGVDb3VudCB8fCAwO1xuICAgICAgICAgICAgY29uc3QgaWR4ID0gcGFyZW50Q29tcG9uZW50Lm5vZGUuY2hpbGRyZW4uZmluZEluZGV4KHggPT4geCA9PT0gdGFyZ2V0Q29tcG9uZW50Lm5vZGUpO1xuICAgICAgICAgICAgY29uc3QgaXNMZWZ0ID0gaWR4ID49IHJpZ2h0Tm9kZUNvdW50O1xuICAgICAgICAgICAgLy8g5qCH5YeG5biD5bGA55qE5bem77yM6ZyA6KaB6LCD5pW0IHhcbiAgICAgICAgICAgIGlmIChpc0xlZnQpIHtcbiAgICAgICAgICAgICAgICBmYWtlWCA9IHRhcmdldENvbXBvbmVudC5ub2RlLnggKyB0YXJnZXRDb21wb25lbnQubm9kZS53aWR0aCAtIDMwO1xuICAgICAgICAgICAgICAgIGZha2VSZWN0YW5nbGVTdGFydFggPSB0YXJnZXRSZWN0LnggKyB0YXJnZXRSZWN0LndpZHRoIC0gMzA7XG4gICAgICAgICAgICAgICAgZmFrZVJlY3RhbmdsZUVuZFggPSB0YXJnZXRSZWN0LnggKyB0YXJnZXRSZWN0LndpZHRoO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgY29uc3QgaXNMZWZ0Rmlyc3QgPSBpZHggPT09IHJpZ2h0Tm9kZUNvdW50O1xuICAgICAgICAgICAgY29uc3QgaXNSaWdodExhc3QgPSBpZHggPT09IHJpZ2h0Tm9kZUNvdW50IC0gMTtcbiAgICAgICAgICAgIC8vIOaLluaLveiHs+W3puesrOS4gOS4quiKgueCueeahOaDheWGtVxuICAgICAgICAgICAgaWYgKGRldGVjdFJlc3VsdCA9PT0gJ3RvcCcgJiYgaXNMZWZ0Rmlyc3QpIHtcbiAgICAgICAgICAgICAgICBmYWtlWSA9IHRhcmdldFJlY3QueSAtIHRhcmdldFJlY3QuaGVpZ2h0O1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKGRldGVjdFJlc3VsdCA9PT0gJ2JvdHRvbScgJiYgaXNSaWdodExhc3QpIHtcbiAgICAgICAgICAgICAgICBmYWtlWSA9IHRhcmdldFJlY3QueSArIHRhcmdldFJlY3QuaGVpZ2h0ICsgMzA7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgZmFrZVJlY3RhbmdsZVN0YXJ0WSA9IGZha2VZO1xuICAgICAgICBmYWtlUmVjdGFuZ2xlRW5kWSA9IGZha2VSZWN0YW5nbGVTdGFydFkgKyAxMjtcbiAgICB9XG5cbiAgICBpZiAoaXNWZXJ0aWNhbExvZ2ljTGF5b3V0KGxheW91dCkpIHtcbiAgICAgICAgcGFyZW50Q29tcG9uZW50ID0gdGFyZ2V0Q29tcG9uZW50O1xuICAgICAgICB0YXJnZXRDb21wb25lbnQgPSBQbGFpdEVsZW1lbnQuZ2V0Q29tcG9uZW50KE1pbmRFbGVtZW50LmdldFBhcmVudCh0YXJnZXRDb21wb25lbnQuZWxlbWVudCkpIGFzIE1pbmROb2RlQ29tcG9uZW50O1xuICAgICAgICBmYWtlWCA9IHBhcmVudENvbXBvbmVudC5ub2RlLng7XG4gICAgICAgIHdpZHRoID0gcGFyZW50Q29tcG9uZW50Lm5vZGUud2lkdGg7XG4gICAgICAgIGNvbnN0IHZHYXAgPSBCQVNFICogNiArIHN0cm9rZVdpZHRoO1xuICAgICAgICBpZiAoaXNUb3BMYXlvdXQobGF5b3V0KSAmJiBkZXRlY3RSZXN1bHQgPT09ICd0b3AnKSB7XG4gICAgICAgICAgICBmYWtlWSA9IHRhcmdldFJlY3QueSAtIHZHYXA7XG4gICAgICAgICAgICBmYWtlUmVjdGFuZ2xlU3RhcnRZID0gZmFrZVkgLSB2R2FwICsgc3Ryb2tlV2lkdGg7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGlzQm90dG9tTGF5b3V0KGxheW91dCkgJiYgZGV0ZWN0UmVzdWx0ID09PSAnYm90dG9tJykge1xuICAgICAgICAgICAgZmFrZVkgPSB0YXJnZXRSZWN0LnkgKyB0YXJnZXRSZWN0LmhlaWdodCArIHZHYXA7XG4gICAgICAgICAgICBmYWtlUmVjdGFuZ2xlU3RhcnRZID0gZmFrZVkgKyB2R2FwIC0gc3Ryb2tlV2lkdGg7XG4gICAgICAgIH1cbiAgICAgICAgZmFrZVJlY3RhbmdsZVN0YXJ0WCA9IGZha2VYICsgTWF0aC5jZWlsKHBhcmVudENvbXBvbmVudC5ub2RlLndpZHRoIC8gMikgLSBwYXJlbnRDb21wb25lbnQubm9kZS5oR2FwIC0gTWF0aC5jZWlsKHN0cm9rZVdpZHRoIC8gMik7XG4gICAgICAgIGZha2VSZWN0YW5nbGVFbmRYID0gZmFrZVJlY3RhbmdsZVN0YXJ0WCArIDMwO1xuICAgICAgICBmYWtlUmVjdGFuZ2xlRW5kWSA9IGZha2VSZWN0YW5nbGVTdGFydFkgKyAxMjtcbiAgICB9XG4gICAgaWYgKGlzSW5kZW50ZWRMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICAvLyDlgY/np7vkuIDkuKogR2FwXG4gICAgICAgIGlmIChpc0xlZnRMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICAgICAgZmFrZVggLT0gQkFTRSAqIDQ7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGlzUmlnaHRMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICAgICAgZmFrZVggKz0gQkFTRSAqIDQ7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGlzVG9wTGF5b3V0KGxheW91dCkpIHtcbiAgICAgICAgICAgIGlmIChkZXRlY3RSZXN1bHQgPT09ICd0b3AnKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgaXNMYXN0Tm9kZSA9IHRhcmdldEluZGV4ID09PSBwYXJlbnRDb21wb25lbnQubm9kZS5vcmlnaW4uY2hpbGRyZW4ubGVuZ3RoIC0gMTtcbiAgICAgICAgICAgICAgICBpZiAoaXNMYXN0Tm9kZSkge1xuICAgICAgICAgICAgICAgICAgICBmYWtlWSA9IHRhcmdldFJlY3QueSAtIHRhcmdldFJlY3QuaGVpZ2h0IC0gQkFTRTtcbiAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBuZXh0Q29tcG9uZW50ID0gUGxhaXRFbGVtZW50LmdldENvbXBvbmVudChcbiAgICAgICAgICAgICAgICAgICAgICAgIHBhcmVudENvbXBvbmVudC5ub2RlLm9yaWdpbi5jaGlsZHJlblt0YXJnZXRJbmRleCArIDFdXG4gICAgICAgICAgICAgICAgICAgICkgYXMgTWluZE5vZGVDb21wb25lbnQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IG5leHRSZWN0ID0gZ2V0UmVjdGFuZ2xlQnlOb2RlKG5leHRDb21wb25lbnQubm9kZSk7XG4gICAgICAgICAgICAgICAgICAgIGZha2VZID0gdGFyZ2V0UmVjdC55IC0gTWF0aC5hYnMoKG5leHRSZWN0LnkgKyBuZXh0UmVjdC5oZWlnaHQgLSB0YXJnZXRSZWN0LnkpIC8gMik7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKGRldGVjdFJlc3VsdCA9PT0gJ2JvdHRvbScpIHtcbiAgICAgICAgICAgICAgICBjb25zdCBpc0ZpcnN0Tm9kZSA9IHRhcmdldEluZGV4ID09PSAwO1xuICAgICAgICAgICAgICAgIGlmIChpc0ZpcnN0Tm9kZSkge1xuICAgICAgICAgICAgICAgICAgICBjb25zdCBwYXJlbnRSZWN0ID0gZ2V0UmVjdGFuZ2xlQnlOb2RlKHBhcmVudENvbXBvbmVudC5ub2RlKTtcbiAgICAgICAgICAgICAgICAgICAgZmFrZVkgPSBwYXJlbnRSZWN0LnkgLSBwYXJlbnRSZWN0LmhlaWdodCAvIDIgLSBCQVNFO1xuICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByZXZpb3VzQ29tcG9uZW50ID0gUGxhaXRFbGVtZW50LmdldENvbXBvbmVudChcbiAgICAgICAgICAgICAgICAgICAgICAgIHBhcmVudENvbXBvbmVudC5ub2RlLm9yaWdpbi5jaGlsZHJlblt0YXJnZXRJbmRleCArIDFdXG4gICAgICAgICAgICAgICAgICAgICkgYXMgTWluZE5vZGVDb21wb25lbnQ7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IHByZXZpb3VzUmVjdCA9IGdldFJlY3RhbmdsZUJ5Tm9kZShwcmV2aW91c0NvbXBvbmVudC5ub2RlKTtcbiAgICAgICAgICAgICAgICAgICAgZmFrZVkgPSBwcmV2aW91c1JlY3QueSAtIE1hdGguYWJzKCh0YXJnZXRSZWN0LnkgKyB0YXJnZXRSZWN0LmhlaWdodCAtIHByZXZpb3VzUmVjdC55KSAvIDIpO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgICBmYWtlUmVjdGFuZ2xlU3RhcnRYID0gZmFrZVg7XG4gICAgICAgIGZha2VSZWN0YW5nbGVFbmRYID0gZmFrZVJlY3RhbmdsZVN0YXJ0WCArIDMwO1xuICAgICAgICBmYWtlUmVjdGFuZ2xlU3RhcnRZID0gZmFrZVk7XG4gICAgICAgIGZha2VSZWN0YW5nbGVFbmRZID0gZmFrZVJlY3RhbmdsZVN0YXJ0WSArIDEyO1xuICAgIH1cblxuICAgIC8vIOaehOmAoOS4gOadoeabsue6v1xuICAgIGNvbnN0IGZha2VOb2RlOiBNaW5kTm9kZSA9IHsgLi4udGFyZ2V0Q29tcG9uZW50Lm5vZGUsIHg6IGZha2VYLCB5OiBmYWtlWSwgd2lkdGgsIGhlaWdodDogMTIgfTtcbiAgICBjb25zdCBsaW5rU1ZHRyA9IGlzSW5kZW50ZWRMYXlvdXQobGF5b3V0KVxuICAgICAgICA/IGRyYXdJbmRlbnRlZExpbmsoYm9hcmQsIHBhcmVudENvbXBvbmVudC5ub2RlLCBmYWtlTm9kZSwgUFJJTUFSWV9DT0xPUiwgZmFsc2UpXG4gICAgICAgIDogZHJhd0xpbmsoYm9hcmQsIHBhcmVudENvbXBvbmVudC5ub2RlLCBmYWtlTm9kZSwgUFJJTUFSWV9DT0xPUiwgaXNIb3Jpem9udGFsTGF5b3V0KGxheW91dCksIGZhbHNlKTtcbiAgICAvLyDmnoTpgKDkuIDkuKrnn6nlvaLmoYblnZDmoIdcbiAgICBjb25zdCBmYWtlUmVjdGFuZ2xlRyA9IGRyYXdSb3VuZFJlY3RhbmdsZShcbiAgICAgICAgUGxhaXRCb2FyZC5nZXRSb3VnaFNWRyhib2FyZCksXG4gICAgICAgIGZha2VSZWN0YW5nbGVTdGFydFgsXG4gICAgICAgIGZha2VSZWN0YW5nbGVTdGFydFksXG4gICAgICAgIGZha2VSZWN0YW5nbGVFbmRYLFxuICAgICAgICBmYWtlUmVjdGFuZ2xlRW5kWSxcbiAgICAgICAge1xuICAgICAgICAgICAgc3Ryb2tlOiBQUklNQVJZX0NPTE9SLFxuICAgICAgICAgICAgc3Ryb2tlV2lkdGg6IDIsXG4gICAgICAgICAgICBmaWxsOiBQUklNQVJZX0NPTE9SLFxuICAgICAgICAgICAgZmlsbFN0eWxlOiAnc29saWQnXG4gICAgICAgIH1cbiAgICApO1xuICAgIGZha2VEcm9wTm9kZUc/LmFwcGVuZENoaWxkKGxpbmtTVkdHKTtcbiAgICBmYWtlRHJvcE5vZGVHPy5hcHBlbmRDaGlsZChmYWtlUmVjdGFuZ2xlRyk7XG59O1xuZXhwb3J0IGNvbnN0IGRyYXdTdHJhaWdodERyb3BOb2RlRyA9IChcbiAgICBib2FyZDogUGxhaXRCb2FyZCxcbiAgICB0YXJnZXRSZWN0OiB7XG4gICAgICAgIHg6IG51bWJlcjtcbiAgICAgICAgeTogbnVtYmVyO1xuICAgICAgICB3aWR0aDogbnVtYmVyO1xuICAgICAgICBoZWlnaHQ6IG51bWJlcjtcbiAgICB9LFxuICAgIGRldGVjdFJlc3VsdDogRGV0ZWN0UmVzdWx0LFxuICAgIHRhcmdldENvbXBvbmVudDogTWluZE5vZGVDb21wb25lbnQsXG4gICAgZmFrZURyb3BOb2RlRzogU1ZHR0VsZW1lbnQgfCB1bmRlZmluZWRcbikgPT4ge1xuICAgIGNvbnN0IHsgeCwgeSwgd2lkdGgsIGhlaWdodCB9ID0gdGFyZ2V0UmVjdDtcbiAgICBjb25zdCBsaW5lTGVuZ3RoID0gNDA7XG4gICAgbGV0IHN0YXJ0TGluZVBvaW50ID0geCArIHdpZHRoO1xuICAgIGxldCBlbmRMaW5lUG9pbnQgPSB4ICsgd2lkdGggKyBsaW5lTGVuZ3RoO1xuICAgIGxldCBzdGFydFJlY3RhbmdsZVBvaW50WCA9IHggKyB3aWR0aCArIGxpbmVMZW5ndGg7XG4gICAgbGV0IGVuZFJlY3RhbmdsZVBvaW50WCA9IHggKyBsaW5lTGVuZ3RoICsgd2lkdGggKyAzMDtcbiAgICBsZXQgc3RhcnRSZWN0YW5nbGVQb2ludFkgPSB5ICsgaGVpZ2h0IC8gMiAtIDY7XG4gICAgbGV0IGVuZFJlY3RhbmdsZVBvaW50WSA9IHkgKyBoZWlnaHQgLyAyIC0gNiArIDEyO1xuXG4gICAgaWYgKGRldGVjdFJlc3VsdCA9PT0gJ2xlZnQnKSB7XG4gICAgICAgIHN0YXJ0TGluZVBvaW50ID0geCAtIGxpbmVMZW5ndGg7XG4gICAgICAgIGVuZExpbmVQb2ludCA9IHg7XG4gICAgICAgIHN0YXJ0UmVjdGFuZ2xlUG9pbnRYID0geCAtIGxpbmVMZW5ndGggLSAzMDtcbiAgICAgICAgZW5kUmVjdGFuZ2xlUG9pbnRYID0geCAtIGxpbmVMZW5ndGg7XG4gICAgfVxuICAgIGxldCBmYWtlWSA9IHRhcmdldENvbXBvbmVudC5ub2RlLnk7XG4gICAgbGV0IGZha2VYID0gdGFyZ2V0UmVjdC54O1xuICAgIGNvbnN0IHN0cm9rZVdpZHRoID0gdGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luLmJyYW5jaFdpZHRoID8gdGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luLmJyYW5jaFdpZHRoIDogU1RST0tFX1dJRFRIO1xuICAgIGNvbnN0IHBvaW50T3B0aW9ucyA9IHtcbiAgICAgICAgZmFrZVgsXG4gICAgICAgIGZha2VZLFxuICAgICAgICB4LFxuICAgICAgICB5LFxuICAgICAgICB3aWR0aCxcbiAgICAgICAgaGVpZ2h0LFxuICAgICAgICBzdHJva2VXaWR0aFxuICAgIH07XG4gICAgY29uc3QgcGFyZW50TGF5b3V0ID0gTWluZFF1ZXJpZXMuZ2V0Q29ycmVjdExheW91dEJ5RWxlbWVudChcbiAgICAgICAgYm9hcmQsXG4gICAgICAgIHRhcmdldENvbXBvbmVudC5ub2RlLm9yaWdpbi5pc1Jvb3QgPyB0YXJnZXRDb21wb25lbnQubm9kZS5vcmlnaW4gOiB0YXJnZXRDb21wb25lbnQubm9kZS5wYXJlbnQub3JpZ2luXG4gICAgKTtcbiAgICBjb25zdCBsYXlvdXQgPSBNaW5kUXVlcmllcy5nZXRDb3JyZWN0TGF5b3V0QnlFbGVtZW50KGJvYXJkLCB0YXJnZXRDb21wb25lbnQubm9kZS5vcmlnaW4pO1xuICAgIGlmICghaXNNaXhlZExheW91dChwYXJlbnRMYXlvdXQsIGxheW91dCkpIHtcbiAgICAgICAgLy8g5p6E6YCg5LiA5p2h55u057q/XG4gICAgICAgIGxldCBsaW5lUG9pbnRzID0gW1xuICAgICAgICAgICAgW3N0YXJ0TGluZVBvaW50LCB5ICsgaGVpZ2h0IC8gMl0sXG4gICAgICAgICAgICBbZW5kTGluZVBvaW50LCB5ICsgaGVpZ2h0IC8gMl1cbiAgICAgICAgXSBhcyBQb2ludFtdO1xuICAgICAgICBpZiAoaXNJbmRlbnRlZExheW91dChwYXJlbnRMYXlvdXQpKSB7XG4gICAgICAgICAgICBjb25zdCBmYWtlUG9pbnQgPSBnZXRJbmRlbnRlZEZha2VQb2ludChwYXJlbnRMYXlvdXQsIHBvaW50T3B0aW9ucyk7XG4gICAgICAgICAgICBkcmF3SW5kZW50Tm9kZUcoYm9hcmQsIGZha2VEcm9wTm9kZUcgYXMgU1ZHR0VsZW1lbnQsIGZha2VQb2ludCwgdGFyZ2V0Q29tcG9uZW50Lm5vZGUpO1xuICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9IGVsc2UgaWYgKGlzVmVydGljYWxMb2dpY0xheW91dChwYXJlbnRMYXlvdXQpKSB7XG4gICAgICAgICAgICBpZiAoIXRhcmdldENvbXBvbmVudC5ub2RlLm9yaWdpbi5pc1Jvb3QpIHtcbiAgICAgICAgICAgICAgICAvKipcbiAgICAgICAgICAgICAgICAgKiDorqHnrpfpgLvovpHvvJpcbiAgICAgICAgICAgICAgICAgKiAgMS4g56e75Yqo5Yiw5bem5L6n77ya5b2T5YmN6IqC54K5IHN0YXJ0WCAtIOWBj+enu+WAvO+8jOWBj+enu+WAvOiuoeeul+WmguS4i++8mlxuICAgICAgICAgICAgICAgICAqICAgICAgYS4g56ys5LiA5Liq6IqC54K577yaIOWbuuWumuWAvO+8iOadpea6kOS6jiBnZXRNYWluQXhsZe+8jOesrOS6jOe6p+iKgueCue+8mkJBU0UgKiA477yM5YW25LuWIEJBU0UgKiAzICsgc3Ryb2tlV2lkdGggLyAy77yJ77ybXG4gICAgICAgICAgICAgICAgICogICAgICBiLiDnrKzkuozkuKroioLngrnliLDmnIDlkI7kuIDkuKroioLngrnkuYvpl7TvvJrkuIrkuIDkuKroioLngrnliLDlvZPliY3oioLngrnpl7Tot53nmoTkuIDljYrvvIgo5b2T5YmN6IqC54K5IHN0YXJ0WCAtIOS4iuS4gOS4quiKgueCueeahCBlbmRYKSAvIDIp77yMZW5kWCA9IOW9k+WJjeiKgueCueeahCBzdGFydFggKyB3aWR0aDtcbiAgICAgICAgICAgICAgICAgKiAgMi4g56e75Yqo5Yiw5Y+z5L6n77ya5b2T5YmN6IqC54K5IHggKyB3aWR0aCArIOWBj+enu+WAvO+8jOWBj+enu+WAvOiuoeeul+WmguS4i++8mlxuICAgICAgICAgICAgICAgICAqICAgICAgYS4g56ys5LqM5Liq6IqC54K55Yiw5pyA5ZCO5LiA5Liq6IqC54K55LmL6Ze055qE5Y+z5L6n77ya5b2T5YmN6IqC54K55Yiw5LiL5LiA5Liq6IqC54K56Ze06Led55qE5LiA5Y2K77yIKOS4i+S4gOS4quiKgueCuSBzdGFydFggLSDlvZPliY3oioLngrnnmoQgZW5kWCkgLyAyKe+8jGVuZFggPSDlvZPliY3oioLngrnnmoQgc3RhcnRYICsgd2lkdGg7XG4gICAgICAgICAgICAgICAgICogICAgICBiLiDmnIDlkI7kuIDkuKroioLngrnnmoTlj7PkvqfvvJrlm7rlrprlgLzvvIjmnaXmupDkuo4gZ2V0TWFpbkF4bGXvvIznrKzkuoznuqfoioLngrnvvJpCQVNFICogOO+8jOWFtuS7liBCQVNFICogMyArIHN0cm9rZVdpZHRoIC8gMu+8ie+8m1xuICAgICAgICAgICAgICAgICAqL1xuICAgICAgICAgICAgICAgIGZha2VZID0gdGFyZ2V0Q29tcG9uZW50Lm5vZGUueTtcbiAgICAgICAgICAgICAgICBjb25zdCBwYXJlbnRDb21wb25lbnQgPSBQbGFpdEVsZW1lbnQuZ2V0Q29tcG9uZW50KE1pbmRFbGVtZW50LmdldFBhcmVudCh0YXJnZXRDb21wb25lbnQuZWxlbWVudCkpIGFzIE1pbmROb2RlQ29tcG9uZW50O1xuICAgICAgICAgICAgICAgIGNvbnN0IHRhcmdldEluZGV4ID0gcGFyZW50Q29tcG9uZW50Lm5vZGUub3JpZ2luLmNoaWxkcmVuLmluZGV4T2YodGFyZ2V0Q29tcG9uZW50Lm5vZGUub3JpZ2luKTtcblxuICAgICAgICAgICAgICAgIGlmIChkZXRlY3RSZXN1bHQgPT09ICdsZWZ0Jykge1xuICAgICAgICAgICAgICAgICAgICBsZXQgb2Zmc2V0WCA9IDA7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGlzRmlyc3ROb2RlID0gdGFyZ2V0SW5kZXggPT09IDA7XG4gICAgICAgICAgICAgICAgICAgIGlmIChpc0ZpcnN0Tm9kZSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgb2Zmc2V0WCA9IHBhcmVudENvbXBvbmVudC5ub2RlLm9yaWdpbi5pc1Jvb3QgPyBCQVNFICogOCA6IEJBU0UgKiAzICsgc3Ryb2tlV2lkdGggLyAyO1xuICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgcHJldmlvdXNDb21wb25lbnQgPSBQbGFpdEVsZW1lbnQuZ2V0Q29tcG9uZW50KFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgIHBhcmVudENvbXBvbmVudC5ub2RlLm9yaWdpbi5jaGlsZHJlblt0YXJnZXRJbmRleCAtIDFdXG4gICAgICAgICAgICAgICAgICAgICAgICApIGFzIE1pbmROb2RlQ29tcG9uZW50O1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgcHJldmlvdXNSZWN0ID0gZ2V0UmVjdGFuZ2xlQnlOb2RlKHByZXZpb3VzQ29tcG9uZW50Lm5vZGUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgc3BhY2UgPSB0YXJnZXRSZWN0LnggLSAocHJldmlvdXNSZWN0LnggKyBwcmV2aW91c1JlY3Qud2lkdGgpO1xuICAgICAgICAgICAgICAgICAgICAgICAgb2Zmc2V0WCA9IHNwYWNlIC8gMjtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICBmYWtlWCA9IHRhcmdldFJlY3QueCAtIG9mZnNldFggLSB3aWR0aCAvIDIgLSBNYXRoLmNlaWwoc3Ryb2tlV2lkdGggLyAyKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgaWYgKGRldGVjdFJlc3VsdCA9PT0gJ3JpZ2h0Jykge1xuICAgICAgICAgICAgICAgICAgICBsZXQgb2Zmc2V0WCA9IDA7XG4gICAgICAgICAgICAgICAgICAgIGNvbnN0IGlzTGFzdE5vZGUgPSB0YXJnZXRJbmRleCA9PT0gcGFyZW50Q29tcG9uZW50Lm5vZGUub3JpZ2luLmNoaWxkcmVuLmxlbmd0aCAtIDE7XG4gICAgICAgICAgICAgICAgICAgIGlmIChpc0xhc3ROb2RlKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBvZmZzZXRYID0gcGFyZW50Q29tcG9uZW50Lm5vZGUub3JpZ2luLmlzUm9vdCA/IEJBU0UgKiA4IDogQkFTRSAqIDMgKyBzdHJva2VXaWR0aCAvIDI7XG4gICAgICAgICAgICAgICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBuZXh0Q29tcG9uZW50ID0gUGxhaXRFbGVtZW50LmdldENvbXBvbmVudChcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnRDb21wb25lbnQubm9kZS5vcmlnaW4uY2hpbGRyZW5bdGFyZ2V0SW5kZXggKyAxXVxuICAgICAgICAgICAgICAgICAgICAgICAgKSBhcyBNaW5kTm9kZUNvbXBvbmVudDtcbiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IG5leHRSZWN0ID0gZ2V0UmVjdGFuZ2xlQnlOb2RlKG5leHRDb21wb25lbnQubm9kZSk7XG4gICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBzcGFjZSA9IG5leHRSZWN0LnggLSAodGFyZ2V0UmVjdC54ICsgdGFyZ2V0UmVjdC53aWR0aCk7XG4gICAgICAgICAgICAgICAgICAgICAgICBvZmZzZXRYID0gc3BhY2UgLyAyO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGZha2VYID0gdGFyZ2V0UmVjdC54ICsgd2lkdGggKyBvZmZzZXRYIC0gd2lkdGggLyAyIC0gTWF0aC5jZWlsKHN0cm9rZVdpZHRoIC8gMik7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIHN0YXJ0UmVjdGFuZ2xlUG9pbnRYID0gZmFrZVg7XG4gICAgICAgICAgICAgICAgaWYgKGlzVG9wTGF5b3V0KHBhcmVudExheW91dCkpIHtcbiAgICAgICAgICAgICAgICAgICAgLy8g5Zug5Li655+p5b2i5piv5LuO5bem5LiK6KeS5Li66LW354K55ZCR5LiL55S755qE77yM5omA5Lul6ZyA6KaB5ZCR5LiK5YGP56e75LiA5Liq55+p5b2i55qE6auY5bqm77yILTEy77yJXG4gICAgICAgICAgICAgICAgICAgIHN0YXJ0UmVjdGFuZ2xlUG9pbnRZID0gZmFrZVkgKyBoZWlnaHQgKyB0YXJnZXRDb21wb25lbnQubm9kZS52R2FwIC0gMTI7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIGlmIChpc0JvdHRvbUxheW91dChwYXJlbnRMYXlvdXQpKSB7XG4gICAgICAgICAgICAgICAgICAgIHN0YXJ0UmVjdGFuZ2xlUG9pbnRZID0gZmFrZVkgKyB0YXJnZXRDb21wb25lbnQubm9kZS52R2FwO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICBlbmRSZWN0YW5nbGVQb2ludFggPSBzdGFydFJlY3RhbmdsZVBvaW50WCArIDMwO1xuICAgICAgICAgICAgICAgIGVuZFJlY3RhbmdsZVBvaW50WSA9IHN0YXJ0UmVjdGFuZ2xlUG9pbnRZICsgMTI7XG4gICAgICAgICAgICAgICAgY29uc3QgZmFrZU5vZGU6IE1pbmROb2RlID0geyAuLi50YXJnZXRDb21wb25lbnQubm9kZSwgeDogZmFrZVgsIHk6IGZha2VZLCB3aWR0aDogMzAgfTtcbiAgICAgICAgICAgICAgICBjb25zdCBsaW5rU1ZHRyA9IGRyYXdMaW5rKGJvYXJkLCBwYXJlbnRDb21wb25lbnQubm9kZSwgZmFrZU5vZGUsIFBSSU1BUllfQ09MT1IsIGZhbHNlLCBmYWxzZSk7XG4gICAgICAgICAgICAgICAgZmFrZURyb3BOb2RlRz8uYXBwZW5kQ2hpbGQobGlua1NWR0cpO1xuICAgICAgICAgICAgfVxuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgbGV0IGxpbmtTVkdHID0gUGxhaXRCb2FyZC5nZXRSb3VnaFNWRyhib2FyZCkubGluZWFyUGF0aChsaW5lUG9pbnRzLCB7IHN0cm9rZTogUFJJTUFSWV9DT0xPUiwgc3Ryb2tlV2lkdGggfSk7XG4gICAgICAgICAgICBmYWtlRHJvcE5vZGVHPy5hcHBlbmRDaGlsZChsaW5rU1ZHRyk7XG4gICAgICAgIH1cbiAgICAgICAgLy8g5p6E6YCg5LiA5Liq55+p5b2i5qGG5Z2Q5qCHXG4gICAgICAgIGxldCBmYWtlUmVjdGFuZ2xlRyA9IGRyYXdSb3VuZFJlY3RhbmdsZShcbiAgICAgICAgICAgIFBsYWl0Qm9hcmQuZ2V0Um91Z2hTVkcoYm9hcmQpLFxuICAgICAgICAgICAgc3RhcnRSZWN0YW5nbGVQb2ludFgsXG4gICAgICAgICAgICBzdGFydFJlY3RhbmdsZVBvaW50WSxcbiAgICAgICAgICAgIGVuZFJlY3RhbmdsZVBvaW50WCxcbiAgICAgICAgICAgIGVuZFJlY3RhbmdsZVBvaW50WSxcbiAgICAgICAgICAgIHtcbiAgICAgICAgICAgICAgICBzdHJva2U6IFBSSU1BUllfQ09MT1IsXG4gICAgICAgICAgICAgICAgc3Ryb2tlV2lkdGg6IDIsXG4gICAgICAgICAgICAgICAgZmlsbDogUFJJTUFSWV9DT0xPUixcbiAgICAgICAgICAgICAgICBmaWxsU3R5bGU6ICdzb2xpZCdcbiAgICAgICAgICAgIH1cbiAgICAgICAgKTtcblxuICAgICAgICBmYWtlRHJvcE5vZGVHPy5hcHBlbmRDaGlsZChmYWtlUmVjdGFuZ2xlRyk7XG4gICAgfSBlbHNlIHtcbiAgICAgICAgLy8g5re35ZCI5biD5bGA55S757q/6YC76L6RXG4gICAgICAgIGlmIChpc0hvcml6b250YWxMb2dpY0xheW91dChwYXJlbnRMYXlvdXQpKSB7XG4gICAgICAgICAgICBpZiAoaXNJbmRlbnRlZExheW91dChsYXlvdXQpKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgZmFrZVBvaW50ID0gZ2V0SW5kZW50ZWRGYWtlUG9pbnQobGF5b3V0LCBwb2ludE9wdGlvbnMpO1xuICAgICAgICAgICAgICAgIGRyYXdJbmRlbnROb2RlRyhib2FyZCwgZmFrZURyb3BOb2RlRyBhcyBTVkdHRWxlbWVudCwgZmFrZVBvaW50LCB0YXJnZXRDb21wb25lbnQubm9kZSk7XG4gICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgfVxufTtcblxuZXhwb3J0IGNvbnN0IGdldEhvcml6b250YWxGYWtlWSA9IChcbiAgICBkZXRlY3RSZXN1bHQ6ICd0b3AnIHwgJ2JvdHRvbScsXG4gICAgdGFyZ2V0SW5kZXg6IG51bWJlcixcbiAgICBwYXJlbnROb2RlOiBNaW5kTm9kZSxcbiAgICB0YXJnZXRSZWN0OiB7XG4gICAgICAgIHg6IG51bWJlcjtcbiAgICAgICAgeTogbnVtYmVyO1xuICAgICAgICB3aWR0aDogbnVtYmVyO1xuICAgICAgICBoZWlnaHQ6IG51bWJlcjtcbiAgICB9LFxuICAgIGxheW91dDogTWluZExheW91dFR5cGUsXG4gICAgZmFrZVk6IG51bWJlclxuKSA9PiB7XG4gICAgY29uc3QgY2hpbGRyZW5MZW5ndGggPSBnZXROb25BYnN0cmFjdENoaWxkcmVuKHBhcmVudE5vZGUpLmxlbmd0aDtcblxuICAgIGlmIChkZXRlY3RSZXN1bHQgPT09ICd0b3AnKSB7XG4gICAgICAgIGlmICh0YXJnZXRJbmRleCA9PT0gMCAmJiBpc1RvcExheW91dChsYXlvdXQpKSB7XG4gICAgICAgICAgICBmYWtlWSA9IHRhcmdldFJlY3QueSArIHRhcmdldFJlY3QuaGVpZ2h0O1xuICAgICAgICB9XG4gICAgICAgIGlmICh0YXJnZXRJbmRleCA+IDApIHtcbiAgICAgICAgICAgIGNvbnN0IHByZXZpb3VzQ29tcG9uZW50ID0gUGxhaXRFbGVtZW50LmdldENvbXBvbmVudChwYXJlbnROb2RlLm9yaWdpbi5jaGlsZHJlblt0YXJnZXRJbmRleCAtIDFdKSBhcyBNaW5kTm9kZUNvbXBvbmVudDtcbiAgICAgICAgICAgIGNvbnN0IHByZXZpb3VzUmVjdCA9IGdldFJlY3RhbmdsZUJ5Tm9kZShwcmV2aW91c0NvbXBvbmVudC5ub2RlKTtcbiAgICAgICAgICAgIGNvbnN0IHRvcFkgPSBwcmV2aW91c1JlY3QueSArIHByZXZpb3VzUmVjdC5oZWlnaHQ7XG4gICAgICAgICAgICBmYWtlWSA9IHRvcFkgKyAodGFyZ2V0UmVjdC55IC0gdG9wWSkgLyA1O1xuICAgICAgICB9XG4gICAgfVxuICAgIGlmIChkZXRlY3RSZXN1bHQgPT09ICdib3R0b20nKSB7XG4gICAgICAgIGZha2VZID0gdGFyZ2V0UmVjdC55ICsgdGFyZ2V0UmVjdC5oZWlnaHQgKyAzMDtcbiAgICAgICAgaWYgKHRhcmdldEluZGV4IDwgY2hpbGRyZW5MZW5ndGggLSAxKSB7XG4gICAgICAgICAgICBjb25zdCBuZXh0Q29tcG9uZW50ID0gUGxhaXRFbGVtZW50LmdldENvbXBvbmVudChwYXJlbnROb2RlLm9yaWdpbi5jaGlsZHJlblt0YXJnZXRJbmRleCArIDFdKSBhcyBNaW5kTm9kZUNvbXBvbmVudDtcbiAgICAgICAgICAgIGNvbnN0IG5leHRSZWN0ID0gZ2V0UmVjdGFuZ2xlQnlOb2RlKG5leHRDb21wb25lbnQubm9kZSk7XG4gICAgICAgICAgICBjb25zdCB0b3BZID0gdGFyZ2V0UmVjdC55ICsgdGFyZ2V0UmVjdC5oZWlnaHQ7XG4gICAgICAgICAgICBmYWtlWSA9IHRvcFkgKyAobmV4dFJlY3QueSAtIHRvcFkpIC8gNTtcbiAgICAgICAgfVxuICAgICAgICBpZiAodGFyZ2V0SW5kZXggPT09IGNoaWxkcmVuTGVuZ3RoIC0gMSkge1xuICAgICAgICAgICAgZmFrZVkgPSB0YXJnZXRSZWN0LnkgKyB0YXJnZXRSZWN0LmhlaWdodCArIDMwO1xuICAgICAgICB9XG4gICAgfVxuICAgIHJldHVybiBmYWtlWTtcbn07XG5cbmV4cG9ydCBjb25zdCBnZXRJbmRlbnRlZEZha2VQb2ludCA9IChcbiAgICBsYXlvdXQ6IE1pbmRMYXlvdXRUeXBlLFxuICAgIHBvaW50T3B0aW9uczoge1xuICAgICAgICBmYWtlWDogbnVtYmVyO1xuICAgICAgICBmYWtlWTogbnVtYmVyO1xuICAgICAgICB4OiBudW1iZXI7XG4gICAgICAgIHk6IG51bWJlcjtcbiAgICAgICAgd2lkdGg6IG51bWJlcjtcbiAgICAgICAgaGVpZ2h0OiBudW1iZXI7XG4gICAgICAgIHN0cm9rZVdpZHRoOiBudW1iZXI7XG4gICAgfVxuKSA9PiB7XG4gICAgbGV0IHsgZmFrZVgsIGZha2VZLCB4LCB5LCB3aWR0aCwgaGVpZ2h0LCBzdHJva2VXaWR0aCB9ID0gcG9pbnRPcHRpb25zO1xuICAgIGNvbnN0IGhHYXAgPSBCQVNFICogNDtcbiAgICBjb25zdCB2R2FwID0gQkFTRSAqIDY7XG4gICAgY29uc3Qgb2Zmc2V0WCA9IGhHYXAgKyB3aWR0aCAvIDIgKyBzdHJva2VXaWR0aDtcbiAgICBjb25zdCBvZmZzZXRZID0gdkdhcCArIGhlaWdodCAvIDIgKyBzdHJva2VXaWR0aDtcbiAgICBpZiAoaXNMZWZ0TGF5b3V0KGxheW91dCkpIHtcbiAgICAgICAgZmFrZVggPSB4IC0gb2Zmc2V0WDtcbiAgICB9XG4gICAgaWYgKGlzUmlnaHRMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICBmYWtlWCA9IHggKyBvZmZzZXRYO1xuICAgIH1cbiAgICBpZiAoaXNUb3BMYXlvdXQobGF5b3V0KSkge1xuICAgICAgICBmYWtlWSA9IHkgLSBvZmZzZXRZO1xuICAgIH1cbiAgICBpZiAoaXNCb3R0b21MYXlvdXQobGF5b3V0KSkge1xuICAgICAgICBmYWtlWSA9IHkgKyBoZWlnaHQgKyBvZmZzZXRZO1xuICAgIH1cbiAgICByZXR1cm4geyBmYWtlWCwgZmFrZVkgfTtcbn07XG5cbmV4cG9ydCBjb25zdCBkcmF3SW5kZW50Tm9kZUcgPSAoXG4gICAgYm9hcmQ6IFBsYWl0Qm9hcmQsXG4gICAgZmFrZURyb3BOb2RlRzogU1ZHR0VsZW1lbnQsXG4gICAgZmFrZVBvaW50OiB7IGZha2VYOiBudW1iZXI7IGZha2VZOiBudW1iZXIgfSxcbiAgICBub2RlOiBNaW5kTm9kZVxuKSA9PiB7XG4gICAgY29uc3QgeyBmYWtlWCwgZmFrZVkgfSA9IGZha2VQb2ludDtcbiAgICBjb25zdCBmYWtlTm9kZTogTWluZE5vZGUgPSB7IC4uLm5vZGUsIHg6IGZha2VYLCB5OiBmYWtlWSwgd2lkdGg6IDMwLCBoZWlnaHQ6IDEyIH07XG4gICAgY29uc3QgbGlua1NWR0cgPSBkcmF3SW5kZW50ZWRMaW5rKGJvYXJkLCBub2RlLCBmYWtlTm9kZSwgUFJJTUFSWV9DT0xPUiwgZmFsc2UpO1xuXG4gICAgY29uc3Qgc3RhcnRSZWN0YW5nbGVQb2ludFggPSBmYWtlWCxcbiAgICAgICAgc3RhcnRSZWN0YW5nbGVQb2ludFkgPSBmYWtlWSxcbiAgICAgICAgZW5kUmVjdGFuZ2xlUG9pbnRYID0gZmFrZVggKyAzMCxcbiAgICAgICAgZW5kUmVjdGFuZ2xlUG9pbnRZID0gZmFrZVkgKyAxMjtcbiAgICBjb25zdCBmYWtlUmVjdGFuZ2xlRyA9IGRyYXdSb3VuZFJlY3RhbmdsZShcbiAgICAgICAgUGxhaXRCb2FyZC5nZXRSb3VnaFNWRyhib2FyZCksXG4gICAgICAgIHN0YXJ0UmVjdGFuZ2xlUG9pbnRYLFxuICAgICAgICBzdGFydFJlY3RhbmdsZVBvaW50WSxcbiAgICAgICAgZW5kUmVjdGFuZ2xlUG9pbnRYLFxuICAgICAgICBlbmRSZWN0YW5nbGVQb2ludFksXG4gICAgICAgIHtcbiAgICAgICAgICAgIHN0cm9rZTogUFJJTUFSWV9DT0xPUixcbiAgICAgICAgICAgIHN0cm9rZVdpZHRoOiAyLFxuICAgICAgICAgICAgZmlsbDogUFJJTUFSWV9DT0xPUixcbiAgICAgICAgICAgIGZpbGxTdHlsZTogJ3NvbGlkJ1xuICAgICAgICB9XG4gICAgKTtcbiAgICBmYWtlRHJvcE5vZGVHPy5hcHBlbmRDaGlsZChsaW5rU1ZHRyk7XG4gICAgZmFrZURyb3BOb2RlRz8uYXBwZW5kQ2hpbGQoZmFrZVJlY3RhbmdsZUcpO1xufTtcbiJdfQ==