@elxjs/ui 0.0.181 → 0.0.183
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/assets/icons/MeatballMenu.svg +3 -0
- package/esm2022/lib/components/carousel/carousel.component.mjs +71 -53
- package/esm2022/lib/components/carousel-fixed/carousel-fixed.component.mjs +258 -186
- package/fesm2022/elxjs-ui.mjs +326 -237
- package/fesm2022/elxjs-ui.mjs.map +1 -1
- package/lib/components/carousel/carousel.component.d.ts +7 -9
- package/lib/components/carousel-fixed/carousel-fixed.component.d.ts +21 -18
- package/package.json +1 -1
|
@@ -2,18 +2,20 @@ import { CommonModule } from '@angular/common';
|
|
|
2
2
|
import { Component, ContentChildren, ElementRef, EventEmitter, Input, Output, ViewChild } from '@angular/core';
|
|
3
3
|
import { EluxIcon } from '../icon';
|
|
4
4
|
import * as i0 from "@angular/core";
|
|
5
|
+
import * as i1 from "@angular/common";
|
|
5
6
|
export class EluxCarouselFixedComponent {
|
|
6
7
|
constructor(renderer) {
|
|
7
8
|
this.renderer = renderer;
|
|
8
|
-
this.itemWidth = 200;
|
|
9
|
-
this.gap = 16;
|
|
10
|
-
this.
|
|
9
|
+
this.itemWidth = 200;
|
|
10
|
+
this.gap = 16;
|
|
11
|
+
this.showArrows = true;
|
|
12
|
+
this.showDots = true;
|
|
11
13
|
this.previousClickEventEmitter = new EventEmitter();
|
|
12
14
|
this.nextClickEventEmitter = new EventEmitter();
|
|
13
|
-
this.itemClickEventEmitter = new EventEmitter();
|
|
14
15
|
this.currentIndex = 0;
|
|
15
16
|
this.translateX = 0;
|
|
16
17
|
this.isDragging = false;
|
|
18
|
+
this.isMouseDown = false;
|
|
17
19
|
this.startX = 0;
|
|
18
20
|
this.currentX = 0;
|
|
19
21
|
this.initialTranslateX = 0;
|
|
@@ -24,27 +26,50 @@ export class EluxCarouselFixedComponent {
|
|
|
24
26
|
this.velocity = 0;
|
|
25
27
|
this.lastMoveTime = 0;
|
|
26
28
|
this.lastMoveX = 0;
|
|
27
|
-
this.wasDragging = false;
|
|
28
29
|
this.touchStartTime = 0;
|
|
29
30
|
this.touchStartX = 0;
|
|
30
31
|
this.touchStartY = 0;
|
|
31
32
|
this.isVerticalScroll = false;
|
|
33
|
+
this.wasDragging = false;
|
|
34
|
+
this.clicksDisabled = false;
|
|
35
|
+
this.clickListeners = [];
|
|
36
|
+
this.dragStarted = false;
|
|
37
|
+
this.mouseDownTime = 0;
|
|
38
|
+
this.calculateRightBleedContainer = () => {
|
|
39
|
+
if (this.rightBleedContainer) {
|
|
40
|
+
const el = this.rightBleedContainer.nativeElement;
|
|
41
|
+
const left = el.getBoundingClientRect().left;
|
|
42
|
+
let scrollbarWidth = window.innerWidth - document.documentElement.clientWidth;
|
|
43
|
+
scrollbarWidth = scrollbarWidth == 0 || scrollbarWidth > 30 ? 0 : scrollbarWidth;
|
|
44
|
+
el.style.setProperty('--scrollbar-width', `${scrollbarWidth}px`);
|
|
45
|
+
el.style.setProperty('--left-offset', `${left}px`);
|
|
46
|
+
}
|
|
47
|
+
};
|
|
32
48
|
}
|
|
33
49
|
ngAfterContentInit() {
|
|
34
|
-
|
|
35
|
-
this.setItemWidths();
|
|
36
|
-
this.updateLimits();
|
|
37
|
-
this.setupItemClickListeners();
|
|
38
|
-
this.items.changes.subscribe(() => {
|
|
50
|
+
setTimeout(() => {
|
|
39
51
|
this.calculateDimensions();
|
|
40
52
|
this.setItemWidths();
|
|
41
53
|
this.updateLimits();
|
|
42
|
-
this.
|
|
43
|
-
this.
|
|
44
|
-
|
|
54
|
+
this.setupClickPrevention();
|
|
55
|
+
this.items.changes.subscribe(() => {
|
|
56
|
+
this.calculateDimensions();
|
|
57
|
+
this.setItemWidths();
|
|
58
|
+
this.updateLimits();
|
|
59
|
+
this.goToFirstItem();
|
|
60
|
+
this.setupClickPrevention();
|
|
61
|
+
// Força atualização visual dos dots
|
|
62
|
+
if (this.cd && typeof this.cd.detectChanges === 'function') {
|
|
63
|
+
this.cd.detectChanges();
|
|
64
|
+
}
|
|
65
|
+
});
|
|
66
|
+
}, 10);
|
|
45
67
|
window.addEventListener('resize', () => this.onResize());
|
|
46
68
|
}
|
|
47
69
|
ngOnDestroy() {
|
|
70
|
+
// Clean up click listeners
|
|
71
|
+
this.clickListeners.forEach(unlisten => unlisten());
|
|
72
|
+
this.clickListeners = [];
|
|
48
73
|
window.removeEventListener('resize', () => this.onResize());
|
|
49
74
|
}
|
|
50
75
|
calculateDimensions() {
|
|
@@ -53,23 +78,41 @@ export class EluxCarouselFixedComponent {
|
|
|
53
78
|
}
|
|
54
79
|
}
|
|
55
80
|
updateLimits() {
|
|
56
|
-
const totalWidth = this.items.length * (this.itemWidth + this.gap)
|
|
81
|
+
const totalWidth = this.items.length * (this.itemWidth + this.gap);
|
|
57
82
|
this.maxTranslateX = 0;
|
|
58
|
-
// Calculate minimum translateX to ensure last item is fully visible
|
|
59
83
|
if (totalWidth > this.containerWidth) {
|
|
60
84
|
this.minTranslateX = this.containerWidth - totalWidth;
|
|
61
|
-
// Add some padding to ensure last item is completely visible
|
|
62
|
-
const paddingOffset = this.gap;
|
|
63
|
-
this.minTranslateX -= paddingOffset;
|
|
64
85
|
}
|
|
65
86
|
else {
|
|
66
87
|
this.minTranslateX = 0;
|
|
67
88
|
}
|
|
68
89
|
}
|
|
69
90
|
onResize() {
|
|
91
|
+
this.calculateRightBleedContainer();
|
|
70
92
|
this.calculateDimensions();
|
|
71
93
|
this.updateLimits();
|
|
94
|
+
// Garante que o currentIndex não ultrapasse o novo máximo
|
|
95
|
+
const maxIndex = this.getMaxIndex();
|
|
96
|
+
if (this.currentIndex > maxIndex) {
|
|
97
|
+
this.currentIndex = maxIndex;
|
|
98
|
+
}
|
|
72
99
|
this.updateTransform();
|
|
100
|
+
// Força detecção de mudanças para atualizar dots
|
|
101
|
+
if (window.ng && window.ng.getInjector) {
|
|
102
|
+
// Angular DevTools presente, não faz nada
|
|
103
|
+
}
|
|
104
|
+
else if (this.cd && typeof this.cd.detectChanges === 'function') {
|
|
105
|
+
this.cd.detectChanges();
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
ngAfterViewInit() {
|
|
109
|
+
// Garante cálculo correto após view carregada
|
|
110
|
+
setTimeout(() => {
|
|
111
|
+
this.calculateRightBleedContainer();
|
|
112
|
+
this.calculateDimensions();
|
|
113
|
+
this.updateLimits();
|
|
114
|
+
this.updateTransform();
|
|
115
|
+
});
|
|
73
116
|
}
|
|
74
117
|
setItemWidths() {
|
|
75
118
|
this.items.forEach((item) => {
|
|
@@ -77,31 +120,64 @@ export class EluxCarouselFixedComponent {
|
|
|
77
120
|
this.renderer.setStyle(item.nativeElement, 'flex-shrink', '0');
|
|
78
121
|
this.renderer.setStyle(item.nativeElement, 'margin-right', `${this.gap}px`);
|
|
79
122
|
});
|
|
80
|
-
// Remove margin from last item
|
|
81
|
-
if (this.items.last) {
|
|
82
|
-
this.renderer.setStyle(this.items.last.nativeElement, 'margin-right', '0');
|
|
83
|
-
}
|
|
84
123
|
}
|
|
85
124
|
// Mouse events
|
|
86
125
|
onMouseDown(event) {
|
|
87
126
|
event.preventDefault();
|
|
88
|
-
this.
|
|
127
|
+
this.mouseDownTime = Date.now();
|
|
128
|
+
this.dragStarted = false;
|
|
129
|
+
this.isMouseDown = true;
|
|
130
|
+
this.wasDragging = false;
|
|
131
|
+
this.clicksDisabled = false;
|
|
132
|
+
this.startX = event.clientX;
|
|
133
|
+
this.currentX = event.clientX;
|
|
134
|
+
this.initialTranslateX = this.translateX;
|
|
135
|
+
this.dragOffset = 0;
|
|
136
|
+
this.velocity = 0;
|
|
137
|
+
this.lastMoveTime = Date.now();
|
|
138
|
+
this.lastMoveX = event.clientX;
|
|
139
|
+
this.calculateDimensions();
|
|
140
|
+
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'none');
|
|
89
141
|
}
|
|
90
142
|
onMouseMove(event) {
|
|
143
|
+
if (!this.isMouseDown)
|
|
144
|
+
return;
|
|
145
|
+
event.preventDefault();
|
|
146
|
+
const dragDistance = Math.abs(event.clientX - this.startX);
|
|
147
|
+
// Only start dragging if moved more than 5px
|
|
148
|
+
if (dragDistance > 5 && !this.isDragging) {
|
|
149
|
+
this.isDragging = true;
|
|
150
|
+
this.dragStarted = true;
|
|
151
|
+
this.wasDragging = true;
|
|
152
|
+
}
|
|
91
153
|
if (this.isDragging) {
|
|
92
|
-
event.preventDefault();
|
|
93
154
|
this.updateDrag(event.clientX);
|
|
94
155
|
}
|
|
95
156
|
}
|
|
96
157
|
onMouseUp(event) {
|
|
158
|
+
if (!this.isMouseDown)
|
|
159
|
+
return;
|
|
160
|
+
this.isMouseDown = false;
|
|
97
161
|
if (this.isDragging) {
|
|
162
|
+
const mouseUpTime = Date.now();
|
|
163
|
+
const holdDuration = mouseUpTime - this.mouseDownTime;
|
|
164
|
+
const mouseDistance = Math.abs(this.currentX - this.startX);
|
|
165
|
+
if (mouseDistance > 5 || (holdDuration > 200 && mouseDistance > 0)) {
|
|
166
|
+
this.wasDragging = true;
|
|
167
|
+
}
|
|
98
168
|
this.endDrag();
|
|
99
169
|
}
|
|
170
|
+
else {
|
|
171
|
+
// Reset transition if it was just a click
|
|
172
|
+
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'transform 0.3s ease-out');
|
|
173
|
+
}
|
|
100
174
|
}
|
|
101
175
|
onMouseLeave(event) {
|
|
102
176
|
if (this.isDragging) {
|
|
177
|
+
this.wasDragging = true;
|
|
103
178
|
this.endDrag();
|
|
104
179
|
}
|
|
180
|
+
this.isMouseDown = false;
|
|
105
181
|
}
|
|
106
182
|
// Touch events
|
|
107
183
|
onTouchStart(event) {
|
|
@@ -109,10 +185,22 @@ export class EluxCarouselFixedComponent {
|
|
|
109
185
|
this.touchStartX = event.touches[0].clientX;
|
|
110
186
|
this.touchStartY = event.touches[0].clientY;
|
|
111
187
|
this.isVerticalScroll = false;
|
|
112
|
-
this.
|
|
188
|
+
this.isMouseDown = true;
|
|
189
|
+
this.wasDragging = false;
|
|
190
|
+
this.dragStarted = false;
|
|
191
|
+
this.clicksDisabled = false;
|
|
192
|
+
this.startX = event.touches[0].clientX;
|
|
193
|
+
this.currentX = event.touches[0].clientX;
|
|
194
|
+
this.initialTranslateX = this.translateX;
|
|
195
|
+
this.dragOffset = 0;
|
|
196
|
+
this.velocity = 0;
|
|
197
|
+
this.lastMoveTime = Date.now();
|
|
198
|
+
this.lastMoveX = event.touches[0].clientX;
|
|
199
|
+
this.calculateDimensions();
|
|
200
|
+
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'none');
|
|
113
201
|
}
|
|
114
202
|
onTouchMove(event) {
|
|
115
|
-
if (!this.
|
|
203
|
+
if (!this.isMouseDown)
|
|
116
204
|
return;
|
|
117
205
|
const currentX = event.touches[0].clientX;
|
|
118
206
|
const currentY = event.touches[0].clientY;
|
|
@@ -122,88 +210,73 @@ export class EluxCarouselFixedComponent {
|
|
|
122
210
|
if (deltaY > deltaX && deltaY > 10) {
|
|
123
211
|
this.isVerticalScroll = true;
|
|
124
212
|
this.isDragging = false;
|
|
125
|
-
this.
|
|
213
|
+
this.isMouseDown = false;
|
|
126
214
|
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'transform 0.3s ease-out');
|
|
127
215
|
return;
|
|
128
216
|
}
|
|
129
|
-
//
|
|
130
|
-
if (deltaX > 10) {
|
|
217
|
+
// Start dragging if horizontal movement > 10px
|
|
218
|
+
if (deltaX > 10 && !this.isDragging) {
|
|
219
|
+
this.isDragging = true;
|
|
220
|
+
this.dragStarted = true;
|
|
221
|
+
this.wasDragging = true;
|
|
222
|
+
}
|
|
223
|
+
if (this.isDragging && deltaX > 10) {
|
|
131
224
|
event.preventDefault();
|
|
132
|
-
this.updateDrag(
|
|
225
|
+
this.updateDrag(currentX);
|
|
133
226
|
}
|
|
134
227
|
}
|
|
135
228
|
onTouchEnd(event) {
|
|
136
229
|
if (this.isVerticalScroll) {
|
|
137
230
|
this.isVerticalScroll = false;
|
|
231
|
+
this.isMouseDown = false;
|
|
138
232
|
return;
|
|
139
233
|
}
|
|
234
|
+
this.isMouseDown = false;
|
|
140
235
|
const touchDuration = Date.now() - this.touchStartTime;
|
|
141
236
|
const touchDistance = Math.abs(this.currentX - this.startX);
|
|
142
|
-
//
|
|
143
|
-
if (
|
|
144
|
-
this.wasDragging =
|
|
145
|
-
this.isDragging = false;
|
|
237
|
+
// Mark as dragging if significant movement occurred
|
|
238
|
+
if (touchDistance > 10 || touchDuration > 300) {
|
|
239
|
+
this.wasDragging = true;
|
|
146
240
|
}
|
|
147
241
|
if (this.isDragging) {
|
|
148
242
|
this.endDrag();
|
|
149
243
|
}
|
|
244
|
+
else {
|
|
245
|
+
// Reset transition if it was just a tap
|
|
246
|
+
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'transform 0.3s ease-out');
|
|
247
|
+
}
|
|
150
248
|
}
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
//
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
const touchDuration = Date.now() - this.touchStartTime;
|
|
164
|
-
const touchDistance = Math.abs(event.changedTouches[0].clientX - this.touchStartX);
|
|
165
|
-
if (touchDuration < 300 && touchDistance < 10) {
|
|
166
|
-
event.preventDefault();
|
|
167
|
-
this.handleItemClick(event, index, newItem);
|
|
168
|
-
}
|
|
249
|
+
setupClickPrevention() {
|
|
250
|
+
// Clean up existing listeners
|
|
251
|
+
this.clickListeners.forEach(unlisten => unlisten());
|
|
252
|
+
this.clickListeners = [];
|
|
253
|
+
this.items.forEach((item) => {
|
|
254
|
+
// Only prevent click events, not mouseup which is needed for drag functionality
|
|
255
|
+
const eventHandler = (event) => {
|
|
256
|
+
if (event.type === 'click' && (this.wasDragging || this.clicksDisabled || this.dragStarted)) {
|
|
257
|
+
event.preventDefault();
|
|
258
|
+
event.stopPropagation();
|
|
259
|
+
event.stopImmediatePropagation();
|
|
260
|
+
return false;
|
|
169
261
|
}
|
|
262
|
+
return true;
|
|
263
|
+
};
|
|
264
|
+
// Only listen to click events to avoid interfering with drag functionality
|
|
265
|
+
item.nativeElement.addEventListener('click', eventHandler, true);
|
|
266
|
+
this.clickListeners.push(() => {
|
|
267
|
+
item.nativeElement.removeEventListener('click', eventHandler, true);
|
|
170
268
|
});
|
|
171
269
|
});
|
|
172
270
|
}
|
|
173
|
-
handleItemClick(event, index, element) {
|
|
174
|
-
// Prevent click if it was preceded by a drag
|
|
175
|
-
if (this.wasDragging) {
|
|
176
|
-
event.preventDefault();
|
|
177
|
-
event.stopPropagation();
|
|
178
|
-
return;
|
|
179
|
-
}
|
|
180
|
-
this.itemClickEventEmitter.emit({
|
|
181
|
-
event,
|
|
182
|
-
index,
|
|
183
|
-
element
|
|
184
|
-
});
|
|
185
|
-
}
|
|
186
|
-
startDrag(clientX) {
|
|
187
|
-
this.isDragging = true;
|
|
188
|
-
this.wasDragging = false;
|
|
189
|
-
this.startX = clientX;
|
|
190
|
-
this.currentX = clientX;
|
|
191
|
-
this.initialTranslateX = this.translateX;
|
|
192
|
-
this.dragOffset = 0;
|
|
193
|
-
this.velocity = 0;
|
|
194
|
-
this.lastMoveTime = Date.now();
|
|
195
|
-
this.lastMoveX = clientX;
|
|
196
|
-
this.calculateDimensions();
|
|
197
|
-
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'none');
|
|
198
|
-
}
|
|
199
271
|
updateDrag(clientX) {
|
|
200
272
|
if (!this.isDragging)
|
|
201
273
|
return;
|
|
202
274
|
this.currentX = clientX;
|
|
203
275
|
const totalDeltaX = this.currentX - this.startX;
|
|
204
|
-
//
|
|
205
|
-
if (Math.abs(totalDeltaX) >
|
|
276
|
+
// Mark as dragging if movement is significant
|
|
277
|
+
if (Math.abs(totalDeltaX) > 5) {
|
|
206
278
|
this.wasDragging = true;
|
|
279
|
+
this.dragStarted = true;
|
|
207
280
|
}
|
|
208
281
|
const now = Date.now();
|
|
209
282
|
const timeDelta = now - this.lastMoveTime;
|
|
@@ -217,11 +290,11 @@ export class EluxCarouselFixedComponent {
|
|
|
217
290
|
// Apply softer resistance at boundaries
|
|
218
291
|
if (potentialTranslateX > this.maxTranslateX) {
|
|
219
292
|
const overDrag = potentialTranslateX - this.maxTranslateX;
|
|
220
|
-
resistedDeltaX = totalDeltaX - (overDrag * 0.5);
|
|
293
|
+
resistedDeltaX = totalDeltaX - (overDrag * 0.5);
|
|
221
294
|
}
|
|
222
295
|
else if (potentialTranslateX < this.minTranslateX) {
|
|
223
296
|
const overDrag = this.minTranslateX - potentialTranslateX;
|
|
224
|
-
resistedDeltaX = totalDeltaX + (overDrag * 0.5);
|
|
297
|
+
resistedDeltaX = totalDeltaX + (overDrag * 0.5);
|
|
225
298
|
}
|
|
226
299
|
this.dragOffset = resistedDeltaX;
|
|
227
300
|
this.updateDragPosition();
|
|
@@ -234,163 +307,162 @@ export class EluxCarouselFixedComponent {
|
|
|
234
307
|
if (!this.isDragging)
|
|
235
308
|
return;
|
|
236
309
|
this.isDragging = false;
|
|
237
|
-
//
|
|
310
|
+
// Disable clicks temporarily after any drag
|
|
311
|
+
if (this.wasDragging || this.dragStarted) {
|
|
312
|
+
this.clicksDisabled = true;
|
|
313
|
+
setTimeout(() => {
|
|
314
|
+
this.clicksDisabled = false;
|
|
315
|
+
}, 200);
|
|
316
|
+
}
|
|
317
|
+
// Clear the wasDragging and dragStarted flags after a shorter delay
|
|
238
318
|
setTimeout(() => {
|
|
239
319
|
this.wasDragging = false;
|
|
240
|
-
|
|
320
|
+
this.dragStarted = false;
|
|
321
|
+
}, 250);
|
|
241
322
|
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transition', 'transform 0.3s ease-out');
|
|
242
|
-
//
|
|
243
|
-
|
|
244
|
-
const itemStep = this.itemWidth + this.gap;
|
|
245
|
-
const movedItemsFloat = Math.abs(currentTranslateX - this.initialTranslateX) / itemStep;
|
|
246
|
-
// Adjusted thresholds for better mobile experience
|
|
247
|
-
const minThreshold = 0.25; // Reduced from 0.3 to 0.25
|
|
248
|
-
const dragDistance = Math.abs(this.currentX - this.startX);
|
|
249
|
-
const momentumThreshold = 0.2; // Reduced from 0.3 to 0.2
|
|
250
|
-
const hasSignificantVelocity = Math.abs(this.velocity) > momentumThreshold;
|
|
251
|
-
// More lenient conditions for mobile
|
|
252
|
-
if (movedItemsFloat > minThreshold || hasSignificantVelocity || dragDistance > 40) { // Reduced from 60px to 40px
|
|
253
|
-
// Calculate how many items to advance based on actual drag distance
|
|
254
|
-
let itemsToAdvance = Math.round(movedItemsFloat);
|
|
255
|
-
// For velocity-based movement, use a separate calculation
|
|
256
|
-
if (hasSignificantVelocity && movedItemsFloat < 1) {
|
|
257
|
-
const velocityMultiplier = Math.abs(this.velocity) * 2;
|
|
258
|
-
itemsToAdvance = Math.max(1, Math.floor(velocityMultiplier));
|
|
259
|
-
}
|
|
260
|
-
// Ensure minimum 1 item for significant drags, but don't double count
|
|
261
|
-
if (itemsToAdvance === 0 && movedItemsFloat >= minThreshold) {
|
|
262
|
-
itemsToAdvance = 1;
|
|
263
|
-
}
|
|
264
|
-
if (this.dragOffset > 0 || (hasSignificantVelocity && this.velocity > 0)) {
|
|
265
|
-
// Dragged right - go to previous items
|
|
266
|
-
this.goToPreviousItems(itemsToAdvance);
|
|
267
|
-
}
|
|
268
|
-
else if (this.dragOffset < 0 || (hasSignificantVelocity && this.velocity < 0)) {
|
|
269
|
-
// Dragged left - go to next items
|
|
270
|
-
this.goToNextItems(itemsToAdvance);
|
|
271
|
-
}
|
|
272
|
-
else {
|
|
273
|
-
this.snapToNearestItem();
|
|
274
|
-
}
|
|
275
|
-
}
|
|
276
|
-
else {
|
|
277
|
-
// Small movement - snap to nearest item
|
|
278
|
-
this.snapToNearestItem();
|
|
279
|
-
}
|
|
323
|
+
// Snap sempre para o início da página mais próxima
|
|
324
|
+
this.snapToNearestItem();
|
|
280
325
|
this.dragOffset = 0;
|
|
281
326
|
this.velocity = 0;
|
|
282
327
|
}
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
this.
|
|
292
|
-
this.updateTransform();
|
|
328
|
+
getMaxIndex() {
|
|
329
|
+
// Permite avançar até que o último item esteja visível (não necessariamente alinhado à esquerda)
|
|
330
|
+
if (!this.items || this.items.length === 0)
|
|
331
|
+
return 0;
|
|
332
|
+
const visibleCount = Math.max(1, Math.floor(this.containerWidth / (this.itemWidth + this.gap)));
|
|
333
|
+
if (this.items.length <= visibleCount)
|
|
334
|
+
return 0;
|
|
335
|
+
// Última posição onde o último item aparece visível
|
|
336
|
+
return this.items.length - visibleCount;
|
|
293
337
|
}
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
const newIndex = Math.max(0, this.currentIndex - itemCount);
|
|
297
|
-
if (newIndex !== this.currentIndex) {
|
|
298
|
-
this.currentIndex = newIndex;
|
|
299
|
-
this.updateTransform();
|
|
300
|
-
this.previousClickEventEmitter.emit();
|
|
301
|
-
}
|
|
302
|
-
else {
|
|
303
|
-
this.snapToNearestItem();
|
|
304
|
-
}
|
|
338
|
+
canGoNext() {
|
|
339
|
+
return this.currentIndex < this.getMaxIndex();
|
|
305
340
|
}
|
|
306
|
-
|
|
307
|
-
// Use the current index instead of visual calculation to avoid double movement
|
|
341
|
+
nextItem() {
|
|
308
342
|
const maxIndex = this.getMaxIndex();
|
|
309
|
-
|
|
310
|
-
|
|
343
|
+
if (this.canGoNext()) {
|
|
344
|
+
let newIndex = this.currentIndex + 1;
|
|
345
|
+
if (newIndex > maxIndex)
|
|
346
|
+
newIndex = maxIndex;
|
|
311
347
|
this.currentIndex = newIndex;
|
|
312
348
|
this.updateTransform();
|
|
313
349
|
this.nextClickEventEmitter.emit();
|
|
314
350
|
}
|
|
315
|
-
else {
|
|
316
|
-
this.snapToNearestItem();
|
|
317
|
-
}
|
|
318
351
|
}
|
|
319
352
|
canGoPrevious() {
|
|
320
353
|
return this.currentIndex > 0;
|
|
321
354
|
}
|
|
322
|
-
canGoNext() {
|
|
323
|
-
return this.currentIndex < this.getMaxIndex();
|
|
324
|
-
}
|
|
325
|
-
goToFirstItem() {
|
|
326
|
-
this.currentIndex = 0;
|
|
327
|
-
this.updateTransform();
|
|
328
|
-
}
|
|
329
355
|
prevItem() {
|
|
330
356
|
if (this.canGoPrevious()) {
|
|
331
|
-
this.currentIndex
|
|
357
|
+
let newIndex = this.currentIndex - 1;
|
|
358
|
+
if (newIndex < 0)
|
|
359
|
+
newIndex = 0;
|
|
360
|
+
this.currentIndex = newIndex;
|
|
332
361
|
this.updateTransform();
|
|
333
362
|
this.previousClickEventEmitter.emit();
|
|
334
363
|
}
|
|
335
364
|
}
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
365
|
+
goToDot(dotIndex) {
|
|
366
|
+
const maxIndex = this.getMaxIndex();
|
|
367
|
+
let newIndex = dotIndex;
|
|
368
|
+
if (newIndex > maxIndex)
|
|
369
|
+
newIndex = maxIndex;
|
|
370
|
+
this.currentIndex = newIndex;
|
|
371
|
+
this.updateTransform();
|
|
372
|
+
}
|
|
373
|
+
snapToNearestItem() {
|
|
374
|
+
const itemStep = this.itemWidth + this.gap;
|
|
375
|
+
const position = -(this.initialTranslateX + this.dragOffset) / itemStep;
|
|
376
|
+
// Threshold: 0.3 = 30%, 0.5 = 50% (padrão)
|
|
377
|
+
const threshold = 0.3;
|
|
378
|
+
let targetIndex;
|
|
379
|
+
// Calcula quantos itens completos foram arrastados
|
|
380
|
+
const itemsMoved = Math.floor(Math.abs(position - this.currentIndex));
|
|
381
|
+
const decimal = Math.abs(position - this.currentIndex) - itemsMoved;
|
|
382
|
+
if (position > this.currentIndex) {
|
|
383
|
+
// Arrastando para frente
|
|
384
|
+
if (decimal >= threshold) {
|
|
385
|
+
targetIndex = this.currentIndex + itemsMoved + 1;
|
|
386
|
+
}
|
|
387
|
+
else {
|
|
388
|
+
targetIndex = this.currentIndex + itemsMoved;
|
|
389
|
+
}
|
|
390
|
+
}
|
|
391
|
+
else if (position < this.currentIndex) {
|
|
392
|
+
// Arrastando para trás
|
|
393
|
+
if (decimal >= threshold) {
|
|
394
|
+
targetIndex = this.currentIndex - itemsMoved - 1;
|
|
395
|
+
}
|
|
396
|
+
else {
|
|
397
|
+
targetIndex = this.currentIndex - itemsMoved;
|
|
398
|
+
}
|
|
341
399
|
}
|
|
400
|
+
else {
|
|
401
|
+
// Não se moveu
|
|
402
|
+
targetIndex = this.currentIndex;
|
|
403
|
+
}
|
|
404
|
+
const maxIndex = this.getMaxIndex();
|
|
405
|
+
targetIndex = Math.max(0, Math.min(targetIndex, maxIndex));
|
|
406
|
+
this.currentIndex = targetIndex;
|
|
407
|
+
this.updateTransform();
|
|
408
|
+
}
|
|
409
|
+
getDotsArray() {
|
|
410
|
+
// Só mostra dots para cada posição possível (cada "página" possível)
|
|
411
|
+
const maxIndex = this.getMaxIndex();
|
|
412
|
+
return Array(maxIndex + 1);
|
|
413
|
+
}
|
|
414
|
+
getCurrentDotIndex() {
|
|
415
|
+
return this.currentIndex;
|
|
342
416
|
}
|
|
343
417
|
updateTransform() {
|
|
344
418
|
const itemStep = this.itemWidth + this.gap;
|
|
345
419
|
this.translateX = -this.currentIndex * itemStep;
|
|
346
|
-
//
|
|
347
|
-
|
|
348
|
-
//
|
|
349
|
-
|
|
350
|
-
|
|
420
|
+
// Clamp para não mostrar espaço vazio à direita
|
|
421
|
+
const visibleCount = Math.max(1, Math.floor(this.containerWidth / itemStep));
|
|
422
|
+
// Inclui o gap após o último item
|
|
423
|
+
const totalWidth = this.items.length * itemStep;
|
|
424
|
+
if (this.items.length > visibleCount) {
|
|
425
|
+
const minTranslateX = this.containerWidth - totalWidth;
|
|
426
|
+
this.translateX = Math.max(this.translateX, minTranslateX);
|
|
351
427
|
}
|
|
352
428
|
else {
|
|
353
|
-
this.
|
|
429
|
+
this.translateX = 0;
|
|
354
430
|
}
|
|
355
431
|
if (!this.isDragging && this.slidesContainer) {
|
|
356
432
|
this.renderer.setStyle(this.slidesContainer.nativeElement, 'transform', `translateX(${this.translateX}px)`);
|
|
357
433
|
}
|
|
358
434
|
}
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
return 0;
|
|
364
|
-
}
|
|
365
|
-
// Calculate how many complete items can fit in the visible area
|
|
366
|
-
const itemsPerView = Math.floor(visibleWidth / (this.itemWidth + this.gap));
|
|
367
|
-
// Maximum index ensures the last item is always fully visible
|
|
368
|
-
const maxIndex = Math.max(0, this.items.length - itemsPerView);
|
|
369
|
-
return maxIndex;
|
|
435
|
+
// Adicione este método para evitar erro de propriedade ausente
|
|
436
|
+
goToFirstItem() {
|
|
437
|
+
this.currentIndex = 0;
|
|
438
|
+
this.updateTransform();
|
|
370
439
|
}
|
|
371
440
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: EluxCarouselFixedComponent, deps: [{ token: i0.Renderer2 }], target: i0.ɵɵFactoryTarget.Component }); }
|
|
372
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: EluxCarouselFixedComponent, isStandalone: true, selector: "lib-elux-carousel-fixed", inputs: { itemWidth: "itemWidth", gap: "gap",
|
|
441
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: EluxCarouselFixedComponent, isStandalone: true, selector: "lib-elux-carousel-fixed", inputs: { itemWidth: "itemWidth", gap: "gap", showArrows: "showArrows", showDots: "showDots" }, outputs: { previousClickEventEmitter: "previousClickEventEmitter", nextClickEventEmitter: "nextClickEventEmitter" }, queries: [{ propertyName: "items", predicate: ["carouselItem"], read: ElementRef }], viewQueries: [{ propertyName: "slidesContainer", first: true, predicate: ["slidesContainer"], descendants: true }, { propertyName: "rightBleedContainer", first: true, predicate: ["rightBleedContainer"], descendants: true }], ngImport: i0, template: "<div class=\"c-carousel-fixed-container\" #rightBleedContainer>\n <div \n class=\"c-carousel-fixed-slides\" \n #slidesContainer\n [style.transform]=\"'translateX(' + translateX + 'px)'\" \n (mousedown)=\"onMouseDown($event)\"\n (mousemove)=\"onMouseMove($event)\"\n (mouseup)=\"onMouseUp($event)\"\n (mouseleave)=\"onMouseLeave($event)\"\n (touchstart)=\"onTouchStart($event)\" \n (touchmove)=\"onTouchMove($event)\" \n (touchend)=\"onTouchEnd($event)\">\n <ng-content></ng-content>\n </div>\n</div>\n<div class=\"c-carousel-fixed-footer\" *ngIf=\"showArrows || showDots\">\n <button *ngIf=\"showArrows\"\n class=\"c-carousel-fixed-nav prev\" \n [disabled]=\"!canGoPrevious()\"\n title=\"Item anterior\" \n aria-label=\"Item anterior\" \n (click)=\"prevItem()\">\n <lib-elux-icon [icon]=\"'Chevron_Left.svg'\" [size]=\"'16'\" [sizeType]=\"'px'\" [color]=\"'#020F2E'\"></lib-elux-icon>\n </button>\n\n <div class=\"c-carousel-fixed-dots\" *ngIf=\"showDots\">\n <ng-container *ngFor=\"let dot of getDotsArray(); let idx = index\">\n <span \n class=\"c-carousel-fixed-dot\" \n [class.active]=\"idx === getCurrentDotIndex()\" \n (click)=\"goToDot(idx)\">\n </span>\n </ng-container>\n </div>\n\n <button *ngIf=\"showArrows\"\n class=\"c-carousel-fixed-nav next\" \n [disabled]=\"!canGoNext()\"\n title=\"Pr\u00F3ximo item\" \n aria-label=\"Pr\u00F3ximo item\" \n (click)=\"nextItem()\">\n <lib-elux-icon [icon]=\"'Chevron_Right.svg'\" [size]=\"'16'\" [sizeType]=\"'px'\" [color]=\"'#020F2E'\"></lib-elux-icon>\n </button>\n</div>\n", styles: [".c-carousel-fixed-container{overflow-x:hidden;width:calc(100vw - var(--left-offset, 0px) - var(--scrollbar-width, 0px))}.c-carousel-fixed-slides{display:flex;transition:transform .5s ease-out;touch-action:pan-y;cursor:grab;will-change:transform}.c-carousel-fixed-slides:active{cursor:grabbing}.c-carousel-fixed-footer{display:flex;justify-content:space-between;padding:16px}.c-carousel-fixed-footer .c-carousel-fixed-nav{background:none;border:none;cursor:pointer;padding:8px;border-radius:50px;background-color:#dfe7ea;transition:all ease-in-out .2s;z-index:2}.c-carousel-fixed-footer .c-carousel-fixed-nav:hover:not(:disabled){transform:scale(1.2)}.c-carousel-fixed-footer .c-carousel-fixed-nav:disabled{opacity:.3;cursor:not-allowed}.c-carousel-fixed-footer .c-carousel-fixed-nav:disabled:hover{transform:none}.c-carousel-fixed-footer .c-carousel-fixed-nav ::ng-deep span{display:block}.c-carousel-fixed-footer .c-carousel-fixed-dots{display:flex;align-items:center;gap:8px;margin:0 16px}.c-carousel-fixed-footer .c-carousel-fixed-dots .c-carousel-fixed-dot{width:10px;height:10px;border-radius:50%;background:#dfe7ea;transition:background .3s;cursor:pointer;display:inline-block}.c-carousel-fixed-footer .c-carousel-fixed-dots .c-carousel-fixed-dot.active{background:#011e41}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: EluxIcon, selector: "lib-elux-icon", inputs: ["color", "useSubscription", "icon", "description", "size", "height", "width", "sizeType"] }] }); }
|
|
373
442
|
}
|
|
374
443
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: EluxCarouselFixedComponent, decorators: [{
|
|
375
444
|
type: Component,
|
|
376
|
-
args: [{ standalone: true, selector: 'lib-elux-carousel-fixed', imports: [CommonModule, EluxIcon], template: "<div class=\"c-carousel-fixed-container\">\n <div \n
|
|
445
|
+
args: [{ standalone: true, selector: 'lib-elux-carousel-fixed', imports: [CommonModule, EluxIcon], template: "<div class=\"c-carousel-fixed-container\" #rightBleedContainer>\n <div \n class=\"c-carousel-fixed-slides\" \n #slidesContainer\n [style.transform]=\"'translateX(' + translateX + 'px)'\" \n (mousedown)=\"onMouseDown($event)\"\n (mousemove)=\"onMouseMove($event)\"\n (mouseup)=\"onMouseUp($event)\"\n (mouseleave)=\"onMouseLeave($event)\"\n (touchstart)=\"onTouchStart($event)\" \n (touchmove)=\"onTouchMove($event)\" \n (touchend)=\"onTouchEnd($event)\">\n <ng-content></ng-content>\n </div>\n</div>\n<div class=\"c-carousel-fixed-footer\" *ngIf=\"showArrows || showDots\">\n <button *ngIf=\"showArrows\"\n class=\"c-carousel-fixed-nav prev\" \n [disabled]=\"!canGoPrevious()\"\n title=\"Item anterior\" \n aria-label=\"Item anterior\" \n (click)=\"prevItem()\">\n <lib-elux-icon [icon]=\"'Chevron_Left.svg'\" [size]=\"'16'\" [sizeType]=\"'px'\" [color]=\"'#020F2E'\"></lib-elux-icon>\n </button>\n\n <div class=\"c-carousel-fixed-dots\" *ngIf=\"showDots\">\n <ng-container *ngFor=\"let dot of getDotsArray(); let idx = index\">\n <span \n class=\"c-carousel-fixed-dot\" \n [class.active]=\"idx === getCurrentDotIndex()\" \n (click)=\"goToDot(idx)\">\n </span>\n </ng-container>\n </div>\n\n <button *ngIf=\"showArrows\"\n class=\"c-carousel-fixed-nav next\" \n [disabled]=\"!canGoNext()\"\n title=\"Pr\u00F3ximo item\" \n aria-label=\"Pr\u00F3ximo item\" \n (click)=\"nextItem()\">\n <lib-elux-icon [icon]=\"'Chevron_Right.svg'\" [size]=\"'16'\" [sizeType]=\"'px'\" [color]=\"'#020F2E'\"></lib-elux-icon>\n </button>\n</div>\n", styles: [".c-carousel-fixed-container{overflow-x:hidden;width:calc(100vw - var(--left-offset, 0px) - var(--scrollbar-width, 0px))}.c-carousel-fixed-slides{display:flex;transition:transform .5s ease-out;touch-action:pan-y;cursor:grab;will-change:transform}.c-carousel-fixed-slides:active{cursor:grabbing}.c-carousel-fixed-footer{display:flex;justify-content:space-between;padding:16px}.c-carousel-fixed-footer .c-carousel-fixed-nav{background:none;border:none;cursor:pointer;padding:8px;border-radius:50px;background-color:#dfe7ea;transition:all ease-in-out .2s;z-index:2}.c-carousel-fixed-footer .c-carousel-fixed-nav:hover:not(:disabled){transform:scale(1.2)}.c-carousel-fixed-footer .c-carousel-fixed-nav:disabled{opacity:.3;cursor:not-allowed}.c-carousel-fixed-footer .c-carousel-fixed-nav:disabled:hover{transform:none}.c-carousel-fixed-footer .c-carousel-fixed-nav ::ng-deep span{display:block}.c-carousel-fixed-footer .c-carousel-fixed-dots{display:flex;align-items:center;gap:8px;margin:0 16px}.c-carousel-fixed-footer .c-carousel-fixed-dots .c-carousel-fixed-dot{width:10px;height:10px;border-radius:50%;background:#dfe7ea;transition:background .3s;cursor:pointer;display:inline-block}.c-carousel-fixed-footer .c-carousel-fixed-dots .c-carousel-fixed-dot.active{background:#011e41}\n"] }]
|
|
377
446
|
}], ctorParameters: () => [{ type: i0.Renderer2 }], propDecorators: { items: [{
|
|
378
447
|
type: ContentChildren,
|
|
379
448
|
args: ['carouselItem', { read: ElementRef }]
|
|
380
449
|
}], slidesContainer: [{
|
|
381
450
|
type: ViewChild,
|
|
382
451
|
args: ['slidesContainer']
|
|
452
|
+
}], rightBleedContainer: [{
|
|
453
|
+
type: ViewChild,
|
|
454
|
+
args: ['rightBleedContainer', { static: false }]
|
|
383
455
|
}], itemWidth: [{
|
|
384
456
|
type: Input
|
|
385
457
|
}], gap: [{
|
|
386
458
|
type: Input
|
|
387
|
-
}],
|
|
459
|
+
}], showArrows: [{
|
|
460
|
+
type: Input
|
|
461
|
+
}], showDots: [{
|
|
388
462
|
type: Input
|
|
389
463
|
}], previousClickEventEmitter: [{
|
|
390
464
|
type: Output
|
|
391
465
|
}], nextClickEventEmitter: [{
|
|
392
466
|
type: Output
|
|
393
|
-
}], itemClickEventEmitter: [{
|
|
394
|
-
type: Output
|
|
395
467
|
}] } });
|
|
396
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vdWkvbGlicmFyeS9zcmMvbGliL2NvbXBvbmVudHMvY2Fyb3VzZWwtZml4ZWQvY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vLi4vdWkvbGlicmFyeS9zcmMvbGliL2NvbXBvbmVudHMvY2Fyb3VzZWwtZml4ZWQvY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50Lmh0bWwiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBQy9DLE9BQU8sRUFBb0IsU0FBUyxFQUFFLGVBQWUsRUFBRSxVQUFVLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBYSxNQUFNLEVBQXdCLFNBQVMsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUNsSyxPQUFPLEVBQUUsUUFBUSxFQUFFLE1BQU0sU0FBUyxDQUFDOztBQVNuQyxNQUFNLE9BQU8sMEJBQTBCO0lBZ0NyQyxZQUFvQixRQUFtQjtRQUFuQixhQUFRLEdBQVIsUUFBUSxDQUFXO1FBNUI5QixjQUFTLEdBQVcsR0FBRyxDQUFDLENBQUMsd0JBQXdCO1FBQ2pELFFBQUcsR0FBVyxFQUFFLENBQUMsQ0FBQyw4QkFBOEI7UUFDaEQsaUJBQVksR0FBWSxLQUFLLENBQUM7UUFFN0IsOEJBQXlCLEdBQUcsSUFBSSxZQUFZLEVBQVMsQ0FBQztRQUN0RCwwQkFBcUIsR0FBRyxJQUFJLFlBQVksRUFBUyxDQUFDO1FBQ2xELDBCQUFxQixHQUFHLElBQUksWUFBWSxFQUF1RCxDQUFDO1FBRTFHLGlCQUFZLEdBQUcsQ0FBQyxDQUFDO1FBQ2pCLGVBQVUsR0FBRyxDQUFDLENBQUM7UUFFUCxlQUFVLEdBQUcsS0FBSyxDQUFDO1FBQ25CLFdBQU0sR0FBRyxDQUFDLENBQUM7UUFDWCxhQUFRLEdBQUcsQ0FBQyxDQUFDO1FB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QkFBcEIsS0FBSztnQkFFSSx5QkFBeUI7c0JBQWxDLE1BQU07Z0JBQ0cscUJBQXFCO3NCQUE5QixNQUFNO2dCQUNHLHFCQUFxQjtzQkFBOUIsTUFBTSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IENvbW1vbk1vZHVsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvbW1vbic7XG5pbXBvcnQgeyBBZnRlckNvbnRlbnRJbml0LCBDb21wb25lbnQsIENvbnRlbnRDaGlsZHJlbiwgRWxlbWVudFJlZiwgRXZlbnRFbWl0dGVyLCBJbnB1dCwgT25EZXN0cm95LCBPdXRwdXQsIFF1ZXJ5TGlzdCwgUmVuZGVyZXIyLCBWaWV3Q2hpbGQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IEVsdXhJY29uIH0gZnJvbSAnLi4vaWNvbic7XG5cbkBDb21wb25lbnQoe1xuICBzdGFuZGFsb25lOiB0cnVlLFxuICBzZWxlY3RvcjogJ2xpYi1lbHV4LWNhcm91c2VsLWZpeGVkJyxcbiAgdGVtcGxhdGVVcmw6ICcuL2Nhcm91c2VsLWZpeGVkLmNvbXBvbmVudC5odG1sJyxcbiAgc3R5bGVVcmxzOiBbJy4vY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50LnNjc3MnXSxcbiAgaW1wb3J0czogW0NvbW1vbk1vZHVsZSwgRWx1eEljb25dLFxufSlcbmV4cG9ydCBjbGFzcyBFbHV4Q2Fyb3VzZWxGaXhlZENvbXBvbmVudCBpbXBsZW1lbnRzIEFmdGVyQ29udGVudEluaXQsIE9uRGVzdHJveSB7XG4gIEBDb250ZW50Q2hpbGRyZW4oJ2Nhcm91c2VsSXRlbScsIHsgcmVhZDogRWxlbWVudFJlZiB9KSBpdGVtcyE6IFF1ZXJ5TGlzdDxFbGVtZW50UmVmPjtcbiAgQFZpZXdDaGlsZCgnc2xpZGVzQ29udGFpbmVyJykgc2xpZGVzQ29udGFpbmVyITogRWxlbWVudFJlZjtcblxuICBASW5wdXQoKSBpdGVtV2lkdGg6IG51bWJlciA9IDIwMDsgLy8gRml4ZWQgd2lkdGggaW4gcGl4ZWxzXG4gIEBJbnB1dCgpIGdhcDogbnVtYmVyID0gMTY7IC8vIEdhcCBiZXR3ZWVuIGl0ZW1zIGluIHBpeGVsc1xuICBASW5wdXQoKSByZW1vdmVBcnJvd3M6IGJvb2xlYW4gPSBmYWxzZTtcblxuICBAT3V0cHV0KCkgcHJldmlvdXNDbGlja0V2ZW50RW1pdHRlciA9IG5ldyBFdmVudEVtaXR0ZXI8RXZlbnQ+KCk7XG4gIEBPdXRwdXQoKSBuZXh0Q2xpY2tFdmVudEVtaXR0ZXIgPSBuZXcgRXZlbnRFbWl0dGVyPEV2ZW50PigpO1xuICBAT3V0cHV0KCkgaXRlbUNsaWNrRXZlbnRFbWl0dGVyID0gbmV3IEV2ZW50RW1pdHRlcjx7ZXZlbnQ6IEV2ZW50LCBpbmRleDogbnVtYmVyLCBlbGVtZW50OiBIVE1MRWxlbWVudH0+KCk7XG5cbiAgY3VycmVudEluZGV4ID0gMDtcbiAgdHJhbnNsYXRlWCA9IDA7XG5cbiAgcHJpdmF0ZSBpc0RyYWdnaW5nID0gZmFsc2U7XG4gIHByaXZhdGUgc3RhcnRYID0gMDtcbiAgcHJpdmF0ZSBjdXJyZW50WCA9IDA7XG4gIHByaXZhdGUgaW5pdGlhbFRyYW5zbGF0ZVggPSAwO1xuICBwcml2YXRlIGRyYWdPZmZzZXQgPSAwO1xuICBwcml2YXRlIGNvbnRhaW5lcldpZHRoID0gMDtcbiAgcHJpdmF0ZSBtYXhUcmFuc2xhdGVYID0gMDtcbiAgcHJpdmF0ZSBtaW5UcmFuc2xhdGVYID0gMDtcbiAgcHJpdmF0ZSB2ZWxvY2l0eSA9IDA7XG4gIHByaXZhdGUgbGFzdE1vdmVUaW1lID0gMDtcbiAgcHJpdmF0ZSBsYXN0TW92ZVggPSAwO1xuICBwcml2YXRlIHdhc0RyYWdnaW5nID0gZmFsc2U7XG4gIHByaXZhdGUgdG91Y2hTdGFydFRpbWUgPSAwO1xuICBwcml2YXRlIHRvdWNoU3RhcnRYID0gMDtcbiAgcHJpdmF0ZSB0b3VjaFN0YXJ0WSA9IDA7XG4gIHByaXZhdGUgaXNWZXJ0aWNhbFNjcm9sbCA9IGZhbHNlO1xuXG4gIGNvbnN0cnVjdG9yKHByaXZhdGUgcmVuZGVyZXI6IFJlbmRlcmVyMikge31cblxuICBuZ0FmdGVyQ29udGVudEluaXQoKSB7XG4gICAgdGhpcy5jYWxjdWxhdGVEaW1lbnNpb25zKCk7XG4gICAgdGhpcy5zZXRJdGVtV2lkdGhzKCk7XG4gICAgdGhpcy51cGRhdGVMaW1pdHMoKTtcbiAgICB0aGlzLnNldHVwSXRlbUNsaWNrTGlzdGVuZXJzKCk7XG5cbiAgICB0aGlzLml0ZW1zLmNoYW5nZXMuc3Vic2NyaWJlKCgpID0+IHtcbiAgICAgIHRoaXMuY2FsY3VsYXRlRGltZW5zaW9ucygpO1xuICAgICAgdGhpcy5zZXRJdGVtV2lkdGhzKCk7XG4gICAgICB0aGlzLnVwZGF0ZUxpbWl0cygpO1xuICAgICAgdGhpcy5nb1RvRmlyc3RJdGVtKCk7XG4gICAgICB0aGlzLnNldHVwSXRlbUNsaWNrTGlzdGVuZXJzKCk7XG4gICAgfSk7XG5cbiAgICB3aW5kb3cuYWRkRXZlbnRMaXN0ZW5lcigncmVzaXplJywgKCkgPT4gdGhpcy5vblJlc2l6ZSgpKTtcbiAgfVxuXG4gIG5nT25EZXN0cm95KCkge1xuICAgIHdpbmRvdy5yZW1vdmVFdmVudExpc3RlbmVyKCdyZXNpemUnLCAoKSA9PiB0aGlzLm9uUmVzaXplKCkpO1xuICB9XG5cbiAgcHJpdmF0ZSBjYWxjdWxhdGVEaW1lbnNpb25zKCkge1xuICAgIGlmICh0aGlzLnNsaWRlc0NvbnRhaW5lcikge1xuICAgICAgdGhpcy5jb250YWluZXJXaWR0aCA9IHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQub2Zmc2V0V2lkdGg7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVMaW1pdHMoKSB7XG4gICAgY29uc3QgdG90YWxXaWR0aCA9IHRoaXMuaXRlbXMubGVuZ3RoICogKHRoaXMuaXRlbVdpZHRoICsgdGhpcy5nYXApIC0gdGhpcy5nYXA7XG4gICAgdGhpcy5tYXhUcmFuc2xhdGVYID0gMDtcbiAgICBcbiAgICAvLyBDYWxjdWxhdGUgbWluaW11bSB0cmFuc2xhdGVYIHRvIGVuc3VyZSBsYXN0IGl0ZW0gaXMgZnVsbHkgdmlzaWJsZVxuICAgIGlmICh0b3RhbFdpZHRoID4gdGhpcy5jb250YWluZXJXaWR0aCkge1xuICAgICAgdGhpcy5taW5UcmFuc2xhdGVYID0gdGhpcy5jb250YWluZXJXaWR0aCAtIHRvdGFsV2lkdGg7XG4gICAgICBcbiAgICAgIC8vIEFkZCBzb21lIHBhZGRpbmcgdG8gZW5zdXJlIGxhc3QgaXRlbSBpcyBjb21wbGV0ZWx5IHZpc2libGVcbiAgICAgIGNvbnN0IHBhZGRpbmdPZmZzZXQgPSB0aGlzLmdhcDtcbiAgICAgIHRoaXMubWluVHJhbnNsYXRlWCAtPSBwYWRkaW5nT2Zmc2V0O1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLm1pblRyYW5zbGF0ZVggPSAwO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgb25SZXNpemUoKSB7XG4gICAgdGhpcy5jYWxjdWxhdGVEaW1lbnNpb25zKCk7XG4gICAgdGhpcy51cGRhdGVMaW1pdHMoKTtcbiAgICB0aGlzLnVwZGF0ZVRyYW5zZm9ybSgpO1xuICB9XG5cbiAgcHJpdmF0ZSBzZXRJdGVtV2lkdGhzKCkge1xuICAgIHRoaXMuaXRlbXMuZm9yRWFjaCgoaXRlbSkgPT4ge1xuICAgICAgdGhpcy5yZW5kZXJlci5zZXRTdHlsZShpdGVtLm5hdGl2ZUVsZW1lbnQsICd3aWR0aCcsIGAke3RoaXMuaXRlbVdpZHRofXB4YCk7XG4gICAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKGl0ZW0ubmF0aXZlRWxlbWVudCwgJ2ZsZXgtc2hyaW5rJywgJzAnKTtcbiAgICAgIHRoaXMucmVuZGVyZXIuc2V0U3R5bGUoaXRlbS5uYXRpdmVFbGVtZW50LCAnbWFyZ2luLXJpZ2h0JywgYCR7dGhpcy5nYXB9cHhgKTtcbiAgICB9KTtcbiAgICBcbiAgICAvLyBSZW1vdmUgbWFyZ2luIGZyb20gbGFzdCBpdGVtXG4gICAgaWYgKHRoaXMuaXRlbXMubGFzdCkge1xuICAgICAgdGhpcy5yZW5kZXJlci5zZXRTdHlsZSh0aGlzLml0ZW1zLmxhc3QubmF0aXZlRWxlbWVudCwgJ21hcmdpbi1yaWdodCcsICcwJyk7XG4gICAgfVxuICB9XG5cbiAgLy8gTW91c2UgZXZlbnRzXG4gIG9uTW91c2VEb3duKGV2ZW50OiBNb3VzZUV2ZW50KSB7XG4gICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICB0aGlzLnN0YXJ0RHJhZyhldmVudC5jbGllbnRYKTtcbiAgfVxuXG4gIG9uTW91c2VNb3ZlKGV2ZW50OiBNb3VzZUV2ZW50KSB7XG4gICAgaWYgKHRoaXMuaXNEcmFnZ2luZykge1xuICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICAgIHRoaXMudXBkYXRlRHJhZyhldmVudC5jbGllbnRYKTtcbiAgICB9XG4gIH1cblxuICBvbk1vdXNlVXAoZXZlbnQ6IE1vdXNlRXZlbnQpIHtcbiAgICBpZiAodGhpcy5pc0RyYWdnaW5nKSB7XG4gICAgICB0aGlzLmVuZERyYWcoKTtcbiAgICB9XG4gIH1cblxuICBvbk1vdXNlTGVhdmUoZXZlbnQ6IE1vdXNlRXZlbnQpIHtcbiAgICBpZiAodGhpcy5pc0RyYWdnaW5nKSB7XG4gICAgICB0aGlzLmVuZERyYWcoKTtcbiAgICB9XG4gIH1cblxuICAvLyBUb3VjaCBldmVudHNcbiAgb25Ub3VjaFN0YXJ0KGV2ZW50OiBUb3VjaEV2ZW50KSB7XG4gICAgdGhpcy50b3VjaFN0YXJ0VGltZSA9IERhdGUubm93KCk7XG4gICAgdGhpcy50b3VjaFN0YXJ0WCA9IGV2ZW50LnRvdWNoZXNbMF0uY2xpZW50WDtcbiAgICB0aGlzLnRvdWNoU3RhcnRZID0gZXZlbnQudG91Y2hlc1swXS5jbGllbnRZO1xuICAgIHRoaXMuaXNWZXJ0aWNhbFNjcm9sbCA9IGZhbHNlO1xuICAgIHRoaXMuc3RhcnREcmFnKGV2ZW50LnRvdWNoZXNbMF0uY2xpZW50WCk7XG4gIH1cblxuICBvblRvdWNoTW92ZShldmVudDogVG91Y2hFdmVudCkge1xuICAgIGlmICghdGhpcy5pc0RyYWdnaW5nKSByZXR1cm47XG4gICAgXG4gICAgY29uc3QgY3VycmVudFggPSBldmVudC50b3VjaGVzWzBdLmNsaWVudFg7XG4gICAgY29uc3QgY3VycmVudFkgPSBldmVudC50b3VjaGVzWzBdLmNsaWVudFk7XG4gICAgY29uc3QgZGVsdGFYID0gTWF0aC5hYnMoY3VycmVudFggLSB0aGlzLnRvdWNoU3RhcnRYKTtcbiAgICBjb25zdCBkZWx0YVkgPSBNYXRoLmFicyhjdXJyZW50WSAtIHRoaXMudG91Y2hTdGFydFkpO1xuICAgIFxuICAgIC8vIENoZWNrIGlmIHRoaXMgaXMgYSB2ZXJ0aWNhbCBzY3JvbGxcbiAgICBpZiAoZGVsdGFZID4gZGVsdGFYICYmIGRlbHRhWSA+IDEwKSB7XG4gICAgICB0aGlzLmlzVmVydGljYWxTY3JvbGwgPSB0cnVlO1xuICAgICAgdGhpcy5pc0RyYWdnaW5nID0gZmFsc2U7XG4gICAgICB0aGlzLndhc0RyYWdnaW5nID0gZmFsc2U7XG4gICAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsICd0cmFuc2l0aW9uJywgJ3RyYW5zZm9ybSAwLjNzIGVhc2Utb3V0Jyk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIFxuICAgIC8vIE9ubHkgcHJldmVudCBkZWZhdWx0IGlmIGl0J3MgYSBob3Jpem9udGFsIGRyYWdcbiAgICBpZiAoZGVsdGFYID4gMTApIHtcbiAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgICB0aGlzLnVwZGF0ZURyYWcoZXZlbnQudG91Y2hlc1swXS5jbGllbnRYKTtcbiAgICB9XG4gIH1cblxuICBvblRvdWNoRW5kKGV2ZW50OiBUb3VjaEV2ZW50KSB7XG4gICAgaWYgKHRoaXMuaXNWZXJ0aWNhbFNjcm9sbCkge1xuICAgICAgdGhpcy5pc1ZlcnRpY2FsU2Nyb2xsID0gZmFsc2U7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIFxuICAgIGNvbnN0IHRvdWNoRHVyYXRpb24gPSBEYXRlLm5vdygpIC0gdGhpcy50b3VjaFN0YXJ0VGltZTtcbiAgICBjb25zdCB0b3VjaERpc3RhbmNlID0gTWF0aC5hYnModGhpcy5jdXJyZW50WCAtIHRoaXMuc3RhcnRYKTtcbiAgICBcbiAgICAvLyBDb25zaWRlciBpdCBhIHRhcCBpZiBkdXJhdGlvbiA8IDMwMG1zIGFuZCBkaXN0YW5jZSA8IDEwcHhcbiAgICBpZiAodG91Y2hEdXJhdGlvbiA8IDMwMCAmJiB0b3VjaERpc3RhbmNlIDwgMTApIHtcbiAgICAgIHRoaXMud2FzRHJhZ2dpbmcgPSBmYWxzZTtcbiAgICAgIHRoaXMuaXNEcmFnZ2luZyA9IGZhbHNlO1xuICAgIH1cbiAgICBcbiAgICBpZiAodGhpcy5pc0RyYWdnaW5nKSB7XG4gICAgICB0aGlzLmVuZERyYWcoKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIHNldHVwSXRlbUNsaWNrTGlzdGVuZXJzKCkge1xuICAgIHRoaXMuaXRlbXMuZm9yRWFjaCgoaXRlbSwgaW5kZXgpID0+IHtcbiAgICAgIC8vIFJlbW92ZSBhbnkgZXhpc3RpbmcgbGlzdGVuZXJzXG4gICAgICBjb25zdCBuZXdJdGVtID0gaXRlbS5uYXRpdmVFbGVtZW50LmNsb25lTm9kZSh0cnVlKTtcbiAgICAgIGl0ZW0ubmF0aXZlRWxlbWVudC5wYXJlbnROb2RlPy5yZXBsYWNlQ2hpbGQobmV3SXRlbSwgaXRlbS5uYXRpdmVFbGVtZW50KTtcbiAgICAgIFxuICAgICAgLy8gQWRkIGJvdGggY2xpY2sgYW5kIHRvdWNoZW5kIGxpc3RlbmVycyBmb3IgYmV0dGVyIG1vYmlsZSBzdXBwb3J0XG4gICAgICB0aGlzLnJlbmRlcmVyLmxpc3RlbihuZXdJdGVtLCAnY2xpY2snLCAoZXZlbnQ6IEV2ZW50KSA9PiB7XG4gICAgICAgIHRoaXMuaGFuZGxlSXRlbUNsaWNrKGV2ZW50LCBpbmRleCwgbmV3SXRlbSk7XG4gICAgICB9KTtcbiAgICAgIFxuICAgICAgdGhpcy5yZW5kZXJlci5saXN0ZW4obmV3SXRlbSwgJ3RvdWNoZW5kJywgKGV2ZW50OiBUb3VjaEV2ZW50KSA9PiB7XG4gICAgICAgIC8vIE9ubHkgaGFuZGxlIHRvdWNoZW5kIGlmIGl0IHdhc24ndCBhIGRyYWdcbiAgICAgICAgaWYgKCF0aGlzLndhc0RyYWdnaW5nICYmICF0aGlzLmlzVmVydGljYWxTY3JvbGwpIHtcbiAgICAgICAgICBjb25zdCB0b3VjaER1cmF0aW9uID0gRGF0ZS5ub3coKSAtIHRoaXMudG91Y2hTdGFydFRpbWU7XG4gICAgICAgICAgY29uc3QgdG91Y2hEaXN0YW5jZSA9IE1hdGguYWJzKGV2ZW50LmNoYW5nZWRUb3VjaGVzWzBdLmNsaWVudFggLSB0aGlzLnRvdWNoU3RhcnRYKTtcbiAgICAgICAgICBcbiAgICAgICAgICBpZiAodG91Y2hEdXJhdGlvbiA8IDMwMCAmJiB0b3VjaERpc3RhbmNlIDwgMTApIHtcbiAgICAgICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgICAgICAgICB0aGlzLmhhbmRsZUl0ZW1DbGljayhldmVudCwgaW5kZXgsIG5ld0l0ZW0pO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfSk7XG4gICAgfSk7XG4gIH1cblxuICBwcml2YXRlIGhhbmRsZUl0ZW1DbGljayhldmVudDogRXZlbnQsIGluZGV4OiBudW1iZXIsIGVsZW1lbnQ6IEhUTUxFbGVtZW50KSB7XG4gICAgLy8gUHJldmVudCBjbGljayBpZiBpdCB3YXMgcHJlY2VkZWQgYnkgYSBkcmFnXG4gICAgaWYgKHRoaXMud2FzRHJhZ2dpbmcpIHtcbiAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgXG4gICAgdGhpcy5pdGVtQ2xpY2tFdmVudEVtaXR0ZXIuZW1pdCh7XG4gICAgICBldmVudCxcbiAgICAgIGluZGV4LFxuICAgICAgZWxlbWVudFxuICAgIH0pO1xuICB9XG5cbiAgcHJpdmF0ZSBzdGFydERyYWcoY2xpZW50WDogbnVtYmVyKSB7XG4gICAgdGhpcy5pc0RyYWdnaW5nID0gdHJ1ZTtcbiAgICB0aGlzLndhc0RyYWdnaW5nID0gZmFsc2U7XG4gICAgdGhpcy5zdGFydFggPSBjbGllbnRYO1xuICAgIHRoaXMuY3VycmVudFggPSBjbGllbnRYO1xuICAgIHRoaXMuaW5pdGlhbFRyYW5zbGF0ZVggPSB0aGlzLnRyYW5zbGF0ZVg7XG4gICAgdGhpcy5kcmFnT2Zmc2V0ID0gMDtcbiAgICB0aGlzLnZlbG9jaXR5ID0gMDtcbiAgICB0aGlzLmxhc3RNb3ZlVGltZSA9IERhdGUubm93KCk7XG4gICAgdGhpcy5sYXN0TW92ZVggPSBjbGllbnRYO1xuICAgIFxuICAgIHRoaXMuY2FsY3VsYXRlRGltZW5zaW9ucygpO1xuICAgIFxuICAgIHRoaXMucmVuZGVyZXIuc2V0U3R5bGUodGhpcy5zbGlkZXNDb250YWluZXIubmF0aXZlRWxlbWVudCwgJ3RyYW5zaXRpb24nLCAnbm9uZScpO1xuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVEcmFnKGNsaWVudFg6IG51bWJlcikge1xuICAgIGlmICghdGhpcy5pc0RyYWdnaW5nKSByZXR1cm47XG5cbiAgICB0aGlzLmN1cnJlbnRYID0gY2xpZW50WDtcbiAgICBjb25zdCB0b3RhbERlbHRhWCA9IHRoaXMuY3VycmVudFggLSB0aGlzLnN0YXJ0WDtcbiAgICBcbiAgICAvLyBNb3JlIGxlbmllbnQgdGhyZXNob2xkIGZvciBtb2JpbGUgLSBtYXJrIGFzIGRyYWdnaW5nIG9ubHkgZm9yIHNpZ25pZmljYW50IG1vdmVtZW50XG4gICAgaWYgKE1hdGguYWJzKHRvdGFsRGVsdGFYKSA+IDE1KSB7IC8vIEluY3JlYXNlZCBmcm9tIDVweCB0byAxNXB4IGZvciBtb2JpbGVcbiAgICAgIHRoaXMud2FzRHJhZ2dpbmcgPSB0cnVlO1xuICAgIH1cbiAgICBcbiAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgIGNvbnN0IHRpbWVEZWx0YSA9IG5vdyAtIHRoaXMubGFzdE1vdmVUaW1lO1xuICAgIGlmICh0aW1lRGVsdGEgPiAwKSB7XG4gICAgICB0aGlzLnZlbG9jaXR5ID0gKGNsaWVudFggLSB0aGlzLmxhc3RNb3ZlWCkgLyB0aW1lRGVsdGE7XG4gICAgfVxuICAgIHRoaXMubGFzdE1vdmVUaW1lID0gbm93O1xuICAgIHRoaXMubGFzdE1vdmVYID0gY2xpZW50WDtcblxuICAgIGxldCByZXNpc3RlZERlbHRhWCA9IHRvdGFsRGVsdGFYO1xuICAgIGNvbnN0IHBvdGVudGlhbFRyYW5zbGF0ZVggPSB0aGlzLmluaXRpYWxUcmFuc2xhdGVYICsgdG90YWxEZWx0YVg7XG4gICAgXG4gICAgLy8gQXBwbHkgc29mdGVyIHJlc2lzdGFuY2UgYXQgYm91bmRhcmllc1xuICAgIGlmIChwb3RlbnRpYWxUcmFuc2xhdGVYID4gdGhpcy5tYXhUcmFuc2xhdGVYKSB7XG4gICAgICBjb25zdCBvdmVyRHJhZyA9IHBvdGVudGlhbFRyYW5zbGF0ZVggLSB0aGlzLm1heFRyYW5zbGF0ZVg7XG4gICAgICByZXNpc3RlZERlbHRhWCA9IHRvdGFsRGVsdGFYIC0gKG92ZXJEcmFnICogMC41KTsgLy8gUmVkdWNlZCByZXNpc3RhbmNlIGZvciBtb3JlIG5hdHVyYWwgZmVlbFxuICAgIH0gZWxzZSBpZiAocG90ZW50aWFsVHJhbnNsYXRlWCA8IHRoaXMubWluVHJhbnNsYXRlWCkge1xuICAgICAgY29uc3Qgb3ZlckRyYWcgPSB0aGlzLm1pblRyYW5zbGF0ZVggLSBwb3RlbnRpYWxUcmFuc2xhdGVYO1xuICAgICAgcmVzaXN0ZWREZWx0YVggPSB0b3RhbERlbHRhWCArIChvdmVyRHJhZyAqIDAuNSk7IC8vIFJlZHVjZWQgcmVzaXN0YW5jZSBmb3IgbW9yZSBuYXR1cmFsIGZlZWxcbiAgICB9XG5cbiAgICB0aGlzLmRyYWdPZmZzZXQgPSByZXNpc3RlZERlbHRhWDtcbiAgICB0aGlzLnVwZGF0ZURyYWdQb3NpdGlvbigpO1xuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVEcmFnUG9zaXRpb24oKSB7XG4gICAgY29uc3QgbmV3VHJhbnNsYXRlWCA9IHRoaXMuaW5pdGlhbFRyYW5zbGF0ZVggKyB0aGlzLmRyYWdPZmZzZXQ7XG4gICAgdGhpcy5yZW5kZXJlci5zZXRTdHlsZShcbiAgICAgIHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsIFxuICAgICAgJ3RyYW5zZm9ybScsIFxuICAgICAgYHRyYW5zbGF0ZVgoJHtuZXdUcmFuc2xhdGVYfXB4KWBcbiAgICApO1xuICB9XG5cbiAgcHJpdmF0ZSBlbmREcmFnKCkge1xuICAgIGlmICghdGhpcy5pc0RyYWdnaW5nKSByZXR1cm47XG5cbiAgICB0aGlzLmlzRHJhZ2dpbmcgPSBmYWxzZTtcbiAgICBcbiAgICAvLyBDbGVhciB0aGUgd2FzRHJhZ2dpbmcgZmxhZyBhZnRlciBhIHNob3J0ZXIgZGVsYXkgZm9yIG1vYmlsZVxuICAgIHNldFRpbWVvdXQoKCkgPT4ge1xuICAgICAgdGhpcy53YXNEcmFnZ2luZyA9IGZhbHNlO1xuICAgIH0sIDUwKTsgLy8gUmVkdWNlZCBmcm9tIDEwMG1zIHRvIDUwbXNcbiAgICBcbiAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsICd0cmFuc2l0aW9uJywgJ3RyYW5zZm9ybSAwLjNzIGVhc2Utb3V0Jyk7XG5cbiAgICAvLyBDYWxjdWxhdGUgaG93IGZhciB3ZSd2ZSBhY3R1YWxseSBtb3ZlZCBpbiB0ZXJtcyBvZiBpdGVtc1xuICAgIGNvbnN0IGN1cnJlbnRUcmFuc2xhdGVYID0gdGhpcy5pbml0aWFsVHJhbnNsYXRlWCArIHRoaXMuZHJhZ09mZnNldDtcbiAgICBjb25zdCBpdGVtU3RlcCA9IHRoaXMuaXRlbVdpZHRoICsgdGhpcy5nYXA7XG4gICAgY29uc3QgbW92ZWRJdGVtc0Zsb2F0ID0gTWF0aC5hYnMoY3VycmVudFRyYW5zbGF0ZVggLSB0aGlzLmluaXRpYWxUcmFuc2xhdGVYKSAvIGl0ZW1TdGVwO1xuICAgIFxuICAgIC8vIEFkanVzdGVkIHRocmVzaG9sZHMgZm9yIGJldHRlciBtb2JpbGUgZXhwZXJpZW5jZVxuICAgIGNvbnN0IG1pblRocmVzaG9sZCA9IDAuMjU7IC8vIFJlZHVjZWQgZnJvbSAwLjMgdG8gMC4yNVxuICAgIGNvbnN0IGRyYWdEaXN0YW5jZSA9IE1hdGguYWJzKHRoaXMuY3VycmVudFggLSB0aGlzLnN0YXJ0WCk7XG4gICAgY29uc3QgbW9tZW50dW1UaHJlc2hvbGQgPSAwLjI7IC8vIFJlZHVjZWQgZnJvbSAwLjMgdG8gMC4yXG4gICAgY29uc3QgaGFzU2lnbmlmaWNhbnRWZWxvY2l0eSA9IE1hdGguYWJzKHRoaXMudmVsb2NpdHkpID4gbW9tZW50dW1UaHJlc2hvbGQ7XG4gICAgXG4gICAgLy8gTW9yZSBsZW5pZW50IGNvbmRpdGlvbnMgZm9yIG1vYmlsZVxuICAgIGlmIChtb3ZlZEl0ZW1zRmxvYXQgPiBtaW5UaHJlc2hvbGQgfHwgaGFzU2lnbmlmaWNhbnRWZWxvY2l0eSB8fCBkcmFnRGlzdGFuY2UgPiA0MCkgeyAvLyBSZWR1Y2VkIGZyb20gNjBweCB0byA0MHB4XG4gICAgICBcbiAgICAgIC8vIENhbGN1bGF0ZSBob3cgbWFueSBpdGVtcyB0byBhZHZhbmNlIGJhc2VkIG9uIGFjdHVhbCBkcmFnIGRpc3RhbmNlXG4gICAgICBsZXQgaXRlbXNUb0FkdmFuY2UgPSBNYXRoLnJvdW5kKG1vdmVkSXRlbXNGbG9hdCk7XG4gICAgICBcbiAgICAgIC8vIEZvciB2ZWxvY2l0eS1iYXNlZCBtb3ZlbWVudCwgdXNlIGEgc2VwYXJhdGUgY2FsY3VsYXRpb25cbiAgICAgIGlmIChoYXNTaWduaWZpY2FudFZlbG9jaXR5ICYmIG1vdmVkSXRlbXNGbG9hdCA8IDEpIHtcbiAgICAgICAgY29uc3QgdmVsb2NpdHlNdWx0aXBsaWVyID0gTWF0aC5hYnModGhpcy52ZWxvY2l0eSkgKiAyO1xuICAgICAgICBpdGVtc1RvQWR2YW5jZSA9IE1hdGgubWF4KDEsIE1hdGguZmxvb3IodmVsb2NpdHlNdWx0aXBsaWVyKSk7XG4gICAgICB9XG4gICAgICBcbiAgICAgIC8vIEVuc3VyZSBtaW5pbXVtIDEgaXRlbSBmb3Igc2lnbmlmaWNhbnQgZHJhZ3MsIGJ1dCBkb24ndCBkb3VibGUgY291bnRcbiAgICAgIGlmIChpdGVtc1RvQWR2YW5jZSA9PT0gMCAmJiBtb3ZlZEl0ZW1zRmxvYXQgPj0gbWluVGhyZXNob2xkKSB7XG4gICAgICAgIGl0ZW1zVG9BZHZhbmNlID0gMTtcbiAgICAgIH1cbiAgICAgIFxuICAgICAgaWYgKHRoaXMuZHJhZ09mZnNldCA+IDAgfHwgKGhhc1NpZ25pZmljYW50VmVsb2NpdHkgJiYgdGhpcy52ZWxvY2l0eSA+IDApKSB7XG4gICAgICAgIC8vIERyYWdnZWQgcmlnaHQgLSBnbyB0byBwcmV2aW91cyBpdGVtc1xuICAgICAgICB0aGlzLmdvVG9QcmV2aW91c0l0ZW1zKGl0ZW1zVG9BZHZhbmNlKTtcbiAgICAgIH0gZWxzZSBpZiAodGhpcy5kcmFnT2Zmc2V0IDwgMCB8fCAoaGFzU2lnbmlmaWNhbnRWZWxvY2l0eSAmJiB0aGlzLnZlbG9jaXR5IDwgMCkpIHtcbiAgICAgICAgLy8gRHJhZ2dlZCBsZWZ0IC0gZ28gdG8gbmV4dCBpdGVtc1xuICAgICAgICB0aGlzLmdvVG9OZXh0SXRlbXMoaXRlbXNUb0FkdmFuY2UpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5zbmFwVG9OZWFyZXN0SXRlbSgpO1xuICAgICAgfVxuICAgIH0gZWxzZSB7XG4gICAgICAvLyBTbWFsbCBtb3ZlbWVudCAtIHNuYXAgdG8gbmVhcmVzdCBpdGVtXG4gICAgICB0aGlzLnNuYXBUb05lYXJlc3RJdGVtKCk7XG4gICAgfVxuXG4gICAgdGhpcy5kcmFnT2Zmc2V0ID0gMDtcbiAgICB0aGlzLnZlbG9jaXR5ID0gMDtcbiAgfVxuXG4gIHByaXZhdGUgc25hcFRvTmVhcmVzdEl0ZW0oKSB7XG4gICAgY29uc3QgY3VycmVudFRyYW5zbGF0ZVggPSB0aGlzLmluaXRpYWxUcmFuc2xhdGVYICsgdGhpcy5kcmFnT2Zmc2V0O1xuICAgIGNvbnN0IGl0ZW1TdGVwID0gdGhpcy5pdGVtV2lkdGggKyB0aGlzLmdhcDtcbiAgICBcbiAgICAvLyBGaW5kIHRoZSBjbG9zZXN0IHZhbGlkIHBvc2l0aW9uXG4gICAgbGV0IHRhcmdldEluZGV4ID0gTWF0aC5yb3VuZCgtY3VycmVudFRyYW5zbGF0ZVggLyBpdGVtU3RlcCk7XG4gICAgXG4gICAgLy8gQ2xhbXAgdG8gdmFsaWQgYm91bmRzXG4gICAgY29uc3QgbWF4SW5kZXggPSB0aGlzLmdldE1heEluZGV4KCk7XG4gICAgdGFyZ2V0SW5kZXggPSBNYXRoLm1heCgwLCBNYXRoLm1pbih0YXJnZXRJbmRleCwgbWF4SW5kZXgpKTtcbiAgICBcbiAgICB0aGlzLmN1cnJlbnRJbmRleCA9IHRhcmdldEluZGV4O1xuICAgIHRoaXMudXBkYXRlVHJhbnNmb3JtKCk7XG4gIH1cblxuICBwcml2YXRlIGdvVG9QcmV2aW91c0l0ZW1zKGl0ZW1Db3VudDogbnVtYmVyKSB7XG4gICAgLy8gVXNlIHRoZSBjdXJyZW50IGluZGV4IGluc3RlYWQgb2YgdmlzdWFsIGNhbGN1bGF0aW9uIHRvIGF2b2lkIGRvdWJsZSBtb3ZlbWVudFxuICAgIGNvbnN0IG5ld0luZGV4ID0gTWF0aC5tYXgoMCwgdGhpcy5jdXJyZW50SW5kZXggLSBpdGVtQ291bnQpO1xuICAgIFxuICAgIGlmIChuZXdJbmRleCAhPT0gdGhpcy5jdXJyZW50SW5kZXgpIHtcbiAgICAgIHRoaXMuY3VycmVudEluZGV4ID0gbmV3SW5kZXg7XG4gICAgICB0aGlzLnVwZGF0ZVRyYW5zZm9ybSgpO1xuICAgICAgdGhpcy5wcmV2aW91c0NsaWNrRXZlbnRFbWl0dGVyLmVtaXQoKTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5zbmFwVG9OZWFyZXN0SXRlbSgpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgZ29Ub05leHRJdGVtcyhpdGVtQ291bnQ6IG51bWJlcikge1xuICAgIC8vIFVzZSB0aGUgY3VycmVudCBpbmRleCBpbnN0ZWFkIG9mIHZpc3VhbCBjYWxjdWxhdGlvbiB0byBhdm9pZCBkb3VibGUgbW92ZW1lbnRcbiAgICBjb25zdCBtYXhJbmRleCA9IHRoaXMuZ2V0TWF4SW5kZXgoKTtcbiAgICBjb25zdCBuZXdJbmRleCA9IE1hdGgubWluKG1heEluZGV4LCB0aGlzLmN1cnJlbnRJbmRleCArIGl0ZW1Db3VudCk7XG4gICAgXG4gICAgaWYgKG5ld0luZGV4ICE9PSB0aGlzLmN1cnJlbnRJbmRleCkge1xuICAgICAgdGhpcy5jdXJyZW50SW5kZXggPSBuZXdJbmRleDtcbiAgICAgIHRoaXMudXBkYXRlVHJhbnNmb3JtKCk7XG4gICAgICB0aGlzLm5leHRDbGlja0V2ZW50RW1pdHRlci5lbWl0KCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMuc25hcFRvTmVhcmVzdEl0ZW0oKTtcbiAgICB9XG4gIH1cblxuICBjYW5Hb1ByZXZpb3VzKCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmN1cnJlbnRJbmRleCA+IDA7XG4gIH1cblxuICBjYW5Hb05leHQoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuY3VycmVudEluZGV4IDwgdGhpcy5nZXRNYXhJbmRleCgpO1xuICB9XG5cbiAgZ29Ub0ZpcnN0SXRlbSgpIHtcbiAgICB0aGlzLmN1cnJlbnRJbmRleCA9IDA7XG4gICAgdGhpcy51cGRhdGVUcmFuc2Zvcm0oKTtcbiAgfVxuXG4gIHByZXZJdGVtKCkge1xuICAgIGlmICh0aGlzLmNhbkdvUHJldmlvdXMoKSkge1xuICAgICAgdGhpcy5jdXJyZW50SW5kZXgtLTtcbiAgICAgIHRoaXMudXBkYXRlVHJhbnNmb3JtKCk7XG4gICAgICB0aGlzLnByZXZpb3VzQ2xpY2tFdmVudEVtaXR0ZXIuZW1pdCgpO1xuICAgIH1cbiAgfVxuXG4gIG5leHRJdGVtKCkge1xuICAgIGlmICh0aGlzLmNhbkdvTmV4dCgpKSB7XG4gICAgICB0aGlzLmN1cnJlbnRJbmRleCsrO1xuICAgICAgdGhpcy51cGRhdGVUcmFuc2Zvcm0oKTtcbiAgICAgIHRoaXMubmV4dENsaWNrRXZlbnRFbWl0dGVyLmVtaXQoKTtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIHVwZGF0ZVRyYW5zZm9ybSgpIHtcbiAgICBjb25zdCBpdGVtU3RlcCA9IHRoaXMuaXRlbVdpZHRoICsgdGhpcy5nYXA7XG4gICAgdGhpcy50cmFuc2xhdGVYID0gLXRoaXMuY3VycmVudEluZGV4ICogaXRlbVN0ZXA7XG4gICAgXG4gICAgLy8gQXBwbHkgc3RyaWN0IGJvdW5kYXJpZXMgdG8gZW5zdXJlIGxhc3QgaXRlbSBpcyBhbHdheXMgZnVsbHkgdmlzaWJsZVxuICAgIHRoaXMudHJhbnNsYXRlWCA9IE1hdGgubWF4KHRoaXMubWluVHJhbnNsYXRlWCwgTWF0aC5taW4odGhpcy5tYXhUcmFuc2xhdGVYLCB0aGlzLnRyYW5zbGF0ZVgpKTtcbiAgICBcbiAgICAvLyBSZWNhbGN1bGF0ZSBjdXJyZW50SW5kZXggYmFzZWQgb24gYWN0dWFsIHRyYW5zbGF0ZVggdG8gc3RheSBpbiBzeW5jXG4gICAgaWYgKHRoaXMudHJhbnNsYXRlWCA8PSB0aGlzLm1pblRyYW5zbGF0ZVgpIHtcbiAgICAgIHRoaXMuY3VycmVudEluZGV4ID0gdGhpcy5nZXRNYXhJbmRleCgpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmN1cnJlbnRJbmRleCA9IE1hdGgubWF4KDAsIE1hdGgubWluKHRoaXMuY3VycmVudEluZGV4LCB0aGlzLmdldE1heEluZGV4KCkpKTtcbiAgICB9XG4gICAgXG4gICAgaWYgKCF0aGlzLmlzRHJhZ2dpbmcgJiYgdGhpcy5zbGlkZXNDb250YWluZXIpIHtcbiAgICAgIHRoaXMucmVuZGVyZXIuc2V0U3R5bGUoXG4gICAgICAgIHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsIFxuICAgICAgICAndHJhbnNmb3JtJywgXG4gICAgICAgIGB0cmFuc2xhdGVYKCR7dGhpcy50cmFuc2xhdGVYfXB4KWBcbiAgICAgICk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBnZXRNYXhJbmRleCgpOiBudW1iZXIge1xuICAgIGNvbnN0IHZpc2libGVXaWR0aCA9IHRoaXMuY29udGFpbmVyV2lkdGg7XG4gICAgY29uc3QgdG90YWxJdGVtc1dpZHRoID0gdGhpcy5pdGVtcy5sZW5ndGggKiAodGhpcy5pdGVtV2lkdGggKyB0aGlzLmdhcCkgLSB0aGlzLmdhcDtcbiAgICBcbiAgICBpZiAodG90YWxJdGVtc1dpZHRoIDw9IHZpc2libGVXaWR0aCkge1xuICAgICAgcmV0dXJuIDA7XG4gICAgfVxuICAgIFxuICAgIC8vIENhbGN1bGF0ZSBob3cgbWFueSBjb21wbGV0ZSBpdGVtcyBjYW4gZml0IGluIHRoZSB2aXNpYmxlIGFyZWFcbiAgICBjb25zdCBpdGVtc1BlclZpZXcgPSBNYXRoLmZsb29yKHZpc2libGVXaWR0aCAvICh0aGlzLml0ZW1XaWR0aCArIHRoaXMuZ2FwKSk7XG4gICAgXG4gICAgLy8gTWF4aW11bSBpbmRleCBlbnN1cmVzIHRoZSBsYXN0IGl0ZW0gaXMgYWx3YXlzIGZ1bGx5IHZpc2libGVcbiAgICBjb25zdCBtYXhJbmRleCA9IE1hdGgubWF4KDAsIHRoaXMuaXRlbXMubGVuZ3RoIC0gaXRlbXNQZXJWaWV3KTtcbiAgICBcbiAgICByZXR1cm4gbWF4SW5kZXg7XG4gIH1cbn1cbiIsIjxkaXYgY2xhc3M9XCJjLWNhcm91c2VsLWZpeGVkLWNvbnRhaW5lclwiPlxuICA8ZGl2IFxuICAgIGNsYXNzPVwiYy1jYXJvdXNlbC1maXhlZC1zbGlkZXNcIiBcbiAgICAjc2xpZGVzQ29udGFpbmVyXG4gICAgW3N0eWxlLnRyYW5zZm9ybV09XCIndHJhbnNsYXRlWCgnICsgdHJhbnNsYXRlWCArICdweCknXCIgXG4gICAgKG1vdXNlZG93bik9XCJvbk1vdXNlRG93bigkZXZlbnQpXCJcbiAgICAobW91c2Vtb3ZlKT1cIm9uTW91c2VNb3ZlKCRldmVudClcIlxuICAgIChtb3VzZXVwKT1cIm9uTW91c2VVcCgkZXZlbnQpXCJcbiAgICAobW91c2VsZWF2ZSk9XCJvbk1vdXNlTGVhdmUoJGV2ZW50KVwiXG4gICAgKHRvdWNoc3RhcnQpPVwib25Ub3VjaFN0YXJ0KCRldmVudClcIiBcbiAgICAodG91Y2htb3ZlKT1cIm9uVG91Y2hNb3ZlKCRldmVudClcIiBcbiAgICAodG91Y2hlbmQpPVwib25Ub3VjaEVuZCgkZXZlbnQpXCI+XG4gICAgPG5nLWNvbnRlbnQ+PC9uZy1jb250ZW50PlxuICA8L2Rpdj5cblxuICA8ZGl2IGNsYXNzPVwiYy1jYXJvdXNlbC1maXhlZC1mb290ZXJcIiBbaGlkZGVuXT1cInJlbW92ZUFycm93c1wiPlxuICAgIDxidXR0b24gXG4gICAgICBjbGFzcz1cImMtY2Fyb3VzZWwtZml4ZWQtbmF2IHByZXZcIiBcbiAgICAgIFtkaXNhYmxlZF09XCIhY2FuR29QcmV2aW91cygpXCJcbiAgICAgIHRpdGxlPVwiSXRlbSBhbnRlcmlvclwiIFxuICAgICAgYXJpYS1sYWJlbD1cIkl0ZW0gYW50ZXJpb3JcIiBcbiAgICAgIChjbGljayk9XCJwcmV2SXRlbSgpXCI+XG4gICAgICA8bGliLWVsdXgtaWNvbiBbaWNvbl09XCInQ2hldnJvbl9MZWZ0LnN2ZydcIiBbc2l6ZV09XCInMTYnXCIgW3NpemVUeXBlXT1cIidweCdcIiBbY29sb3JdPVwiJyMwMjBGMkUnXCI+PC9saWItZWx1eC1pY29uPlxuICAgIDwvYnV0dG9uPlxuXG4gICAgPGJ1dHRvbiBcbiAgICAgIGNsYXNzPVwiYy1jYXJvdXNlbC1maXhlZC1uYXYgbmV4dFwiIFxuICAgICAgW2Rpc2FibGVkXT1cIiFjYW5Hb05leHQoKVwiXG4gICAgICB0aXRsZT1cIlByw7N4aW1vIGl0ZW1cIiBcbiAgICAgIGFyaWEtbGFiZWw9XCJQcsOzeGltbyBpdGVtXCIgXG4gICAgICAoY2xpY2spPVwibmV4dEl0ZW0oKVwiPlxuICAgICAgPGxpYi1lbHV4LWljb24gW2ljb25dPVwiJ0NoZXZyb25fUmlnaHQuc3ZnJ1wiIFtzaXplXT1cIicxNidcIiBbc2l6ZVR5cGVdPVwiJ3B4J1wiIFtjb2xvcl09XCInIzAyMEYyRSdcIj48L2xpYi1lbHV4LWljb24+XG4gICAgPC9idXR0b24+XG4gIDwvZGl2PlxuPC9kaXY+XG4iXX0=
|
|
468
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vdWkvbGlicmFyeS9zcmMvbGliL2NvbXBvbmVudHMvY2Fyb3VzZWwtZml4ZWQvY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vLi4vdWkvbGlicmFyeS9zcmMvbGliL2NvbXBvbmVudHMvY2Fyb3VzZWwtZml4ZWQvY2Fyb3VzZWwtZml4ZWQuY29tcG9uZW50Lmh0bWwiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBQy9DLE9BQU8sRUFBb0IsU0FBUyxFQUFFLGVBQWUsRUFBRSxVQUFVLEVBQUUsWUFBWSxFQUFFLEtBQUssRUFBYSxNQUFNLEVBQXdCLFNBQVMsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUNsSyxPQUFPLEVBQUUsUUFBUSxFQUFFLE1BQU0sU0FBUyxDQUFDOzs7QUFTbkMsTUFBTSxPQUFPLDBCQUEwQjtJQXVDckMsWUFBb0IsUUFBbUI7UUFBbkIsYUFBUSxHQUFSLFFBQVEsQ0FBVztRQWpDOUIsY0FBUyxHQUFXLEdBQUcsQ0FBQztRQUN4QixRQUFHLEdBQVcsRUFBRSxDQUFDO1FBQ2pCLGVBQVUsR0FBWSxJQUFJLENBQUM7UUFDM0IsYUFBUSxHQUFZLElBQUksQ0FBQztRQUV4Qiw4QkFBeUIsR0FBRyxJQUFJLFlBQVksRUFBUyxDQUFDO1FBQ3RELDBCQUFxQixHQUFHLElBQUksWUFBWSxFQUFTLENBQUM7UUFFNUQsaUJBQVksR0FBRyxDQUFDLENBQUM7UUFDakIsZUFBVSxHQUFHLENBQUMsQ0FBQztRQUVQLGVBQVUsR0FBRyxLQUFLLENBQUM7UUFDbkIsZ0JBQVcsR0FBRyxLQUFLLENBQUM7UUFDcEIsV0FBTSxHQUFHLENBQUMsQ0FBQztRQUNYLGFBQVEsR0FBRyxDQUFDLENBQUM7UUFDYixzQkFBaUIs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ekIsQ0FBQzsrR0E1ZlUsMEJBQTBCO21HQUExQiwwQkFBMEIsc1ZBQ0ksVUFBVSw4UENackQsdW9EQTRDQSwwekNEbkNZLFlBQVksZ1FBQUUsUUFBUTs7NEZBRXJCLDBCQUEwQjtrQkFQdEMsU0FBUztpQ0FDSSxJQUFJLFlBQ04seUJBQXlCLFdBRzFCLENBQUMsWUFBWSxFQUFFLFFBQVEsQ0FBQzs4RUFHc0IsS0FBSztzQkFBM0QsZUFBZTt1QkFBQyxjQUFjLEVBQUUsRUFBRSxJQUFJLEVBQUUsVUFBVSxFQUFFO2dCQUN2QixlQUFlO3NCQUE1QyxTQUFTO3VCQUFDLGlCQUFpQjtnQkFDeUIsbUJBQW1CO3NCQUF2RSxTQUFTO3VCQUFDLHFCQUFxQixFQUFFLEVBQUUsTUFBTSxFQUFFLEtBQUssRUFBRTtnQkFHMUMsU0FBUztzQkFBakIsS0FBSztnQkFDRyxHQUFHO3NCQUFYLEtBQUs7Z0JBQ0csVUFBVTtzQkFBbEIsS0FBSztnQkFDRyxRQUFRO3NCQUFoQixLQUFLO2dCQUVJLHlCQUF5QjtzQkFBbEMsTUFBTTtnQkFDRyxxQkFBcUI7c0JBQTlCLE1BQU0iLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBDb21tb25Nb2R1bGUgfSBmcm9tICdAYW5ndWxhci9jb21tb24nO1xuaW1wb3J0IHsgQWZ0ZXJDb250ZW50SW5pdCwgQ29tcG9uZW50LCBDb250ZW50Q2hpbGRyZW4sIEVsZW1lbnRSZWYsIEV2ZW50RW1pdHRlciwgSW5wdXQsIE9uRGVzdHJveSwgT3V0cHV0LCBRdWVyeUxpc3QsIFJlbmRlcmVyMiwgVmlld0NoaWxkIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBFbHV4SWNvbiB9IGZyb20gJy4uL2ljb24nO1xuXG5AQ29tcG9uZW50KHtcbiAgc3RhbmRhbG9uZTogdHJ1ZSxcbiAgc2VsZWN0b3I6ICdsaWItZWx1eC1jYXJvdXNlbC1maXhlZCcsXG4gIHRlbXBsYXRlVXJsOiAnLi9jYXJvdXNlbC1maXhlZC5jb21wb25lbnQuaHRtbCcsXG4gIHN0eWxlVXJsczogWycuL2Nhcm91c2VsLWZpeGVkLmNvbXBvbmVudC5zY3NzJ10sXG4gIGltcG9ydHM6IFtDb21tb25Nb2R1bGUsIEVsdXhJY29uXSxcbn0pXG5leHBvcnQgY2xhc3MgRWx1eENhcm91c2VsRml4ZWRDb21wb25lbnQgaW1wbGVtZW50cyBBZnRlckNvbnRlbnRJbml0LCBPbkRlc3Ryb3kge1xuICBAQ29udGVudENoaWxkcmVuKCdjYXJvdXNlbEl0ZW0nLCB7IHJlYWQ6IEVsZW1lbnRSZWYgfSkgaXRlbXMhOiBRdWVyeUxpc3Q8RWxlbWVudFJlZj47XG4gIEBWaWV3Q2hpbGQoJ3NsaWRlc0NvbnRhaW5lcicpIHNsaWRlc0NvbnRhaW5lciE6IEVsZW1lbnRSZWY7XG4gIEBWaWV3Q2hpbGQoJ3JpZ2h0QmxlZWRDb250YWluZXInLCB7IHN0YXRpYzogZmFsc2UgfSkgcmlnaHRCbGVlZENvbnRhaW5lciE6IEVsZW1lbnRSZWY8SFRNTERpdkVsZW1lbnQ+O1xuXG5cbiAgQElucHV0KCkgaXRlbVdpZHRoOiBudW1iZXIgPSAyMDA7XG4gIEBJbnB1dCgpIGdhcDogbnVtYmVyID0gMTY7XG4gIEBJbnB1dCgpIHNob3dBcnJvd3M6IGJvb2xlYW4gPSB0cnVlO1xuICBASW5wdXQoKSBzaG93RG90czogYm9vbGVhbiA9IHRydWU7XG5cbiAgQE91dHB1dCgpIHByZXZpb3VzQ2xpY2tFdmVudEVtaXR0ZXIgPSBuZXcgRXZlbnRFbWl0dGVyPEV2ZW50PigpO1xuICBAT3V0cHV0KCkgbmV4dENsaWNrRXZlbnRFbWl0dGVyID0gbmV3IEV2ZW50RW1pdHRlcjxFdmVudD4oKTtcblxuICBjdXJyZW50SW5kZXggPSAwO1xuICB0cmFuc2xhdGVYID0gMDtcblxuICBwcml2YXRlIGlzRHJhZ2dpbmcgPSBmYWxzZTtcbiAgcHJpdmF0ZSBpc01vdXNlRG93biA9IGZhbHNlO1xuICBwcml2YXRlIHN0YXJ0WCA9IDA7XG4gIHByaXZhdGUgY3VycmVudFggPSAwO1xuICBwcml2YXRlIGluaXRpYWxUcmFuc2xhdGVYID0gMDtcbiAgcHJpdmF0ZSBkcmFnT2Zmc2V0ID0gMDtcbiAgcHJpdmF0ZSBjb250YWluZXJXaWR0aCA9IDA7XG4gIHByaXZhdGUgbWF4VHJhbnNsYXRlWCA9IDA7XG4gIHByaXZhdGUgbWluVHJhbnNsYXRlWCA9IDA7XG4gIHByaXZhdGUgdmVsb2NpdHkgPSAwO1xuICBwcml2YXRlIGxhc3RNb3ZlVGltZSA9IDA7XG4gIHByaXZhdGUgbGFzdE1vdmVYID0gMDtcbiAgcHJpdmF0ZSB0b3VjaFN0YXJ0VGltZSA9IDA7XG4gIHByaXZhdGUgdG91Y2hTdGFydFggPSAwO1xuICBwcml2YXRlIHRvdWNoU3RhcnRZID0gMDtcbiAgcHJpdmF0ZSBpc1ZlcnRpY2FsU2Nyb2xsID0gZmFsc2U7XG4gIHByaXZhdGUgd2FzRHJhZ2dpbmcgPSBmYWxzZTtcbiAgcHJpdmF0ZSBjbGlja3NEaXNhYmxlZCA9IGZhbHNlO1xuICBwcml2YXRlIGNsaWNrTGlzdGVuZXJzOiAoKCkgPT4gdm9pZClbXSA9IFtdO1xuICBwcml2YXRlIGRyYWdTdGFydGVkID0gZmFsc2U7XG4gIHByaXZhdGUgbW91c2VEb3duVGltZSA9IDA7XG5cbiAgY29uc3RydWN0b3IocHJpdmF0ZSByZW5kZXJlcjogUmVuZGVyZXIyKSB7fVxuXG4gIHByaXZhdGUgY2FsY3VsYXRlUmlnaHRCbGVlZENvbnRhaW5lciA9ICgpID0+IHtcbiAgICBpZiAodGhpcy5yaWdodEJsZWVkQ29udGFpbmVyKSB7XG4gICAgICBjb25zdCBlbCA9IHRoaXMucmlnaHRCbGVlZENvbnRhaW5lci5uYXRpdmVFbGVtZW50O1xuICAgICAgY29uc3QgbGVmdCA9IGVsLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLmxlZnQ7XG5cbiAgICAgIGxldCBzY3JvbGxiYXJXaWR0aCA9IHdpbmRvdy5pbm5lcldpZHRoIC0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LmNsaWVudFdpZHRoO1xuICAgICAgc2Nyb2xsYmFyV2lkdGggPSBzY3JvbGxiYXJXaWR0aCA9PSAwIHx8IHNjcm9sbGJhcldpZHRoID4gMzAgPyAwIDogc2Nyb2xsYmFyV2lkdGg7ICAgICBcbiAgICAgIFxuICAgICAgZWwuc3R5bGUuc2V0UHJvcGVydHkoJy0tc2Nyb2xsYmFyLXdpZHRoJywgYCR7c2Nyb2xsYmFyV2lkdGh9cHhgKTtcbiAgICAgIGVsLnN0eWxlLnNldFByb3BlcnR5KCctLWxlZnQtb2Zmc2V0JywgYCR7bGVmdH1weGApO1xuICAgIH1cbiAgfTtcblxuICBuZ0FmdGVyQ29udGVudEluaXQoKSB7XG4gICAgc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICB0aGlzLmNhbGN1bGF0ZURpbWVuc2lvbnMoKTtcbiAgICAgIHRoaXMuc2V0SXRlbVdpZHRocygpO1xuICAgICAgdGhpcy51cGRhdGVMaW1pdHMoKTtcbiAgICAgIHRoaXMuc2V0dXBDbGlja1ByZXZlbnRpb24oKTtcblxuICAgICAgdGhpcy5pdGVtcy5jaGFuZ2VzLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgIHRoaXMuY2FsY3VsYXRlRGltZW5zaW9ucygpO1xuICAgICAgICB0aGlzLnNldEl0ZW1XaWR0aHMoKTtcbiAgICAgICAgdGhpcy51cGRhdGVMaW1pdHMoKTtcbiAgICAgICAgdGhpcy5nb1RvRmlyc3RJdGVtKCk7XG4gICAgICAgIHRoaXMuc2V0dXBDbGlja1ByZXZlbnRpb24oKTtcbiAgICAgICAgLy8gRm9yw6dhIGF0dWFsaXphw6fDo28gdmlzdWFsIGRvcyBkb3RzXG4gICAgICAgIGlmICgodGhpcyBhcyBhbnkpLmNkICYmIHR5cGVvZiAodGhpcyBhcyBhbnkpLmNkLmRldGVjdENoYW5nZXMgPT09ICdmdW5jdGlvbicpIHtcbiAgICAgICAgICAodGhpcyBhcyBhbnkpLmNkLmRldGVjdENoYW5nZXMoKTtcbiAgICAgICAgfVxuICAgICAgfSk7XG4gICAgfSwgMTApO1xuXG4gICAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ3Jlc2l6ZScsICgpID0+IHRoaXMub25SZXNpemUoKSk7XG4gIH1cblxuICBuZ09uRGVzdHJveSgpIHtcbiAgICAvLyBDbGVhbiB1cCBjbGljayBsaXN0ZW5lcnNcbiAgICB0aGlzLmNsaWNrTGlzdGVuZXJzLmZvckVhY2godW5saXN0ZW4gPT4gdW5saXN0ZW4oKSk7XG4gICAgdGhpcy5jbGlja0xpc3RlbmVycyA9IFtdO1xuICAgIHdpbmRvdy5yZW1vdmVFdmVudExpc3RlbmVyKCdyZXNpemUnLCAoKSA9PiB0aGlzLm9uUmVzaXplKCkpO1xuICB9XG5cbiAgcHJpdmF0ZSBjYWxjdWxhdGVEaW1lbnNpb25zKCkge1xuICAgIGlmICh0aGlzLnNsaWRlc0NvbnRhaW5lcikge1xuICAgICAgdGhpcy5jb250YWluZXJXaWR0aCA9IHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQub2Zmc2V0V2lkdGg7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVMaW1pdHMoKSB7XG4gICAgY29uc3QgdG90YWxXaWR0aCA9IHRoaXMuaXRlbXMubGVuZ3RoICogKHRoaXMuaXRlbVdpZHRoICsgdGhpcy5nYXApO1xuICAgIHRoaXMubWF4VHJhbnNsYXRlWCA9IDA7XG4gICAgXG4gICAgaWYgKHRvdGFsV2lkdGggPiB0aGlzLmNvbnRhaW5lcldpZHRoKSB7XG4gICAgICB0aGlzLm1pblRyYW5zbGF0ZVggPSB0aGlzLmNvbnRhaW5lcldpZHRoIC0gdG90YWxXaWR0aDtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5taW5UcmFuc2xhdGVYID0gMDtcbiAgICB9XG4gIH1cblxuICBwcml2YXRlIG9uUmVzaXplKCkge1xuICAgIHRoaXMuY2FsY3VsYXRlUmlnaHRCbGVlZENvbnRhaW5lcigpO1xuICAgIHRoaXMuY2FsY3VsYXRlRGltZW5zaW9ucygpO1xuICAgIHRoaXMudXBkYXRlTGltaXRzKCk7XG5cbiAgICAvLyBHYXJhbnRlIHF1ZSBvIGN1cnJlbnRJbmRleCBuw6NvIHVsdHJhcGFzc2UgbyBub3ZvIG3DoXhpbW9cbiAgICBjb25zdCBtYXhJbmRleCA9IHRoaXMuZ2V0TWF4SW5kZXgoKTtcbiAgICBpZiAodGhpcy5jdXJyZW50SW5kZXggPiBtYXhJbmRleCkge1xuICAgICAgdGhpcy5jdXJyZW50SW5kZXggPSBtYXhJbmRleDtcbiAgICB9XG5cbiAgICB0aGlzLnVwZGF0ZVRyYW5zZm9ybSgpO1xuICAgIFxuICAgIC8vIEZvcsOnYSBkZXRlY8Onw6NvIGRlIG11ZGFuw6dhcyBwYXJhIGF0dWFsaXphciBkb3RzXG4gICAgaWYgKCh3aW5kb3cgYXMgYW55KS5uZyAmJiAod2luZG93IGFzIGFueSkubmcuZ2V0SW5qZWN0b3IpIHtcbiAgICAgIC8vIEFuZ3VsYXIgRGV2VG9vbHMgcHJlc2VudGUsIG7Do28gZmF6IG5hZGFcbiAgICB9IGVsc2UgaWYgKCh0aGlzIGFzIGFueSkuY2QgJiYgdHlwZW9mICh0aGlzIGFzIGFueSkuY2QuZGV0ZWN0Q2hhbmdlcyA9PT0gJ2Z1bmN0aW9uJykge1xuICAgICAgKHRoaXMgYXMgYW55KS5jZC5kZXRlY3RDaGFuZ2VzKCk7XG4gICAgfVxuICB9XG5cbiAgbmdBZnRlclZpZXdJbml0KCkge1xuICAgIC8vIEdhcmFudGUgY8OhbGN1bG8gY29ycmV0byBhcMOzcyB2aWV3IGNhcnJlZ2FkYVxuICAgIHNldFRpbWVvdXQoKCkgPT4ge1xuICAgICAgdGhpcy5jYWxjdWxhdGVSaWdodEJsZWVkQ29udGFpbmVyKCk7XG4gICAgICB0aGlzLmNhbGN1bGF0ZURpbWVuc2lvbnMoKTtcbiAgICAgIHRoaXMudXBkYXRlTGltaXRzKCk7XG4gICAgICB0aGlzLnVwZGF0ZVRyYW5zZm9ybSgpO1xuICAgIH0pO1xuICB9XG5cbiAgcHJpdmF0ZSBzZXRJdGVtV2lkdGhzKCkge1xuICAgIHRoaXMuaXRlbXMuZm9yRWFjaCgoaXRlbSkgPT4ge1xuICAgICAgdGhpcy5yZW5kZXJlci5zZXRTdHlsZShpdGVtLm5hdGl2ZUVsZW1lbnQsICd3aWR0aCcsIGAke3RoaXMuaXRlbVdpZHRofXB4YCk7XG4gICAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKGl0ZW0ubmF0aXZlRWxlbWVudCwgJ2ZsZXgtc2hyaW5rJywgJzAnKTtcbiAgICAgIHRoaXMucmVuZGVyZXIuc2V0U3R5bGUoaXRlbS5uYXRpdmVFbGVtZW50LCAnbWFyZ2luLXJpZ2h0JywgYCR7dGhpcy5nYXB9cHhgKTtcbiAgICB9KTtcbiAgfVxuXG4gIC8vIE1vdXNlIGV2ZW50c1xuICBvbk1vdXNlRG93bihldmVudDogTW91c2VFdmVudCkge1xuICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgdGhpcy5tb3VzZURvd25UaW1lID0gRGF0ZS5ub3coKTtcbiAgICB0aGlzLmRyYWdTdGFydGVkID0gZmFsc2U7XG4gICAgdGhpcy5pc01vdXNlRG93biA9IHRydWU7XG4gICAgdGhpcy53YXNEcmFnZ2luZyA9IGZhbHNlO1xuICAgIHRoaXMuY2xpY2tzRGlzYWJsZWQgPSBmYWxzZTtcbiAgICB0aGlzLnN0YXJ0WCA9IGV2ZW50LmNsaWVudFg7XG4gICAgdGhpcy5jdXJyZW50WCA9IGV2ZW50LmNsaWVudFg7XG4gICAgdGhpcy5pbml0aWFsVHJhbnNsYXRlWCA9IHRoaXMudHJhbnNsYXRlWDtcbiAgICB0aGlzLmRyYWdPZmZzZXQgPSAwO1xuICAgIHRoaXMudmVsb2NpdHkgPSAwO1xuICAgIHRoaXMubGFzdE1vdmVUaW1lID0gRGF0ZS5ub3coKTtcbiAgICB0aGlzLmxhc3RNb3ZlWCA9IGV2ZW50LmNsaWVudFg7XG4gICAgXG4gICAgdGhpcy5jYWxjdWxhdGVEaW1lbnNpb25zKCk7XG4gICAgXG4gICAgdGhpcy5yZW5kZXJlci5zZXRTdHlsZSh0aGlzLnNsaWRlc0NvbnRhaW5lci5uYXRpdmVFbGVtZW50LCAndHJhbnNpdGlvbicsICdub25lJyk7XG4gIH1cblxuICBvbk1vdXNlTW92ZShldmVudDogTW91c2VFdmVudCkge1xuICAgIGlmICghdGhpcy5pc01vdXNlRG93bikgcmV0dXJuO1xuICAgIFxuICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgXG4gICAgY29uc3QgZHJhZ0Rpc3RhbmNlID0gTWF0aC5hYnMoZXZlbnQuY2xpZW50WCAtIHRoaXMuc3RhcnRYKTtcbiAgICBcbiAgICAvLyBPbmx5IHN0YXJ0IGRyYWdnaW5nIGlmIG1vdmVkIG1vcmUgdGhhbiA1cHhcbiAgICBpZiAoZHJhZ0Rpc3RhbmNlID4gNSAmJiAhdGhpcy5pc0RyYWdnaW5nKSB7XG4gICAgICB0aGlzLmlzRHJhZ2dpbmcgPSB0cnVlO1xuICAgICAgdGhpcy5kcmFnU3RhcnRlZCA9IHRydWU7XG4gICAgICB0aGlzLndhc0RyYWdnaW5nID0gdHJ1ZTtcbiAgICB9XG4gICAgXG4gICAgaWYgKHRoaXMuaXNEcmFnZ2luZykge1xuICAgICAgdGhpcy51cGRhdGVEcmFnKGV2ZW50LmNsaWVudFgpO1xuICAgIH1cbiAgfVxuXG4gIG9uTW91c2VVcChldmVudDogTW91c2VFdmVudCkge1xuICAgIGlmICghdGhpcy5pc01vdXNlRG93bikgcmV0dXJuO1xuICAgIFxuICAgIHRoaXMuaXNNb3VzZURvd24gPSBmYWxzZTtcbiAgICBcbiAgICBpZiAodGhpcy5pc0RyYWdnaW5nKSB7XG4gICAgICBjb25zdCBtb3VzZVVwVGltZSA9IERhdGUubm93KCk7XG4gICAgICBjb25zdCBob2xkRHVyYXRpb24gPSBtb3VzZVVwVGltZSAtIHRoaXMubW91c2VEb3duVGltZTtcbiAgICAgIGNvbnN0IG1vdXNlRGlzdGFuY2UgPSBNYXRoLmFicyh0aGlzLmN1cnJlbnRYIC0gdGhpcy5zdGFydFgpO1xuICAgICAgXG4gICAgICBpZiAobW91c2VEaXN0YW5jZSA+IDUgfHwgKGhvbGREdXJhdGlvbiA+IDIwMCAmJiBtb3VzZURpc3RhbmNlID4gMCkpIHtcbiAgICAgICAgdGhpcy53YXNEcmFnZ2luZyA9IHRydWU7XG4gICAgICB9XG4gICAgICBcbiAgICAgIHRoaXMuZW5kRHJhZygpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBSZXNldCB0cmFuc2l0aW9uIGlmIGl0IHdhcyBqdXN0IGEgY2xpY2tcbiAgICAgIHRoaXMucmVuZGVyZXIuc2V0U3R5bGUodGhpcy5zbGlkZXNDb250YWluZXIubmF0aXZlRWxlbWVudCwgJ3RyYW5zaXRpb24nLCAndHJhbnNmb3JtIDAuM3MgZWFzZS1vdXQnKTtcbiAgICB9XG4gIH1cblxuICBvbk1vdXNlTGVhdmUoZXZlbnQ6IE1vdXNlRXZlbnQpIHtcbiAgICBpZiAodGhpcy5pc0RyYWdnaW5nKSB7XG4gICAgICB0aGlzLndhc0RyYWdnaW5nID0gdHJ1ZTtcbiAgICAgIHRoaXMuZW5kRHJhZygpO1xuICAgIH1cbiAgICB0aGlzLmlzTW91c2VEb3duID0gZmFsc2U7XG4gIH1cblxuICAvLyBUb3VjaCBldmVudHNcbiAgb25Ub3VjaFN0YXJ0KGV2ZW50OiBUb3VjaEV2ZW50KSB7XG4gICAgdGhpcy50b3VjaFN0YXJ0VGltZSA9IERhdGUubm93KCk7XG4gICAgdGhpcy50b3VjaFN0YXJ0WCA9IGV2ZW50LnRvdWNoZXNbMF0uY2xpZW50WDtcbiAgICB0aGlzLnRvdWNoU3RhcnRZID0gZXZlbnQudG91Y2hlc1swXS5jbGllbnRZO1xuICAgIHRoaXMuaXNWZXJ0aWNhbFNjcm9sbCA9IGZhbHNlO1xuICAgIHRoaXMuaXNNb3VzZURvd24gPSB0cnVlO1xuICAgIHRoaXMud2FzRHJhZ2dpbmcgPSBmYWxzZTtcbiAgICB0aGlzLmRyYWdTdGFydGVkID0gZmFsc2U7XG4gICAgdGhpcy5jbGlja3NEaXNhYmxlZCA9IGZhbHNlO1xuICAgIHRoaXMuc3RhcnRYID0gZXZlbnQudG91Y2hlc1swXS5jbGllbnRYO1xuICAgIHRoaXMuY3VycmVudFggPSBldmVudC50b3VjaGVzWzBdLmNsaWVudFg7XG4gICAgdGhpcy5pbml0aWFsVHJhbnNsYXRlWCA9IHRoaXMudHJhbnNsYXRlWDtcbiAgICB0aGlzLmRyYWdPZmZzZXQgPSAwO1xuICAgIHRoaXMudmVsb2NpdHkgPSAwO1xuICAgIHRoaXMubGFzdE1vdmVUaW1lID0gRGF0ZS5ub3coKTtcbiAgICB0aGlzLmxhc3RNb3ZlWCA9IGV2ZW50LnRvdWNoZXNbMF0uY2xpZW50WDtcbiAgICBcbiAgICB0aGlzLmNhbGN1bGF0ZURpbWVuc2lvbnMoKTtcbiAgICBcbiAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsICd0cmFuc2l0aW9uJywgJ25vbmUnKTtcbiAgfVxuXG4gIG9uVG91Y2hNb3ZlKGV2ZW50OiBUb3VjaEV2ZW50KSB7XG4gICAgaWYgKCF0aGlzLmlzTW91c2VEb3duKSByZXR1cm47XG4gICAgXG4gICAgY29uc3QgY3VycmVudFggPSBldmVudC50b3VjaGVzWzBdLmNsaWVudFg7XG4gICAgY29uc3QgY3VycmVudFkgPSBldmVudC50b3VjaGVzWzBdLmNsaWVudFk7XG4gICAgY29uc3QgZGVsdGFYID0gTWF0aC5hYnMoY3VycmVudFggLSB0aGlzLnRvdWNoU3RhcnRYKTtcbiAgICBjb25zdCBkZWx0YVkgPSBNYXRoLmFicyhjdXJyZW50WSAtIHRoaXMudG91Y2hTdGFydFkpO1xuICAgIFxuICAgIC8vIENoZWNrIGlmIHRoaXMgaXMgYSB2ZXJ0aWNhbCBzY3JvbGxcbiAgICBpZiAoZGVsdGFZID4gZGVsdGFYICYmIGRlbHRhWSA+IDEwKSB7XG4gICAgICB0aGlzLmlzVmVydGljYWxTY3JvbGwgPSB0cnVlO1xuICAgICAgdGhpcy5pc0RyYWdnaW5nID0gZmFsc2U7XG4gICAgICB0aGlzLmlzTW91c2VEb3duID0gZmFsc2U7XG4gICAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsICd0cmFuc2l0aW9uJywgJ3RyYW5zZm9ybSAwLjNzIGVhc2Utb3V0Jyk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIFxuICAgIC8vIFN0YXJ0IGRyYWdnaW5nIGlmIGhvcml6b250YWwgbW92ZW1lbnQgPiAxMHB4XG4gICAgaWYgKGRlbHRhWCA+IDEwICYmICF0aGlzLmlzRHJhZ2dpbmcpIHtcbiAgICAgIHRoaXMuaXNEcmFnZ2luZyA9IHRydWU7XG4gICAgICB0aGlzLmRyYWdTdGFydGVkID0gdHJ1ZTtcbiAgICAgIHRoaXMud2FzRHJhZ2dpbmcgPSB0cnVlO1xuICAgIH1cbiAgICBcbiAgICBpZiAodGhpcy5pc0RyYWdnaW5nICYmIGRlbHRhWCA+IDEwKSB7XG4gICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuICAgICAgdGhpcy51cGRhdGVEcmFnKGN1cnJlbnRYKTtcbiAgICB9XG4gIH1cblxuICBvblRvdWNoRW5kKGV2ZW50OiBUb3VjaEV2ZW50KSB7XG4gICAgaWYgKHRoaXMuaXNWZXJ0aWNhbFNjcm9sbCkge1xuICAgICAgdGhpcy5pc1ZlcnRpY2FsU2Nyb2xsID0gZmFsc2U7XG4gICAgICB0aGlzLmlzTW91c2VEb3duID0gZmFsc2U7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIFxuICAgIHRoaXMuaXNNb3VzZURvd24gPSBmYWxzZTtcbiAgICBcbiAgICBjb25zdCB0b3VjaER1cmF0aW9uID0gRGF0ZS5ub3coKSAtIHRoaXMudG91Y2hTdGFydFRpbWU7XG4gICAgY29uc3QgdG91Y2hEaXN0YW5jZSA9IE1hdGguYWJzKHRoaXMuY3VycmVudFggLSB0aGlzLnN0YXJ0WCk7XG4gICAgXG4gICAgLy8gTWFyayBhcyBkcmFnZ2luZyBpZiBzaWduaWZpY2FudCBtb3ZlbWVudCBvY2N1cnJlZFxuICAgIGlmICh0b3VjaERpc3RhbmNlID4gMTAgfHwgdG91Y2hEdXJhdGlvbiA+IDMwMCkge1xuICAgICAgdGhpcy53YXNEcmFnZ2luZyA9IHRydWU7XG4gICAgfVxuICAgIFxuICAgIGlmICh0aGlzLmlzRHJhZ2dpbmcpIHtcbiAgICAgIHRoaXMuZW5kRHJhZygpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBSZXNldCB0cmFuc2l0aW9uIGlmIGl0IHdhcyBqdXN0IGEgdGFwXG4gICAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKHRoaXMuc2xpZGVzQ29udGFpbmVyLm5hdGl2ZUVsZW1lbnQsICd0cmFuc2l0aW9uJywgJ3RyYW5zZm9ybSAwLjNzIGVhc2Utb3V0Jyk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBzZXR1cENsaWNrUHJldmVudGlvbigpIHtcbiAgICAvLyBDbGVhbiB1cCBleGlzdGluZyBsaXN0ZW5lcnNcbiAgICB0aGlzLmNsaWNrTGlzdGVuZXJzLmZvckVhY2godW5saXN0ZW4gPT4gdW5saXN0ZW4oKSk7XG4gICAgdGhpcy5jbGlja0xpc3RlbmVycyA9IFtdO1xuXG4gICAgdGhpcy5pdGVtcy5mb3JFYWNoKChpdGVtKSA9PiB7XG4gICAgICAvLyBPbmx5IHByZXZlbnQgY2xpY2sgZXZlbnRzLCBub3QgbW91c2V1cCB3aGljaCBpcyBuZWVkZWQgZm9yIGRyYWcgZnVuY3Rpb25hbGl0eVxuICAgICAgY29uc3QgZXZlbnRIYW5kbGVyID0gKGV2ZW50OiBFdmVudCkgPT4ge1xuICAgICAgICBpZiAoZXZlbnQudHlwZSA9PT0gJ2NsaWNrJyAmJiAodGhpcy53YXNEcmFnZ2luZyB8fCB0aGlzLmNsaWNrc0Rpc2FibGVkIHx8IHRoaXMuZHJhZ1N0YXJ0ZWQpKSB7XG4gICAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICAgICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcbiAgICAgICAgICBldmVudC5zdG9wSW1tZWRpYXRlUHJvcGFnYXRpb24oKTtcbiAgICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgICAgIH1cbiAgICAgICAgcmV0dXJuIHRydWU7XG4gICAgICB9O1xuXG4gICAgICAvLyBPbmx5IGxpc3RlbiB0byBjbGljayBldmVudHMgdG8gYXZvaWQgaW50ZXJmZXJpbmcgd2l0aCBkcmFnIGZ1bmN0aW9uYWxpdHlcbiAgICAgIGl0ZW0ubmF0aXZlRWxlbWVudC5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsIGV2ZW50SGFuZGxlciwgdHJ1ZSk7XG4gICAgICBcbiAgICAgIHRoaXMuY2xpY2tMaXN0ZW5lcnMucHVzaCgoKSA9PiB7XG4gICAgICAgIGl0ZW0ubmF0aXZlRWxlbWVudC5yZW1vdmVFdmVudExpc3RlbmVyKCdjbGljaycsIGV2ZW50SGFuZGxlciwgdHJ1ZSk7XG4gICAgICB9KTtcbiAgICB9KTtcbiAgfVxuXG4gIHByaXZhdGUgdXBkYXRlRHJhZyhjbGllbnRYOiBudW1iZXIpIHtcbiAgICBpZiAoIXRoaXMuaXNEcmFnZ2luZykgcmV0dXJuO1xuXG4gICAgdGhpcy5jdXJyZW50WCA9IGNsaWVudFg7XG4gICAgY29uc3QgdG90YWxEZWx0YVggPSB0aGlzLmN1cnJlbnRYIC0gdGhpcy5zdGFydFg7XG4gICAgXG4gICAgLy8gTWFyayBhcyBkcmFnZ2luZyBpZiBtb3ZlbWVudCBpcyBzaWduaWZpY2FudFxuICAgIGlmIChNYXRoLmFicyh0b3RhbERlbHRhWCkgPiA1KSB7XG4gICAgICB0aGlzLndhc0RyYWdnaW5nID0gdHJ1ZTtcbiAgICAgIHRoaXMuZHJhZ1N0YXJ0ZWQgPSB0cnVlO1xuICAgIH1cbiAgICBcbiAgICBjb25zdCBub3cgPSBEYXRlLm5vdygpO1xuICAgIGNvbnN0IHRpbWVEZWx0YSA9IG5vdyAtIHRoaXMubGFzdE1vdmVUaW1lO1xuICAgIGlmICh0aW1lRGVsdGEgPiAwKSB7XG4gICAgICB0aGlzLnZlbG9jaXR5ID0gKGNsaWVudFggLSB0aGlzLmxhc3RNb3ZlWCkgLyB0aW1lRGVsdGE7XG4gICAgfVxuICAgIHRoaXMubGFzdE1vdmVUaW1lID0gbm93O1xuICAgIHRoaXMubGFzdE1vdmVYID0gY2xpZW50WDtcblxuICAgIGxldCByZXNpc3RlZERlbHRhWCA9IHRvdGFsRGVsdGFYO1xuICAgIGNvbnN0IHBvdGVudGlhbFRyYW5zbGF0ZVggPSB0aGlzLmluaXRpYWxUcmFuc2xhdGVYICsgdG90YWxEZWx0YVg7XG4gICAgXG4gICAgLy8gQXBwbHkgc29mdGVyIHJlc2lzdGFuY2UgYXQgYm91bmRhcmllc1xuICAgIGlmIChwb3RlbnRpYWxUcmFuc2xhdGVYID4gdGhpcy5tYXhUcmFuc2xhdGVYKSB7XG4gICAgICBjb25zdCBvdmVyRHJhZyA9IHBvdGVudGlhbFRyYW5zbGF0ZVggLSB0aGlzLm1heFRyYW5zbGF0ZVg7XG4gICAgICByZXNpc3RlZERlbHRhWCA9IHRvdGFsRGVsdGFYIC0gKG92ZXJEcmFnICogMC41KTtcbiAgICB9IGVsc2UgaWYgKHBvdGVudGlhbFRyYW5zbGF0ZVggPCB0aGlzLm1pblRyYW5zbGF0ZVgpIHtcbiAgICAgIGNvbnN0IG92ZXJEcmFnID0gdGhpcy5taW5UcmFuc2xhdGVYIC0gcG90ZW50aWFsVHJhbnNsYXRlWDtcbiAgICAgIHJlc2lzdGVkRGVsdGFYID0gdG90YWxEZWx0YVggKyAob3ZlckRyYWcgKiAwLjUpO1xuICAgIH1cblxuICAgIHRoaXMuZHJhZ09mZnNldCA9IHJlc2lzdGVkRGVsdGFYO1xuICAgIHRoaXMudXBkYXRlRHJhZ1Bvc2l0aW9uKCk7XG4gIH1cblxuICBwcml2YXRlIHVwZGF0ZURyYWdQb3NpdGlvbigpIHtcbiAgICBjb25zdCBuZXdUcmFuc2xhdGVYID0gdGhpcy5pbml0aWFsVHJhbnNsYXRlWCArIHRoaXMuZHJhZ09mZnNldDtcbiAgICB0aGlzLnJlbmRlcmVyLnNldFN0eWxlKFxuICAgICAgdGhpcy5zbGlkZXNDb250YWluZXIubmF0aXZlRWxlbWVudCwgXG4gICAgICAndHJhbnNmb3JtJywgXG4gICAgICBgdHJhbnNsYXRlWCgke25ld1RyYW5zbGF0ZVh9cHgpYFxuICAgICk7XG4gIH1cblxuICBwcml2YXRlIGVuZERyYWcoKSB7XG4gICAgaWYgKCF0aGlzLmlzRHJhZ2dpbmcpIHJldHVybjtcblxuICAgIHRoaXMuaXNEcmFnZ2luZyA9IGZhbHNlO1xuICAgIFxuICAgIC8vIERpc2FibGUgY2xpY2tzIHRlbXBvcmFyaWx5IGFmdGVyIGFueSBkcmFnXG4gICAgaWYgKHRoaXMud2FzRHJhZ2dpbmcgfHwgdGhpcy5kcmFnU3RhcnRlZCkge1xuICAgICAgdGhpcy5jbGlja3NEaXNhYmxlZCA9IHRydWU7XG4gICAgICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgdGhpcy5jbGlja3NEaXNhYmxlZCA9IGZhbHNlO1xuICAgICAgfSwgMjAwKTtcbiAgICB9XG4gICAgXG4gICAgLy8gQ2xlYXIgdGhlIHdhc0RyYWdnaW5nIGFuZCBkcmFnU3RhcnRlZCBmbGFncyBhZnRlciBhIHNob3J0ZXIgZGVsYXlcbiAgICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgIHRoaXMud2FzRHJhZ2dpbmcgPSBmYWxzZTtcbiAgICAgIHRoaXMuZHJhZ1N0YXJ0ZWQgPSBmYWxzZTtcbiAgICB9LCAyNTApO1xuICAgIFxuICAgIHRoaXMucmVuZGVyZXIuc2V0U3R5bGUodGhpcy5zbGlkZXNDb250YWluZXIubmF0aXZlRWxlbWVudCwgJ3RyYW5zaXRpb24nLCAndHJhbnNmb3JtIDAuM3MgZWFzZS1vdXQnKTtcblxuICAgIC8vIFNuYXAgc2VtcHJlIHBhcmEgbyBpbsOtY2lvIGRhIHDDoWdpbmEgbWFpcyBwcsOzeGltYVxuICAgIHRoaXMuc25hcFRvTmVhcmVzdEl0ZW0oKTtcblxuICAgIHRoaXMuZHJhZ09mZnNldCA9IDA7XG4gICAgdGhpcy52ZWxvY2l0eSA9IDA7XG4gIH1cblxuICBwcml2YXRlIGdldE1heEluZGV4KCk6IG51bWJlciB7XG4gICAgLy8gUGVybWl0ZSBhdmFuw6dhciBhdMOpIHF1ZSBvIMO6bHRpbW8gaXRlbSBlc3RlamEgdmlzw612ZWwgKG7Do28gbmVjZXNzYXJpYW1lbnRlIGFsaW5oYWRvIMOgIGVzcXVlcmRhKVxuICAgIGlmICghdGhpcy5pdGVtcyB8fCB0aGlzLml0ZW1zLmxlbmd0aCA9PT0gMCkgcmV0dXJuIDA7XG4gICAgY29uc3QgdmlzaWJsZUNvdW50ID0gTWF0aC5tYXgoMSwgTWF0aC5mbG9vcih0aGlzLmNvbnRhaW5lcldpZHRoIC8gKHRoaXMuaXRlbVdpZHRoICsgdGhpcy5nYXApKSk7XG4gICAgaWYgKHRoaXMuaXRlbXMubGVuZ3RoIDw9IHZpc2libGVDb3VudCkgcmV0dXJuIDA7XG4gICAgLy8gw5psdGltYSBwb3Npw6fDo28gb25kZSBvIMO6bHRpbW8gaXRlbSBhcGFyZWNlIHZpc8OtdmVsXG4gICAgcmV0dXJuIHRoaXMuaXRlbXMubGVuZ3RoIC0gdmlzaWJsZUNvdW50O1xuICB9XG5cbiAgY2FuR29OZXh0KCk6IGJvb2xlYW4ge1xuICAgIHJldHVybiB0aGlzLmN1cnJlbnRJbmRleCA8IHRoaXMuZ2V0TWF4SW5kZXgoKTtcbiAgfVxuXG4gIG5leHRJdGVtKCkge1xuICAgIGNvbnN0IG1heEluZGV4ID0gdGhpcy5nZXRNYXhJbmRleCgpO1xuICAgIGlmICh0aGlzLmNhbkdvTmV4dCgpKSB7XG4gICAgICBsZXQgbmV3SW5kZXggPSB0aGlzLmN1cnJlbnRJbmRleCArIDE7XG4gICAgICBpZiAobmV3SW5kZXggPiBtYXhJbmRleCkgbmV3SW5kZXggPSBtYXhJbmRleDtcbiAgICAgIHRoaXMuY3VycmVudEluZGV4ID0gbmV3SW5kZXg7XG4gICAgICB0aGlzLnVwZGF0ZVRyYW5zZm9ybSgpO1xuICAgICAgdGhpcy5uZXh0Q2xpY2tFdmVudEVtaXR0ZXIuZW1pdCgpO1xuICAgIH1cbiAgfVxuXG4gIGNhbkdvUHJldmlvdXMoKTogYm9vbGVhbiB7XG4gICAgcmV0dXJuIHRoaXMuY3VycmVudEluZGV4ID4gMDtcbiAgfVxuXG4gIHByZXZJdGVtKCkge1xuICAgIGlmICh0aGlzLmNhbkdvUHJldmlvdXMoKSkge1xuICAgICAgbGV0IG5ld0luZGV4ID0gdGhpcy5jdXJyZW50SW5kZXggLSAxO1xuICAgICAgaWYgKG5ld0luZGV4IDwgMCkgbmV3SW5kZXggPSAwO1xuICAgICAgdGhpcy5jdXJyZW50SW5kZXggPSBuZXdJbmRleDtcbiAgICAgIHRoaXMudXBkYXRlVHJhbnNmb3JtKCk7XG4gICAgICB0aGlzLnByZXZpb3VzQ2xpY2tFdmVudEVtaXR0ZXIuZW1pdCgpO1xuICAgIH1cbiAgfVxuXG4gIGdvVG9Eb3QoZG90SW5kZXg6IG51bWJlcikge1xuICAgIGNvbnN0IG1heEluZGV4ID0gdGhpcy5nZXRNYXhJbmRleCgpO1xuICAgIGxldCBuZXdJbmRleCA9IGRvdEluZGV4O1xuICAgIGlmIChuZXdJbmRleCA+IG1heEluZGV4KSBuZXdJbmRleCA9IG1heEluZGV4O1xuICAgIHRoaXMuY3VycmVudEluZGV4ID0gbmV3SW5kZXg7XG4gICAgdGhpcy51cGRhdGVUcmFuc2Zvcm0oKTtcbiAgfVxuXG4gIHByaXZhdGUgc25hcFRvTmVhcmVzdEl0ZW0oKSB7XG4gICAgY29uc3QgaXRlbVN0ZXAgPSB0aGlzLml0ZW1XaWR0aCArIHRoaXMuZ2FwO1xuICAgIGNvbnN0IHBvc2l0aW9uID0gLSh0aGlzLmluaXRpYWxUcmFuc2xhdGVYICsgdGhpcy5kcmFnT2Zmc2V0KSAvIGl0ZW1TdGVwO1xuICAgIFxuICAgIC8vIFRocmVzaG9sZDogMC4zID0gMzAlLCAwLjUgPSA1MCUgKHBhZHLDo28pXG4gICAgY29uc3QgdGhyZXNob2xkID0gMC4zO1xuICAgIFxuICAgIGxldCB0YXJnZXRJbmRleDogbnVtYmVyO1xuICAgIFxuICAgIC8vIENhbGN1bGEgcXVhbnRvcyBpdGVucyBjb21wbGV0b3MgZm9yYW0gYXJyYXN0YWRvc1xuICAgIGNvbnN0IGl0ZW1zTW92ZWQgPSBNYXRoLmZsb29yKE1hdGguYWJzKHBvc2l0aW9uIC0gdGhpcy5jdXJyZW50SW5kZXgpKTtcbiAgICBjb25zdCBkZWNpbWFsID0gTWF0aC5hYnMocG9zaXRpb24gLSB0aGlzLmN1cnJlbnRJbmRleCkgLSBpdGVtc01vdmVkO1xuICAgIFxuICAgIGlmIChwb3NpdGlvbiA+IHRoaXMuY3VycmVudEluZGV4KSB7XG4gICAgICAvLyBBcnJhc3RhbmRvIHBhcmEgZnJlbnRlXG4gICAgICBpZiAoZGVjaW1hbCA+PSB0aHJlc2hvbGQpIHtcbiAgICAgICAgdGFyZ2V0SW5kZXggPSB0aGlzLmN1cnJlbnRJbmRleCArIGl0ZW1zTW92ZWQgKyAxO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGFyZ2V0SW5kZXggPSB0aGlzLmN1cnJlbnRJbmRleCArIGl0ZW1zTW92ZWQ7XG4gICAgICB9XG4gICAgfSBlbHNlIGlmIChwb3NpdGlvbiA8IHRoaXMuY3VycmVudEluZGV4KSB7XG4gICAgICAvLyBBcnJhc3RhbmRvIHBhcmEgdHLDoXNcbiAgICAgIGlmIChkZWNpbWFsID49IHRocmVzaG9sZCkge1xuICAgICAgICB0YXJnZXRJbmRleCA9IHRoaXMuY3VycmVudEluZGV4IC0gaXRlbXNNb3ZlZCAtIDE7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0YXJnZXRJbmRleCA9IHRoaXMuY3VycmVudEluZGV4IC0gaXRlbXNNb3ZlZDtcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgLy8gTsOjbyBzZSBtb3ZldVxuICAgICAgdGFyZ2V0SW5kZXggPSB0aGlzLmN1cnJlbnRJbmRleDtcbiAgICB9XG4gICAgXG4gICAgY29uc3QgbWF4SW5kZXggPSB0aGlzLmdldE1heEluZGV4KCk7XG4gICAgdGFyZ2V0SW5kZXggPSBNYXRoLm1heCgwLCBNYXRoLm1pbih0YXJnZXRJbmRleCwgbWF4SW5kZXgpKTtcbiAgICB0aGlzLmN1cnJlbnRJbmRleCA9IHRhcmdldEluZGV4O1xuICAgIHRoaXMudXBkYXRlVHJhbnNmb3JtKCk7XG4gIH1cblxuICBnZXREb3RzQXJyYXkoKTogYW55W10ge1xuICAgIC8vIFPDsyBtb3N0cmEgZG90cyBwYXJhIGNhZGEgcG9zacOnw6NvIHBvc3PDrXZlbCAoY2FkYSBcInDDoWdpbmFcIiBwb3Nzw612ZWwpXG4gICAgY29uc3QgbWF4SW5kZXggPSB0aGlzLmdldE1heEluZGV4KCk7XG4gICAgcmV0dXJuIEFycmF5KG1heEluZGV4ICsgMSk7XG4gIH1cblxuICBnZXRDdXJyZW50RG90SW5kZXgoKTogbnVtYmVyIHtcbiAgICByZXR1cm4gdGhpcy5jdXJyZW50SW5kZXg7XG4gIH1cblxuICBwcml2YXRlIHVwZGF0ZVRyYW5zZm9ybSgpIHtcbiAgICBjb25zdCBpdGVtU3RlcCA9IHRoaXMuaXRlbVdpZHRoICsgdGhpcy5nYXA7XG4gICAgdGhpcy50cmFuc2xhdGVYID0gLXRoaXMuY3VycmVudEluZGV4ICogaXRlbVN0ZXA7XG5cbiAgICAvLyBDbGFtcCBwYXJhIG7Do28gbW9zdHJhciBlc3Bhw6dvIHZhemlvIMOgIGRpcmVpdGFcbiAgICBjb25zdCB2aXNpYmxlQ291bnQgPSBNYXRoLm1heCgxLCBNYXRoLmZsb29yKHRoaXMuY29udGFpbmVyV2lkdGggLyBpdGVtU3RlcCkpO1xuICAgIC8vIEluY2x1aSBvIGdhcCBhcMOzcyBvIMO6bHRpbW8gaXRlbVxuICAgIGNvbnN0IHRvdGFsV2lkdGggPSB0aGlzLml0ZW1zLmxlbmd0aCAqIGl0ZW1TdGVwO1xuICAgIGlmICh0aGlzLml0ZW1zLmxlbmd0aCA+IHZpc2libGVDb3VudCkge1xuICAgICAgY29uc3QgbWluVHJhbnNsYXRlWCA9IHRoaXMuY29udGFpbmVyV2lkdGggLSB0b3RhbFdpZHRoO1xuICAgICAgdGhpcy50cmFuc2xhdGVYID0gTWF0aC5tYXgodGhpcy50cmFuc2xhdGVYLCBtaW5UcmFuc2xhdGVYKTtcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy50cmFuc2xhdGVYID0gMDtcbiAgICB9XG5cbiAgICBpZiAoIXRoaXMuaXNEcmFnZ2luZyAmJiB0aGlzLnNsaWRlc0NvbnRhaW5lcikge1xuICAgICAgdGhpcy5yZW5kZXJlci5zZXRTdHlsZShcbiAgICAgICAgdGhpcy5zbGlkZXNDb250YWluZXIubmF0aXZlRWxlbWVudCxcbiAgICAgICAgJ3RyYW5zZm9ybScsXG4gICAgICAgIGB0cmFuc2xhdGVYKCR7dGhpcy50cmFuc2xhdGVYfXB4KWBcbiAgICAgICk7XG4gICAgfVxuICB9XG5cbiAgLy8gQWRpY2lvbmUgZXN0ZSBtw6l0b2RvIHBhcmEgZXZpdGFyIGVycm8gZGUgcHJvcHJpZWRhZGUgYXVzZW50ZVxuICBnb1RvRmlyc3RJdGVtKCkge1xuICAgIHRoaXMuY3VycmVudEluZGV4ID0gMDtcbiAgICB0aGlzLnVwZGF0ZVRyYW5zZm9ybSgpO1xuICB9XG59XG4iLCI8ZGl2IGNsYXNzPVwiYy1jYXJvdXNlbC1maXhlZC1jb250YWluZXJcIiAjcmlnaHRCbGVlZENvbnRhaW5lcj5cbiAgPGRpdiBcbiAgY2xhc3M9XCJjLWNhcm91c2VsLWZpeGVkLXNsaWRlc1wiIFxuICAjc2xpZGVzQ29udGFpbmVyXG4gIFtzdHlsZS50cmFuc2Zvcm1dPVwiJ3RyYW5zbGF0ZVgoJyArIHRyYW5zbGF0ZVggKyAncHgpJ1wiIFxuICAobW91c2Vkb3duKT1cIm9uTW91c2VEb3duKCRldmVudClcIlxuICAobW91c2Vtb3ZlKT1cIm9uTW91c2VNb3ZlKCRldmVudClcIlxuICAobW91c2V1cCk9XCJvbk1vdXNlVXAoJGV2ZW50KVwiXG4gIChtb3VzZWxlYXZlKT1cIm9uTW91c2VMZWF2ZSgkZXZlbnQpXCJcbiAgKHRvdWNoc3RhcnQpPVwib25Ub3VjaFN0YXJ0KCRldmVudClcIiBcbiAgKHRvdWNobW92ZSk9XCJvblRvdWNoTW92ZSgkZXZlbnQpXCIgXG4gICh0b3VjaGVuZCk9XCJvblRvdWNoRW5kKCRldmVudClcIj5cbiAgPG5nLWNvbnRlbnQ+PC9uZy1jb250ZW50PlxuICA8L2Rpdj5cbjwvZGl2PlxuPGRpdiBjbGFzcz1cImMtY2Fyb3VzZWwtZml4ZWQtZm9vdGVyXCIgKm5nSWY9XCJzaG93QXJyb3dzIHx8IHNob3dEb3RzXCI+XG4gICAgPGJ1dHRvbiAqbmdJZj1cInNob3dBcnJvd3NcIlxuICAgICAgY2xhc3M9XCJjLWNhcm91c2VsLWZpeGVkLW5hdiBwcmV2XCIgXG4gICAgICBbZGlzYWJsZWRdPVwiIWNhbkdvUHJldmlvdXMoKVwiXG4gICAgICB0aXRsZT1cIkl0ZW0gYW50ZXJpb3JcIiBcbiAgICAgIGFyaWEtbGFiZWw9XCJJdGVtIGFudGVyaW9yXCIgXG4gICAgICAoY2xpY2spPVwicHJldkl0ZW0oKVwiPlxuICAgICAgPGxpYi1lbHV4LWljb24gW2ljb25dPVwiJ0NoZXZyb25fTGVmdC5zdmcnXCIgW3NpemVdPVwiJzE2J1wiIFtzaXplVHlwZV09XCIncHgnXCIgW2NvbG9yXT1cIicjMDIwRjJFJ1wiPjwvbGliLWVsdXgtaWNvbj5cbiAgICA8L2J1dHRvbj5cblxuICAgIDxkaXYgY2xhc3M9XCJjLWNhcm91c2VsLWZpeGVkLWRvdHNcIiAqbmdJZj1cInNob3dEb3RzXCI+XG4gICAgICA8bmctY29udGFpbmVyICpuZ0Zvcj1cImxldCBkb3Qgb2YgZ2V0RG90c0FycmF5KCk7IGxldCBpZHggPSBpbmRleFwiPlxuICAgICAgICA8c3BhbiBcbiAgICAgICAgICBjbGFzcz1cImMtY2Fyb3VzZWwtZml4ZWQtZG90XCIgXG4gICAgICAgICAgW2NsYXNzLmFjdGl2ZV09XCJpZHggPT09IGdldEN1cnJlbnREb3RJbmRleCgpXCIgXG4gICAgICAgICAgKGNsaWNrKT1cImdvVG9Eb3QoaWR4KVwiPlxuICAgICAgICA8L3NwYW4+XG4gICAgICA8L25nLWNvbnRhaW5lcj5cbiAgICA8L2Rpdj5cblxuICAgIDxidXR0b24gKm5nSWY9XCJzaG93QXJyb3dzXCJcbiAgICAgIGNsYXNzPVwiYy1jYXJvdXNlbC1maXhlZC1uYXYgbmV4dFwiIFxuICAgICAgW2Rpc2FibGVkXT1cIiFjYW5Hb05leHQoKVwiXG4gICAgICB0aXRsZT1cIlByw7N4aW1vIGl0ZW1cIiBcbiAgICAgIGFyaWEtbGFiZWw9XCJQcsOzeGltbyBpdGVtXCIgXG4gICAgICAoY2xpY2spPVwibmV4dEl0ZW0oKVwiPlxuICAgICAgPGxpYi1lbHV4LWljb24gW2ljb25dPVwiJ0NoZXZyb25fUmlnaHQuc3ZnJ1wiIFtzaXplXT1cIicxNidcIiBbc2l6ZVR5cGVdPVwiJ3B4J1wiIFtjb2xvcl09XCInIzAyMEYyRSdcIj48L2xpYi1lbHV4LWljb24+XG4gICAgPC9idXR0b24+XG48L2Rpdj5cbiJdfQ==
|