@plait/draw 0.50.0 → 0.51.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 (83) hide show
  1. package/README.md +13 -1
  2. package/constants/line.d.ts +1 -0
  3. package/engines/basic-shapes/ellipse.d.ts +1 -10
  4. package/engines/flowchart/terminal.d.ts +1 -0
  5. package/esm2022/constants/line.mjs +2 -1
  6. package/esm2022/engines/basic-shapes/comment.mjs +4 -5
  7. package/esm2022/engines/basic-shapes/ellipse.mjs +5 -29
  8. package/esm2022/engines/basic-shapes/parallelogram.mjs +3 -2
  9. package/esm2022/engines/basic-shapes/pentagon.mjs +3 -3
  10. package/esm2022/engines/basic-shapes/polygon.mjs +20 -4
  11. package/esm2022/engines/basic-shapes/process-arrow.mjs +3 -3
  12. package/esm2022/engines/basic-shapes/rectangle.mjs +4 -4
  13. package/esm2022/engines/basic-shapes/round-comment.mjs +4 -5
  14. package/esm2022/engines/basic-shapes/round-rectangle.mjs +3 -3
  15. package/esm2022/engines/basic-shapes/star.mjs +3 -3
  16. package/esm2022/engines/basic-shapes/trapezoid.mjs +3 -2
  17. package/esm2022/engines/basic-shapes/triangle.mjs +5 -4
  18. package/esm2022/engines/flowchart/delay.mjs +6 -6
  19. package/esm2022/engines/flowchart/manual-input.mjs +5 -4
  20. package/esm2022/engines/flowchart/manual-loop.mjs +3 -2
  21. package/esm2022/engines/flowchart/merge.mjs +4 -4
  22. package/esm2022/engines/flowchart/stored-data.mjs +16 -10
  23. package/esm2022/engines/flowchart/terminal.mjs +37 -27
  24. package/esm2022/generators/geometry-shape.generator.mjs +3 -3
  25. package/esm2022/generators/line-active.generator.mjs +52 -68
  26. package/esm2022/generators/line.generator.mjs +2 -2
  27. package/esm2022/geometry.component.mjs +4 -4
  28. package/esm2022/interfaces/geometry.mjs +1 -1
  29. package/esm2022/interfaces/line.mjs +2 -2
  30. package/esm2022/line.component.mjs +39 -9
  31. package/esm2022/plugins/with-draw-fragment.mjs +3 -3
  32. package/esm2022/plugins/with-draw-hotkey.mjs +6 -6
  33. package/esm2022/plugins/with-draw-resize.mjs +149 -0
  34. package/esm2022/plugins/with-draw.mjs +14 -8
  35. package/esm2022/plugins/with-geometry-create.mjs +10 -10
  36. package/esm2022/plugins/with-geometry-resize.mjs +27 -74
  37. package/esm2022/plugins/with-line-auto-complete.mjs +17 -5
  38. package/esm2022/plugins/with-line-bound-reaction.mjs +6 -5
  39. package/esm2022/plugins/with-line-create.mjs +2 -2
  40. package/esm2022/plugins/with-line-resize.mjs +105 -19
  41. package/esm2022/plugins/with-line-text-move.mjs +5 -4
  42. package/esm2022/plugins/with-line-text.mjs +7 -5
  43. package/esm2022/transforms/geometry.mjs +4 -4
  44. package/esm2022/transforms/line.mjs +6 -8
  45. package/esm2022/utils/clipboard.mjs +2 -2
  46. package/esm2022/utils/geometry.mjs +16 -33
  47. package/esm2022/utils/hit.mjs +18 -10
  48. package/esm2022/utils/index.mjs +2 -2
  49. package/esm2022/utils/line/elbow.mjs +101 -0
  50. package/esm2022/utils/line/index.mjs +6 -0
  51. package/esm2022/utils/line/line-arrow.mjs +123 -0
  52. package/esm2022/utils/line/line-basic.mjs +258 -0
  53. package/esm2022/utils/line/line-common.mjs +111 -0
  54. package/esm2022/utils/line/line-resize.mjs +313 -0
  55. package/esm2022/utils/polygon.mjs +30 -0
  56. package/esm2022/utils/position/geometry.mjs +5 -6
  57. package/esm2022/utils/position/line.mjs +38 -15
  58. package/esm2022/utils/resize-align-reaction.mjs +316 -0
  59. package/esm2022/utils/resize-align.mjs +37 -0
  60. package/fesm2022/plait-draw.mjs +2108 -1143
  61. package/fesm2022/plait-draw.mjs.map +1 -1
  62. package/generators/line-active.generator.d.ts +4 -2
  63. package/interfaces/geometry.d.ts +1 -0
  64. package/interfaces/line.d.ts +4 -0
  65. package/package.json +1 -1
  66. package/plugins/with-draw-resize.d.ts +13 -0
  67. package/utils/geometry.d.ts +1 -3
  68. package/utils/hit.d.ts +3 -1
  69. package/utils/index.d.ts +1 -1
  70. package/utils/line/elbow.d.ts +19 -0
  71. package/utils/line/index.d.ts +5 -0
  72. package/utils/{line-arrow.d.ts → line/line-arrow.d.ts} +1 -1
  73. package/utils/line/line-basic.d.ts +13 -0
  74. package/utils/line/line-common.d.ts +35 -0
  75. package/utils/line/line-resize.d.ts +23 -0
  76. package/utils/polygon.d.ts +4 -0
  77. package/utils/position/geometry.d.ts +2 -3
  78. package/utils/position/line.d.ts +4 -2
  79. package/utils/resize-align-reaction.d.ts +42 -0
  80. package/utils/resize-align.d.ts +8 -0
  81. package/esm2022/utils/line-arrow.mjs +0 -123
  82. package/esm2022/utils/line.mjs +0 -392
  83. package/utils/line.d.ts +0 -25
@@ -0,0 +1,316 @@
1
+ import { PlaitBoard, Point, RectangleClient, SELECTION_BORDER_COLOR, createG, findElements } from '@plait/core';
2
+ import { getResizeZoom, movePointByZoomAndOriginPoint } from '../plugins/with-draw-resize';
3
+ const ALIGN_TOLERANCE = 2;
4
+ const EQUAL_SPACING = 10;
5
+ const ALIGN_SPACING = 24;
6
+ export class ResizeAlignReaction {
7
+ constructor(board, activeElements) {
8
+ this.board = board;
9
+ this.activeElements = activeElements;
10
+ this.alignRectangles = this.getAlignRectangle();
11
+ }
12
+ getAlignRectangle() {
13
+ const elements = findElements(this.board, {
14
+ match: element => this.board.isAlign(element) && !this.activeElements.some(item => item.id === element.id),
15
+ recursion: () => false,
16
+ isReverse: false
17
+ });
18
+ return elements.map(item => this.board.getRectangle(item));
19
+ }
20
+ getAlignLineRef(resizeAlignDelta, resizeAlignOptions) {
21
+ const { deltaX, deltaY } = resizeAlignDelta;
22
+ const { resizeState, originPoint, handlePoint, isFromCorner, isAspectRatio, resizeOriginPoints } = resizeAlignOptions;
23
+ const newResizeState = {
24
+ ...resizeState,
25
+ endPoint: [resizeState.endPoint[0] + deltaX, resizeState.endPoint[1] + deltaY]
26
+ };
27
+ const { xZoom, yZoom } = getResizeZoom(newResizeState, originPoint, handlePoint, isFromCorner, isAspectRatio);
28
+ const activePoints = resizeOriginPoints.map(p => {
29
+ return movePointByZoomAndOriginPoint(p, originPoint, xZoom, yZoom);
30
+ });
31
+ return {
32
+ deltaX,
33
+ deltaY,
34
+ xZoom,
35
+ yZoom,
36
+ activePoints
37
+ };
38
+ }
39
+ getEqualLineDelta(resizeAlignOptions) {
40
+ let equalLineDelta = {
41
+ deltaX: 0,
42
+ deltaY: 0
43
+ };
44
+ const { isAspectRatio, activeRectangle } = resizeAlignOptions;
45
+ const widthAlignRectangle = this.alignRectangles.find(item => Math.abs(item.width - activeRectangle.width) < ALIGN_TOLERANCE);
46
+ if (widthAlignRectangle) {
47
+ const deltaWidth = widthAlignRectangle.width - activeRectangle.width;
48
+ equalLineDelta.deltaX = deltaWidth * resizeAlignOptions.directionFactors[0];
49
+ if (isAspectRatio) {
50
+ const deltaHeight = deltaWidth / (activeRectangle.width / activeRectangle.height);
51
+ equalLineDelta.deltaY = deltaHeight * resizeAlignOptions.directionFactors[1];
52
+ return equalLineDelta;
53
+ }
54
+ }
55
+ const heightAlignRectangle = this.alignRectangles.find(item => Math.abs(item.height - activeRectangle.height) < ALIGN_TOLERANCE);
56
+ if (heightAlignRectangle) {
57
+ const deltaHeight = heightAlignRectangle.height - activeRectangle.height;
58
+ equalLineDelta.deltaY = deltaHeight * resizeAlignOptions.directionFactors[1];
59
+ if (isAspectRatio) {
60
+ const deltaWidth = deltaHeight * (activeRectangle.width / activeRectangle.height);
61
+ equalLineDelta.deltaX = deltaWidth * resizeAlignOptions.directionFactors[0];
62
+ return equalLineDelta;
63
+ }
64
+ }
65
+ return equalLineDelta;
66
+ }
67
+ drawEqualLines(activePoints, resizeAlignOptions) {
68
+ let widthEqualPoints = [];
69
+ let heightEqualPoints = [];
70
+ const drawHorizontalLine = resizeAlignOptions.directionFactors[0] !== 0 || resizeAlignOptions.isAspectRatio;
71
+ const drawVerticalLine = resizeAlignOptions.directionFactors[1] !== 0 || resizeAlignOptions.isAspectRatio;
72
+ const activeRectangle = RectangleClient.getRectangleByPoints(activePoints);
73
+ for (let alignRectangle of this.alignRectangles) {
74
+ if (activeRectangle.width === alignRectangle.width && drawHorizontalLine) {
75
+ widthEqualPoints.push(getEqualLinePoints(alignRectangle, true));
76
+ }
77
+ if (activeRectangle.height === alignRectangle.height && drawVerticalLine) {
78
+ heightEqualPoints.push(getEqualLinePoints(alignRectangle, false));
79
+ }
80
+ }
81
+ if (widthEqualPoints.length && drawHorizontalLine) {
82
+ widthEqualPoints.push(getEqualLinePoints(activeRectangle, true));
83
+ }
84
+ if (heightEqualPoints.length && drawVerticalLine) {
85
+ heightEqualPoints.push(getEqualLinePoints(activeRectangle, false));
86
+ }
87
+ const equalLinePoints = [...widthEqualPoints, ...heightEqualPoints];
88
+ return drawEqualLines(this.board, equalLinePoints);
89
+ }
90
+ getAlignLineDelta(resizeAlignOptions) {
91
+ let alignLineDelta = {
92
+ deltaX: 0,
93
+ deltaY: 0
94
+ };
95
+ const { isAspectRatio, activeRectangle, directionFactors } = resizeAlignOptions;
96
+ const drawHorizontal = directionFactors[0] !== 0 || isAspectRatio;
97
+ const drawVertical = directionFactors[1] !== 0 || isAspectRatio;
98
+ if (drawHorizontal) {
99
+ const xAlignAxis = getTripleAlignAxis(activeRectangle, true);
100
+ const alignX = directionFactors[0] === -1 ? xAlignAxis[0] : xAlignAxis[2];
101
+ const deltaX = getMinAlignDelta(this.alignRectangles, alignX, true);
102
+ if (Math.abs(deltaX) < ALIGN_TOLERANCE) {
103
+ alignLineDelta.deltaX = deltaX;
104
+ if (alignLineDelta.deltaX !== 0 && isAspectRatio) {
105
+ alignLineDelta.deltaY = alignLineDelta.deltaX / (activeRectangle.width / activeRectangle.height);
106
+ return alignLineDelta;
107
+ }
108
+ }
109
+ }
110
+ if (drawVertical) {
111
+ const yAlignAxis = getTripleAlignAxis(activeRectangle, false);
112
+ const alignY = directionFactors[1] === -1 ? yAlignAxis[0] : yAlignAxis[2];
113
+ const deltaY = getMinAlignDelta(this.alignRectangles, alignY, false);
114
+ if (Math.abs(deltaY) < ALIGN_TOLERANCE) {
115
+ alignLineDelta.deltaY = deltaY;
116
+ if (alignLineDelta.deltaY !== 0 && isAspectRatio) {
117
+ alignLineDelta.deltaX = alignLineDelta.deltaY * (activeRectangle.width / activeRectangle.height);
118
+ return alignLineDelta;
119
+ }
120
+ }
121
+ }
122
+ return alignLineDelta;
123
+ }
124
+ drawAlignLines(activePoints, resizeAlignOptions) {
125
+ let alignLinePoints = [];
126
+ const activeRectangle = RectangleClient.getRectangleByPoints(activePoints);
127
+ const alignAxisX = getTripleAlignAxis(activeRectangle, true);
128
+ const alignAxisY = getTripleAlignAxis(activeRectangle, false);
129
+ const alignLineRefs = [
130
+ {
131
+ axis: alignAxisX[0],
132
+ isHorizontal: true,
133
+ alignRectangles: []
134
+ },
135
+ {
136
+ axis: alignAxisX[2],
137
+ isHorizontal: true,
138
+ alignRectangles: []
139
+ },
140
+ {
141
+ axis: alignAxisY[0],
142
+ isHorizontal: false,
143
+ alignRectangles: []
144
+ },
145
+ {
146
+ axis: alignAxisY[2],
147
+ isHorizontal: false,
148
+ alignRectangles: []
149
+ }
150
+ ];
151
+ const setAlignLine = (axis, alignRectangle, isHorizontal) => {
152
+ const boundingRectangle = RectangleClient.inflate(RectangleClient.getBoundingRectangle([activeRectangle, alignRectangle]), ALIGN_SPACING);
153
+ if (isHorizontal) {
154
+ const pointStart = [axis, boundingRectangle.y];
155
+ const pointEnd = [axis, boundingRectangle.y + boundingRectangle.height];
156
+ alignLinePoints.push([pointStart, pointEnd]);
157
+ }
158
+ else {
159
+ const pointStart = [boundingRectangle.x, axis];
160
+ const pointEnd = [boundingRectangle.x + boundingRectangle.width, axis];
161
+ alignLinePoints.push([pointStart, pointEnd]);
162
+ }
163
+ };
164
+ const { isAspectRatio, directionFactors } = resizeAlignOptions;
165
+ const drawHorizontal = directionFactors[0] !== 0 || isAspectRatio;
166
+ const drawVertical = directionFactors[1] !== 0 || isAspectRatio;
167
+ for (let index = 0; index < this.alignRectangles.length; index++) {
168
+ const element = this.alignRectangles[index];
169
+ if (isAlign(alignLineRefs[0].axis, element, alignLineRefs[0].isHorizontal)) {
170
+ alignLineRefs[0].alignRectangles.push(element);
171
+ }
172
+ if (isAlign(alignLineRefs[1].axis, element, alignLineRefs[1].isHorizontal)) {
173
+ alignLineRefs[1].alignRectangles.push(element);
174
+ }
175
+ if (isAlign(alignLineRefs[2].axis, element, alignLineRefs[2].isHorizontal)) {
176
+ alignLineRefs[2].alignRectangles.push(element);
177
+ }
178
+ if (isAlign(alignLineRefs[3].axis, element, alignLineRefs[3].isHorizontal)) {
179
+ alignLineRefs[3].alignRectangles.push(element);
180
+ }
181
+ }
182
+ if (drawHorizontal && alignLineRefs[0].alignRectangles.length) {
183
+ const leftRectangle = alignLineRefs[0].alignRectangles.length === 1
184
+ ? alignLineRefs[0].alignRectangles[0]
185
+ : getNearestAlignRectangle(alignLineRefs[0].alignRectangles, activeRectangle);
186
+ setAlignLine(alignLineRefs[0].axis, leftRectangle, alignLineRefs[0].isHorizontal);
187
+ }
188
+ if (drawHorizontal && alignLineRefs[1].alignRectangles.length) {
189
+ const rightRectangle = alignLineRefs[1].alignRectangles.length === 1
190
+ ? alignLineRefs[1].alignRectangles[0]
191
+ : getNearestAlignRectangle(alignLineRefs[1].alignRectangles, activeRectangle);
192
+ setAlignLine(alignLineRefs[1].axis, rightRectangle, alignLineRefs[1].isHorizontal);
193
+ }
194
+ if (drawVertical && alignLineRefs[2].alignRectangles.length) {
195
+ const topRectangle = alignLineRefs[2].alignRectangles.length === 1
196
+ ? alignLineRefs[2].alignRectangles[0]
197
+ : getNearestAlignRectangle(alignLineRefs[2].alignRectangles, activeRectangle);
198
+ setAlignLine(alignLineRefs[2].axis, topRectangle, alignLineRefs[2].isHorizontal);
199
+ }
200
+ if (drawVertical && alignLineRefs[3].alignRectangles.length) {
201
+ const bottomRectangle = alignLineRefs[3].alignRectangles.length === 1
202
+ ? alignLineRefs[3].alignRectangles[0]
203
+ : getNearestAlignRectangle(alignLineRefs[3].alignRectangles, activeRectangle);
204
+ setAlignLine(alignLineRefs[3].axis, bottomRectangle, alignLineRefs[3].isHorizontal);
205
+ }
206
+ return drawAlignLines(this.board, alignLinePoints);
207
+ }
208
+ handleResizeAlign(resizeAlignOptions) {
209
+ const alignG = createG();
210
+ let alignLineDelta = this.getEqualLineDelta(resizeAlignOptions);
211
+ if (alignLineDelta.deltaX === 0 && alignLineDelta.deltaY === 0) {
212
+ alignLineDelta = this.getAlignLineDelta(resizeAlignOptions);
213
+ }
214
+ const equalLineRef = this.getAlignLineRef(alignLineDelta, resizeAlignOptions);
215
+ const equalLinesG = this.drawEqualLines(equalLineRef.activePoints, resizeAlignOptions);
216
+ const alignLinesG = this.drawAlignLines(equalLineRef.activePoints, resizeAlignOptions);
217
+ alignG.append(equalLinesG, alignLinesG);
218
+ return { ...equalLineRef, alignG };
219
+ }
220
+ }
221
+ function getBarPoint(point, isHorizontal) {
222
+ return isHorizontal
223
+ ? [
224
+ [point[0], point[1] - 4],
225
+ [point[0], point[1] + 4]
226
+ ]
227
+ : [
228
+ [point[0] - 4, point[1]],
229
+ [point[0] + 4, point[1]]
230
+ ];
231
+ }
232
+ function getEqualLinePoints(rectangle, isHorizontal) {
233
+ return isHorizontal
234
+ ? [
235
+ [rectangle.x, rectangle.y - EQUAL_SPACING],
236
+ [rectangle.x + rectangle.width, rectangle.y - EQUAL_SPACING]
237
+ ]
238
+ : [
239
+ [rectangle.x - EQUAL_SPACING, rectangle.y],
240
+ [rectangle.x - EQUAL_SPACING, rectangle.y + rectangle.height]
241
+ ];
242
+ }
243
+ function drawEqualLines(board, lines) {
244
+ const g = createG();
245
+ lines.forEach(line => {
246
+ if (!line.length)
247
+ return;
248
+ const yAlign = PlaitBoard.getRoughSVG(board).line(line[0][0], line[0][1], line[1][0], line[1][1], {
249
+ stroke: SELECTION_BORDER_COLOR,
250
+ strokeWidth: 1
251
+ });
252
+ g.appendChild(yAlign);
253
+ line.forEach(point => {
254
+ const barPoint = getBarPoint(point, !!Point.isHorizontal(line[0], line[1]));
255
+ const bar = PlaitBoard.getRoughSVG(board).line(barPoint[0][0], barPoint[0][1], barPoint[1][0], barPoint[1][1], {
256
+ stroke: SELECTION_BORDER_COLOR,
257
+ strokeWidth: 1
258
+ });
259
+ g.appendChild(bar);
260
+ });
261
+ });
262
+ return g;
263
+ }
264
+ function drawAlignLines(board, lines) {
265
+ const g = createG();
266
+ lines.forEach(points => {
267
+ if (!points.length)
268
+ return;
269
+ const xAlign = PlaitBoard.getRoughSVG(board).line(points[0][0], points[0][1], points[1][0], points[1][1], {
270
+ stroke: SELECTION_BORDER_COLOR,
271
+ strokeWidth: 1,
272
+ strokeLineDash: [4, 4]
273
+ });
274
+ g.appendChild(xAlign);
275
+ });
276
+ return g;
277
+ }
278
+ export const getTripleAlignAxis = (rectangle, isHorizontal) => {
279
+ const axis = isHorizontal ? 'x' : 'y';
280
+ const side = isHorizontal ? 'width' : 'height';
281
+ return [rectangle[axis], rectangle[axis] + rectangle[side] / 2, rectangle[axis] + rectangle[side]];
282
+ };
283
+ export const isAlign = (axis, rectangle, isHorizontal) => {
284
+ const alignAxis = getTripleAlignAxis(rectangle, isHorizontal);
285
+ return alignAxis.includes(axis);
286
+ };
287
+ export const getClosestDelta = (axis, rectangle, isHorizontal) => {
288
+ const alignAxis = getTripleAlignAxis(rectangle, isHorizontal);
289
+ const deltas = alignAxis.map(item => item - axis);
290
+ const absDeltas = deltas.map(item => Math.abs(item));
291
+ const index = absDeltas.indexOf(Math.min(...absDeltas));
292
+ return deltas[index];
293
+ };
294
+ function getMinAlignDelta(alignRectangles, axis, isHorizontal) {
295
+ let delta = ALIGN_TOLERANCE;
296
+ alignRectangles.forEach(item => {
297
+ const distance = getClosestDelta(axis, item, isHorizontal);
298
+ if (Math.abs(distance) < Math.abs(delta)) {
299
+ delta = distance;
300
+ }
301
+ });
302
+ return delta;
303
+ }
304
+ function getNearestAlignRectangle(alignRectangles, activeRectangle) {
305
+ let minDistance = Infinity;
306
+ let nearestRectangle = alignRectangles[0];
307
+ alignRectangles.forEach(item => {
308
+ const distance = Math.sqrt(Math.pow(activeRectangle.x - item.x, 2) + Math.pow(activeRectangle.y - item.y, 2));
309
+ if (distance < minDistance) {
310
+ minDistance = distance;
311
+ nearestRectangle = item;
312
+ }
313
+ });
314
+ return nearestRectangle;
315
+ }
316
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVzaXplLWFsaWduLXJlYWN0aW9uLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vcGFja2FnZXMvZHJhdy9zcmMvdXRpbHMvcmVzaXplLWFsaWduLXJlYWN0aW9uLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUNBLE9BQU8sRUFFSCxVQUFVLEVBRVYsS0FBSyxFQUNMLGVBQWUsRUFDZixzQkFBc0IsRUFDdEIsT0FBTyxFQUNQLFlBQVksRUFDZixNQUFNLGFBQWEsQ0FBQztBQUNyQixPQUFPLEVBQUUsYUFBYSxFQUFFLDZCQUE2QixFQUFFLE1BQU0sNkJBQTZCLENBQUM7QUFvQzNGLE1BQU0sZUFBZSxHQUFHLENBQUMsQ0FBQztBQUUxQixNQUFNLGFBQWEsR0FBRyxFQUFFLENBQUM7QUFFekIsTUFBTSxhQUFhLEdBQUcsRUFBRSxDQUFDO0FBRXpCLE1BQU0sT0FBTyxtQkFBbUI7SUFHNUIsWUFBb0IsS0FBaUIsRUFBVSxjQUE4QjtRQUF6RCxVQUFLLEdBQUwsS0FBSyxDQUFZO1FBQVUsbUJBQWMsR0FBZCxjQUFjLENBQWdCO1FBQ3pFLElBQUksQ0FBQyxlQUFlLEdBQUcsSUFBSSxDQUFDLGlCQUFpQixFQUFFLENBQUM7SUFDcEQsQ0FBQztJQUVELGlCQUFpQjtRQUNiLE1BQU0sUUFBUSxHQUFHLFlBQVksQ0FBQyxJQUFJLENBQUMsS0FBSyxFQUFFO1lBQ3RDLEtBQUssRUFBRSxPQUFPLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLGNBQWMsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxJQUFJLENBQUMsRUFBRSxLQUFLLE9BQU8sQ0FBQyxFQUFFLENBQUM7WUFDMUcsU0FBUyxFQUFFLEdBQUcsRUFBRSxDQUFDLEtBQUs7WUFDdEIsU0FBUyxFQUFFLEtBQUs7U0FDbkIsQ0FBQyxDQUFDO1FBQ0gsT0FBTyxRQUFRLENB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LEVBQUU7UUFDM0IsTUFBTSxRQUFRLEdBQUcsZUFBZSxDQUFDLElBQUksRUFBRSxJQUFJLEVBQUUsWUFBWSxDQUFDLENBQUM7UUFDM0QsSUFBSSxJQUFJLENBQUMsR0FBRyxDQUFDLFFBQVEsQ0FBQyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLEVBQUU7WUFDdEMsS0FBSyxHQUFHLFFBQVEsQ0FBQztTQUNwQjtJQUNMLENBQUMsQ0FBQyxDQUFDO0lBQ0gsT0FBTyxLQUFLLENBQUM7QUFDakIsQ0FBQztBQUVELFNBQVMsd0JBQXdCLENBQUMsZUFBa0MsRUFBRSxlQUFnQztJQUNsRyxJQUFJLFdBQVcsR0FBRyxRQUFRLENBQUM7SUFDM0IsSUFBSSxnQkFBZ0IsR0FBRyxlQUFlLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFFMUMsZUFBZSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsRUFBRTtRQUMzQixNQUFNLFFBQVEsR0FBRyxJQUFJLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsZUFBZSxDQUFDLENBQUMsR0FBRyxJQUFJLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsZUFBZSxDQUFDLENBQUMsR0FBRyxJQUFJLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDOUcsSUFBSSxRQUFRLEdBQUcsV0FBVyxFQUFFO1lBQ3hCLFdBQVcsR0FBRyxRQUFRLENBQUM7WUFDdkIsZ0JBQWdCLEdBQUcsSUFBSSxDQUFDO1NBQzNCO0lBQ0wsQ0FBQyxDQUFDLENBQUM7SUFDSCxPQUFPLGdCQUFnQixDQUFDO0FBQzVCLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBSZXNpemVTdGF0ZSB9IGZyb20gJ0BwbGFpdC9jb21tb24nO1xuaW1wb3J0IHtcbiAgICBEaXJlY3Rpb25GYWN0b3JzLFxuICAgIFBsYWl0Qm9hcmQsXG4gICAgUGxhaXRFbGVtZW50LFxuICAgIFBvaW50LFxuICAgIFJlY3RhbmdsZUNsaWVudCxcbiAgICBTRUxFQ1RJT05fQk9SREVSX0NPTE9SLFxuICAgIGNyZWF0ZUcsXG4gICAgZmluZEVsZW1lbnRzXG59IGZyb20gJ0BwbGFpdC9jb3JlJztcbmltcG9ydCB7IGdldFJlc2l6ZVpvb20sIG1vdmVQb2ludEJ5Wm9vbUFuZE9yaWdpblBvaW50IH0gZnJvbSAnLi4vcGx1Z2lucy93aXRoLWRyYXctcmVzaXplJztcblxuZXhwb3J0IGludGVyZmFjZSBSZXNpemVBbGlnbkRlbHRhIHtcbiAgICBkZWx0YVg6IG51bWJlcjtcbiAgICBkZWx0YVk6IG51bWJlcjtcbn1cblxuZXhwb3J0IGludGVyZmFjZSBBbGlnbkxpbmVSZWYgZXh0ZW5kcyBSZXNpemVBbGlnbkRlbHRhIHtcbiAgICB4Wm9vbTogbnVtYmVyO1xuICAgIHlab29tOiBudW1iZXI7XG4gICAgYWN0aXZlUG9pbnRzOiBQb2ludFtdO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIFJlc2l6ZUFsaWduUmVmIGV4dGVuZHMgQWxpZ25MaW5lUmVmIHtcbiAgICBhbGlnbkc6IFNWR0dFbGVtZW50O1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIFJlc2l6ZUFsaWduT3B0aW9ucyB7XG4gICAgcmVzaXplU3RhdGU6IFJlc2l6ZVN0YXRlO1xuICAgIHJlc2l6ZU9yaWdpblBvaW50czogUG9pbnRbXTtcbiAgICBhY3RpdmVSZWN0YW5nbGU6IFJlY3RhbmdsZUNsaWVudDtcbiAgICBkaXJlY3Rpb25GYWN0b3JzOiBEaXJlY3Rpb25GYWN0b3JzO1xuICAgIG9yaWdpblBvaW50OiBQb2ludDtcbiAgICBoYW5kbGVQb2ludDogUG9pbnQ7XG4gICAgaXNGcm9tQ29ybmVyOiBib29sZWFuO1xuICAgIGlzQXNwZWN0UmF0aW86IGJvb2xlYW47XG59XG5cbnR5cGUgVHJpcGxlQWxpZ25BeGlzID0gW251bWJlciwgbnVtYmVyLCBudW1iZXJdO1xuXG50eXBlIERyYXdBbGlnbkxpbmVSZWYgPSB7XG4gICAgYXhpczogbnVtYmVyO1xuICAgIGlzSG9yaXpvbnRhbDogYm9vbGVhbjtcbiAgICBhbGlnblJlY3RhbmdsZXM6IFJlY3RhbmdsZUNsaWVudFtdO1xufTtcblxuY29uc3QgQUxJR05fVE9MRVJBTkNFID0gMjtcblxuY29uc3QgRVFVQUxfU1BBQ0lORyA9IDEwO1xuXG5jb25zdCBBTElHTl9TUEFDSU5HID0gMjQ7XG5cbmV4cG9ydCBjbGFzcyBSZXNpemVBbGlnblJlYWN0aW9uIHtcbiAgICBhbGlnblJlY3RhbmdsZXM6IFJlY3RhbmdsZUNsaWVudFtdO1xuXG4gICAgY29uc3RydWN0b3IocHJpdmF0ZSBib2FyZDogUGxhaXRCb2FyZCwgcHJpdmF0ZSBhY3RpdmVFbGVtZW50czogUGxhaXRFbGVtZW50W10pIHtcbiAgICAgICAgdGhpcy5hbGlnblJlY3RhbmdsZXMgPSB0aGlzLmdldEFsaWduUmVjdGFuZ2xlKCk7XG4gICAgfVxuXG4gICAgZ2V0QWxpZ25SZWN0YW5nbGUoKSB7XG4gICAgICAgIGNvbnN0IGVsZW1lbnRzID0gZmluZEVsZW1lbnRzKHRoaXMuYm9hcmQsIHtcbiAgICAgICAgICAgIG1hdGNoOiBlbGVtZW50ID0+IHRoaXMuYm9hcmQuaXNBbGlnbihlbGVtZW50KSAmJiAhdGhpcy5hY3RpdmVFbGVtZW50cy5zb21lKGl0ZW0gPT4gaXRlbS5pZCA9PT0gZWxlbWVudC5pZCksXG4gICAgICAgICAgICByZWN1cnNpb246ICgpID0+IGZhbHNlLFxuICAgICAgICAgICAgaXNSZXZlcnNlOiBmYWxzZVxuICAgICAgICB9KTtcbiAgICAgICAgcmV0dXJuIGVsZW1lbnRzLm1hcChpdGVtID0+IHRoaXMuYm9hcmQuZ2V0UmVjdGFuZ2xlKGl0ZW0pISk7XG4gICAgfVxuXG4gICAgZ2V0QWxpZ25MaW5lUmVmKHJlc2l6ZUFsaWduRGVsdGE6IFJlc2l6ZUFsaWduRGVsdGEsIHJlc2l6ZUFsaWduT3B0aW9uczogUmVzaXplQWxpZ25PcHRpb25zKTogQWxpZ25MaW5lUmVmIHtcbiAgICAgICAgY29uc3QgeyBkZWx0YVgsIGRlbHRhWSB9ID0gcmVzaXplQWxpZ25EZWx0YTtcbiAgICAgICAgY29uc3QgeyByZXNpemVTdGF0ZSwgb3JpZ2luUG9pbnQsIGhhbmRsZVBvaW50LCBpc0Zyb21Db3JuZXIsIGlzQXNwZWN0UmF0aW8sIHJlc2l6ZU9yaWdpblBvaW50cyB9ID0gcmVzaXplQWxpZ25PcHRpb25zO1xuICAgICAgICBjb25zdCBuZXdSZXNpemVTdGF0ZTogUmVzaXplU3RhdGUgPSB7XG4gICAgICAgICAgICAuLi5yZXNpemVTdGF0ZSxcbiAgICAgICAgICAgIGVuZFBvaW50OiBbcmVzaXplU3RhdGUuZW5kUG9pbnRbMF0gKyBkZWx0YVgsIHJlc2l6ZVN0YXRlLmVuZFBvaW50WzFdICsgZGVsdGFZXVxuICAgICAgICB9O1xuICAgICAgICBjb25zdCB7IHhab29tLCB5Wm9vbSB9ID0gZ2V0UmVzaXplWm9vbShuZXdSZXNpemVTdGF0ZSwgb3JpZ2luUG9pbnQsIGhhbmRsZVBvaW50LCBpc0Zyb21Db3JuZXIsIGlzQXNwZWN0UmF0aW8pO1xuICAgICAgICBjb25zdCBhY3RpdmVQb2ludHMgPSByZXNpemVPcmlnaW5Qb2ludHMubWFwKHAgPT4ge1xuICAgICAgICAgICAgcmV0dXJuIG1vdmVQb2ludEJ5Wm9vbUFuZE9yaWdpblBvaW50KHAsIG9yaWdpblBvaW50LCB4Wm9vbSwgeVpvb20pO1xuICAgICAgICB9KSBhcyBbUG9pbnQsIFBvaW50XTtcblxuICAgICAgICByZXR1cm4ge1xuICAgICAgICAgICAgZGVsdGFYLFxuICAgICAgICAgICAgZGVsdGFZLFxuICAgICAgICAgICAgeFpvb20sXG4gICAgICAgICAgICB5Wm9vbSxcbiAgICAgICAgICAgIGFjdGl2ZVBvaW50c1xuICAgICAgICB9O1xuICAgIH1cblxuICAgIGdldEVxdWFsTGluZURlbHRhKHJlc2l6ZUFsaWduT3B0aW9uczogUmVzaXplQWxpZ25PcHRpb25zKSB7XG4gICAgICAgIGxldCBlcXVhbExpbmVEZWx0YTogUmVzaXplQWxpZ25EZWx0YSA9IHtcbiAgICAgICAgICAgIGRlbHRhWDogMCxcbiAgICAgICAgICAgIGRlbHRhWTogMFxuICAgICAgICB9O1xuICAgICAgICBjb25zdCB7IGlzQXNwZWN0UmF0aW8sIGFjdGl2ZVJlY3RhbmdsZSB9ID0gcmVzaXplQWxpZ25PcHRpb25zO1xuICAgICAgICBjb25zdCB3aWR0aEFsaWduUmVjdGFuZ2xlID0gdGhpcy5hbGlnblJlY3RhbmdsZXMuZmluZChpdGVtID0+IE1hdGguYWJzKGl0ZW0ud2lkdGggLSBhY3RpdmVSZWN0YW5nbGUud2lkdGgpIDwgQUxJR05fVE9MRVJBTkNFKTtcbiAgICAgICAgaWYgKHdpZHRoQWxpZ25SZWN0YW5nbGUpIHtcbiAgICAgICAgICAgIGNvbnN0IGRlbHRhV2lkdGggPSB3aWR0aEFsaWduUmVjdGFuZ2xlLndpZHRoIC0gYWN0aXZlUmVjdGFuZ2xlLndpZHRoO1xuICAgICAgICAgICAgZXF1YWxMaW5lRGVsdGEuZGVsdGFYID0gZGVsdGFXaWR0aCAqIHJlc2l6ZUFsaWduT3B0aW9ucy5kaXJlY3Rpb25GYWN0b3JzWzBdO1xuICAgICAgICAgICAgaWYgKGlzQXNwZWN0UmF0aW8pIHtcbiAgICAgICAgICAgICAgICBjb25zdCBkZWx0YUhlaWdodCA9IGRlbHRhV2lkdGggLyAoYWN0aXZlUmVjdGFuZ2xlLndpZHRoIC8gYWN0aXZlUmVjdGFuZ2xlLmhlaWdodCk7XG4gICAgICAgICAgICAgICAgZXF1YWxMaW5lRGVsdGEuZGVsdGFZID0gZGVsdGFIZWlnaHQgKiByZXNpemVBbGlnbk9wdGlvbnMuZGlyZWN0aW9uRmFjdG9yc1sxXTtcbiAgICAgICAgICAgICAgICByZXR1cm4gZXF1YWxMaW5lRGVsdGE7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgY29uc3QgaGVpZ2h0QWxpZ25SZWN0YW5nbGUgPSB0aGlzLmFsaWduUmVjdGFuZ2xlcy5maW5kKGl0ZW0gPT4gTWF0aC5hYnMoaXRlbS5oZWlnaHQgLSBhY3RpdmVSZWN0YW5nbGUuaGVpZ2h0KSA8IEFMSUdOX1RPTEVSQU5DRSk7XG4gICAgICAgIGlmIChoZWlnaHRBbGlnblJlY3RhbmdsZSkge1xuICAgICAgICAgICAgY29uc3QgZGVsdGFIZWlnaHQgPSBoZWlnaHRBbGlnblJlY3RhbmdsZS5oZWlnaHQgLSBhY3RpdmVSZWN0YW5nbGUuaGVpZ2h0O1xuICAgICAgICAgICAgZXF1YWxMaW5lRGVsdGEuZGVsdGFZID0gZGVsdGFIZWlnaHQgKiByZXNpemVBbGlnbk9wdGlvbnMuZGlyZWN0aW9uRmFjdG9yc1sxXTtcbiAgICAgICAgICAgIGlmIChpc0FzcGVjdFJhdGlvKSB7XG4gICAgICAgICAgICAgICAgY29uc3QgZGVsdGFXaWR0aCA9IGRlbHRhSGVpZ2h0ICogKGFjdGl2ZVJlY3RhbmdsZS53aWR0aCAvIGFjdGl2ZVJlY3RhbmdsZS5oZWlnaHQpO1xuICAgICAgICAgICAgICAgIGVxdWFsTGluZURlbHRhLmRlbHRhWCA9IGRlbHRhV2lkdGggKiByZXNpemVBbGlnbk9wdGlvbnMuZGlyZWN0aW9uRmFjdG9yc1swXTtcbiAgICAgICAgICAgICAgICByZXR1cm4gZXF1YWxMaW5lRGVsdGE7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIGVxdWFsTGluZURlbHRhO1xuICAgIH1cblxuICAgIGRyYXdFcXVhbExpbmVzKGFjdGl2ZVBvaW50czogUG9pbnRbXSwgcmVzaXplQWxpZ25PcHRpb25zOiBSZXNpemVBbGlnbk9wdGlvbnMpIHtcbiAgICAgICAgbGV0IHdpZHRoRXF1YWxQb2ludHMgPSBbXTtcbiAgICAgICAgbGV0IGhlaWdodEVxdWFsUG9pbnRzID0gW107XG5cbiAgICAgICAgY29uc3QgZHJhd0hvcml6b250YWxMaW5lID0gcmVzaXplQWxpZ25PcHRpb25zLmRpcmVjdGlvbkZhY3RvcnNbMF0gIT09IDAgfHwgcmVzaXplQWxpZ25PcHRpb25zLmlzQXNwZWN0UmF0aW87XG4gICAgICAgIGNvbnN0IGRyYXdWZXJ0aWNhbExpbmUgPSByZXNpemVBbGlnbk9wdGlvbnMuZGlyZWN0aW9uRmFjdG9yc1sxXSAhPT0gMCB8fCByZXNpemVBbGlnbk9wdGlvbnMuaXNBc3BlY3RSYXRpbztcblxuICAgICAgICBjb25zdCBhY3RpdmVSZWN0YW5nbGUgPSBSZWN0YW5nbGVDbGllbnQuZ2V0UmVjdGFuZ2xlQnlQb2ludHMoYWN0aXZlUG9pbnRzKTtcbiAgICAgICAgZm9yIChsZXQgYWxpZ25SZWN0YW5nbGUgb2YgdGhpcy5hbGlnblJlY3RhbmdsZXMpIHtcbiAgICAgICAgICAgIGlmIChhY3RpdmVSZWN0YW5nbGUud2lkdGggPT09IGFsaWduUmVjdGFuZ2xlLndpZHRoICYmIGRyYXdIb3Jpem9udGFsTGluZSkge1xuICAgICAgICAgICAgICAgIHdpZHRoRXF1YWxQb2ludHMucHVzaChnZXRFcXVhbExpbmVQb2ludHMoYWxpZ25SZWN0YW5nbGUsIHRydWUpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGlmIChhY3RpdmVSZWN0YW5nbGUuaGVpZ2h0ID09PSBhbGlnblJlY3RhbmdsZS5oZWlnaHQgJiYgZHJhd1ZlcnRpY2FsTGluZSkge1xuICAgICAgICAgICAgICAgIGhlaWdodEVxdWFsUG9pbnRzLnB1c2goZ2V0RXF1YWxMaW5lUG9pbnRzKGFsaWduUmVjdGFuZ2xlLCBmYWxzZSkpO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICAgIGlmICh3aWR0aEVxdWFsUG9pbnRzLmxlbmd0aCAmJiBkcmF3SG9yaXpvbnRhbExpbmUpIHtcbiAgICAgICAgICAgIHdpZHRoRXF1YWxQb2ludHMucHVzaChnZXRFcXVhbExpbmVQb2ludHMoYWN0aXZlUmVjdGFuZ2xlLCB0cnVlKSk7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGhlaWdodEVxdWFsUG9pbnRzLmxlbmd0aCAmJiBkcmF3VmVydGljYWxMaW5lKSB7XG4gICAgICAgICAgICBoZWlnaHRFcXVhbFBvaW50cy5wdXNoKGdldEVxdWFsTGluZVBvaW50cyhhY3RpdmVSZWN0YW5nbGUsIGZhbHNlKSk7XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCBlcXVhbExpbmVQb2ludHMgPSBbLi4ud2lkdGhFcXVhbFBvaW50cywgLi4uaGVpZ2h0RXF1YWxQb2ludHNdO1xuICAgICAgICByZXR1cm4gZHJhd0VxdWFsTGluZXModGhpcy5ib2FyZCwgZXF1YWxMaW5lUG9pbnRzKTtcbiAgICB9XG5cbiAgICBnZXRBbGlnbkxpbmVEZWx0YShyZXNpemVBbGlnbk9wdGlvbnM6IFJlc2l6ZUFsaWduT3B0aW9ucykge1xuICAgICAgICBsZXQgYWxpZ25MaW5lRGVsdGE6IFJlc2l6ZUFsaWduRGVsdGEgPSB7XG4gICAgICAgICAgICBkZWx0YVg6IDAsXG4gICAgICAgICAgICBkZWx0YVk6IDBcbiAgICAgICAgfTtcbiAgICAgICAgY29uc3QgeyBpc0FzcGVjdFJhdGlvLCBhY3RpdmVSZWN0YW5nbGUsIGRpcmVjdGlvbkZhY3RvcnMgfSA9IHJlc2l6ZUFsaWduT3B0aW9ucztcbiAgICAgICAgY29uc3QgZHJhd0hvcml6b250YWwgPSBkaXJlY3Rpb25GYWN0b3JzWzBdICE9PSAwIHx8IGlzQXNwZWN0UmF0aW87XG4gICAgICAgIGNvbnN0IGRyYXdWZXJ0aWNhbCA9IGRpcmVjdGlvbkZhY3RvcnNbMV0gIT09IDAgfHwgaXNBc3BlY3RSYXRpbztcblxuICAgICAgICBpZiAoZHJhd0hvcml6b250YWwpIHtcbiAgICAgICAgICAgIGNvbnN0IHhBbGlnbkF4aXMgPSBnZXRUcmlwbGVBbGlnbkF4aXMoYWN0aXZlUmVjdGFuZ2xlLCB0cnVlKTtcbiAgICAgICAgICAgIGNvbnN0IGFsaWduWCA9IGRpcmVjdGlvbkZhY3RvcnNbMF0gPT09IC0xID8geEFsaWduQXhpc1swXSA6IHhBbGlnbkF4aXNbMl07XG4gICAgICAgICAgICBjb25zdCBkZWx0YVggPSBnZXRNaW5BbGlnbkRlbHRhKHRoaXMuYWxpZ25SZWN0YW5nbGVzLCBhbGlnblgsIHRydWUpO1xuICAgICAgICAgICAgaWYgKE1hdGguYWJzKGRlbHRhWCkgPCBBTElHTl9UT0xFUkFOQ0UpIHtcbiAgICAgICAgICAgICAgICBhbGlnbkxpbmVEZWx0YS5kZWx0YVggPSBkZWx0YVg7XG4gICAgICAgICAgICAgICAgaWYgKGFsaWduTGluZURlbHRhLmRlbHRhWCAhPT0gMCAmJiBpc0FzcGVjdFJhdGlvKSB7XG4gICAgICAgICAgICAgICAgICAgIGFsaWduTGluZURlbHRhLmRlbHRhWSA9IGFsaWduTGluZURlbHRhLmRlbHRhWCAvIChhY3RpdmVSZWN0YW5nbGUud2lkdGggLyBhY3RpdmVSZWN0YW5nbGUuaGVpZ2h0KTtcbiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGFsaWduTGluZURlbHRhO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChkcmF3VmVydGljYWwpIHtcbiAgICAgICAgICAgIGNvbnN0IHlBbGlnbkF4aXMgPSBnZXRUcmlwbGVBbGlnbkF4aXMoYWN0aXZlUmVjdGFuZ2xlLCBmYWxzZSk7XG4gICAgICAgICAgICBjb25zdCBhbGlnblkgPSBkaXJlY3Rpb25GYWN0b3JzWzFdID09PSAtMSA/IHlBbGlnbkF4aXNbMF0gOiB5QWxpZ25BeGlzWzJdO1xuICAgICAgICAgICAgY29uc3QgZGVsdGFZID0gZ2V0TWluQWxpZ25EZWx0YSh0aGlzLmFsaWduUmVjdGFuZ2xlcywgYWxpZ25ZLCBmYWxzZSk7XG4gICAgICAgICAgICBpZiAoTWF0aC5hYnMoZGVsdGFZKSA8IEFMSUdOX1RPTEVSQU5DRSkge1xuICAgICAgICAgICAgICAgIGFsaWduTGluZURlbHRhLmRlbHRhWSA9IGRlbHRhWTtcbiAgICAgICAgICAgICAgICBpZiAoYWxpZ25MaW5lRGVsdGEuZGVsdGFZICE9PSAwICYmIGlzQXNwZWN0UmF0aW8pIHtcbiAgICAgICAgICAgICAgICAgICAgYWxpZ25MaW5lRGVsdGEuZGVsdGFYID0gYWxpZ25MaW5lRGVsdGEuZGVsdGFZICogKGFjdGl2ZVJlY3RhbmdsZS53aWR0aCAvIGFjdGl2ZVJlY3RhbmdsZS5oZWlnaHQpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4gYWxpZ25MaW5lRGVsdGE7XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICB9XG5cbiAgICAgICAgcmV0dXJuIGFsaWduTGluZURlbHRhO1xuICAgIH1cblxuICAgIGRyYXdBbGlnbkxpbmVzKGFjdGl2ZVBvaW50czogUG9pbnRbXSwgcmVzaXplQWxpZ25PcHRpb25zOiBSZXNpemVBbGlnbk9wdGlvbnMpIHtcbiAgICAgICAgbGV0IGFsaWduTGluZVBvaW50czogW1BvaW50LCBQb2ludF1bXSA9IFtdO1xuICAgICAgICBjb25zdCBhY3RpdmVSZWN0YW5nbGUgPSBSZWN0YW5nbGVDbGllbnQuZ2V0UmVjdGFuZ2xlQnlQb2ludHMoYWN0aXZlUG9pbnRzKTtcbiAgICAgICAgY29uc3QgYWxpZ25BeGlzWCA9IGdldFRyaXBsZUFsaWduQXhpcyhhY3RpdmVSZWN0YW5nbGUsIHRydWUpO1xuICAgICAgICBjb25zdCBhbGlnbkF4aXNZID0gZ2V0VHJpcGxlQWxpZ25BeGlzKGFjdGl2ZVJlY3RhbmdsZSwgZmFsc2UpO1xuICAgICAgICBjb25zdCBhbGlnbkxpbmVSZWZzOiBEcmF3QWxpZ25MaW5lUmVmW10gPSBbXG4gICAgICAgICAgICB7XG4gICAgICAgICAgICAgICAgYXhpczogYWxpZ25BeGlzWFswXSxcbiAgICAgICAgICAgICAgICBpc0hvcml6b250YWw6IHRydWUsXG4gICAgICAgICAgICAgICAgYWxpZ25SZWN0YW5nbGVzOiBbXVxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIHtcbiAgICAgICAgICAgICAgICBheGlzOiBhbGlnbkF4aXNYWzJdLFxuICAgICAgICAgICAgICAgIGlzSG9yaXpvbnRhbDogdHJ1ZSxcbiAgICAgICAgICAgICAgICBhbGlnblJlY3RhbmdsZXM6IFtdXG4gICAgICAgICAgICB9LFxuICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgIGF4aXM6IGFsaWduQXhpc1lbMF0sXG4gICAgICAgICAgICAgICAgaXNIb3Jpem9udGFsOiBmYWxzZSxcbiAgICAgICAgICAgICAgICBhbGlnblJlY3RhbmdsZXM6IFtdXG4gICAgICAgICAgICB9LFxuICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgIGF4aXM6IGFsaWduQXhpc1lbMl0sXG4gICAgICAgICAgICAgICAgaXNIb3Jpem9udGFsOiBmYWxzZSxcbiAgICAgICAgICAgICAgICBhbGlnblJlY3RhbmdsZXM6IFtdXG4gICAgICAgICAgICB9XG4gICAgICAgIF07XG4gICAgICAgIGNvbnN0IHNldEFsaWduTGluZSA9IChheGlzOiBudW1iZXIsIGFsaWduUmVjdGFuZ2xlOiBSZWN0YW5nbGVDbGllbnQsIGlzSG9yaXpvbnRhbDogYm9vbGVhbikgPT4ge1xuICAgICAgICAgICAgY29uc3QgYm91bmRpbmdSZWN0YW5nbGUgPSBSZWN0YW5nbGVDbGllbnQuaW5mbGF0ZShcbiAgICAgICAgICAgICAgICBSZWN0YW5nbGVDbGllbnQuZ2V0Qm91bmRpbmdSZWN0YW5nbGUoW2FjdGl2ZVJlY3RhbmdsZSwgYWxpZ25SZWN0YW5nbGVdKSxcbiAgICAgICAgICAgICAgICBBTElHTl9TUEFDSU5HXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgaWYgKGlzSG9yaXpvbnRhbCkge1xuICAgICAgICAgICAgICAgIGNvbnN0IHBvaW50U3RhcnQgPSBbYXhpcywgYm91bmRpbmdSZWN0YW5nbGUueV0gYXMgUG9pbnQ7XG4gICAgICAgICAgICAgICAgY29uc3QgcG9pbnRFbmQgPSBbYXhpcywgYm91bmRpbmdSZWN0YW5nbGUueSArIGJvdW5kaW5nUmVjdGFuZ2xlLmhlaWdodF0gYXMgUG9pbnQ7XG4gICAgICAgICAgICAgICAgYWxpZ25MaW5lUG9pbnRzLnB1c2goW3BvaW50U3RhcnQsIHBvaW50RW5kXSk7XG4gICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgIGNvbnN0IHBvaW50U3RhcnQgPSBbYm91bmRpbmdSZWN0YW5nbGUueCwgYXhpc10gYXMgUG9pbnQ7XG4gICAgICAgICAgICAgICAgY29uc3QgcG9pbnRFbmQgPSBbYm91bmRpbmdSZWN0YW5nbGUueCArIGJvdW5kaW5nUmVjdGFuZ2xlLndpZHRoLCBheGlzXSBhcyBQb2ludDtcbiAgICAgICAgICAgICAgICBhbGlnbkxpbmVQb2ludHMucHVzaChbcG9pbnRTdGFydCwgcG9pbnRFbmRdKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCB7IGlzQXNwZWN0UmF0aW8sIGRpcmVjdGlvbkZhY3RvcnMgfSA9IHJlc2l6ZUFsaWduT3B0aW9ucztcbiAgICAgICAgY29uc3QgZHJhd0hvcml6b250YWwgPSBkaXJlY3Rpb25GYWN0b3JzWzBdICE9PSAwIHx8IGlzQXNwZWN0UmF0aW87XG4gICAgICAgIGNvbnN0IGRyYXdWZXJ0aWNhbCA9IGRpcmVjdGlvbkZhY3RvcnNbMV0gIT09IDAgfHwgaXNBc3BlY3RSYXRpbztcblxuICAgICAgICBmb3IgKGxldCBpbmRleCA9IDA7IGluZGV4IDwgdGhpcy5hbGlnblJlY3RhbmdsZXMubGVuZ3RoOyBpbmRleCsrKSB7XG4gICAgICAgICAgICBjb25zdCBlbGVtZW50ID0gdGhpcy5hbGlnblJlY3RhbmdsZXNbaW5kZXhdO1xuICAgICAgICAgICAgaWYgKGlzQWxpZ24oYWxpZ25MaW5lUmVmc1swXS5heGlzLCBlbGVtZW50LCBhbGlnbkxpbmVSZWZzWzBdLmlzSG9yaXpvbnRhbCkpIHtcbiAgICAgICAgICAgICAgICBhbGlnbkxpbmVSZWZzWzBdLmFsaWduUmVjdGFuZ2xlcy5wdXNoKGVsZW1lbnQpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKGlzQWxpZ24oYWxpZ25MaW5lUmVmc1sxXS5heGlzLCBlbGVtZW50LCBhbGlnbkxpbmVSZWZzWzFdLmlzSG9yaXpvbnRhbCkpIHtcbiAgICAgICAgICAgICAgICBhbGlnbkxpbmVSZWZzWzFdLmFsaWduUmVjdGFuZ2xlcy5wdXNoKGVsZW1lbnQpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKGlzQWxpZ24oYWxpZ25MaW5lUmVmc1syXS5heGlzLCBlbGVtZW50LCBhbGlnbkxpbmVSZWZzWzJdLmlzSG9yaXpvbnRhbCkpIHtcbiAgICAgICAgICAgICAgICBhbGlnbkxpbmVSZWZzWzJdLmFsaWduUmVjdGFuZ2xlcy5wdXNoKGVsZW1lbnQpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgaWYgKGlzQWxpZ24oYWxpZ25MaW5lUmVmc1szXS5heGlzLCBlbGVtZW50LCBhbGlnbkxpbmVSZWZzWzNdLmlzSG9yaXpvbnRhbCkpIHtcbiAgICAgICAgICAgICAgICBhbGlnbkxpbmVSZWZzWzNdLmFsaWduUmVjdGFuZ2xlcy5wdXNoKGVsZW1lbnQpO1xuICAgICAgICAgICAgfVxuICAgICAgICB9XG5cbiAgICAgICAgaWYgKGRyYXdIb3Jpem9udGFsICYmIGFsaWduTGluZVJlZnNbMF0uYWxpZ25SZWN0YW5nbGVzLmxlbmd0aCkge1xuICAgICAgICAgICAgY29uc3QgbGVmdFJlY3RhbmdsZSA9XG4gICAgICAgICAgICAgICAgYWxpZ25MaW5lUmVmc1swXS5hbGlnblJlY3RhbmdsZXMubGVuZ3RoID09PSAxXG4gICAgICAgICAgICAgICAgICAgID8gYWxpZ25MaW5lUmVmc1swXS5hbGlnblJlY3RhbmdsZXNbMF1cbiAgICAgICAgICAgICAgICAgICAgOiBnZXROZWFyZXN0QWxpZ25SZWN0YW5nbGUoYWxpZ25MaW5lUmVmc1swXS5hbGlnblJlY3RhbmdsZXMsIGFjdGl2ZVJlY3RhbmdsZSk7XG4gICAgICAgICAgICBzZXRBbGlnbkxpbmUoYWxpZ25MaW5lUmVmc1swXS5heGlzLCBsZWZ0UmVjdGFuZ2xlLCBhbGlnbkxpbmVSZWZzWzBdLmlzSG9yaXpvbnRhbCk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoZHJhd0hvcml6b250YWwgJiYgYWxpZ25MaW5lUmVmc1sxXS5hbGlnblJlY3RhbmdsZXMubGVuZ3RoKSB7XG4gICAgICAgICAgICBjb25zdCByaWdodFJlY3RhbmdsZSA9XG4gICAgICAgICAgICAgICAgYWxpZ25MaW5lUmVmc1sxXS5hbGlnblJlY3RhbmdsZXMubGVuZ3RoID09PSAxXG4gICAgICAgICAgICAgICAgICAgID8gYWxpZ25MaW5lUmVmc1sxXS5hbGlnblJlY3RhbmdsZXNbMF1cbiAgICAgICAgICAgICAgICAgICAgOiBnZXROZWFyZXN0QWxpZ25SZWN0YW5nbGUoYWxpZ25MaW5lUmVmc1sxXS5hbGlnblJlY3RhbmdsZXMsIGFjdGl2ZVJlY3RhbmdsZSk7XG4gICAgICAgICAgICBzZXRBbGlnbkxpbmUoYWxpZ25MaW5lUmVmc1sxXS5heGlzLCByaWdodFJlY3RhbmdsZSwgYWxpZ25MaW5lUmVmc1sxXS5pc0hvcml6b250YWwpO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKGRyYXdWZXJ0aWNhbCAmJiBhbGlnbkxpbmVSZWZzWzJdLmFsaWduUmVjdGFuZ2xlcy5sZW5ndGgpIHtcbiAgICAgICAgICAgIGNvbnN0IHRvcFJlY3RhbmdsZSA9XG4gICAgICAgICAgICAgICAgYWxpZ25MaW5lUmVmc1syXS5hbGlnblJlY3RhbmdsZXMubGVuZ3RoID09PSAxXG4gICAgICAgICAgICAgICAgICAgID8gYWxpZ25MaW5lUmVmc1syXS5hbGlnblJlY3RhbmdsZXNbMF1cbiAgICAgICAgICAgICAgICAgICAgOiBnZXROZWFyZXN0QWxpZ25SZWN0YW5nbGUoYWxpZ25MaW5lUmVmc1syXS5hbGlnblJlY3RhbmdsZXMsIGFjdGl2ZVJlY3RhbmdsZSk7XG4gICAgICAgICAgICBzZXRBbGlnbkxpbmUoYWxpZ25MaW5lUmVmc1syXS5heGlzLCB0b3BSZWN0YW5nbGUsIGFsaWduTGluZVJlZnNbMl0uaXNIb3Jpem9udGFsKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChkcmF3VmVydGljYWwgJiYgYWxpZ25MaW5lUmVmc1szXS5hbGlnblJlY3RhbmdsZXMubGVuZ3RoKSB7XG4gICAgICAgICAgICBjb25zdCBib3R0b21SZWN0YW5nbGUgPVxuICAgICAgICAgICAgICAgIGFsaWduTGluZVJlZnNbM10uYWxpZ25SZWN0YW5nbGVzLmxlbmd0aCA9PT0gMVxuICAgICAgICAgICAgICAgICAgICA/IGFsaWduTGluZVJlZnNbM10uYWxpZ25SZWN0YW5nbGVzWzBdXG4gICAgICAgICAgICAgICAgICAgIDogZ2V0TmVhcmVzdEFsaWduUmVjdGFuZ2xlKGFsaWduTGluZVJlZnNbM10uYWxpZ25SZWN0YW5nbGVzLCBhY3RpdmVSZWN0YW5nbGUpO1xuICAgICAgICAgICAgc2V0QWxpZ25MaW5lKGFsaWduTGluZVJlZnNbM10uYXhpcywgYm90dG9tUmVjdGFuZ2xlLCBhbGlnbkxpbmVSZWZzWzNdLmlzSG9yaXpvbnRhbCk7XG4gICAgICAgIH1cblxuICAgICAgICByZXR1cm4gZHJhd0FsaWduTGluZXModGhpcy5ib2FyZCwgYWxpZ25MaW5lUG9pbnRzKTtcbiAgICB9XG5cbiAgICBoYW5kbGVSZXNpemVBbGlnbihyZXNpemVBbGlnbk9wdGlvbnM6IFJlc2l6ZUFsaWduT3B0aW9ucyk6IFJlc2l6ZUFsaWduUmVmIHtcbiAgICAgICAgY29uc3QgYWxpZ25HID0gY3JlYXRlRygpO1xuICAgICAgICBsZXQgYWxpZ25MaW5lRGVsdGEgPSB0aGlzLmdldEVxdWFsTGluZURlbHRhKHJlc2l6ZUFsaWduT3B0aW9ucyk7XG4gICAgICAgIGlmIChhbGlnbkxpbmVEZWx0YS5kZWx0YVggPT09IDAgJiYgYWxpZ25MaW5lRGVsdGEuZGVsdGFZID09PSAwKSB7XG4gICAgICAgICAgICBhbGlnbkxpbmVEZWx0YSA9IHRoaXMuZ2V0QWxpZ25MaW5lRGVsdGEocmVzaXplQWxpZ25PcHRpb25zKTtcbiAgICAgICAgfVxuICAgICAgICBjb25zdCBlcXVhbExpbmVSZWYgPSB0aGlzLmdldEFsaWduTGluZVJlZihhbGlnbkxpbmVEZWx0YSwgcmVzaXplQWxpZ25PcHRpb25zKTtcbiAgICAgICAgY29uc3QgZXF1YWxMaW5lc0cgPSB0aGlzLmRyYXdFcXVhbExpbmVzKGVxdWFsTGluZVJlZi5hY3RpdmVQb2ludHMsIHJlc2l6ZUFsaWduT3B0aW9ucyk7XG4gICAgICAgIGNvbnN0IGFsaWduTGluZXNHID0gdGhpcy5kcmF3QWxpZ25MaW5lcyhlcXVhbExpbmVSZWYuYWN0aXZlUG9pbnRzLCByZXNpemVBbGlnbk9wdGlvbnMpO1xuICAgICAgICBhbGlnbkcuYXBwZW5kKGVxdWFsTGluZXNHLCBhbGlnbkxpbmVzRyk7XG4gICAgICAgIHJldHVybiB7IC4uLmVxdWFsTGluZVJlZiwgYWxpZ25HIH07XG4gICAgfVxufVxuXG5mdW5jdGlvbiBnZXRCYXJQb2ludChwb2ludDogUG9pbnQsIGlzSG9yaXpvbnRhbDogYm9vbGVhbikge1xuICAgIHJldHVybiBpc0hvcml6b250YWxcbiAgICAgICAgPyBbXG4gICAgICAgICAgICAgIFtwb2ludFswXSwgcG9pbnRbMV0gLSA0XSxcbiAgICAgICAgICAgICAgW3BvaW50WzBdLCBwb2ludFsxXSArIDRdXG4gICAgICAgICAgXVxuICAgICAgICA6IFtcbiAgICAgICAgICAgICAgW3BvaW50WzBdIC0gNCwgcG9pbnRbMV1dLFxuICAgICAgICAgICAgICBbcG9pbnRbMF0gKyA0LCBwb2ludFsxXV1cbiAgICAgICAgICBdO1xufVxuXG5mdW5jdGlvbiBnZXRFcXVhbExpbmVQb2ludHMocmVjdGFuZ2xlOiBSZWN0YW5nbGVDbGllbnQsIGlzSG9yaXpvbnRhbDogYm9vbGVhbik6IFBvaW50W10ge1xuICAgIHJldHVybiBpc0hvcml6b250YWxcbiAgICAgICAgPyBbXG4gICAgICAgICAgICAgIFtyZWN0YW5nbGUueCwgcmVjdGFuZ2xlLnkgLSBFUVVBTF9TUEFDSU5HXSxcbiAgICAgICAgICAgICAgW3JlY3RhbmdsZS54ICsgcmVjdGFuZ2xlLndpZHRoLCByZWN0YW5nbGUueSAtIEVRVUFMX1NQQUNJTkddXG4gICAgICAgICAgXVxuICAgICAgICA6IFtcbiAgICAgICAgICAgICAgW3JlY3RhbmdsZS54IC0gRVFVQUxfU1BBQ0lORywgcmVjdGFuZ2xlLnldLFxuICAgICAgICAgICAgICBbcmVjdGFuZ2xlLnggLSBFUVVBTF9TUEFDSU5HLCByZWN0YW5nbGUueSArIHJlY3RhbmdsZS5oZWlnaHRdXG4gICAgICAgICAgXTtcbn1cblxuZnVuY3Rpb24gZHJhd0VxdWFsTGluZXMoYm9hcmQ6IFBsYWl0Qm9hcmQsIGxpbmVzOiBQb2ludFtdW10pIHtcbiAgICBjb25zdCBnID0gY3JlYXRlRygpO1xuICAgIGxpbmVzLmZvckVhY2gobGluZSA9PiB7XG4gICAgICAgIGlmICghbGluZS5sZW5ndGgpIHJldHVybjtcbiAgICAgICAgY29uc3QgeUFsaWduID0gUGxhaXRCb2FyZC5nZXRSb3VnaFNWRyhib2FyZCkubGluZShsaW5lWzBdWzBdLCBsaW5lWzBdWzFdLCBsaW5lWzFdWzBdLCBsaW5lWzFdWzFdLCB7XG4gICAgICAgICAgICBzdHJva2U6IFNFTEVDVElPTl9CT1JERVJfQ09MT1IsXG4gICAgICAgICAgICBzdHJva2VXaWR0aDogMVxuICAgICAgICB9KTtcbiAgICAgICAgZy5hcHBlbmRDaGlsZCh5QWxpZ24pO1xuICAgICAgICBsaW5lLmZvckVhY2gocG9pbnQgPT4ge1xuICAgICAgICAgICAgY29uc3QgYmFyUG9pbnQgPSBnZXRCYXJQb2ludChwb2ludCwgISFQb2ludC5pc0hvcml6b250YWwobGluZVswXSwgbGluZVsxXSkpO1xuICAgICAgICAgICAgY29uc3QgYmFyID0gUGxhaXRCb2FyZC5nZXRSb3VnaFNWRyhib2FyZCkubGluZShiYXJQb2ludFswXVswXSwgYmFyUG9pbnRbMF1bMV0sIGJhclBvaW50WzFdWzBdLCBiYXJQb2ludFsxXVsxXSwge1xuICAgICAgICAgICAgICAgIHN0cm9rZTogU0VMRUNUSU9OX0JPUkRFUl9DT0xPUixcbiAgICAgICAgICAgICAgICBzdHJva2VXaWR0aDogMVxuICAgICAgICAgICAgfSk7XG4gICAgICAgICAgICBnLmFwcGVuZENoaWxkKGJhcik7XG4gICAgICAgIH0pO1xuICAgIH0pO1xuICAgIHJldHVybiBnO1xufVxuXG5mdW5jdGlvbiBkcmF3QWxpZ25MaW5lcyhib2FyZDogUGxhaXRCb2FyZCwgbGluZXM6IFtQb2ludCwgUG9pbnRdW10pIHtcbiAgICBjb25zdCBnID0gY3JlYXRlRygpO1xuICAgIGxpbmVzLmZvckVhY2gocG9pbnRzID0+IHtcbiAgICAgICAgaWYgKCFwb2ludHMubGVuZ3RoKSByZXR1cm47XG4gICAgICAgIGNvbnN0IHhBbGlnbiA9IFBsYWl0Qm9hcmQuZ2V0Um91Z2hTVkcoYm9hcmQpLmxpbmUocG9pbnRzWzBdWzBdLCBwb2ludHNbMF1bMV0sIHBvaW50c1sxXVswXSwgcG9pbnRzWzFdWzFdLCB7XG4gICAgICAgICAgICBzdHJva2U6IFNFTEVDVElPTl9CT1JERVJfQ09MT1IsXG4gICAgICAgICAgICBzdHJva2VXaWR0aDogMSxcbiAgICAgICAgICAgIHN0cm9rZUxpbmVEYXNoOiBbNCwgNF1cbiAgICAgICAgfSk7XG4gICAgICAgIGcuYXBwZW5kQ2hpbGQoeEFsaWduKTtcbiAgICB9KTtcbiAgICByZXR1cm4gZztcbn1cblxuZXhwb3J0IGNvbnN0IGdldFRyaXBsZUFsaWduQXhpcyA9IChyZWN0YW5nbGU6IFJlY3RhbmdsZUNsaWVudCwgaXNIb3Jpem9udGFsOiBib29sZWFuKTogVHJpcGxlQWxpZ25BeGlzID0+IHtcbiAgICBjb25zdCBheGlzID0gaXNIb3Jpem9udGFsID8gJ3gnIDogJ3knO1xuICAgIGNvbnN0IHNpZGUgPSBpc0hvcml6b250YWwgPyAnd2lkdGgnIDogJ2hlaWdodCc7XG4gICAgcmV0dXJuIFtyZWN0YW5nbGVbYXhpc10sIHJlY3RhbmdsZVtheGlzXSArIHJlY3RhbmdsZVtzaWRlXSAvIDIsIHJlY3RhbmdsZVtheGlzXSArIHJlY3RhbmdsZVtzaWRlXV07XG59O1xuXG5leHBvcnQgY29uc3QgaXNBbGlnbiA9IChheGlzOiBudW1iZXIsIHJlY3RhbmdsZTogUmVjdGFuZ2xlQ2xpZW50LCBpc0hvcml6b250YWw6IGJvb2xlYW4pID0+IHtcbiAgICBjb25zdCBhbGlnbkF4aXMgPSBnZXRUcmlwbGVBbGlnbkF4aXMocmVjdGFuZ2xlLCBpc0hvcml6b250YWwpO1xuICAgIHJldHVybiBhbGlnbkF4aXMuaW5jbHVkZXMoYXhpcyk7XG59O1xuXG5leHBvcnQgY29uc3QgZ2V0Q2xvc2VzdERlbHRhID0gKGF4aXM6IG51bWJlciwgcmVjdGFuZ2xlOiBSZWN0YW5nbGVDbGllbnQsIGlzSG9yaXpvbnRhbDogYm9vbGVhbikgPT4ge1xuICAgIGNvbnN0IGFsaWduQXhpcyA9IGdldFRyaXBsZUFsaWduQXhpcyhyZWN0YW5nbGUsIGlzSG9yaXpvbnRhbCk7XG4gICAgY29uc3QgZGVsdGFzID0gYWxpZ25BeGlzLm1hcChpdGVtID0+IGl0ZW0gLSBheGlzKTtcbiAgICBjb25zdCBhYnNEZWx0YXMgPSBkZWx0YXMubWFwKGl0ZW0gPT4gTWF0aC5hYnMoaXRlbSkpO1xuICAgIGNvbnN0IGluZGV4ID0gYWJzRGVsdGFzLmluZGV4T2YoTWF0aC5taW4oLi4uYWJzRGVsdGFzKSk7XG4gICAgcmV0dXJuIGRlbHRhc1tpbmRleF07XG59O1xuXG5mdW5jdGlvbiBnZXRNaW5BbGlnbkRlbHRhKGFsaWduUmVjdGFuZ2xlczogUmVjdGFuZ2xlQ2xpZW50W10sIGF4aXM6IG51bWJlciwgaXNIb3Jpem9udGFsOiBib29sZWFuKSB7XG4gICAgbGV0IGRlbHRhID0gQUxJR05fVE9MRVJBTkNFO1xuXG4gICAgYWxpZ25SZWN0YW5nbGVzLmZvckVhY2goaXRlbSA9PiB7XG4gICAgICAgIGNvbnN0IGRpc3RhbmNlID0gZ2V0Q2xvc2VzdERlbHRhKGF4aXMsIGl0ZW0sIGlzSG9yaXpvbnRhbCk7XG4gICAgICAgIGlmIChNYXRoLmFicyhkaXN0YW5jZSkgPCBNYXRoLmFicyhkZWx0YSkpIHtcbiAgICAgICAgICAgIGRlbHRhID0gZGlzdGFuY2U7XG4gICAgICAgIH1cbiAgICB9KTtcbiAgICByZXR1cm4gZGVsdGE7XG59XG5cbmZ1bmN0aW9uIGdldE5lYXJlc3RBbGlnblJlY3RhbmdsZShhbGlnblJlY3RhbmdsZXM6IFJlY3RhbmdsZUNsaWVudFtdLCBhY3RpdmVSZWN0YW5nbGU6IFJlY3RhbmdsZUNsaWVudCkge1xuICAgIGxldCBtaW5EaXN0YW5jZSA9IEluZmluaXR5O1xuICAgIGxldCBuZWFyZXN0UmVjdGFuZ2xlID0gYWxpZ25SZWN0YW5nbGVzWzBdO1xuXG4gICAgYWxpZ25SZWN0YW5nbGVzLmZvckVhY2goaXRlbSA9PiB7XG4gICAgICAgIGNvbnN0IGRpc3RhbmNlID0gTWF0aC5zcXJ0KE1hdGgucG93KGFjdGl2ZVJlY3RhbmdsZS54IC0gaXRlbS54LCAyKSArIE1hdGgucG93KGFjdGl2ZVJlY3RhbmdsZS55IC0gaXRlbS55LCAyKSk7XG4gICAgICAgIGlmIChkaXN0YW5jZSA8IG1pbkRpc3RhbmNlKSB7XG4gICAgICAgICAgICBtaW5EaXN0YW5jZSA9IGRpc3RhbmNlO1xuICAgICAgICAgICAgbmVhcmVzdFJlY3RhbmdsZSA9IGl0ZW07XG4gICAgICAgIH1cbiAgICB9KTtcbiAgICByZXR1cm4gbmVhcmVzdFJlY3RhbmdsZTtcbn1cbiJdfQ==
@@ -0,0 +1,37 @@
1
+ import { RectangleClient, getRectangleByElements } from '@plait/core';
2
+ import { getResizeZoom, movePointByZoomAndOriginPoint } from '../plugins/with-draw-resize';
3
+ import { getDirectionFactorByVectorComponent, getUnitVectorByPointAndPoint } from '@plait/common';
4
+ import { ResizeAlignReaction } from './resize-align-reaction';
5
+ export function getResizeAlignRef(board, resizeRef, resizeState, resizeOriginPointAndHandlePoint, isAspectRatio, isFromCorner) {
6
+ const { originPoint, handlePoint } = resizeOriginPointAndHandlePoint;
7
+ const { xZoom, yZoom } = getResizeZoom(resizeState, originPoint, handlePoint, isFromCorner, isAspectRatio);
8
+ let activeElements;
9
+ let resizeOriginPoints = [];
10
+ if (Array.isArray(resizeRef.element)) {
11
+ activeElements = resizeRef.element;
12
+ const rectangle = getRectangleByElements(board, resizeRef.element, false);
13
+ resizeOriginPoints = RectangleClient.getPoints(rectangle);
14
+ }
15
+ else {
16
+ activeElements = [resizeRef.element];
17
+ resizeOriginPoints = resizeRef.element.points;
18
+ }
19
+ const points = resizeOriginPoints.map(p => {
20
+ return movePointByZoomAndOriginPoint(p, originPoint, xZoom, yZoom);
21
+ });
22
+ const activeRectangle = RectangleClient.getRectangleByPoints(points);
23
+ const resizeAlignReaction = new ResizeAlignReaction(board, activeElements);
24
+ const resizeHandlePoint = movePointByZoomAndOriginPoint(handlePoint, originPoint, xZoom, yZoom);
25
+ const [x, y] = getUnitVectorByPointAndPoint(originPoint, resizeHandlePoint);
26
+ return resizeAlignReaction.handleResizeAlign({
27
+ resizeState,
28
+ resizeOriginPoints,
29
+ activeRectangle,
30
+ originPoint,
31
+ handlePoint,
32
+ directionFactors: [getDirectionFactorByVectorComponent(x), getDirectionFactorByVectorComponent(y)],
33
+ isAspectRatio,
34
+ isFromCorner
35
+ });
36
+ }
37
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVzaXplLWFsaWduLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vcGFja2FnZXMvZHJhdy9zcmMvdXRpbHMvcmVzaXplLWFsaWduLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBcUIsZUFBZSxFQUFFLHNCQUFzQixFQUFpQyxNQUFNLGFBQWEsQ0FBQztBQUN4SCxPQUFPLEVBQUUsYUFBYSxFQUFFLDZCQUE2QixFQUFFLE1BQU0sNkJBQTZCLENBQUM7QUFDM0YsT0FBTyxFQUEwQixtQ0FBbUMsRUFBRSw0QkFBNEIsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUUxSCxPQUFPLEVBQUUsbUJBQW1CLEVBQWtCLE1BQU0seUJBQXlCLENBQUM7QUFFOUUsTUFBTSxVQUFVLGlCQUFpQixDQUM3QixLQUFpQixFQUNqQixTQUEyRCxFQUMzRCxXQUF3QixFQUN4QiwrQkFHQyxFQUNELGFBQXNCLEVBQ3RCLFlBQXFCO0lBRXJCLE1BQU0sRUFBRSxXQUFXLEVBQUUsV0FBVyxFQUFFLEdBQUcsK0JBQStCLENBQUM7SUFDckUsTUFBTSxFQUFFLEtBQUssRUFBRSxLQUFLLEVBQUUsR0FBRyxhQUFhLENBQUMsV0FBVyxFQUFFLFdBQVcsRUFBRSxXQUFXLEVBQUUsWUFBWSxFQUFFLGFBQWEsQ0FBQyxDQUFDO0lBRTNHLElBQUksY0FBOEIsQ0FBQztJQUNuQyxJQUFJLGtCQUFrQixHQUFZLEVBQUUsQ0FBQztJQUNyQyxJQUFJLEtBQUssQ0FBQyxPQUFPLENBQUMsU0FBUyxDQUFDLE9BQU8sQ0FBQyxFQUFFO1FBQ2xDLGNBQWMsR0FBRyxTQUFTLENBQUMsT0FBTyxDQUFDO1FBQ25DLE1BQU0sU0FBUyxHQUFHLHNCQUFzQixDQUFDLEtBQUssRUFBRSxTQUFTLENBQUMsT0FBTyxFQUFFLEtBQUssQ0FBQyxDQUFDO1FBQzFFLGtCQUFrQixHQUFHLGVBQWUsQ0FBQyxTQUFTLENBQUMsU0FBUyxDQUFDLENBQUM7S0FDN0Q7U0FBTTtRQUNILGNBQWMsR0FBRyxDQUFDLFNBQVMsQ0FBQyxPQUFPLENBQUMsQ0FBQztRQUNyQyxrQkFBa0IsR0FBRyxTQUFTLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQztLQUNqRDtJQUVELE1BQU0sTUFBTSxHQUFHLGtCQUFrQixDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRTtRQUN0QyxPQUFPLDZCQUE2QixDQUFDLENBQUMsRUFBRSxXQUFXLEVBQUUsS0FBSyxFQUFFLEtBQUssQ0FBQyxDQUFDO0lBQ3ZFLENBQUMsQ0FBbUIsQ0FBQztJQUNyQixNQUFNLGVBQWUsR0FBRyxlQUFlLENBQUMsb0JBQW9CLENBQUMsTUFBTSxDQUFDLENBQUM7SUFFckUsTUFBTSxtQkFBbUIsR0FBRyxJQUFJLG1CQUFtQixDQUFDLEtBQUssRUFBRSxjQUFjLENBQUMsQ0FBQztJQUMzRSxNQUFNLGlCQUFpQixHQUFHLDZCQUE2QixDQUFDLFdBQVcsRUFBRSxXQUFXLEVBQUUsS0FBSyxFQUFFLEtBQUssQ0FBQyxDQUFDO0lBQ2hHLE1BQU0sQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLEdBQUcsNEJBQTRCLENBQUMsV0FBVyxFQUFFLGlCQUFpQixDQUFDLENBQUM7SUFFNUUsT0FBTyxtQkFBbUIsQ0FBQyxpQkFBaUIsQ0FBQztRQUN6QyxXQUFXO1FBQ1gsa0JBQWtCO1FBQ2xCLGVBQWU7UUFDZixXQUFXO1FBQ1gsV0FBVztRQUNYLGdCQUFnQixFQUFFLENBQUMsbUNBQW1DLENBQUMsQ0FBQyxDQUFDLEVBQUUsbUNBQW1DLENBQUMsQ0FBQyxDQUFDLENBQUM7UUFDbEcsYUFBYTtRQUNiLFlBQVk7S0FDZixDQUFDLENBQUM7QUFDUCxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgUGxhaXRCb2FyZCwgUG9pbnQsIFJlY3RhbmdsZUNsaWVudCwgZ2V0UmVjdGFuZ2xlQnlFbGVtZW50cywgUGxhaXRFbGVtZW50LCBEaXJlY3Rpb25GYWN0b3IgfSBmcm9tICdAcGxhaXQvY29yZSc7XG5pbXBvcnQgeyBnZXRSZXNpemVab29tLCBtb3ZlUG9pbnRCeVpvb21BbmRPcmlnaW5Qb2ludCB9IGZyb20gJy4uL3BsdWdpbnMvd2l0aC1kcmF3LXJlc2l6ZSc7XG5pbXBvcnQgeyBSZXNpemVSZWYsIFJlc2l6ZVN0YXRlLCBnZXREaXJlY3Rpb25GYWN0b3JCeVZlY3RvckNvbXBvbmVudCwgZ2V0VW5pdFZlY3RvckJ5UG9pbnRBbmRQb2ludCB9IGZyb20gJ0BwbGFpdC9jb21tb24nO1xuaW1wb3J0IHsgUGxhaXREcmF3RWxlbWVudCB9IGZyb20gJy4uL2ludGVyZmFjZXMnO1xuaW1wb3J0IHsgUmVzaXplQWxpZ25SZWFjdGlvbiwgUmVzaXplQWxpZ25SZWYgfSBmcm9tICcuL3Jlc2l6ZS1hbGlnbi1yZWFjdGlvbic7XG5cbmV4cG9ydCBmdW5jdGlvbiBnZXRSZXNpemVBbGlnblJlZihcbiAgICBib2FyZDogUGxhaXRCb2FyZCxcbiAgICByZXNpemVSZWY6IFJlc2l6ZVJlZjxQbGFpdERyYXdFbGVtZW50IHwgUGxhaXREcmF3RWxlbWVudFtdPixcbiAgICByZXNpemVTdGF0ZTogUmVzaXplU3RhdGUsXG4gICAgcmVzaXplT3JpZ2luUG9pbnRBbmRIYW5kbGVQb2ludDoge1xuICAgICAgICBvcmlnaW5Qb2ludDogUG9pbnQ7XG4gICAgICAgIGhhbmRsZVBvaW50OiBQb2ludDtcbiAgICB9LFxuICAgIGlzQXNwZWN0UmF0aW86IGJvb2xlYW4sXG4gICAgaXNGcm9tQ29ybmVyOiBib29sZWFuXG4pOiBSZXNpemVBbGlnblJlZiB7XG4gICAgY29uc3QgeyBvcmlnaW5Qb2ludCwgaGFuZGxlUG9pbnQgfSA9IHJlc2l6ZU9yaWdpblBvaW50QW5kSGFuZGxlUG9pbnQ7XG4gICAgY29uc3QgeyB4Wm9vbSwgeVpvb20gfSA9IGdldFJlc2l6ZVpvb20ocmVzaXplU3RhdGUsIG9yaWdpblBvaW50LCBoYW5kbGVQb2ludCwgaXNGcm9tQ29ybmVyLCBpc0FzcGVjdFJhdGlvKTtcblxuICAgIGxldCBhY3RpdmVFbGVtZW50czogUGxhaXRFbGVtZW50W107XG4gICAgbGV0IHJlc2l6ZU9yaWdpblBvaW50czogUG9pbnRbXSA9IFtdO1xuICAgIGlmIChBcnJheS5pc0FycmF5KHJlc2l6ZVJlZi5lbGVtZW50KSkge1xuICAgICAgICBhY3RpdmVFbGVtZW50cyA9IHJlc2l6ZVJlZi5lbGVtZW50O1xuICAgICAgICBjb25zdCByZWN0YW5nbGUgPSBnZXRSZWN0YW5nbGVCeUVsZW1lbnRzKGJvYXJkLCByZXNpemVSZWYuZWxlbWVudCwgZmFsc2UpO1xuICAgICAgICByZXNpemVPcmlnaW5Qb2ludHMgPSBSZWN0YW5nbGVDbGllbnQuZ2V0UG9pbnRzKHJlY3RhbmdsZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgICAgYWN0aXZlRWxlbWVudHMgPSBbcmVzaXplUmVmLmVsZW1lbnRdO1xuICAgICAgICByZXNpemVPcmlnaW5Qb2ludHMgPSByZXNpemVSZWYuZWxlbWVudC5wb2ludHM7XG4gICAgfVxuXG4gICAgY29uc3QgcG9pbnRzID0gcmVzaXplT3JpZ2luUG9pbnRzLm1hcChwID0+IHtcbiAgICAgICAgcmV0dXJuIG1vdmVQb2ludEJ5Wm9vbUFuZE9yaWdpblBvaW50KHAsIG9yaWdpblBvaW50LCB4Wm9vbSwgeVpvb20pO1xuICAgIH0pIGFzIFtQb2ludCwgUG9pbnRdO1xuICAgIGNvbnN0IGFjdGl2ZVJlY3RhbmdsZSA9IFJlY3RhbmdsZUNsaWVudC5nZXRSZWN0YW5nbGVCeVBvaW50cyhwb2ludHMpO1xuXG4gICAgY29uc3QgcmVzaXplQWxpZ25SZWFjdGlvbiA9IG5ldyBSZXNpemVBbGlnblJlYWN0aW9uKGJvYXJkLCBhY3RpdmVFbGVtZW50cyk7XG4gICAgY29uc3QgcmVzaXplSGFuZGxlUG9pbnQgPSBtb3ZlUG9pbnRCeVpvb21BbmRPcmlnaW5Qb2ludChoYW5kbGVQb2ludCwgb3JpZ2luUG9pbnQsIHhab29tLCB5Wm9vbSk7XG4gICAgY29uc3QgW3gsIHldID0gZ2V0VW5pdFZlY3RvckJ5UG9pbnRBbmRQb2ludChvcmlnaW5Qb2ludCwgcmVzaXplSGFuZGxlUG9pbnQpO1xuXG4gICAgcmV0dXJuIHJlc2l6ZUFsaWduUmVhY3Rpb24uaGFuZGxlUmVzaXplQWxpZ24oe1xuICAgICAgICByZXNpemVTdGF0ZSxcbiAgICAgICAgcmVzaXplT3JpZ2luUG9pbnRzLFxuICAgICAgICBhY3RpdmVSZWN0YW5nbGUsXG4gICAgICAgIG9yaWdpblBvaW50LFxuICAgICAgICBoYW5kbGVQb2ludCxcbiAgICAgICAgZGlyZWN0aW9uRmFjdG9yczogW2dldERpcmVjdGlvbkZhY3RvckJ5VmVjdG9yQ29tcG9uZW50KHgpLCBnZXREaXJlY3Rpb25GYWN0b3JCeVZlY3RvckNvbXBvbmVudCh5KV0sXG4gICAgICAgIGlzQXNwZWN0UmF0aW8sXG4gICAgICAgIGlzRnJvbUNvcm5lclxuICAgIH0pO1xufVxuIl19