@libs-ui/services-diagram-draw 0.2.356-37
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +279 -0
- package/canvas.service.d.ts +42 -0
- package/diagram-draw.service.d.ts +91 -0
- package/direction.service.d.ts +43 -0
- package/esm2022/canvas.service.mjs +628 -0
- package/esm2022/diagram-draw.service.mjs +711 -0
- package/esm2022/direction.service.mjs +255 -0
- package/esm2022/index.mjs +6 -0
- package/esm2022/interfaces/canvas.interface.mjs +2 -0
- package/esm2022/interfaces/coordinates.interface.mjs +2 -0
- package/esm2022/interfaces/diagram.interface.mjs +2 -0
- package/esm2022/libs-ui-services-diagram-draw.mjs +5 -0
- package/esm2022/utils/calculator-branch.util.mjs +187 -0
- package/esm2022/utils/calculator-element.util.mjs +335 -0
- package/esm2022/utils/canvas.util.mjs +176 -0
- package/esm2022/utils/diagram.util.mjs +54 -0
- package/esm2022/utils/direction.util.mjs +103 -0
- package/esm2022/utils/horizontal/calculator-branch.util.mjs +243 -0
- package/esm2022/utils/horizontal/calculator-coordinates.util.mjs +315 -0
- package/fesm2022/libs-ui-services-diagram-draw.mjs +2982 -0
- package/fesm2022/libs-ui-services-diagram-draw.mjs.map +1 -0
- package/index.d.ts +5 -0
- package/interfaces/canvas.interface.d.ts +21 -0
- package/interfaces/coordinates.interface.d.ts +40 -0
- package/interfaces/diagram.interface.d.ts +109 -0
- package/package.json +27 -0
- package/utils/calculator-branch.util.d.ts +16 -0
- package/utils/calculator-element.util.d.ts +24 -0
- package/utils/canvas.util.d.ts +21 -0
- package/utils/diagram.util.d.ts +6 -0
- package/utils/direction.util.d.ts +6 -0
- package/utils/horizontal/calculator-branch.util.d.ts +67 -0
- package/utils/horizontal/calculator-coordinates.util.d.ts +42 -0
|
@@ -0,0 +1,315 @@
|
|
|
1
|
+
import { canvasConfigReadonly } from '../../diagram-draw.service';
|
|
2
|
+
import { checkMaxTop } from '../calculator-element.util';
|
|
3
|
+
import { buildFlatElement } from '../diagram.util';
|
|
4
|
+
import { MoLibDiagramHorizontalCalculatorBranchUtil } from './calculator-branch.util';
|
|
5
|
+
/**
|
|
6
|
+
* Horizontal layout calculator.
|
|
7
|
+
* Mirrors MoLibDiagramCalculatorCoordinatesUtil (vertical) but rotated 90°:
|
|
8
|
+
* - Elements grow LEFT → RIGHT (specific_x advances along main axis)
|
|
9
|
+
* - Branches split UP / DOWN (specific_y for branch offset)
|
|
10
|
+
* - "above" branch = upper side (y decreases)
|
|
11
|
+
* - "under" branch = lower side (y increases)
|
|
12
|
+
*
|
|
13
|
+
* Key axis mapping vs. vertical:
|
|
14
|
+
* vertical: specific_y ↕ specific_x centered
|
|
15
|
+
* horizontal: specific_x → specific_y centered
|
|
16
|
+
*/
|
|
17
|
+
export class MoLibDiagramHorizontalCalculatorCoordinatesUtil {
|
|
18
|
+
static setXYElements(elements, config, positionY) {
|
|
19
|
+
if (!elements || !elements.length) {
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
elements.forEach((currentElement, index) => {
|
|
23
|
+
currentElement.specific_y = (currentElement.specific_y ?? 0) + (positionY ?? 0);
|
|
24
|
+
const preElement = elements[index - 1];
|
|
25
|
+
if (preElement) {
|
|
26
|
+
// Trong horizontal: y (chiều cao) căn giữa theo preElement, x tiến sang phải
|
|
27
|
+
currentElement.specific_y = (preElement.specific_y ?? 0) + (preElement.specific_height ?? 0) / 2 - (currentElement.specific_height ?? 0) / 2;
|
|
28
|
+
currentElement.specific_x = (preElement.specific_x ?? 0) + (preElement.specific_width ?? 0) + this.checkElementGetMargin(preElement.nodeOtherConfig);
|
|
29
|
+
if (preElement.position_end_branch) {
|
|
30
|
+
currentElement.specific_x = preElement.position_end_branch;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
checkMaxTop(config, currentElement.specific_y, currentElement.branches?.[0]?.positionMaxTop);
|
|
34
|
+
const top = currentElement.specific_y ?? 0;
|
|
35
|
+
const left = (currentElement.specific_x ?? 0) + (currentElement.specific_width ?? 0) / 2; // điểm giữa theo X (điểm vẽ SVG)
|
|
36
|
+
let lineBetweenElements = (currentElement.specific_width ?? 0) + this.checkElementGetMargin(currentElement.nodeOtherConfig);
|
|
37
|
+
if (currentElement.branches && currentElement.branches.length) {
|
|
38
|
+
lineBetweenElements = (currentElement.specific_width ?? 0) + canvasConfigReadonly().ELEMENT_MARGIN_DEFAULT_BRANCH;
|
|
39
|
+
}
|
|
40
|
+
const maxY = (currentElement.specific_y ?? 0) + (currentElement.specific_height ?? 0) + 200;
|
|
41
|
+
const maxXRight = (currentElement.specific_x ?? 0) + (currentElement.specific_width ?? 0) + 200;
|
|
42
|
+
const configSvg = config.widthHeightSvgCanvas;
|
|
43
|
+
configSvg.heightSvg = maxY > configSvg.heightSvg ? maxY : configSvg.heightSvg;
|
|
44
|
+
configSvg.widthSvg = maxXRight > configSvg.widthSvg ? maxXRight : configSvg.widthSvg;
|
|
45
|
+
if (!currentElement.branches || !currentElement.branches.length) {
|
|
46
|
+
// Element không có nhánh: vẽ đường thẳng ngang
|
|
47
|
+
const drawFormToWidthExit = (currentElement.subCodeOfElement || currentElement.code) === canvasConfigReadonly().TYPE_ELEMENT_EXIT ? (currentElement.specific_width ?? 0) / 2 : lineBetweenElements;
|
|
48
|
+
currentElement.attributeSvgD = `M ${currentElement.specific_x ?? 0} ${top + (currentElement.specific_height ?? 0) / 2} l ${drawFormToWidthExit} 0`;
|
|
49
|
+
currentElement.position_end = (currentElement.specific_x ?? 0) + lineBetweenElements;
|
|
50
|
+
if (currentElement.nodeOtherConfig) {
|
|
51
|
+
const waitWidth = this.getWidthWaitConfig(currentElement.nodeOtherConfig);
|
|
52
|
+
const distanceElementToWait = (currentElement.specific_width ?? 0) + canvasConfigReadonly().DISTANCE_TO_WAIT;
|
|
53
|
+
const leftStartLine2 = (currentElement.specific_x ?? 0) + distanceElementToWait + waitWidth;
|
|
54
|
+
currentElement.attributeSvgD = `M ${currentElement.specific_x ?? 0} ${top + (currentElement.specific_height ?? 0) / 2} l ${distanceElementToWait} 0`;
|
|
55
|
+
currentElement.position_end = leftStartLine2 + lineBetweenElements;
|
|
56
|
+
currentElement.nodeOtherConfig.specific_x = (currentElement.specific_x ?? 0) + distanceElementToWait;
|
|
57
|
+
// specific_y = tâm Y của đường line — setTranslatePositions sẽ trừ height/2 để căn giữa dọc
|
|
58
|
+
currentElement.nodeOtherConfig.specific_y = top + (currentElement.specific_height ?? 0) / 2;
|
|
59
|
+
// Đảm bảo có kích thước để setTranslatePositions tính offset đúng
|
|
60
|
+
if (!currentElement.nodeOtherConfig.specific_height) {
|
|
61
|
+
currentElement.nodeOtherConfig.specific_height = canvasConfigReadonly().ELEMENT_WAIT_DEFAULT;
|
|
62
|
+
}
|
|
63
|
+
if (!currentElement.nodeOtherConfig.specific_width) {
|
|
64
|
+
currentElement.nodeOtherConfig.specific_width = canvasConfigReadonly().ELEMENT_WAIT_DEFAULT;
|
|
65
|
+
}
|
|
66
|
+
delete currentElement.nodeOtherConfig.attributeSvgD;
|
|
67
|
+
if (currentElement.subCodeOfElement !== canvasConfigReadonly().TYPE_ELEMENT_EXIT) {
|
|
68
|
+
currentElement.nodeOtherConfig.attributeSvgD = `M ${leftStartLine2} ${top + (currentElement.specific_height ?? 0) / 2} l ${canvasConfigReadonly().WAIT_TO_ELEMENT} 0`;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return;
|
|
72
|
+
}
|
|
73
|
+
// Elements có nhánh
|
|
74
|
+
const half = Math.ceil(currentElement.branches.length / 2);
|
|
75
|
+
const aboveHalf = currentElement.branches.slice(0, half);
|
|
76
|
+
const underHalf = currentElement.branches.slice(half);
|
|
77
|
+
let brachMiddle;
|
|
78
|
+
if (aboveHalf.length !== underHalf.length) {
|
|
79
|
+
brachMiddle = aboveHalf.pop();
|
|
80
|
+
}
|
|
81
|
+
// TÍNH CHIỀU CAO TỐI ĐA CỦA NHÁNH (đây là chiều rộng trong horizontal context nhưng
|
|
82
|
+
// dùng chung maxHeightBranch để đơn giản, ý nghĩa là "khoảng trống tối thiểu dành cho nhánh không có element")
|
|
83
|
+
const maxWidthBranch = { width: 0 };
|
|
84
|
+
this.calculatorMaxBranchWidth(currentElement, maxWidthBranch);
|
|
85
|
+
currentElement.maxHeightBranch = maxWidthBranch.width;
|
|
86
|
+
const maxWidthBrachMiddle = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
87
|
+
const lineFormElementToBranching = (currentElement.specific_width ?? 0) + canvasConfigReadonly().ELEMENT_MARGIN_DEFAULT_BRANCH;
|
|
88
|
+
// top = y + height/2: điểm giữa theo chiều Y → dùng làm tọa độ Y của đường ngang chính
|
|
89
|
+
const topMid = top + (currentElement.specific_height ?? 0) / 2;
|
|
90
|
+
if (brachMiddle) {
|
|
91
|
+
brachMiddle.onTheSide = 'center';
|
|
92
|
+
this.calculatorHeightBranch(brachMiddle.elements, maxWidthBrachMiddle);
|
|
93
|
+
brachMiddle.widthBranch = {
|
|
94
|
+
width: maxWidthBrachMiddle.width,
|
|
95
|
+
above: maxWidthBrachMiddle.aboveWidth,
|
|
96
|
+
under: maxWidthBrachMiddle.underWidth,
|
|
97
|
+
};
|
|
98
|
+
MoLibDiagramHorizontalCalculatorBranchUtil.drawStraightLine(topMid, lineFormElementToBranching, currentElement.specific_x ?? 0, brachMiddle, maxWidthBranch.width, config);
|
|
99
|
+
}
|
|
100
|
+
let hasNextSameParentElementNext = false;
|
|
101
|
+
const aboveHalfReverse = aboveHalf.reverse();
|
|
102
|
+
aboveHalfReverse.forEach((branch, indexBranch) => {
|
|
103
|
+
if (!hasNextSameParentElementNext) {
|
|
104
|
+
const flatElementOnBranch = [];
|
|
105
|
+
buildFlatElement(branch.elements, flatElementOnBranch);
|
|
106
|
+
hasNextSameParentElementNext = !flatElementOnBranch || !flatElementOnBranch.length ? true : flatElementOnBranch.find((item) => item.next_id === currentElement.next_id) ? true : false;
|
|
107
|
+
}
|
|
108
|
+
branch.onTheSide = 'above';
|
|
109
|
+
const maxWidthB = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
110
|
+
this.calculatorHeightBranch(branch.elements, maxWidthB);
|
|
111
|
+
branch.widthBranch = {
|
|
112
|
+
width: maxWidthB.width,
|
|
113
|
+
above: maxWidthB.aboveWidth,
|
|
114
|
+
under: maxWidthB.underWidth,
|
|
115
|
+
};
|
|
116
|
+
const branchPre = aboveHalfReverse[indexBranch - 1];
|
|
117
|
+
let lineBetweenBranch = maxWidthB.underWidth + canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT / 2;
|
|
118
|
+
if (branchPre) {
|
|
119
|
+
lineBetweenBranch += (branchPre.widthBranch?.width ?? 0) + canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT;
|
|
120
|
+
}
|
|
121
|
+
if (brachMiddle) {
|
|
122
|
+
lineBetweenBranch += (brachMiddle.widthBranch?.above ?? 0) + canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT / 2;
|
|
123
|
+
}
|
|
124
|
+
MoLibDiagramHorizontalCalculatorBranchUtil.aboveLine(topMid, lineFormElementToBranching, currentElement.specific_x ?? 0, lineBetweenBranch, branch, maxWidthBranch.width, currentElement, config);
|
|
125
|
+
});
|
|
126
|
+
underHalf.forEach((branch, indexBranch) => {
|
|
127
|
+
if (!hasNextSameParentElementNext) {
|
|
128
|
+
const flatElementOnBranch = [];
|
|
129
|
+
buildFlatElement(branch.elements, flatElementOnBranch);
|
|
130
|
+
hasNextSameParentElementNext = !flatElementOnBranch || !flatElementOnBranch.length ? true : flatElementOnBranch.find((item) => item.next_id === currentElement.next_id) ? true : false;
|
|
131
|
+
}
|
|
132
|
+
branch.onTheSide = 'under';
|
|
133
|
+
const maxWidthB = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
134
|
+
this.calculatorHeightBranch(branch.elements, maxWidthB);
|
|
135
|
+
branch.widthBranch = {
|
|
136
|
+
width: maxWidthB.width,
|
|
137
|
+
above: maxWidthB.aboveWidth,
|
|
138
|
+
under: maxWidthB.underWidth,
|
|
139
|
+
};
|
|
140
|
+
const branchPre = underHalf[indexBranch - 1];
|
|
141
|
+
let lineBetweenBranch = maxWidthB.aboveWidth + canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT / 2;
|
|
142
|
+
if (branchPre) {
|
|
143
|
+
lineBetweenBranch += (branchPre.widthBranch?.width ?? 0) + canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT;
|
|
144
|
+
}
|
|
145
|
+
if (brachMiddle) {
|
|
146
|
+
lineBetweenBranch += (brachMiddle.widthBranch?.under ?? 0) + canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT / 2;
|
|
147
|
+
}
|
|
148
|
+
MoLibDiagramHorizontalCalculatorBranchUtil.underLine(topMid, lineFormElementToBranching, currentElement.specific_x ?? 0, lineBetweenBranch, branch, maxWidthBranch.width, currentElement, config);
|
|
149
|
+
});
|
|
150
|
+
});
|
|
151
|
+
this.setTranslatePositions(elements);
|
|
152
|
+
}
|
|
153
|
+
/**
|
|
154
|
+
* Set translateX/Y cho tất cả elements (bao gồm branches và nodeOtherConfig)
|
|
155
|
+
*/
|
|
156
|
+
static setTranslatePositions(elements) {
|
|
157
|
+
elements.forEach((element) => {
|
|
158
|
+
element.translateX = element.specific_x;
|
|
159
|
+
element.translateY = element.specific_y;
|
|
160
|
+
if (element.nodeOtherConfig) {
|
|
161
|
+
const offsetY = (element.nodeOtherConfig.specific_height ?? 0) / 2;
|
|
162
|
+
element.nodeOtherConfig.translateX = element.nodeOtherConfig.specific_x;
|
|
163
|
+
element.nodeOtherConfig.translateY = (element.nodeOtherConfig.specific_y ?? 0) - offsetY;
|
|
164
|
+
}
|
|
165
|
+
if (element.branches && element.branches.length > 0) {
|
|
166
|
+
element.branches.forEach((branch) => {
|
|
167
|
+
if (branch.nodeOtherConfig) {
|
|
168
|
+
const offsetY = (branch.nodeOtherConfig.specific_height ?? 0) / 2;
|
|
169
|
+
branch.nodeOtherConfig.translateX = branch.nodeOtherConfig.specific_x;
|
|
170
|
+
branch.nodeOtherConfig.translateY = (branch.nodeOtherConfig.specific_y ?? 0) - offsetY;
|
|
171
|
+
}
|
|
172
|
+
if (branch.elements && branch.elements.length > 0) {
|
|
173
|
+
this.setTranslatePositions(branch.elements);
|
|
174
|
+
}
|
|
175
|
+
});
|
|
176
|
+
}
|
|
177
|
+
});
|
|
178
|
+
}
|
|
179
|
+
/** Tính chiều rộng tối đa của nhánh (trong horizontal = chiều cao thực của nhánh không có element) */
|
|
180
|
+
static calculatorMaxBranchWidth(element, maxWidthBranch) {
|
|
181
|
+
if (!element.branches || !element.branches.length) {
|
|
182
|
+
return;
|
|
183
|
+
}
|
|
184
|
+
element.branches.forEach((branch) => {
|
|
185
|
+
if (!branch.elements || !branch.elements.length) {
|
|
186
|
+
const lineBranchNoHasElement = canvasConfigReadonly().ELEMENT_WIDTH_DEFAULT_BRANCH_WHEN_NOT_ELEMENT;
|
|
187
|
+
maxWidthBranch.width = lineBranchNoHasElement > maxWidthBranch.width ? lineBranchNoHasElement : maxWidthBranch.width;
|
|
188
|
+
return;
|
|
189
|
+
}
|
|
190
|
+
const total = { height: 0 };
|
|
191
|
+
this.plusWidthElementInBranch(branch.elements, total);
|
|
192
|
+
maxWidthBranch.width = total.height > maxWidthBranch.width ? total.height : maxWidthBranch.width;
|
|
193
|
+
});
|
|
194
|
+
}
|
|
195
|
+
/** Tính tổng chiều rộng các elements trong nhánh (dọc theo trục X) */
|
|
196
|
+
static plusWidthElementInBranch(elements, total) {
|
|
197
|
+
elements.forEach((element) => {
|
|
198
|
+
const margin = !element.branches || !element.branches.length ? this.checkElementGetMargin(element.nodeOtherConfig) : canvasConfigReadonly().ELEMENT_MARGIN_DEFAULT_BRANCH;
|
|
199
|
+
total.height += (element.specific_width ?? 0) + margin;
|
|
200
|
+
if (!element.branches || !element.branches.length) {
|
|
201
|
+
return;
|
|
202
|
+
}
|
|
203
|
+
total.height += 64;
|
|
204
|
+
const theMostElementsInBranch = { height: 0 };
|
|
205
|
+
element.branches.forEach((branch) => {
|
|
206
|
+
const widthInBranch = { height: 0 };
|
|
207
|
+
widthInBranch.height += canvasConfigReadonly().ELEMENT_MARGIN_DEFAULT_BRANCH_TO_ELEMENT_FIRST + 20;
|
|
208
|
+
if (!branch.elements || !branch.elements.length) {
|
|
209
|
+
widthInBranch.height += canvasConfigReadonly().ELEMENT_WIDTH_DEFAULT_BRANCH_WHEN_NOT_ELEMENT;
|
|
210
|
+
if (theMostElementsInBranch.height < widthInBranch.height) {
|
|
211
|
+
theMostElementsInBranch.height = widthInBranch.height;
|
|
212
|
+
}
|
|
213
|
+
return;
|
|
214
|
+
}
|
|
215
|
+
this.plusWidthElementInBranch(branch.elements, widthInBranch);
|
|
216
|
+
if (theMostElementsInBranch.height < widthInBranch.height) {
|
|
217
|
+
theMostElementsInBranch.height = widthInBranch.height;
|
|
218
|
+
}
|
|
219
|
+
});
|
|
220
|
+
total.height += theMostElementsInBranch.height;
|
|
221
|
+
});
|
|
222
|
+
}
|
|
223
|
+
/**
|
|
224
|
+
* Tính chiều cao (Y span) của một nhánh — dùng để offset các nhánh trên/dưới.
|
|
225
|
+
* Trong horizontal context: mỗi nhánh trải dài theo Y (lên/xuống).
|
|
226
|
+
*/
|
|
227
|
+
static calculatorHeightBranch(elements, maxWidth) {
|
|
228
|
+
if (!elements || !elements.length) {
|
|
229
|
+
const w = canvasConfigReadonly().DEFAULT_BRANCH_WHEN_NO_ELEMENT;
|
|
230
|
+
maxWidth.width = w;
|
|
231
|
+
maxWidth.aboveWidth = w / 2;
|
|
232
|
+
maxWidth.underWidth = w / 2;
|
|
233
|
+
return;
|
|
234
|
+
}
|
|
235
|
+
const maxWidthInElements = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
236
|
+
elements.forEach((element) => {
|
|
237
|
+
if (!element.branches || !element.branches.length) {
|
|
238
|
+
// element không nhánh: dùng specific_height làm Y span
|
|
239
|
+
if ((element.specific_height ?? 0) < maxWidthInElements.width) {
|
|
240
|
+
return;
|
|
241
|
+
}
|
|
242
|
+
const h = element.specific_height ?? 0;
|
|
243
|
+
maxWidthInElements.width = h;
|
|
244
|
+
maxWidthInElements.aboveWidth = h / 2;
|
|
245
|
+
maxWidthInElements.underWidth = h / 2;
|
|
246
|
+
return;
|
|
247
|
+
}
|
|
248
|
+
const widthElementIncludeBranch = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
249
|
+
const h = element.specific_height ?? 0;
|
|
250
|
+
if (h > widthElementIncludeBranch.width) {
|
|
251
|
+
widthElementIncludeBranch.width = h;
|
|
252
|
+
widthElementIncludeBranch.aboveWidth = h / 2;
|
|
253
|
+
widthElementIncludeBranch.underWidth = h / 2;
|
|
254
|
+
}
|
|
255
|
+
const half = Math.ceil(element.branches.length / 2);
|
|
256
|
+
const aboveHalf = element.branches.slice(0, half);
|
|
257
|
+
const underHalf = element.branches.slice(half);
|
|
258
|
+
let brachMiddle;
|
|
259
|
+
if (aboveHalf.length !== underHalf.length) {
|
|
260
|
+
brachMiddle = aboveHalf.pop();
|
|
261
|
+
}
|
|
262
|
+
if (brachMiddle)
|
|
263
|
+
brachMiddle.onTheSide = 'center';
|
|
264
|
+
aboveHalf.forEach((branch) => (branch.onTheSide = 'above'));
|
|
265
|
+
underHalf.forEach((branch) => (branch.onTheSide = 'under'));
|
|
266
|
+
const widthBranch = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
267
|
+
element.branches.forEach((branch) => {
|
|
268
|
+
const w = { width: 0, aboveWidth: 0, underWidth: 0 };
|
|
269
|
+
this.calculatorHeightBranch(branch.elements, w);
|
|
270
|
+
switch (branch.onTheSide) {
|
|
271
|
+
case 'above':
|
|
272
|
+
widthBranch.aboveWidth += w.width;
|
|
273
|
+
break;
|
|
274
|
+
case 'under':
|
|
275
|
+
widthBranch.underWidth += w.width;
|
|
276
|
+
break;
|
|
277
|
+
case 'center':
|
|
278
|
+
widthBranch.aboveWidth += w.aboveWidth;
|
|
279
|
+
widthBranch.underWidth += w.underWidth;
|
|
280
|
+
break;
|
|
281
|
+
}
|
|
282
|
+
});
|
|
283
|
+
const marginBetweenBranch = (element.branches.length - 1) * canvasConfigReadonly().ELEMENT_MARGIN_BETWEEN_BRANCH_DEFAULT;
|
|
284
|
+
widthBranch.aboveWidth += marginBetweenBranch / 2;
|
|
285
|
+
widthBranch.underWidth += marginBetweenBranch / 2;
|
|
286
|
+
const maxAboveWidth = Math.max(widthElementIncludeBranch.aboveWidth, widthBranch.aboveWidth);
|
|
287
|
+
const maxUnderWidth = Math.max(widthElementIncludeBranch.underWidth, widthBranch.underWidth);
|
|
288
|
+
if (maxWidthInElements.aboveWidth < maxAboveWidth) {
|
|
289
|
+
maxWidthInElements.aboveWidth = maxAboveWidth;
|
|
290
|
+
}
|
|
291
|
+
if (maxWidthInElements.underWidth < maxUnderWidth) {
|
|
292
|
+
maxWidthInElements.underWidth = maxUnderWidth;
|
|
293
|
+
}
|
|
294
|
+
maxWidthInElements.width = maxWidthInElements.aboveWidth + maxWidthInElements.underWidth;
|
|
295
|
+
});
|
|
296
|
+
maxWidth.width += maxWidthInElements.aboveWidth + maxWidthInElements.underWidth;
|
|
297
|
+
maxWidth.aboveWidth += maxWidthInElements.aboveWidth;
|
|
298
|
+
maxWidth.underWidth += maxWidthInElements.underWidth;
|
|
299
|
+
}
|
|
300
|
+
/** Tính khoảng cách thêm vào sau element (bao gồm wait config nếu có) */
|
|
301
|
+
static checkElementGetMargin(hasWaitConfig) {
|
|
302
|
+
if (hasWaitConfig) {
|
|
303
|
+
return canvasConfigReadonly().DISTANCE_TO_WAIT + this.getWidthWaitConfig(hasWaitConfig) + canvasConfigReadonly().WAIT_TO_ELEMENT;
|
|
304
|
+
}
|
|
305
|
+
return canvasConfigReadonly().ELEMENT_MARGIN_DEFAULT;
|
|
306
|
+
}
|
|
307
|
+
/** Tính chiều rộng của wait config node */
|
|
308
|
+
static getWidthWaitConfig(hasWaitConfig) {
|
|
309
|
+
if (hasWaitConfig) {
|
|
310
|
+
return (hasWaitConfig.specific_width ?? canvasConfigReadonly().ELEMENT_WAIT_DEFAULT) + canvasConfigReadonly().DISTANCE_WAIT_TO_NEXT_LINE;
|
|
311
|
+
}
|
|
312
|
+
return canvasConfigReadonly().ELEMENT_WAIT_DEFAULT + canvasConfigReadonly().DISTANCE_WAIT_TO_NEXT_LINE;
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY2FsY3VsYXRvci1jb29yZGluYXRlcy51dGlsLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vbGlicy11aS9zZXJ2aWNlcy9kaWFncmFtLWRyYXcvc3JjL3V0aWxzL2hvcml6b250YWwvY2FsY3VsYXRvci1jb29yZGluYXRlcy51dGlsLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxvQkFBb0IsRUFBRSxNQUFNLDRCQUE0QixDQUFDO0FBRWxFLE9BQU8sRUFBRSxXQUFXLEVBQUUsTUFBTSw0QkFBNEIsQ0FBQztBQUV6RCxPQUFPLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQUNuRCxPQUFPLEVBQUUsMENBQTBDLEVBQUUsTUFBTSwwQkFBMEIsQ0FBQztBQUV0Rjs7Ozs7Ozs7Ozs7R0FXRztBQUNILE1BQU0sT0FBTywrQ0FBK0M7SUFDMUQsTUFBTSxDQUFDLGFBQWEsQ0FBQyxRQUFnQyxFQUFFLE1BQTZCLEVBQUUsU0FBa0I7UUFDdEcsSUFBSSxDQUFDLFFBQVEsSUFBSSxDQUFDLFFBQVEsQ0FBQyxNQUFNLEVBQUUsQ0FBQztZQUNsQyxPQUFPO1FBQ1QsQ0FBQztRQUVELFFBQVEsQ0FBQyxPQUFPLENBQUMsQ0FBQyxjQUFjLEVBQUUsS0FBSyxFQUFFLEVBQUU7WUFDekMsY0FBYyxDQUFDLFVBQVUsR0FBRyxDQUFDLGNBQWMsQ0FBQyxVQUFVLElBQUksQ0FBQyxDQUFDLEdBQUcsQ0FBQyxTQUFTLElBQUksQ0FBQyxDQUFDLENBQUM7WUFDaEYsTUFBTSxVQUFVLEdBQUcsUUFBUSxDQUFDLEtBQUssR0FBRyxDQUFDLENBQUMsQ0FBQztZQUV2QyxJQUFJLFVBQVUsRUFBRSxDQUFDO2dCQUNmLDZFQUE2RTtnQkFDN0UsY0FBYyxDQUFDLFVBQVUsR0FBRyxDQUFDLFVBQVUsQ0FBQyxVQUFVLElBQUksQ0FBQyxDQUFDLEdBQUcsQ0FBQyxVQUFVLENBQUMsZUFBZSxJQUFJLENB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QVUsSUFBSSxrQkFBa0IsQ0FBQyxVQUFVLENBQUM7SUFDdkQsQ0FBQztJQUVELHlFQUF5RTtJQUNqRSxNQUFNLENBQUMscUJBQXFCLENBQUMsYUFBK0I7UUFDbEUsSUFBSSxhQUFhLEVBQUUsQ0FBQztZQUNsQixPQUFPLG9CQUFvQixFQUFFLENBQUMsZ0JBQWdCLEdBQUcsSUFBSSxDQUFDLGtCQUFrQixDQUFDLGFBQWEsQ0FBQyxHQUFHLG9CQUFvQixFQUFFLENBQUMsZUFBZSxDQUFDO1FBQ25JLENBQUM7UUFDRCxPQUFPLG9CQUFvQixFQUFFLENBQUMsc0JBQXNCLENBQUM7SUFDdkQsQ0FBQztJQUVELDJDQUEyQztJQUNuQyxNQUFNLENBQUMsa0JBQWtCLENBQUMsYUFBK0I7UUFDL0QsSUFBSSxhQUFhLEVBQUUsQ0FBQztZQUNsQixPQUFPLENBQUMsYUFBYSxDQUFDLGNBQWMsSUFBSSxvQkFBb0IsRUFBRSxDQUFDLG9CQUFvQixDQUFDLEdBQUcsb0JBQW9CLEVBQUUsQ0FBQywwQkFBMEIsQ0FBQztRQUMzSSxDQUFDO1FBQ0QsT0FBTyxvQkFBb0IsRUFBRSxDQUFDLG9CQUFvQixHQUFHLG9CQUFvQixFQUFFLENBQUMsMEJBQTBCLENBQUM7SUFDekcsQ0FBQztDQUNGIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgY2FudmFzQ29uZmlnUmVhZG9ubHkgfSBmcm9tICcuLi8uLi9kaWFncmFtLWRyYXcuc2VydmljZSc7XG5pbXBvcnQgeyBJRGF0YURpYWdyYW1Db25maWdTdmcgfSBmcm9tICcuLi8uLi9pbnRlcmZhY2VzL2Nvb3JkaW5hdGVzLmludGVyZmFjZSc7XG5pbXBvcnQgeyBjaGVja01heFRvcCB9IGZyb20gJy4uL2NhbGN1bGF0b3ItZWxlbWVudC51dGlsJztcbmltcG9ydCB7IElEaWFncmFtRWxlbWVudCwgSURpYWdyYW1FbGVtZW50QnJhbmNoIH0gZnJvbSAnLi4vLi4vaW50ZXJmYWNlcy9kaWFncmFtLmludGVyZmFjZSc7XG5pbXBvcnQgeyBidWlsZEZsYXRFbGVtZW50IH0gZnJvbSAnLi4vZGlhZ3JhbS51dGlsJztcbmltcG9ydCB7IE1vTGliRGlhZ3JhbUhvcml6b250YWxDYWxjdWxhdG9yQnJhbmNoVXRpbCB9IGZyb20gJy4vY2FsY3VsYXRvci1icmFuY2gudXRpbCc7XG5cbi8qKlxuICogSG9yaXpvbnRhbCBsYXlvdXQgY2FsY3VsYXRvci5cbiAqIE1pcnJvcnMgTW9MaWJEaWFncmFtQ2FsY3VsYXRvckNvb3JkaW5hdGVzVXRpbCAodmVydGljYWwpIGJ1dCByb3RhdGVkIDkwwrA6XG4gKiAgLSBFbGVtZW50cyBncm93IExFRlQg4oaSIFJJR0hUICAoc3BlY2lmaWNfeCBhZHZhbmNlcyBhbG9uZyBtYWluIGF4aXMpXG4gKiAgLSBCcmFuY2hlcyBzcGxpdCBVUCAvIERPV04gICAgKHNwZWNpZmljX3kgZm9yIGJyYW5jaCBvZmZzZXQpXG4gKiAgLSBcImFib3ZlXCIgYnJhbmNoID0gdXBwZXIgc2lkZSAoeSBkZWNyZWFzZXMpXG4gKiAgLSBcInVuZGVyXCIgYnJhbmNoID0gbG93ZXIgc2lkZSAoeSBpbmNyZWFzZXMpXG4gKlxuICogS2V5IGF4aXMgbWFwcGluZyB2cy4gdmVydGljYWw6XG4gKiAgIHZlcnRpY2FsOiBzcGVjaWZpY195IOKGlSAgc3BlY2lmaWNfeCBjZW50ZXJlZFxuICogICBob3Jpem9udGFsOiBzcGVjaWZpY194IOKGkiBzcGVjaWZpY195IGNlbnRlcmVkXG4gKi9cbmV4cG9ydCBjbGFzcyBNb0xpYkRpYWdyYW1Ib3Jpem9udGFsQ2FsY3VsYXRvckNvb3JkaW5hdGVzVXRpbCB7XG4gIHN0YXRpYyBzZXRYWUVsZW1lbnRzKGVsZW1lbnRzOiBBcnJheTxJRGlhZ3JhbUVsZW1lbnQ+LCBjb25maWc6IElEYXRhRGlhZ3JhbUNvbmZpZ1N2ZywgcG9zaXRpb25ZPzogbnVtYmVyKSB7XG4gICAgaWYgKCFlbGVtZW50cyB8fCAhZWxlbWVudHMubGVuZ3RoKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgZWxlbWVudHMuZm9yRWFjaCgoY3VycmVudEVsZW1lbnQsIGluZGV4KSA9PiB7XG4gICAgICBjdXJyZW50RWxlbWVudC5zcGVjaWZpY195ID0gKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3kgPz8gMCkgKyAocG9zaXRpb25ZID8/IDApO1xuICAgICAgY29uc3QgcHJlRWxlbWVudCA9IGVsZW1lbnRzW2luZGV4IC0gMV07XG5cbiAgICAgIGlmIChwcmVFbGVtZW50KSB7XG4gICAgICAgIC8vIFRyb25nIGhvcml6b250YWw6IHkgKGNoaeG7gXUgY2FvKSBjxINuIGdp4buvYSB0aGVvIHByZUVsZW1lbnQsIHggdGnhur9uIHNhbmcgcGjhuqNpXG4gICAgICAgIGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3kgPSAocHJlRWxlbWVudC5zcGVjaWZpY195ID8/IDApICsgKHByZUVsZW1lbnQuc3BlY2lmaWNfaGVpZ2h0ID8/IDApIC8gMiAtIChjdXJyZW50RWxlbWVudC5zcGVjaWZpY19oZWlnaHQgPz8gMCkgLyAyO1xuICAgICAgICBjdXJyZW50RWxlbWVudC5zcGVjaWZpY194ID0gKHByZUVsZW1lbnQuc3BlY2lmaWNfeCA/PyAwKSArIChwcmVFbGVtZW50LnNwZWNpZmljX3dpZHRoID8/IDApICsgdGhpcy5jaGVja0VsZW1lbnRHZXRNYXJnaW4ocHJlRWxlbWVudC5ub2RlT3RoZXJDb25maWcpO1xuXG4gICAgICAgIGlmIChwcmVFbGVtZW50LnBvc2l0aW9uX2VuZF9icmFuY2gpIHtcbiAgICAgICAgICBjdXJyZW50RWxlbWVudC5zcGVjaWZpY194ID0gcHJlRWxlbWVudC5wb3NpdGlvbl9lbmRfYnJhbmNoO1xuICAgICAgICB9XG4gICAgICB9XG5cbiAgICAgIGNoZWNrTWF4VG9wKGNvbmZpZywgY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfeSwgY3VycmVudEVsZW1lbnQuYnJhbmNoZXM/LlswXT8ucG9zaXRpb25NYXhUb3ApO1xuXG4gICAgICBjb25zdCB0b3AgPSBjdXJyZW50RWxlbWVudC5zcGVjaWZpY195ID8/IDA7XG4gICAgICBjb25zdCBsZWZ0ID0gKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3ggPz8gMCkgKyAoY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfd2lkdGggPz8gMCkgLyAyOyAvLyDEkWnhu4NtIGdp4buvYSB0aGVvIFggKMSRaeG7g20gduG6vSBTVkcpXG4gICAgICBsZXQgbGluZUJldHdlZW5FbGVtZW50cyA9IChjdXJyZW50RWxlbWVudC5zcGVjaWZpY193aWR0aCA/PyAwKSArIHRoaXMuY2hlY2tFbGVtZW50R2V0TWFyZ2luKGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZyk7XG5cbiAgICAgIGlmIChjdXJyZW50RWxlbWVudC5icmFuY2hlcyAmJiBjdXJyZW50RWxlbWVudC5icmFuY2hlcy5sZW5ndGgpIHtcbiAgICAgICAgbGluZUJldHdlZW5FbGVtZW50cyA9IChjdXJyZW50RWxlbWVudC5zcGVjaWZpY193aWR0aCA/PyAwKSArIGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9NQVJHSU5fREVGQVVMVF9CUkFOQ0g7XG4gICAgICB9XG5cbiAgICAgIGNvbnN0IG1heFkgPSAoY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfeSA/PyAwKSArIChjdXJyZW50RWxlbWVudC5zcGVjaWZpY19oZWlnaHQgPz8gMCkgKyAyMDA7XG4gICAgICBjb25zdCBtYXhYUmlnaHQgPSAoY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfeCA/PyAwKSArIChjdXJyZW50RWxlbWVudC5zcGVjaWZpY193aWR0aCA/PyAwKSArIDIwMDtcbiAgICAgIGNvbnN0IGNvbmZpZ1N2ZyA9IGNvbmZpZy53aWR0aEhlaWdodFN2Z0NhbnZhcztcblxuICAgICAgY29uZmlnU3ZnLmhlaWdodFN2ZyA9IG1heFkgPiBjb25maWdTdmcuaGVpZ2h0U3ZnID8gbWF4WSA6IGNvbmZpZ1N2Zy5oZWlnaHRTdmc7XG4gICAgICBjb25maWdTdmcud2lkdGhTdmcgPSBtYXhYUmlnaHQgPiBjb25maWdTdmcud2lkdGhTdmcgPyBtYXhYUmlnaHQgOiBjb25maWdTdmcud2lkdGhTdmc7XG5cbiAgICAgIGlmICghY3VycmVudEVsZW1lbnQuYnJhbmNoZXMgfHwgIWN1cnJlbnRFbGVtZW50LmJyYW5jaGVzLmxlbmd0aCkge1xuICAgICAgICAvLyBFbGVtZW50IGtow7RuZyBjw7MgbmjDoW5oOiB24bq9IMSRxrDhu51uZyB0aOG6s25nIG5nYW5nXG4gICAgICAgIGNvbnN0IGRyYXdGb3JtVG9XaWR0aEV4aXQgPSAoY3VycmVudEVsZW1lbnQuc3ViQ29kZU9mRWxlbWVudCB8fCBjdXJyZW50RWxlbWVudC5jb2RlKSA9PT0gY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5UWVBFX0VMRU1FTlRfRVhJVCA/IChjdXJyZW50RWxlbWVudC5zcGVjaWZpY193aWR0aCA/PyAwKSAvIDIgOiBsaW5lQmV0d2VlbkVsZW1lbnRzO1xuXG4gICAgICAgIGN1cnJlbnRFbGVtZW50LmF0dHJpYnV0ZVN2Z0QgPSBgTSAke2N1cnJlbnRFbGVtZW50LnNwZWNpZmljX3ggPz8gMH0gJHt0b3AgKyAoY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfaGVpZ2h0ID8/IDApIC8gMn0gbCAke2RyYXdGb3JtVG9XaWR0aEV4aXR9IDBgO1xuICAgICAgICBjdXJyZW50RWxlbWVudC5wb3NpdGlvbl9lbmQgPSAoY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfeCA/PyAwKSArIGxpbmVCZXR3ZWVuRWxlbWVudHM7XG5cbiAgICAgICAgaWYgKGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZykge1xuICAgICAgICAgIGNvbnN0IHdhaXRXaWR0aCA9IHRoaXMuZ2V0V2lkdGhXYWl0Q29uZmlnKGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZyk7XG4gICAgICAgICAgY29uc3QgZGlzdGFuY2VFbGVtZW50VG9XYWl0ID0gKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3dpZHRoID8/IDApICsgY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5ESVNUQU5DRV9UT19XQUlUO1xuICAgICAgICAgIGNvbnN0IGxlZnRTdGFydExpbmUyID0gKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3ggPz8gMCkgKyBkaXN0YW5jZUVsZW1lbnRUb1dhaXQgKyB3YWl0V2lkdGg7XG5cbiAgICAgICAgICBjdXJyZW50RWxlbWVudC5hdHRyaWJ1dGVTdmdEID0gYE0gJHtjdXJyZW50RWxlbWVudC5zcGVjaWZpY194ID8/IDB9ICR7dG9wICsgKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX2hlaWdodCA/PyAwKSAvIDJ9IGwgJHtkaXN0YW5jZUVsZW1lbnRUb1dhaXR9IDBgO1xuICAgICAgICAgIGN1cnJlbnRFbGVtZW50LnBvc2l0aW9uX2VuZCA9IGxlZnRTdGFydExpbmUyICsgbGluZUJldHdlZW5FbGVtZW50cztcblxuICAgICAgICAgIGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY194ID0gKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3ggPz8gMCkgKyBkaXN0YW5jZUVsZW1lbnRUb1dhaXQ7XG4gICAgICAgICAgLy8gc3BlY2lmaWNfeSA9IHTDom0gWSBj4bunYSDEkcaw4budbmcgbGluZSDigJQgc2V0VHJhbnNsYXRlUG9zaXRpb25zIHPhur0gdHLhu6sgaGVpZ2h0LzIgxJHhu4MgY8SDbiBnaeG7r2EgZOG7jWNcbiAgICAgICAgICBjdXJyZW50RWxlbWVudC5ub2RlT3RoZXJDb25maWcuc3BlY2lmaWNfeSA9IHRvcCArIChjdXJyZW50RWxlbWVudC5zcGVjaWZpY19oZWlnaHQgPz8gMCkgLyAyO1xuICAgICAgICAgIC8vIMSQ4bqjbSBi4bqjbyBjw7Mga8OtY2ggdGjGsOG7m2MgxJHhu4Mgc2V0VHJhbnNsYXRlUG9zaXRpb25zIHTDrW5oIG9mZnNldCDEkcO6bmdcbiAgICAgICAgICBpZiAoIWN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY19oZWlnaHQpIHtcbiAgICAgICAgICAgIGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY19oZWlnaHQgPSBjYW52YXNDb25maWdSZWFkb25seSgpLkVMRU1FTlRfV0FJVF9ERUZBVUxUO1xuICAgICAgICAgIH1cbiAgICAgICAgICBpZiAoIWN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY193aWR0aCkge1xuICAgICAgICAgICAgY3VycmVudEVsZW1lbnQubm9kZU90aGVyQ29uZmlnLnNwZWNpZmljX3dpZHRoID0gY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX1dBSVRfREVGQVVMVDtcbiAgICAgICAgICB9XG4gICAgICAgICAgZGVsZXRlIGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5hdHRyaWJ1dGVTdmdEO1xuXG4gICAgICAgICAgaWYgKGN1cnJlbnRFbGVtZW50LnN1YkNvZGVPZkVsZW1lbnQgIT09IGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuVFlQRV9FTEVNRU5UX0VYSVQpIHtcbiAgICAgICAgICAgIGN1cnJlbnRFbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5hdHRyaWJ1dGVTdmdEID0gYE0gJHtsZWZ0U3RhcnRMaW5lMn0gJHt0b3AgKyAoY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfaGVpZ2h0ID8/IDApIC8gMn0gbCAke2NhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuV0FJVF9UT19FTEVNRU5UfSAwYDtcbiAgICAgICAgICB9XG4gICAgICAgIH1cblxuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIC8vIEVsZW1lbnRzIGPDsyBuaMOhbmhcbiAgICAgIGNvbnN0IGhhbGYgPSBNYXRoLmNlaWwoY3VycmVudEVsZW1lbnQuYnJhbmNoZXMubGVuZ3RoIC8gMik7XG4gICAgICBjb25zdCBhYm92ZUhhbGYgPSBjdXJyZW50RWxlbWVudC5icmFuY2hlcy5zbGljZSgwLCBoYWxmKTtcbiAgICAgIGNvbnN0IHVuZGVySGFsZiA9IGN1cnJlbnRFbGVtZW50LmJyYW5jaGVzLnNsaWNlKGhhbGYpO1xuICAgICAgbGV0IGJyYWNoTWlkZGxlOiBJRGlhZ3JhbUVsZW1lbnRCcmFuY2ggfCB1bmRlZmluZWQ7XG5cbiAgICAgIGlmIChhYm92ZUhhbGYubGVuZ3RoICE9PSB1bmRlckhhbGYubGVuZ3RoKSB7XG4gICAgICAgIGJyYWNoTWlkZGxlID0gYWJvdmVIYWxmLnBvcCgpO1xuICAgICAgfVxuXG4gICAgICAvLyBUw41OSCBDSEnhu4BVIENBTyBU4buQSSDEkEEgQ+G7pkEgTkjDgU5IICjEkcOieSBsw6AgY2hp4buBdSBy4buZbmcgdHJvbmcgaG9yaXpvbnRhbCBjb250ZXh0IG5oxrBuZ1xuICAgICAgLy8gZMO5bmcgY2h1bmcgbWF4SGVpZ2h0QnJhbmNoIMSR4buDIMSRxqFuIGdp4bqjbiwgw70gbmdoxKlhIGzDoCBcImtob+G6o25nIHRy4buRbmcgdOG7kWkgdGhp4buDdSBkw6BuaCBjaG8gbmjDoW5oIGtow7RuZyBjw7MgZWxlbWVudFwiKVxuICAgICAgY29uc3QgbWF4V2lkdGhCcmFuY2ggPSB7IHdpZHRoOiAwIH07XG5cbiAgICAgIHRoaXMuY2FsY3VsYXRvck1heEJyYW5jaFdpZHRoKGN1cnJlbnRFbGVtZW50LCBtYXhXaWR0aEJyYW5jaCk7XG4gICAgICBjdXJyZW50RWxlbWVudC5tYXhIZWlnaHRCcmFuY2ggPSBtYXhXaWR0aEJyYW5jaC53aWR0aDtcblxuICAgICAgY29uc3QgbWF4V2lkdGhCcmFjaE1pZGRsZSA9IHsgd2lkdGg6IDAsIGFib3ZlV2lkdGg6IDAsIHVuZGVyV2lkdGg6IDAgfTtcbiAgICAgIGNvbnN0IGxpbmVGb3JtRWxlbWVudFRvQnJhbmNoaW5nID0gKGN1cnJlbnRFbGVtZW50LnNwZWNpZmljX3dpZHRoID8/IDApICsgY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX01BUkdJTl9ERUZBVUxUX0JSQU5DSDtcblxuICAgICAgLy8gdG9wID0geSArIGhlaWdodC8yOiDEkWnhu4NtIGdp4buvYSB0aGVvIGNoaeG7gXUgWSDihpIgZMO5bmcgbMOgbSB04buNYSDEkeG7mSBZIGPhu6dhIMSRxrDhu51uZyBuZ2FuZyBjaMOtbmhcbiAgICAgIGNvbnN0IHRvcE1pZCA9IHRvcCArIChjdXJyZW50RWxlbWVudC5zcGVjaWZpY19oZWlnaHQgPz8gMCkgLyAyO1xuXG4gICAgICBpZiAoYnJhY2hNaWRkbGUpIHtcbiAgICAgICAgYnJhY2hNaWRkbGUub25UaGVTaWRlID0gJ2NlbnRlcic7XG4gICAgICAgIHRoaXMuY2FsY3VsYXRvckhlaWdodEJyYW5jaChicmFjaE1pZGRsZS5lbGVtZW50cywgbWF4V2lkdGhCcmFjaE1pZGRsZSk7XG4gICAgICAgIGJyYWNoTWlkZGxlLndpZHRoQnJhbmNoID0ge1xuICAgICAgICAgIHdpZHRoOiBtYXhXaWR0aEJyYWNoTWlkZGxlLndpZHRoLFxuICAgICAgICAgIGFib3ZlOiBtYXhXaWR0aEJyYWNoTWlkZGxlLmFib3ZlV2lkdGgsXG4gICAgICAgICAgdW5kZXI6IG1heFdpZHRoQnJhY2hNaWRkbGUudW5kZXJXaWR0aCxcbiAgICAgICAgfTtcbiAgICAgICAgTW9MaWJEaWFncmFtSG9yaXpvbnRhbENhbGN1bGF0b3JCcmFuY2hVdGlsLmRyYXdTdHJhaWdodExpbmUodG9wTWlkLCBsaW5lRm9ybUVsZW1lbnRUb0JyYW5jaGluZywgY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfeCA/PyAwLCBicmFjaE1pZGRsZSwgbWF4V2lkdGhCcmFuY2gud2lkdGgsIGNvbmZpZyk7XG4gICAgICB9XG5cbiAgICAgIGxldCBoYXNOZXh0U2FtZVBhcmVudEVsZW1lbnROZXh0ID0gZmFsc2U7XG4gICAgICBjb25zdCBhYm92ZUhhbGZSZXZlcnNlID0gYWJvdmVIYWxmLnJldmVyc2UoKTtcblxuICAgICAgYWJvdmVIYWxmUmV2ZXJzZS5mb3JFYWNoKChicmFuY2gsIGluZGV4QnJhbmNoKSA9PiB7XG4gICAgICAgIGlmICghaGFzTmV4dFNhbWVQYXJlbnRFbGVtZW50TmV4dCkge1xuICAgICAgICAgIGNvbnN0IGZsYXRFbGVtZW50T25CcmFuY2g6IElEaWFncmFtRWxlbWVudFtdID0gW107XG5cbiAgICAgICAgICBidWlsZEZsYXRFbGVtZW50KGJyYW5jaC5lbGVtZW50cywgZmxhdEVsZW1lbnRPbkJyYW5jaCk7XG4gICAgICAgICAgaGFzTmV4dFNhbWVQYXJlbnRFbGVtZW50TmV4dCA9ICFmbGF0RWxlbWVudE9uQnJhbmNoIHx8ICFmbGF0RWxlbWVudE9uQnJhbmNoLmxlbmd0aCA/IHRydWUgOiBmbGF0RWxlbWVudE9uQnJhbmNoLmZpbmQoKGl0ZW0pID0+IGl0ZW0ubmV4dF9pZCA9PT0gY3VycmVudEVsZW1lbnQubmV4dF9pZCkgPyB0cnVlIDogZmFsc2U7XG4gICAgICAgIH1cblxuICAgICAgICBicmFuY2gub25UaGVTaWRlID0gJ2Fib3ZlJztcbiAgICAgICAgY29uc3QgbWF4V2lkdGhCID0geyB3aWR0aDogMCwgYWJvdmVXaWR0aDogMCwgdW5kZXJXaWR0aDogMCB9O1xuXG4gICAgICAgIHRoaXMuY2FsY3VsYXRvckhlaWdodEJyYW5jaChicmFuY2guZWxlbWVudHMsIG1heFdpZHRoQik7XG4gICAgICAgIGJyYW5jaC53aWR0aEJyYW5jaCA9IHtcbiAgICAgICAgICB3aWR0aDogbWF4V2lkdGhCLndpZHRoLFxuICAgICAgICAgIGFib3ZlOiBtYXhXaWR0aEIuYWJvdmVXaWR0aCxcbiAgICAgICAgICB1bmRlcjogbWF4V2lkdGhCLnVuZGVyV2lkdGgsXG4gICAgICAgIH07XG5cbiAgICAgICAgY29uc3QgYnJhbmNoUHJlID0gYWJvdmVIYWxmUmV2ZXJzZVtpbmRleEJyYW5jaCAtIDFdO1xuICAgICAgICBsZXQgbGluZUJldHdlZW5CcmFuY2ggPSBtYXhXaWR0aEIudW5kZXJXaWR0aCArIGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9NQVJHSU5fQkVUV0VFTl9CUkFOQ0hfREVGQVVMVCAvIDI7XG5cbiAgICAgICAgaWYgKGJyYW5jaFByZSkge1xuICAgICAgICAgIGxpbmVCZXR3ZWVuQnJhbmNoICs9IChicmFuY2hQcmUud2lkdGhCcmFuY2g/LndpZHRoID8/IDApICsgY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX01BUkdJTl9CRVRXRUVOX0JSQU5DSF9ERUZBVUxUO1xuICAgICAgICB9XG4gICAgICAgIGlmIChicmFjaE1pZGRsZSkge1xuICAgICAgICAgIGxpbmVCZXR3ZWVuQnJhbmNoICs9IChicmFjaE1pZGRsZS53aWR0aEJyYW5jaD8uYWJvdmUgPz8gMCkgKyBjYW52YXNDb25maWdSZWFkb25seSgpLkVMRU1FTlRfTUFSR0lOX0JFVFdFRU5fQlJBTkNIX0RFRkFVTFQgLyAyO1xuICAgICAgICB9XG5cbiAgICAgICAgTW9MaWJEaWFncmFtSG9yaXpvbnRhbENhbGN1bGF0b3JCcmFuY2hVdGlsLmFib3ZlTGluZSh0b3BNaWQsIGxpbmVGb3JtRWxlbWVudFRvQnJhbmNoaW5nLCBjdXJyZW50RWxlbWVudC5zcGVjaWZpY194ID8/IDAsIGxpbmVCZXR3ZWVuQnJhbmNoLCBicmFuY2gsIG1heFdpZHRoQnJhbmNoLndpZHRoLCBjdXJyZW50RWxlbWVudCwgY29uZmlnKTtcbiAgICAgIH0pO1xuXG4gICAgICB1bmRlckhhbGYuZm9yRWFjaCgoYnJhbmNoLCBpbmRleEJyYW5jaCkgPT4ge1xuICAgICAgICBpZiAoIWhhc05leHRTYW1lUGFyZW50RWxlbWVudE5leHQpIHtcbiAgICAgICAgICBjb25zdCBmbGF0RWxlbWVudE9uQnJhbmNoOiBJRGlhZ3JhbUVsZW1lbnRbXSA9IFtdO1xuXG4gICAgICAgICAgYnVpbGRGbGF0RWxlbWVudChicmFuY2guZWxlbWVudHMsIGZsYXRFbGVtZW50T25CcmFuY2gpO1xuICAgICAgICAgIGhhc05leHRTYW1lUGFyZW50RWxlbWVudE5leHQgPSAhZmxhdEVsZW1lbnRPbkJyYW5jaCB8fCAhZmxhdEVsZW1lbnRPbkJyYW5jaC5sZW5ndGggPyB0cnVlIDogZmxhdEVsZW1lbnRPbkJyYW5jaC5maW5kKChpdGVtKSA9PiBpdGVtLm5leHRfaWQgPT09IGN1cnJlbnRFbGVtZW50Lm5leHRfaWQpID8gdHJ1ZSA6IGZhbHNlO1xuICAgICAgICB9XG4gICAgICAgIGJyYW5jaC5vblRoZVNpZGUgPSAndW5kZXInO1xuICAgICAgICBjb25zdCBtYXhXaWR0aEIgPSB7IHdpZHRoOiAwLCBhYm92ZVdpZHRoOiAwLCB1bmRlcldpZHRoOiAwIH07XG5cbiAgICAgICAgdGhpcy5jYWxjdWxhdG9ySGVpZ2h0QnJhbmNoKGJyYW5jaC5lbGVtZW50cywgbWF4V2lkdGhCKTtcbiAgICAgICAgYnJhbmNoLndpZHRoQnJhbmNoID0ge1xuICAgICAgICAgIHdpZHRoOiBtYXhXaWR0aEIud2lkdGgsXG4gICAgICAgICAgYWJvdmU6IG1heFdpZHRoQi5hYm92ZVdpZHRoLFxuICAgICAgICAgIHVuZGVyOiBtYXhXaWR0aEIudW5kZXJXaWR0aCxcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCBicmFuY2hQcmUgPSB1bmRlckhhbGZbaW5kZXhCcmFuY2ggLSAxXTtcbiAgICAgICAgbGV0IGxpbmVCZXR3ZWVuQnJhbmNoID0gbWF4V2lkdGhCLmFib3ZlV2lkdGggKyBjYW52YXNDb25maWdSZWFkb25seSgpLkVMRU1FTlRfTUFSR0lOX0JFVFdFRU5fQlJBTkNIX0RFRkFVTFQgLyAyO1xuXG4gICAgICAgIGlmIChicmFuY2hQcmUpIHtcbiAgICAgICAgICBsaW5lQmV0d2VlbkJyYW5jaCArPSAoYnJhbmNoUHJlLndpZHRoQnJhbmNoPy53aWR0aCA/PyAwKSArIGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9NQVJHSU5fQkVUV0VFTl9CUkFOQ0hfREVGQVVMVDtcbiAgICAgICAgfVxuICAgICAgICBpZiAoYnJhY2hNaWRkbGUpIHtcbiAgICAgICAgICBsaW5lQmV0d2VlbkJyYW5jaCArPSAoYnJhY2hNaWRkbGUud2lkdGhCcmFuY2g/LnVuZGVyID8/IDApICsgY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX01BUkdJTl9CRVRXRUVOX0JSQU5DSF9ERUZBVUxUIC8gMjtcbiAgICAgICAgfVxuXG4gICAgICAgIE1vTGliRGlhZ3JhbUhvcml6b250YWxDYWxjdWxhdG9yQnJhbmNoVXRpbC51bmRlckxpbmUodG9wTWlkLCBsaW5lRm9ybUVsZW1lbnRUb0JyYW5jaGluZywgY3VycmVudEVsZW1lbnQuc3BlY2lmaWNfeCA/PyAwLCBsaW5lQmV0d2VlbkJyYW5jaCwgYnJhbmNoLCBtYXhXaWR0aEJyYW5jaC53aWR0aCwgY3VycmVudEVsZW1lbnQsIGNvbmZpZyk7XG4gICAgICB9KTtcbiAgICB9KTtcblxuICAgIHRoaXMuc2V0VHJhbnNsYXRlUG9zaXRpb25zKGVsZW1lbnRzKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBTZXQgdHJhbnNsYXRlWC9ZIGNobyB04bqldCBj4bqjIGVsZW1lbnRzIChiYW8gZ+G7k20gYnJhbmNoZXMgdsOgIG5vZGVPdGhlckNvbmZpZylcbiAgICovXG4gIHByaXZhdGUgc3RhdGljIHNldFRyYW5zbGF0ZVBvc2l0aW9ucyhlbGVtZW50czogQXJyYXk8SURpYWdyYW1FbGVtZW50Pikge1xuICAgIGVsZW1lbnRzLmZvckVhY2goKGVsZW1lbnQpID0+IHtcbiAgICAgIGVsZW1lbnQudHJhbnNsYXRlWCA9IGVsZW1lbnQuc3BlY2lmaWNfeDtcbiAgICAgIGVsZW1lbnQudHJhbnNsYXRlWSA9IGVsZW1lbnQuc3BlY2lmaWNfeTtcblxuICAgICAgaWYgKGVsZW1lbnQubm9kZU90aGVyQ29uZmlnKSB7XG4gICAgICAgIGNvbnN0IG9mZnNldFkgPSAoZWxlbWVudC5ub2RlT3RoZXJDb25maWcuc3BlY2lmaWNfaGVpZ2h0ID8/IDApIC8gMjtcblxuICAgICAgICBlbGVtZW50Lm5vZGVPdGhlckNvbmZpZy50cmFuc2xhdGVYID0gZWxlbWVudC5ub2RlT3RoZXJDb25maWcuc3BlY2lmaWNfeDtcbiAgICAgICAgZWxlbWVudC5ub2RlT3RoZXJDb25maWcudHJhbnNsYXRlWSA9IChlbGVtZW50Lm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY195ID8/IDApIC0gb2Zmc2V0WTtcbiAgICAgIH1cblxuICAgICAgaWYgKGVsZW1lbnQuYnJhbmNoZXMgJiYgZWxlbWVudC5icmFuY2hlcy5sZW5ndGggPiAwKSB7XG4gICAgICAgIGVsZW1lbnQuYnJhbmNoZXMuZm9yRWFjaCgoYnJhbmNoKSA9PiB7XG4gICAgICAgICAgaWYgKGJyYW5jaC5ub2RlT3RoZXJDb25maWcpIHtcbiAgICAgICAgICAgIGNvbnN0IG9mZnNldFkgPSAoYnJhbmNoLm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY19oZWlnaHQgPz8gMCkgLyAyO1xuXG4gICAgICAgICAgICBicmFuY2gubm9kZU90aGVyQ29uZmlnLnRyYW5zbGF0ZVggPSBicmFuY2gubm9kZU90aGVyQ29uZmlnLnNwZWNpZmljX3g7XG4gICAgICAgICAgICBicmFuY2gubm9kZU90aGVyQ29uZmlnLnRyYW5zbGF0ZVkgPSAoYnJhbmNoLm5vZGVPdGhlckNvbmZpZy5zcGVjaWZpY195ID8/IDApIC0gb2Zmc2V0WTtcbiAgICAgICAgICB9XG5cbiAgICAgICAgICBpZiAoYnJhbmNoLmVsZW1lbnRzICYmIGJyYW5jaC5lbGVtZW50cy5sZW5ndGggPiAwKSB7XG4gICAgICAgICAgICB0aGlzLnNldFRyYW5zbGF0ZVBvc2l0aW9ucyhicmFuY2guZWxlbWVudHMpO1xuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICB9XG4gICAgfSk7XG4gIH1cblxuICAvKiogVMOtbmggY2hp4buBdSBy4buZbmcgdOG7kWkgxJFhIGPhu6dhIG5ow6FuaCAodHJvbmcgaG9yaXpvbnRhbCA9IGNoaeG7gXUgY2FvIHRo4buxYyBj4bunYSBuaMOhbmgga2jDtG5nIGPDsyBlbGVtZW50KSAqL1xuICBzdGF0aWMgY2FsY3VsYXRvck1heEJyYW5jaFdpZHRoKGVsZW1lbnQ6IElEaWFncmFtRWxlbWVudCwgbWF4V2lkdGhCcmFuY2g6IHsgd2lkdGg6IG51bWJlciB9KSB7XG4gICAgaWYgKCFlbGVtZW50LmJyYW5jaGVzIHx8ICFlbGVtZW50LmJyYW5jaGVzLmxlbmd0aCkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGVsZW1lbnQuYnJhbmNoZXMuZm9yRWFjaCgoYnJhbmNoKSA9PiB7XG4gICAgICBpZiAoIWJyYW5jaC5lbGVtZW50cyB8fCAhYnJhbmNoLmVsZW1lbnRzLmxlbmd0aCkge1xuICAgICAgICBjb25zdCBsaW5lQnJhbmNoTm9IYXNFbGVtZW50ID0gY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX1dJRFRIX0RFRkFVTFRfQlJBTkNIX1dIRU5fTk9UX0VMRU1FTlQ7XG5cbiAgICAgICAgbWF4V2lkdGhCcmFuY2gud2lkdGggPSBsaW5lQnJhbmNoTm9IYXNFbGVtZW50ID4gbWF4V2lkdGhCcmFuY2gud2lkdGggPyBsaW5lQnJhbmNoTm9IYXNFbGVtZW50IDogbWF4V2lkdGhCcmFuY2gud2lkdGg7XG5cbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICBjb25zdCB0b3RhbCA9IHsgaGVpZ2h0OiAwIH07XG5cbiAgICAgIHRoaXMucGx1c1dpZHRoRWxlbWVudEluQnJhbmNoKGJyYW5jaC5lbGVtZW50cywgdG90YWwpO1xuICAgICAgbWF4V2lkdGhCcmFuY2gud2lkdGggPSB0b3RhbC5oZWlnaHQgPiBtYXhXaWR0aEJyYW5jaC53aWR0aCA/IHRvdGFsLmhlaWdodCA6IG1heFdpZHRoQnJhbmNoLndpZHRoO1xuICAgIH0pO1xuICB9XG5cbiAgLyoqIFTDrW5oIHThu5VuZyBjaGnhu4F1IHLhu5luZyBjw6FjIGVsZW1lbnRzIHRyb25nIG5ow6FuaCAoZOG7jWMgdGhlbyB0cuG7pWMgWCkgKi9cbiAgc3RhdGljIHBsdXNXaWR0aEVsZW1lbnRJbkJyYW5jaChlbGVtZW50czogSURpYWdyYW1FbGVtZW50W10sIHRvdGFsOiB7IGhlaWdodDogbnVtYmVyIH0pIHtcbiAgICBlbGVtZW50cy5mb3JFYWNoKChlbGVtZW50KSA9PiB7XG4gICAgICBjb25zdCBtYXJnaW4gPSAhZWxlbWVudC5icmFuY2hlcyB8fCAhZWxlbWVudC5icmFuY2hlcy5sZW5ndGggPyB0aGlzLmNoZWNrRWxlbWVudEdldE1hcmdpbihlbGVtZW50Lm5vZGVPdGhlckNvbmZpZykgOiBjYW52YXNDb25maWdSZWFkb25seSgpLkVMRU1FTlRfTUFSR0lOX0RFRkFVTFRfQlJBTkNIO1xuXG4gICAgICB0b3RhbC5oZWlnaHQgKz0gKGVsZW1lbnQuc3BlY2lmaWNfd2lkdGggPz8gMCkgKyBtYXJnaW47XG4gICAgICBpZiAoIWVsZW1lbnQuYnJhbmNoZXMgfHwgIWVsZW1lbnQuYnJhbmNoZXMubGVuZ3RoKSB7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIHRvdGFsLmhlaWdodCArPSA2NDtcbiAgICAgIGNvbnN0IHRoZU1vc3RFbGVtZW50c0luQnJhbmNoID0geyBoZWlnaHQ6IDAgfTtcblxuICAgICAgZWxlbWVudC5icmFuY2hlcy5mb3JFYWNoKChicmFuY2gpID0+IHtcbiAgICAgICAgY29uc3Qgd2lkdGhJbkJyYW5jaCA9IHsgaGVpZ2h0OiAwIH07XG5cbiAgICAgICAgd2lkdGhJbkJyYW5jaC5oZWlnaHQgKz0gY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX01BUkdJTl9ERUZBVUxUX0JSQU5DSF9UT19FTEVNRU5UX0ZJUlNUICsgMjA7XG4gICAgICAgIGlmICghYnJhbmNoLmVsZW1lbnRzIHx8ICFicmFuY2guZWxlbWVudHMubGVuZ3RoKSB7XG4gICAgICAgICAgd2lkdGhJbkJyYW5jaC5oZWlnaHQgKz0gY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5FTEVNRU5UX1dJRFRIX0RFRkFVTFRfQlJBTkNIX1dIRU5fTk9UX0VMRU1FTlQ7XG4gICAgICAgICAgaWYgKHRoZU1vc3RFbGVtZW50c0luQnJhbmNoLmhlaWdodCA8IHdpZHRoSW5CcmFuY2guaGVpZ2h0KSB7XG4gICAgICAgICAgICB0aGVNb3N0RWxlbWVudHNJbkJyYW5jaC5oZWlnaHQgPSB3aWR0aEluQnJhbmNoLmhlaWdodDtcbiAgICAgICAgICB9XG4gICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMucGx1c1dpZHRoRWxlbWVudEluQnJhbmNoKGJyYW5jaC5lbGVtZW50cywgd2lkdGhJbkJyYW5jaCk7XG4gICAgICAgIGlmICh0aGVNb3N0RWxlbWVudHNJbkJyYW5jaC5oZWlnaHQgPCB3aWR0aEluQnJhbmNoLmhlaWdodCkge1xuICAgICAgICAgIHRoZU1vc3RFbGVtZW50c0luQnJhbmNoLmhlaWdodCA9IHdpZHRoSW5CcmFuY2guaGVpZ2h0O1xuICAgICAgICB9XG4gICAgICB9KTtcblxuICAgICAgdG90YWwuaGVpZ2h0ICs9IHRoZU1vc3RFbGVtZW50c0luQnJhbmNoLmhlaWdodDtcbiAgICB9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUw61uaCBjaGnhu4F1IGNhbyAoWSBzcGFuKSBj4bunYSBt4buZdCBuaMOhbmgg4oCUIGTDuW5nIMSR4buDIG9mZnNldCBjw6FjIG5ow6FuaCB0csOqbi9kxrDhu5tpLlxuICAgKiBUcm9uZyBob3Jpem9udGFsIGNvbnRleHQ6IG3hu5dpIG5ow6FuaCB0cuG6o2kgZMOgaSB0aGVvIFkgKGzDqm4veHXhu5FuZykuXG4gICAqL1xuICBzdGF0aWMgY2FsY3VsYXRvckhlaWdodEJyYW5jaChlbGVtZW50czogSURpYWdyYW1FbGVtZW50W10gfCB1bmRlZmluZWQsIG1heFdpZHRoOiB7IHdpZHRoOiBudW1iZXI7IGFib3ZlV2lkdGg6IG51bWJlcjsgdW5kZXJXaWR0aDogbnVtYmVyIH0pIHtcbiAgICBpZiAoIWVsZW1lbnRzIHx8ICFlbGVtZW50cy5sZW5ndGgpIHtcbiAgICAgIGNvbnN0IHcgPSBjYW52YXNDb25maWdSZWFkb25seSgpLkRFRkFVTFRfQlJBTkNIX1dIRU5fTk9fRUxFTUVOVDtcblxuICAgICAgbWF4V2lkdGgud2lkdGggPSB3O1xuICAgICAgbWF4V2lkdGguYWJvdmVXaWR0aCA9IHcgLyAyO1xuICAgICAgbWF4V2lkdGgudW5kZXJXaWR0aCA9IHcgLyAyO1xuXG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgY29uc3QgbWF4V2lkdGhJbkVsZW1lbnRzID0geyB3aWR0aDogMCwgYWJvdmVXaWR0aDogMCwgdW5kZXJXaWR0aDogMCB9O1xuXG4gICAgZWxlbWVudHMuZm9yRWFjaCgoZWxlbWVudCkgPT4ge1xuICAgICAgaWYgKCFlbGVtZW50LmJyYW5jaGVzIHx8ICFlbGVtZW50LmJyYW5jaGVzLmxlbmd0aCkge1xuICAgICAgICAvLyBlbGVtZW50IGtow7RuZyBuaMOhbmg6IGTDuW5nIHNwZWNpZmljX2hlaWdodCBsw6BtIFkgc3BhblxuICAgICAgICBpZiAoKGVsZW1lbnQuc3BlY2lmaWNfaGVpZ2h0ID8/IDApIDwgbWF4V2lkdGhJbkVsZW1lbnRzLndpZHRoKSB7XG4gICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG4gICAgICAgIGNvbnN0IGggPSBlbGVtZW50LnNwZWNpZmljX2hlaWdodCA/PyAwO1xuXG4gICAgICAgIG1heFdpZHRoSW5FbGVtZW50cy53aWR0aCA9IGg7XG4gICAgICAgIG1heFdpZHRoSW5FbGVtZW50cy5hYm92ZVdpZHRoID0gaCAvIDI7XG4gICAgICAgIG1heFdpZHRoSW5FbGVtZW50cy51bmRlcldpZHRoID0gaCAvIDI7XG5cbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICBjb25zdCB3aWR0aEVsZW1lbnRJbmNsdWRlQnJhbmNoID0geyB3aWR0aDogMCwgYWJvdmVXaWR0aDogMCwgdW5kZXJXaWR0aDogMCB9O1xuICAgICAgY29uc3QgaCA9IGVsZW1lbnQuc3BlY2lmaWNfaGVpZ2h0ID8/IDA7XG5cbiAgICAgIGlmIChoID4gd2lkdGhFbGVtZW50SW5jbHVkZUJyYW5jaC53aWR0aCkge1xuICAgICAgICB3aWR0aEVsZW1lbnRJbmNsdWRlQnJhbmNoLndpZHRoID0gaDtcbiAgICAgICAgd2lkdGhFbGVtZW50SW5jbHVkZUJyYW5jaC5hYm92ZVdpZHRoID0gaCAvIDI7XG4gICAgICAgIHdpZHRoRWxlbWVudEluY2x1ZGVCcmFuY2gudW5kZXJXaWR0aCA9IGggLyAyO1xuICAgICAgfVxuXG4gICAgICBjb25zdCBoYWxmID0gTWF0aC5jZWlsKGVsZW1lbnQuYnJhbmNoZXMubGVuZ3RoIC8gMik7XG4gICAgICBjb25zdCBhYm92ZUhhbGYgPSBlbGVtZW50LmJyYW5jaGVzLnNsaWNlKDAsIGhhbGYpO1xuICAgICAgY29uc3QgdW5kZXJIYWxmID0gZWxlbWVudC5icmFuY2hlcy5zbGljZShoYWxmKTtcbiAgICAgIGxldCBicmFjaE1pZGRsZTogSURpYWdyYW1FbGVtZW50QnJhbmNoIHwgdW5kZWZpbmVkO1xuXG4gICAgICBpZiAoYWJvdmVIYWxmLmxlbmd0aCAhPT0gdW5kZXJIYWxmLmxlbmd0aCkge1xuICAgICAgICBicmFjaE1pZGRsZSA9IGFib3ZlSGFsZi5wb3AoKTtcbiAgICAgIH1cbiAgICAgIGlmIChicmFjaE1pZGRsZSkgYnJhY2hNaWRkbGUub25UaGVTaWRlID0gJ2NlbnRlcic7XG4gICAgICBhYm92ZUhhbGYuZm9yRWFjaCgoYnJhbmNoKSA9PiAoYnJhbmNoLm9uVGhlU2lkZSA9ICdhYm92ZScpKTtcbiAgICAgIHVuZGVySGFsZi5mb3JFYWNoKChicmFuY2gpID0+IChicmFuY2gub25UaGVTaWRlID0gJ3VuZGVyJykpO1xuXG4gICAgICBjb25zdCB3aWR0aEJyYW5jaCA9IHsgd2lkdGg6IDAsIGFib3ZlV2lkdGg6IDAsIHVuZGVyV2lkdGg6IDAgfTtcblxuICAgICAgZWxlbWVudC5icmFuY2hlcy5mb3JFYWNoKChicmFuY2gpID0+IHtcbiAgICAgICAgY29uc3QgdyA9IHsgd2lkdGg6IDAsIGFib3ZlV2lkdGg6IDAsIHVuZGVyV2lkdGg6IDAgfTtcblxuICAgICAgICB0aGlzLmNhbGN1bGF0b3JIZWlnaHRCcmFuY2goYnJhbmNoLmVsZW1lbnRzLCB3KTtcbiAgICAgICAgc3dpdGNoIChicmFuY2gub25UaGVTaWRlKSB7XG4gICAgICAgICAgY2FzZSAnYWJvdmUnOlxuICAgICAgICAgICAgd2lkdGhCcmFuY2guYWJvdmVXaWR0aCArPSB3LndpZHRoO1xuICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgY2FzZSAndW5kZXInOlxuICAgICAgICAgICAgd2lkdGhCcmFuY2gudW5kZXJXaWR0aCArPSB3LndpZHRoO1xuICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgICAgY2FzZSAnY2VudGVyJzpcbiAgICAgICAgICAgIHdpZHRoQnJhbmNoLmFib3ZlV2lkdGggKz0gdy5hYm92ZVdpZHRoO1xuICAgICAgICAgICAgd2lkdGhCcmFuY2gudW5kZXJXaWR0aCArPSB3LnVuZGVyV2lkdGg7XG4gICAgICAgICAgICBicmVhaztcbiAgICAgICAgfVxuICAgICAgfSk7XG5cbiAgICAgIGNvbnN0IG1hcmdpbkJldHdlZW5CcmFuY2ggPSAoZWxlbWVudC5icmFuY2hlcy5sZW5ndGggLSAxKSAqIGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9NQVJHSU5fQkVUV0VFTl9CUkFOQ0hfREVGQVVMVDtcblxuICAgICAgd2lkdGhCcmFuY2guYWJvdmVXaWR0aCArPSBtYXJnaW5CZXR3ZWVuQnJhbmNoIC8gMjtcbiAgICAgIHdpZHRoQnJhbmNoLnVuZGVyV2lkdGggKz0gbWFyZ2luQmV0d2VlbkJyYW5jaCAvIDI7XG4gICAgICBjb25zdCBtYXhBYm92ZVdpZHRoID0gTWF0aC5tYXgod2lkdGhFbGVtZW50SW5jbHVkZUJyYW5jaC5hYm92ZVdpZHRoLCB3aWR0aEJyYW5jaC5hYm92ZVdpZHRoKTtcbiAgICAgIGNvbnN0IG1heFVuZGVyV2lkdGggPSBNYXRoLm1heCh3aWR0aEVsZW1lbnRJbmNsdWRlQnJhbmNoLnVuZGVyV2lkdGgsIHdpZHRoQnJhbmNoLnVuZGVyV2lkdGgpO1xuXG4gICAgICBpZiAobWF4V2lkdGhJbkVsZW1lbnRzLmFib3ZlV2lkdGggPCBtYXhBYm92ZVdpZHRoKSB7XG4gICAgICAgIG1heFdpZHRoSW5FbGVtZW50cy5hYm92ZVdpZHRoID0gbWF4QWJvdmVXaWR0aDtcbiAgICAgIH1cbiAgICAgIGlmIChtYXhXaWR0aEluRWxlbWVudHMudW5kZXJXaWR0aCA8IG1heFVuZGVyV2lkdGgpIHtcbiAgICAgICAgbWF4V2lkdGhJbkVsZW1lbnRzLnVuZGVyV2lkdGggPSBtYXhVbmRlcldpZHRoO1xuICAgICAgfVxuXG4gICAgICBtYXhXaWR0aEluRWxlbWVudHMud2lkdGggPSBtYXhXaWR0aEluRWxlbWVudHMuYWJvdmVXaWR0aCArIG1heFdpZHRoSW5FbGVtZW50cy51bmRlcldpZHRoO1xuICAgIH0pO1xuXG4gICAgbWF4V2lkdGgud2lkdGggKz0gbWF4V2lkdGhJbkVsZW1lbnRzLmFib3ZlV2lkdGggKyBtYXhXaWR0aEluRWxlbWVudHMudW5kZXJXaWR0aDtcbiAgICBtYXhXaWR0aC5hYm92ZVdpZHRoICs9IG1heFdpZHRoSW5FbGVtZW50cy5hYm92ZVdpZHRoO1xuICAgIG1heFdpZHRoLnVuZGVyV2lkdGggKz0gbWF4V2lkdGhJbkVsZW1lbnRzLnVuZGVyV2lkdGg7XG4gIH1cblxuICAvKiogVMOtbmgga2hv4bqjbmcgY8OhY2ggdGjDqm0gdsOgbyBzYXUgZWxlbWVudCAoYmFvIGfhu5NtIHdhaXQgY29uZmlnIG7hur91IGPDsykgKi9cbiAgcHJpdmF0ZSBzdGF0aWMgY2hlY2tFbGVtZW50R2V0TWFyZ2luKGhhc1dhaXRDb25maWc/OiBJRGlhZ3JhbUVsZW1lbnQpOiBudW1iZXIge1xuICAgIGlmIChoYXNXYWl0Q29uZmlnKSB7XG4gICAgICByZXR1cm4gY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5ESVNUQU5DRV9UT19XQUlUICsgdGhpcy5nZXRXaWR0aFdhaXRDb25maWcoaGFzV2FpdENvbmZpZykgKyBjYW52YXNDb25maWdSZWFkb25seSgpLldBSVRfVE9fRUxFTUVOVDtcbiAgICB9XG4gICAgcmV0dXJuIGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9NQVJHSU5fREVGQVVMVDtcbiAgfVxuXG4gIC8qKiBUw61uaCBjaGnhu4F1IHLhu5luZyBj4bunYSB3YWl0IGNvbmZpZyBub2RlICovXG4gIHByaXZhdGUgc3RhdGljIGdldFdpZHRoV2FpdENvbmZpZyhoYXNXYWl0Q29uZmlnPzogSURpYWdyYW1FbGVtZW50KTogbnVtYmVyIHtcbiAgICBpZiAoaGFzV2FpdENvbmZpZykge1xuICAgICAgcmV0dXJuIChoYXNXYWl0Q29uZmlnLnNwZWNpZmljX3dpZHRoID8/IGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9XQUlUX0RFRkFVTFQpICsgY2FudmFzQ29uZmlnUmVhZG9ubHkoKS5ESVNUQU5DRV9XQUlUX1RPX05FWFRfTElORTtcbiAgICB9XG4gICAgcmV0dXJuIGNhbnZhc0NvbmZpZ1JlYWRvbmx5KCkuRUxFTUVOVF9XQUlUX0RFRkFVTFQgKyBjYW52YXNDb25maWdSZWFkb25seSgpLkRJU1RBTkNFX1dBSVRfVE9fTkVYVF9MSU5FO1xuICB9XG59XG4iXX0=
|