UNPKG

ngx-masonry-layout

Version:
266 lines (260 loc) 29.1 kB
import { Component, ElementRef, HostListener, Input, Output, EventEmitter, NgModule } from '@angular/core'; import { CommonModule } from '@angular/common'; /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc */ class MasonryLayoutComponent { /** * @param {?} elementRef */ constructor(elementRef) { this.elementRef = elementRef; this.GUTTER = 0; this.savedNodeDimensions = []; this.gridState = 'not started'; this.ENABLE_MASONRY = true; this.MAX_HEIGHT = 400; this.events = new EventEmitter(); this.elem = this.elementRef.nativeElement; } /** * @param {?} value * @return {?} */ set gutter(value) { this.GUTTER = value / 2; } /** * @return {?} */ get isMobile() { /** @type {?} */ var check = false; (function (a) { if (/(android|bb\d+|meego).+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows ce|xda|xiino/i.test(a) || /1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i.test(a.substr(0, 4))) check = true; })(navigator.userAgent || navigator.vendor); return check; } ; /** * @param {?} event * @return {?} */ onWindowResize(event) { clearTimeout(this.resizeTimer); this.resizeTimer = setTimeout(() => { this.gridState = 'not started'; this.buildGrid(); }, 250); } /** * @return {?} */ ngOnInit() { this.buildGrid(); } /** * @return {?} */ ngOnChanges() { clearTimeout(this.changesTimer); this.changesTimer = setTimeout(() => { this.gridState = 'not started'; this.buildGrid(); }, 250); } /** * @return {?} */ buildGrid() { /** @type {?} */ let parentWidth = Math.floor(this.elem.parentNode.offsetWidth); /** @type {?} */ let row = { startIndex: 0, endIndex: 0, length: 0, totalWidth: 0 }; if (!this.images || !this.images.length) { return; } this.elem.style.width = parentWidth + 'px'; this.elem.style.display = 'table'; this.images.forEach((node, index) => { if (row.totalWidth === 0) { row.startIndex = index; row.length = 0; } row.length++; row.totalWidth += this.getComputedWidth(index); if (row.totalWidth >= parentWidth || this.isLastChild(index)) { row.endIndex = index; /** @type {?} */ let scaling = row.totalWidth / parentWidth; this.setColDimensions(scaling, row); row.totalWidth = 0; } }); } /** * @param {?} scaling * @param {?} row * @return {?} */ setColDimensions(scaling, row) { /** @type {?} */ let totalRowWidth = 0; /** @type {?} */ let parentWidth = this.elem.parentNode.offsetWidth; scaling = (scaling < 1) ? 1 : scaling; this.images.forEach((node, index) => { if (!this.ENABLE_MASONRY) { node.computedHeight = this.MAX_HEIGHT + 'px'; node.computedWidth = this.getComputedWidth(index) + 'px'; node.margin = this.getNodeMargin(parentWidth); return; } if (index >= row.startIndex && index <= row.endIndex) { /** @type {?} */ let nodeWidth; // last image if (index === row.endIndex && scaling > 1) { nodeWidth = (100 - totalRowWidth) - ((this.GUTTER * 2) / parentWidth * 100); node.computedWidth = 'calc(' + nodeWidth + '%)'; if (this.gridState === 'not started') { this.gridState = 'pre-building'; setTimeout(() => { this.buildGrid(); }, 100); } } else { nodeWidth = ((this.getComputedWidth(index) / scaling) / parentWidth * 100) - ((row.length * (this.GUTTER * 2)) * (this.getComputedWidth(index) / scaling) / parentWidth) / parentWidth * 100; node.computedWidth = 'calc(' + nodeWidth + '%)'; totalRowWidth += nodeWidth; totalRowWidth += (this.GUTTER / parentWidth * 100) * 2; } // last row and last image if (index === row.endIndex && row.length === 1 && this.isMobile) { nodeWidth = 100 - ((this.GUTTER * 2) / parentWidth * 100); /** @type {?} */ let height = node.height * (parentWidth * (nodeWidth / 100) / node.width); if (height / 2 < this.MAX_HEIGHT) { node.computedWidth = 'calc(' + nodeWidth + '%)'; } } node.margin = this.getNodeMargin(parentWidth); node.computedHeight = node.height * (parentWidth * (nodeWidth / 100) / node.width) + 'px'; } }); } /** * @param {?} index * @return {?} */ getComputedWidth(index) { return this.images[index].width / (this.images[index].height / this.MAX_HEIGHT); } /** * @param {?} index * @return {?} */ isLastChild(index) { return index + 1 === this.images.length; } /** * @param {?} parentWidth * @return {?} */ getNodeMargin(parentWidth) { return 'calc(' + this.GUTTER / parentWidth * 100 + '%)'; } /** * @param {?} image * @param {?} i * @return {?} */ clickOnImage(image, i) { this.events.emit({ type: 'click-on-image', image: image, index: i }); } /** * @param {?} elem * @return {?} */ onImageLoaded(elem) { elem.style.opacity = 1; } } MasonryLayoutComponent.decorators = [ { type: Component, args: [{ selector: 'masonry-layout', template: `<div [ngClass]="CLASS_NAME" *ngFor="let image of images; let i = index;" [style.width]="image.computedWidth" [style.height]="image.computedHeight" [style.float]="'left'" [style.margin]="image.margin" [style.background]="'#eeeeee'" [style.lineHeight]="0"> <img #imageElem [src]="image.path" [style.width.%]="100" [style.height]="'auto'" [style.opacity]="0" (click)="clickOnImage(image, i)" (load)="onImageLoaded(imageElem)" /> </div>`, },] }, ]; /** @nocollapse */ MasonryLayoutComponent.ctorParameters = () => [ { type: ElementRef } ]; MasonryLayoutComponent.propDecorators = { images: [{ type: Input, args: ['images',] }], ENABLE_MASONRY: [{ type: Input, args: ['masonry',] }], MAX_HEIGHT: [{ type: Input, args: ['max-height',] }], CLASS_NAME: [{ type: Input, args: ['class-name',] }], gutter: [{ type: Input, args: ['gutter',] }], events: [{ type: Output }], onWindowResize: [{ type: HostListener, args: ['window:resize', ['$event'],] }] }; /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc */ class MasonryLayoutModule { } MasonryLayoutModule.decorators = [ { type: NgModule, args: [{ declarations: [ MasonryLayoutComponent ], imports: [ CommonModule ], exports: [ MasonryLayoutComponent ], entryComponents: [ MasonryLayoutComponent ] },] }, ]; /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc */ /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,uselessCode} checked by tsc */ export { MasonryLayoutComponent, MasonryLayoutModule }; //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmd4LW1hc29ucnktbGF5b3V0LmpzLm1hcCIsInNvdXJjZXMiOlsibmc6Ly9uZ3gtbWFzb25yeS1sYXlvdXQvbGliL21hc29ucnktbGF5b3V0LmNvbXBvbmVudC50cyIsIm5nOi8vbmd4LW1hc29ucnktbGF5b3V0L2xpYi9tYXNvbnJ5LWxheW91dC5tb2R1bGUudHMiXSwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgQ29tcG9uZW50LCBFbGVtZW50UmVmLCBIb3N0TGlzdGVuZXIsIElucHV0LCBPdXRwdXQsIE9uSW5pdCwgT25DaGFuZ2VzLCBFdmVudEVtaXR0ZXIgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcblxuZXhwb3J0IGludGVyZmFjZSBJbWFnZSB7XG4gICAgcGF0aDogc3RyaW5nOyBcbiAgICB3aWR0aDogbnVtYmVyOyBcbiAgICBoZWlnaHQ6IG51bWJlcjtcbiAgICBjb21wdXRlZEhlaWdodD86IHN0cmluZztcbiAgICBjb21wdXRlZFdpZHRoPzogc3RyaW5nO1xuICAgIG1hcmdpbj86IHN0cmluZztcbn07XG5cbmV4cG9ydCBpbnRlcmZhY2UgSW1hZ2VzIGV4dGVuZHMgQXJyYXk8SW1hZ2U+e31cblxuQENvbXBvbmVudCh7XG4gICAgc2VsZWN0b3I6ICdtYXNvbnJ5LWxheW91dCcsIFxuICAgIHRlbXBsYXRlOiBgPGRpdiBcblx0W25nQ2xhc3NdPVwiQ0xBU1NfTkFNRVwiXG5cdCpuZ0Zvcj1cImxldCBpbWFnZSBvZiBpbWFnZXM7IGxldCBpID0gaW5kZXg7XCJcbiAgICBbc3R5bGUud2lkdGhdPVwiaW1hZ2UuY29tcHV0ZWRXaWR0aFwiXG4gICAgW3N0eWxlLmhlaWdodF09XCJpbWFnZS5jb21wdXRlZEhlaWdodFwiXG4gICAgW3N0eWxlLmZsb2F0XT1cIidsZWZ0J1wiXG4gICAgW3N0eWxlLm1hcmdpbl09XCJpbWFnZS5tYXJnaW5cIlxuICAgIFtzdHlsZS5iYWNrZ3JvdW5kXT1cIicjZWVlZWVlJ1wiXG4gICAgW3N0eWxlLmxpbmVIZWlnaHRdPVwiMFwiPlxuXHQ8aW1nIFxuICAgICAgICAjaW1hZ2VFbGVtXG4gICAgICAgIFtzcmNdPVwiaW1hZ2UucGF0aFwiIFxuICAgICAgICBbc3R5bGUud2lkdGguJV09XCIxMDBcIiBcbiAgICAgICAgW3N0eWxlLmhlaWdodF09XCInYXV0bydcIlxuICAgICAgICBbc3R5bGUub3BhY2l0eV09XCIwXCJcbiAgICAgICAgKGNsaWNrKT1cImNsaWNrT25JbWFnZShpbWFnZSwgaSlcIlxuICAgICAgICAobG9hZCk9XCJvbkltYWdlTG9hZGVkKGltYWdlRWxlbSlcIiAvPlxuPC9kaXY+YCxcbn0pXG5cbmV4cG9ydCBjbGFzcyBNYXNvbnJ5TGF5b3V0Q29tcG9uZW50IHtcbiAgICBHVVRURVI6IG51bWJlciA9IDA7XG4gICAgbm9kZXM6IGFueTtcbiAgICBlbGVtOiBhbnk7XG4gICAgc2F2ZWROb2RlRGltZW5zaW9uczogYW55ID0gW107XG4gICAgb2JzZXJ2ZXI6IGFueTtcbiAgICBncmlkU3RhdGU6IHN0cmluZyA9ICdub3Qgc3RhcnRlZCc7XG4gICAgcmVzaXplVGltZXI6IGFueTtcbiAgICBjaGFuZ2VzVGltZXI6IGFueTtcblxuICAgIEBJbnB1dCgnaW1hZ2VzJykgaW1hZ2VzOiBJbWFnZXM7IFxuICAgIEBJbnB1dCgnbWFzb25yeScpIEVOQUJMRV9NQVNPTlJZOiBib29sZWFuID0gdHJ1ZTsgXG4gICAgQElucHV0KCdtYXgtaGVpZ2h0JykgTUFYX0hFSUdIVDogbnVtYmVyID0gNDAwOyBcbiAgICBASW5wdXQoJ2NsYXNzLW5hbWUnKSBDTEFTU19OQU1FOiBzdHJpbmcgfCB7IFtrZXk6IHN0cmluZ106IGFueTsgfTtcblxuICAgIEBJbnB1dCgnZ3V0dGVyJylcbiAgICBzZXQgZ3V0dGVyKHZhbHVlOiBudW1iZXIpe1xuICAgICAgICB0aGlzLkdVVFRFUiA9IHZhbHVlIC8gMjtcbiAgICB9XG5cbiAgICBAT3V0cHV0KCkgZXZlbnRzOiBFdmVudEVtaXR0ZXI8YW55PiA9IG5ldyBFdmVudEVtaXR0ZXI8YW55PigpO1xuICAgICBcbiAgICBnZXQgaXNNb2JpbGUoKTpib29sZWFuIHtcbiAgICAgICAgdmFyIGNoZWNrID0gZmFsc2U7XG4gICAgICAgIChmdW5jdGlvbihhKXtpZigvKGFuZHJvaWR8YmJcXGQrfG1lZWdvKS4rbW9iaWxlfGF2YW50Z298YmFkYVxcL3xibGFja2JlcnJ5fGJsYXplcnxjb21wYWx8ZWxhaW5lfGZlbm5lY3xoaXB0b3B8aWVtb2JpbGV8aXAoaG9uZXxvZCl8aXJpc3xraW5kbGV8bGdlIHxtYWVtb3xtaWRwfG1tcHxtb2JpbGUuK2ZpcmVmb3h8bmV0ZnJvbnR8b3BlcmEgbShvYnxpbilpfHBhbG0oIG9zKT98cGhvbmV8cChpeGl8cmUpXFwvfHBsdWNrZXJ8cG9ja2V0fHBzcHxzZXJpZXMoNHw2KTB8c3ltYmlhbnx0cmVvfHVwXFwuKGJyb3dzZXJ8bGluayl8dm9kYWZvbmV8d2FwfHdpbmRvd3MgY2V8eGRhfHhpaW5vL2kudGVzdChhKXx8LzEyMDd8NjMxMHw2NTkwfDNnc298NHRocHw1MFsxLTZdaXw3NzBzfDgwMnN8YSB3YXxhYmFjfGFjKGVyfG9vfHNcXC0pfGFpKGtvfHJuKXxhbChhdnxjYXxjbyl8YW1vaXxhbihleHxueXx5dyl8YXB0dXxhcihjaHxnbyl8YXModGV8dXMpfGF0dHd8YXUoZGl8XFwtbXxyIHxzICl8YXZhbnxiZShja3xsbHxucSl8YmkobGJ8cmQpfGJsKGFjfGF6KXxicihlfHYpd3xidW1ifGJ3XFwtKG58dSl8YzU1XFwvfGNhcGl8Y2N3YXxjZG1cXC18Y2VsbHxjaHRtfGNsZGN8Y21kXFwtfGNvKG1wfG5kKXxjcmF3fGRhKGl0fGxsfG5nKXxkYnRlfGRjXFwtc3xkZXZpfGRpY2F8ZG1vYnxkbyhjfHApb3xkcygxMnxcXC1kKXxlbCg0OXxhaSl8ZW0obDJ8dWwpfGVyKGljfGswKXxlc2w4fGV6KFs0LTddMHxvc3x3YXx6ZSl8ZmV0Y3xmbHkoXFwtfF8pfGcxIHV8ZzU2MHxnZW5lfGdmXFwtNXxnXFwtbW98Z28oXFwud3xvZCl8Z3IoYWR8dW4pfGhhaWV8aGNpdHxoZFxcLShtfHB8dCl8aGVpXFwtfGhpKHB0fHRhKXxocCggaXxpcCl8aHNcXC1jfGh0KGMoXFwtfCB8X3xhfGd8cHxzfHQpfHRwKXxodShhd3x0Yyl8aVxcLSgyMHxnb3xtYSl8aTIzMHxpYWMoIHxcXC18XFwvKXxpYnJvfGlkZWF8aWcwMXxpa29tfGltMWt8aW5ub3xpcGFxfGlyaXN8amEodHx2KWF8amJyb3xqZW11fGppZ3N8a2RkaXxrZWppfGtndCggfFxcLyl8a2xvbnxrcHQgfGt3Y1xcLXxreW8oY3xrKXxsZShub3x4aSl8bGcoIGd8XFwvKGt8bHx1KXw1MHw1NHxcXC1bYS13XSl8bGlid3xseW54fG0xXFwtd3xtM2dhfG01MFxcL3xtYSh0ZXx1aXx4byl8bWMoMDF8MjF8Y2EpfG1cXC1jcnxtZShyY3xyaSl8bWkobzh8b2F8dHMpfG1tZWZ8bW8oMDF8MDJ8Yml8ZGV8ZG98dChcXC18IHxvfHYpfHp6KXxtdCg1MHxwMXx2ICl8bXdicHxteXdhfG4xMFswLTJdfG4yMFsyLTNdfG4zMCgwfDIpfG41MCgwfDJ8NSl8bjcoMCgwfDEpfDEwKXxuZSgoY3xtKVxcLXxvbnx0Znx3Znx3Z3x3dCl8bm9rKDZ8aSl8bnpwaHxvMmltfG9wKHRpfHd2KXxvcmFufG93ZzF8cDgwMHxwYW4oYXxkfHQpfHBkeGd8cGcoMTN8XFwtKFsxLThdfGMpKXxwaGlsfHBpcmV8cGwoYXl8dWMpfHBuXFwtMnxwbyhja3xydHxzZSl8cHJveHxwc2lvfHB0XFwtZ3xxYVxcLWF8cWMoMDd8MTJ8MjF8MzJ8NjB8XFwtWzItN118aVxcLSl8cXRla3xyMzgwfHI2MDB8cmFrc3xyaW05fHJvKHZlfHpvKXxzNTVcXC98c2EoZ2V8bWF8bW18bXN8bnl8dmEpfHNjKDAxfGhcXC18b298cFxcLSl8c2RrXFwvfHNlKGMoXFwtfDB8MSl8NDd8bWN8bmR8cmkpfHNnaFxcLXxzaGFyfHNpZShcXC18bSl8c2tcXC0wfHNsKDQ1fGlkKXxzbShhbHxhcnxiM3xpdHx0NSl8c28oZnR8bnkpfHNwKDAxfGhcXC18dlxcLXx2ICl8c3koMDF8bWIpfHQyKDE4fDUwKXx0NigwMHwxMHwxOCl8dGEoZ3R8bGspfHRjbFxcLXx0ZGdcXC18dGVsKGl8bSl8dGltXFwtfHRcXC1tb3x0byhwbHxzaCl8dHMoNzB8bVxcLXxtM3xtNSl8dHhcXC05fHVwKFxcLmJ8ZzF8c2kpfHV0c3R8djQwMHx2NzUwfHZlcml8dmkocmd8dGUpfHZrKDQwfDVbMC0zXXxcXC12KXx2bTQwfHZvZGF8dnVsY3x2eCg1Mnw1M3w2MHw2MXw3MHw4MHw4MXw4M3w4NXw5OCl8dzNjKFxcLXwgKXx3ZWJjfHdoaXR8d2koZyB8bmN8bncpfHdtbGJ8d29udXx4NzAwfHlhc1xcLXx5b3VyfHpldG98enRlXFwtL2kudGVzdChhLnN1YnN0cigwLDQpKSkgY2hlY2sgPSB0cnVlO30pKG5hdmlnYXRvci51c2VyQWdlbnR8fG5hdmlnYXRvci52ZW5kb3IpO1xuICAgICAgICByZXR1cm4gY2hlY2s7XG4gICAgfTtcbiAgICAgXG4gICAgY29uc3RydWN0b3IocHJpdmF0ZSBlbGVtZW50UmVmOiBFbGVtZW50UmVmKXtcbiAgICAgICAgdGhpcy5lbGVtID0gdGhpcy5lbGVtZW50UmVmLm5hdGl2ZUVsZW1lbnQ7XG4gICAgfVxuXG4gICAgQEhvc3RMaXN0ZW5lcignd2luZG93OnJlc2l6ZScsIFsnJGV2ZW50J10pXG4gICAgb25XaW5kb3dSZXNpemUoZXZlbnQpIHtcbiAgICAgICAgY2xlYXJUaW1lb3V0KHRoaXMucmVzaXplVGltZXIpO1xuXG4gICAgICAgIHRoaXMucmVzaXplVGltZXIgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgIHRoaXMuZ3JpZFN0YXRlID0gJ25vdCBzdGFydGVkJztcbiAgICAgICAgICAgIHRoaXMuYnVpbGRHcmlkKCk7IFxuICAgICAgICB9LCAyNTApO1xuICAgIH1cblxuICAgIG5nT25Jbml0KCkge1xuICAgICAgICB0aGlzLmJ1aWxkR3JpZCgpO1xuICAgIH1cblxuICAgIG5nT25DaGFuZ2VzKCl7XG4gICAgICAgIGNsZWFyVGltZW91dCh0aGlzLmNoYW5nZXNUaW1lcik7XG5cbiAgICAgICAgdGhpcy5jaGFuZ2VzVGltZXIgPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgIHRoaXMuZ3JpZFN0YXRlID0gJ25vdCBzdGFydGVkJztcbiAgICAgICAgICAgIHRoaXMuYnVpbGRHcmlkKCk7IFxuICAgICAgICB9LCAyNTApO1xuICAgIH1cblxuICAgIGJ1aWxkR3JpZCgpe1xuICAgICAgICBsZXQgcGFyZW50V2lkdGggPSBNYXRoLmZsb29yKHRoaXMuZWxlbS5wYXJlbnROb2RlLm9mZnNldFdpZHRoKTtcbiAgICAgICAgbGV0IHRvdGFsUm93V2lkdGg6IGFueSA9IDA7IFxuICAgICAgICBsZXQgcm93OiBhbnkgPSB7XG4gICAgICAgICAgICBzdGFydEluZGV4OiAwLFxuICAgICAgICAgICAgZW5kSW5kZXg6IDAsXG4gICAgICAgICAgICBsZW5ndGg6IDAsXG4gICAgICAgICAgICB0b3RhbFdpZHRoOiAwXG4gICAgICAgIH07XG5cbiAgICAgICAgaWYgKCF0aGlzLmltYWdlcyB8fCAhdGhpcy5pbWFnZXMubGVuZ3RoKXtcbiAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgfVxuXG4gICAgICAgIHRoaXMuZWxlbS5zdHlsZS53aWR0aCA9IHBhcmVudFdpZHRoICsncHgnO1xuICAgICAgICB0aGlzLmVsZW0uc3R5bGUuZGlzcGxheSA9ICd0YWJsZSc7XG5cbiAgICAgICAgdGhpcy5pbWFnZXMuZm9yRWFjaCgobm9kZSwgaW5kZXgpID0+IHtcbiAgICAgICAgICAgIGlmIChyb3cudG90YWxXaWR0aCA9PT0gMCl7XG4gICAgICAgICAgICAgICAgcm93LnN0YXJ0SW5kZXggPSBpbmRleDtcbiAgICAgICAgICAgICAgICByb3cubGVuZ3RoID0gMDtcbiAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgcm93Lmxlbmd0aCsrO1xuICAgICAgICAgICAgcm93LnRvdGFsV2lkdGggKz0gdGhpcy5nZXRDb21wdXRlZFdpZHRoKGluZGV4KTtcbiAgICAgICAgICAgIFxuICAgICAgICAgICAgaWYgKHJvdy50b3RhbFdpZHRoID49IHBhcmVudFdpZHRoIHx8IHRoaXMuaXNMYXN0Q2hpbGQoaW5kZXgpKXtcbiAgICAgICAgICAgICAgICByb3cuZW5kSW5kZXggPSBpbmRleDtcbiAgICAgICAgICAgICAgICBsZXQgc2NhbGluZyA9IHJvdy50b3RhbFdpZHRoL3BhcmVudFdpZHRoO1xuXG4gICAgICAgICAgICAgICAgdGhpcy5zZXRDb2xEaW1lbnNpb25zKHNjYWxpbmcsIHJvdyk7XG4gICAgICAgICAgICAgICAgcm93LnRvdGFsV2lkdGggPSAwOyBcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfVxuXG4gICAgc2V0Q29sRGltZW5zaW9ucyhzY2FsaW5nOiBudW1iZXIsIHJvdzogYW55KXtcbiAgICAgICAgbGV0IHRvdGFsUm93V2lkdGg6IGFueSA9IDA7XG4gICAgICAgIGxldCBwYXJlbnRXaWR0aCA9IHRoaXMuZWxlbS5wYXJlbnROb2RlLm9mZnNldFdpZHRoO1xuICAgICAgICBzY2FsaW5nID0gKHNjYWxpbmcgPCAxKSA/IDEgOiBzY2FsaW5nO1xuXG4gICAgICAgIHRoaXMuaW1hZ2VzLmZvckVhY2goKG5vZGUsIGluZGV4KSA9PiB7XG4gICAgICAgICAgICBpZiAoIXRoaXMuRU5BQkxFX01BU09OUlkpe1xuICAgICAgICAgICAgICAgIG5vZGUuY29tcHV0ZWRIZWlnaHQgPSB0aGlzLk1BWF9IRUlHSFQgKyAncHgnO1xuICAgICAgICAgICAgICAgIG5vZGUuY29tcHV0ZWRXaWR0aCA9IHRoaXMuZ2V0Q29tcHV0ZWRXaWR0aChpbmRleCkgKyAncHgnO1xuICAgICAgICAgICAgICAgIG5vZGUubWFyZ2luID0gdGhpcy5nZXROb2RlTWFyZ2luKHBhcmVudFdpZHRoKTtcbiAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICB9XG5cbiAgICAgICAgICAgIGlmIChpbmRleCA+PSByb3cuc3RhcnRJbmRleCAmJiBpbmRleCA8PSByb3cuZW5kSW5kZXgpe1xuICAgICAgICAgICAgICAgIGxldCBub2RlV2lkdGg7XG5cbiAgICAgICAgICAgICAgICAvLyBsYXN0IGltYWdlXG4gICAgICAgICAgICAgICAgaWYgKGluZGV4ID09PSByb3cuZW5kSW5kZXggJiYgc2NhbGluZyA+IDEpeyBcbiAgICAgICAgICAgICAgICAgICAgbm9kZVdpZHRoID0gKDEwMCAtIHRvdGFsUm93V2lkdGgpIC0gKCh0aGlzLkdVVFRFUiAqIDIpIC8gcGFyZW50V2lkdGggKiAxMDApO1xuICAgICAgICAgICAgICAgICAgICBub2RlLmNvbXB1dGVkV2lkdGggPSAnY2FsYygnK25vZGVXaWR0aCsnJSknO1xuXG4gICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLmdyaWRTdGF0ZSA9PT0gJ25vdCBzdGFydGVkJyl7XG4gICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmdyaWRTdGF0ZSA9ICdwcmUtYnVpbGRpbmcnO1xuXG4gICAgICAgICAgICAgICAgICAgICAgICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmJ1aWxkR3JpZCgpO1xuICAgICAgICAgICAgICAgICAgICAgICAgfSwgMTAwKTtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH0gXG4gICAgICAgICAgICAgICAgZWxzZSB7XG4gICAgICAgICAgICAgICAgICAgIG5vZGVXaWR0aCA9ICgodGhpcy5nZXRDb21wdXRlZFdpZHRoKGluZGV4KSAvIHNjYWxpbmcpIC8gcGFyZW50V2lkdGggKiAxMDApIC0gKChyb3cubGVuZ3RoICogKHRoaXMuR1VUVEVSICogMikpICogKHRoaXMuZ2V0Q29tcHV0ZWRXaWR0aChpbmRleCkgLyBzY2FsaW5nKSAvIHBhcmVudFdpZHRoKSAvIHBhcmVudFdpZHRoICogMTAwO1xuICAgICAgICAgICAgICAgICAgICBub2RlLmNvbXB1dGVkV2lkdGggPSAnY2FsYygnK25vZGVXaWR0aCsnJSknO1xuICAgICAgICAgICAgICAgICAgICBcbiAgICAgICAgICAgICAgICAgICAgdG90YWxSb3dXaWR0aCArPSBub2RlV2lkdGg7XG4gICAgICAgICAgICAgICAgICAgIHRvdGFsUm93V2lkdGggKz0gKHRoaXMuR1VUVEVSIC8gcGFyZW50V2lkdGggKiAxMDApICogMjsgIFxuICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgIC8vIGxhc3Qgcm93IGFuZCBsYXN0IGltYWdlXG4gICAgICAgICAgICAgICAgaWYgKGluZGV4ID09PSByb3cuZW5kSW5kZXggJiYgcm93Lmxlbmd0aCA9PT0gMSAmJiB0aGlzLmlzTW9iaWxlKXtcbiAgICAgICAgICAgICAgICBcdG5vZGVXaWR0aCA9IDEwMCAtICgodGhpcy5HVVRURVIgKiAyKSAvIHBhcmVudFdpZHRoICogMTAwKTtcbiAgICAgICAgICAgICAgICAgICAgbGV0IGhlaWdodCA9IG5vZGUuaGVpZ2h0ICogKCBwYXJlbnRXaWR0aCAqIChub2RlV2lkdGggLyAxMDApIC8gbm9kZS53aWR0aCk7XG5cbiAgICAgICAgICAgICAgICAgICAgaWYgKGhlaWdodC8yIDwgdGhpcy5NQVhfSEVJR0hUKXtcbiAgICAgICAgICAgICAgICAgICAgICAgIG5vZGUuY29tcHV0ZWRXaWR0aCA9ICdjYWxjKCcrbm9kZVdpZHRoKyclKSc7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9XG5cbiAgICAgICAgICAgICAgICBub2RlLm1hcmdpbiA9IHRoaXMuZ2V0Tm9kZU1hcmdpbihwYXJlbnRXaWR0aCk7XG4gICAgICAgICAgICAgICAgbm9kZS5jb21wdXRlZEhlaWdodCA9IG5vZGUuaGVpZ2h0ICogKCBwYXJlbnRXaWR0aCAqIChub2RlV2lkdGggLyAxMDApIC8gbm9kZS53aWR0aCkgKyAncHgnO1xuICAgICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICB9XG5cbiAgICBnZXRDb21wdXRlZFdpZHRoKGluZGV4OiBudW1iZXIpe1xuICAgICAgICByZXR1cm4gdGhpcy5pbWFnZXNbaW5kZXhdLndpZHRoIC8gKHRoaXMuaW1hZ2VzW2luZGV4XS5oZWlnaHQgLyB0aGlzLk1BWF9IRUlHSFQpO1xuICAgIH1cblxuICAgIGlzTGFzdENoaWxkKGluZGV4OiBudW1iZXIpe1xuICAgICAgICByZXR1cm4gaW5kZXggKyAxID09PSB0aGlzLmltYWdlcy5sZW5ndGg7XG4gICAgfVxuXG4gICAgZ2V0Tm9kZU1hcmdpbihwYXJlbnRXaWR0aDogbnVtYmVyKXtcbiAgICAgICAgcmV0dXJuICdjYWxjKCcrdGhpcy5HVVRURVIgLyBwYXJlbnRXaWR0aCAqIDEwMCsnJSknO1xuICAgIH1cblxuICAgIGNsaWNrT25JbWFnZShpbWFnZTogYW55LCBpOiBudW1iZXIpe1xuICAgICAgICB0aGlzLmV2ZW50cy5lbWl0KHtcbiAgICAgICAgICAgIHR5cGU6ICdjbGljay1vbi1pbWFnZScsXG4gICAgICAgICAgICBpbWFnZTogaW1hZ2UsXG4gICAgICAgICAgICBpbmRleDogaVxuICAgICAgICB9KTtcbiAgICB9XG5cbiAgICBvbkltYWdlTG9hZGVkKGVsZW0pe1xuICAgICAgICBlbGVtLnN0eWxlLm9wYWNpdHkgPSAxO1xuICAgIH1cbn0iLCJpbXBvcnQgeyBOZ01vZHVsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgQ29tbW9uTW9kdWxlIH0gZnJvbSAnQGFuZ3VsYXIvY29tbW9uJztcbmltcG9ydCB7IE1hc29ucnlMYXlvdXRDb21wb25lbnQgfSBmcm9tICcuL21hc29ucnktbGF5b3V0LmNvbXBvbmVudCc7IFxuXG5ATmdNb2R1bGUoe1xuICAgIGRlY2xhcmF0aW9uczogW1xuICAgICAgICBNYXNvbnJ5TGF5b3V0Q29tcG9uZW50XG4gICAgXSxcbiAgICBpbXBvcnRzOiBbXG4gICAgICAgIENvbW1vbk1vZHVsZVxuICAgIF0sXG4gICAgZXhwb3J0czogW1xuICAgICAgICBNYXNvbnJ5TGF5b3V0Q29tcG9uZW50XG4gICAgXSxcbiAgICBlbnRyeUNvbXBvbmVudHM6IFtcbiAgICAgICAgTWFzb25yeUxheW91dENvbXBvbmVudFxuICAgIF1cbn0pXG5leHBvcnQgY2xhc3MgTWFzb25yeUxheW91dE1vZHVsZSB7IH1cbiJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7Ozs7O0FBQUE7Ozs7SUErREksWUFBb0IsVUFBc0I7UUFBdEIsZUFBVSxHQUFWLFVBQVUsQ0FBWTtzQkEzQnpCLENBQUM7bUNBR1MsRUFBRTt5QkFFVCxhQUFhOzhCQUtXLElBQUk7MEJBQ04sR0FBRztzQkFRUCxJQUFJLFlBQVksRUFBTztRQVN6RCxJQUFJLENBQUMsSUFBSSxHQUFHLElBQUksQ0FBQyxVQUFVLENBQUMsYUFBYSxDQUFDO0tBQzdDOzs7OztJQWZELElBQ0ksTUFBTSxDQUFDLEtBQWE7UUFDcEIsSUFBSSxDQUFDLE1BQU0sR0FBRyxLQUFLLEdBQUcsQ0FBQyxDQUFDO0tBQzNCOzs7O0lBSUQsSUFBSSxRQUFROztRQUNSLElBQUksS0FBSyxHQUFHLEtBQUssQ0FBQztRQUNsQixDQUFDLFVBQVMsQ0FBQyxJQUFFLElBQUcsMFRBQTBULENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxJQUFFLHlrREFBeWtELENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQyxFQUFDLENBQUMsQ0FBQyxDQUFDO1lBQUUsS0FBSyxHQUFHLElBQUksQ0FBQyxFQUFDLEVBQUUsU0FBUyxDQUFDLFNBQVMsSUFBRSxTQUFTLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDMStELE9BQU8sS0FBSyxDQUFDO0tBQ2hCOzs7Ozs7SUFPRCxjQUFjLENBQUMsS0FBSztRQUNoQixZQUFZLENBQUMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxDQUFDO1FBRS9CLElBQUksQ0FBQyxXQUFXLEdBQUcsVUFBVSxDQUFDO1lBQzFCLElBQUksQ0FBQyxTQUFTLEdBQUcsYUFBYSxDQUFDO1lBQy9CLElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQztTQUNwQixFQUFFLEdBQUcsQ0FBQyxDQUFDO0tBQ1g7Ozs7SUFFRCxRQUFRO1FBQ0osSUFBSSxDQUFDLFNBQVMs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