UNPKG

ngx-m-carousel

Version:

Simple and effective carousel library for angular

153 lines 36 kB
import { trigger, state, style, transition, animate } from '@angular/animations'; import { Component, ElementRef, Input, ViewChild } from '@angular/core'; import * as i0 from "@angular/core"; import * as i1 from "@angular/common"; export class NgxMCarouselComponent { constructor() { this.images = []; this.delay = 5000; this.pauseOnHover = false; this.width = '100%'; this.height = '100%'; this.indicators = true; this.controls = true; this.clickToFullScreen = true; this.preserveRatioOnFullScreen = false; this.slide = 'slideZero'; this.x = 0; this.isFullScreen = false; } ngOnInit() { this.toggle(); } toggle() { this.handler = setTimeout(() => { if (this.x < (this.images.length - 1) * 100) { this.x = this.x + 100; this.slide = this.slide == "slideOne" ? "slideTwo" : "slideOne"; } else { this.slide = "slideZero"; this.x = 0; } this.toggle(); }, this.delay); } goTo(event, x) { event.stopPropagation(); this.x = x * 100; this.slide = this.slide == "slideOne" ? "slideTwo" : "slideOne"; window.clearTimeout(this.handler); this.toggle(); this.onHover(); } onHover() { if (this.pauseOnHover) window.clearTimeout(this.handler); } onLeave() { if (this.pauseOnHover) this.toggle(); } openFullscreen() { if (this.clickToFullScreen) { this.isFullScreen = true; if (this.carousel?.nativeElement.requestFullscreen) { this.carousel?.nativeElement.requestFullscreen(); } else if (this.carousel?.nativeElement.webkitRequestFullscreen) { /* Safari */ this.carousel?.nativeElement.webkitRequestFullscreen(); } else if (this.carousel?.nativeElement.msRequestFullscreen) { /* IE11 */ this.carousel?.nativeElement.msRequestFullscreen(); } } } closeFullScreen(event) { event.stopPropagation(); this.isFullScreen = false; if (this.isFullScreen && document.exitFullscreen) { document.exitFullscreen(); } else if (document.webkitExitFullscreen) { /* Safari */ document.webkitExitFullscreen(); } else if (document.msExitFullscreen) { /* IE11 */ document.msExitFullscreen(); } } } NgxMCarouselComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.3.9", ngImport: i0, type: NgxMCarouselComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); NgxMCarouselComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "12.0.0", version: "13.3.9", type: NgxMCarouselComponent, selector: "ngx-m-carousel", inputs: { images: "images", delay: "delay", pauseOnHover: "pauseOnHover", width: "width", height: "height", indicators: "indicators", controls: "controls", clickToFullScreen: "clickToFullScreen", preserveRatioOnFullScreen: "preserveRatioOnFullScreen" }, viewQueries: [{ propertyName: "carousel", first: true, predicate: ["carousel"], descendants: true, read: ElementRef }], ngImport: i0, template: "<div #carousel (click)=\"openFullscreen()\" (mouseenter)=\"onHover()\" (mouseleave)=\"onLeave()\" class=\"main\"\n [style.width]=\"width\" [style.height]=\"height\" [style.display]=\"isFullScreen?'flex':'block'\">\n <div [@slide]=\"{value: slide, params: {translateValue: x}}\" class=\"carousel\">\n <img *ngFor=\"let img of images\" [src]=\"img\">\n </div>\n <div *ngIf=\"controls\" class=\"controls\">\n <span (click)=\"goTo($event,(x/100)>0?(x/100)-1:images.length-1)\" class=\"buttons prev\">\n <svg version=\"1.1\" id=\"Layer_1\" xmlns=\"http://www.w3.org/2000/svg\"\n xmlns:xlink=\"http://www.w3.org/1999/xlink\" x=\"0px\" y=\"0px\" viewBox=\"0 0 475.558 475.558\"\n style=\"enable-background:new 0 0 475.558 475.558;\" xml:space=\"preserve\">\n <circle style=\"fill:#ffffff;\" cx=\"237.779\" cy=\"237.779\" r=\"237.779\" />\n <path style=\"fill:#000000;\" d=\"M214.181,240.332c29.429-29.425,58.857-58.853,88.278-88.278\n c25.666-25.663-14.316-65.341-40.039-39.615c-36.029,36.029-72.055,72.055-108.084,108.084\n c-10.888,10.885-10.588,29.023,0.214,39.829c36.029,36.029,72.055,72.058,108.084,108.087\n c25.666,25.666,65.345-14.316,39.615-40.043C272.888,299.039,243.535,269.686,214.181,240.332z\" />\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n </svg>\n </span>\n <span (click)=\"goTo($event,(x/100)<images.length-1?(x/100)+1:0)\" class=\"buttons next\">\n <svg version=\"1.1\" id=\"Layer_1\" xmlns=\"http://www.w3.org/2000/svg\"\n xmlns:xlink=\"http://www.w3.org/1999/xlink\" x=\"0px\" y=\"0px\" viewBox=\"0 0 475.558 475.558\"\n style=\"enable-background:new 0 0 475.558 475.558;\" xml:space=\"preserve\">\n <circle style=\"fill:#ffffff;\" cx=\"237.779\" cy=\"237.779\" r=\"237.779\" />\n <path style=\"fill:#000000;\" d=\"M214.181,240.332c29.429-29.425,58.857-58.853,88.278-88.278\n c25.666-25.663-14.316-65.341-40.039-39.615c-36.029,36.029-72.055,72.055-108.084,108.084\n c-10.888,10.885-10.588,29.023,0.214,39.829c36.029,36.029,72.055,72.058,108.084,108.087\n c25.666,25.666,65.345-14.316,39.615-40.043C272.888,299.039,243.535,269.686,214.181,240.332z\" />\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n </svg>\n </span>\n </div>\n <div *ngIf=\"indicators\" class=\"indicators\">\n <ol class=\"carousel-buttons\">\n <li *ngFor=\"let img of images; let i = index\" (click)=\"goTo($event,i)\" [class.active]=\"x===i*100\"></li>\n </ol>\n </div>\n <span *ngIf=\"isFullScreen\" class=\"buttons close\" (click)=\"closeFullScreen($event)\">\n <svg version=\"1.1\" id=\"Capa_1\" xmlns=\"http://www.w3.org/2000/svg\" xmlns:xlink=\"http://www.w3.org/1999/xlink\"\n x=\"0px\" y=\"0px\" viewBox=\"0 0 252 252\" style=\"enable-background:new 0 0 252 252;\" xml:space=\"preserve\">\n <g>\n <path d=\"M126,0C56.523,0,0,56.523,0,126s56.523,126,126,126s126-56.523,126-126S195.477,0,126,0z M126,234\n\t\tc-59.551,0-108-48.449-108-108S66.449,18,126,18s108,48.449,108,108S185.551,234,126,234z\" />\n <path d=\"M164.612,87.388c-3.515-3.515-9.213-3.515-12.728,0L126,113.272l-25.885-25.885c-3.515-3.515-9.213-3.515-12.728,0\n\t\tc-3.515,3.515-3.515,9.213,0,12.728L113.272,126l-25.885,25.885c-3.515,3.515-3.515,9.213,0,12.728\n\t\tc1.757,1.757,4.061,2.636,6.364,2.636s4.606-0.879,6.364-2.636L126,138.728l25.885,25.885c1.757,1.757,4.061,2.636,6.364,2.636\n\t\ts4.606-0.879,6.364-2.636c3.515-3.515,3.515-9.213,0-12.728L138.728,126l25.885-25.885\n\t\tC168.127,96.601,168.127,90.902,164.612,87.388z\" />\n </g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n </svg>\n\n </span>\n</div>", styles: [".main{overflow:hidden;position:relative}img{width:100%}.carousel{display:flex;width:100%}.indicators{position:absolute;display:flex;align-items:center;justify-content:center;width:100%;bottom:10%}.carousel-buttons li:before{position:absolute;top:-10px;left:0;display:inline-block;width:100%;height:10px;content:\"\"}.carousel-buttons li:after{position:absolute;bottom:-10px;left:0;display:inline-block;width:100%;height:10px;content:\"\"}.carousel-buttons li{position:relative;flex:0 1 auto;width:40px;height:5px;margin-right:3px;margin-left:3px;text-indent:-999px;background-color:#ffffff80;cursor:pointer}.carousel-buttons{list-style:none;display:flex}.carousel-buttons li.active{background-color:#fff}.buttons:hover{opacity:1!important}.controls{display:flex;align-items:center;justify-content:space-between;position:absolute;width:100%;height:100%;top:0}.buttons{filter:invert(100%);transition:opacity .3s;opacity:.5;cursor:pointer;width:5%;height:10%;background-size:contain;background-repeat:no-repeat}.next{transform:rotateY(180deg)}.close{position:absolute;top:5%;right:2.5%}.buttons.close{width:4%;height:8%}\n"], directives: [{ type: i1.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { type: i1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }], animations: [ trigger('slide', [ state('slideOne', style({ transform: 'translateX(-{{translateValue}}%)' }), { params: { translateValue: 0 } }), state('slideTwo', style({ transform: 'translateX(-{{translateValue}}%)' }), { params: { translateValue: 0 } }), state('slideZero', style({}), { params: { translateValue: 0 } }), state('slideBack', style({ transform: 'translateX({{translateValue}}%)' }), { params: { translateValue: 0 } }), transition('*=>slideOne', [ animate('1000ms ease-out') ]), transition('*=>slideTwo', [ animate('1000ms ease-out') ]), transition('*=>slideZero', [ style({ opacity: 0, transform: 'translateX(0)' }), animate('1500ms ease-out', style({ opacity: 1 })) ]) ]), ] }); i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.3.9", ngImport: i0, type: NgxMCarouselComponent, decorators: [{ type: Component, args: [{ selector: 'ngx-m-carousel', animations: [ trigger('slide', [ state('slideOne', style({ transform: 'translateX(-{{translateValue}}%)' }), { params: { translateValue: 0 } }), state('slideTwo', style({ transform: 'translateX(-{{translateValue}}%)' }), { params: { translateValue: 0 } }), state('slideZero', style({}), { params: { translateValue: 0 } }), state('slideBack', style({ transform: 'translateX({{translateValue}}%)' }), { params: { translateValue: 0 } }), transition('*=>slideOne', [ animate('1000ms ease-out') ]), transition('*=>slideTwo', [ animate('1000ms ease-out') ]), transition('*=>slideZero', [ style({ opacity: 0, transform: 'translateX(0)' }), animate('1500ms ease-out', style({ opacity: 1 })) ]) ]), ], template: "<div #carousel (click)=\"openFullscreen()\" (mouseenter)=\"onHover()\" (mouseleave)=\"onLeave()\" class=\"main\"\n [style.width]=\"width\" [style.height]=\"height\" [style.display]=\"isFullScreen?'flex':'block'\">\n <div [@slide]=\"{value: slide, params: {translateValue: x}}\" class=\"carousel\">\n <img *ngFor=\"let img of images\" [src]=\"img\">\n </div>\n <div *ngIf=\"controls\" class=\"controls\">\n <span (click)=\"goTo($event,(x/100)>0?(x/100)-1:images.length-1)\" class=\"buttons prev\">\n <svg version=\"1.1\" id=\"Layer_1\" xmlns=\"http://www.w3.org/2000/svg\"\n xmlns:xlink=\"http://www.w3.org/1999/xlink\" x=\"0px\" y=\"0px\" viewBox=\"0 0 475.558 475.558\"\n style=\"enable-background:new 0 0 475.558 475.558;\" xml:space=\"preserve\">\n <circle style=\"fill:#ffffff;\" cx=\"237.779\" cy=\"237.779\" r=\"237.779\" />\n <path style=\"fill:#000000;\" d=\"M214.181,240.332c29.429-29.425,58.857-58.853,88.278-88.278\n c25.666-25.663-14.316-65.341-40.039-39.615c-36.029,36.029-72.055,72.055-108.084,108.084\n c-10.888,10.885-10.588,29.023,0.214,39.829c36.029,36.029,72.055,72.058,108.084,108.087\n c25.666,25.666,65.345-14.316,39.615-40.043C272.888,299.039,243.535,269.686,214.181,240.332z\" />\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n </svg>\n </span>\n <span (click)=\"goTo($event,(x/100)<images.length-1?(x/100)+1:0)\" class=\"buttons next\">\n <svg version=\"1.1\" id=\"Layer_1\" xmlns=\"http://www.w3.org/2000/svg\"\n xmlns:xlink=\"http://www.w3.org/1999/xlink\" x=\"0px\" y=\"0px\" viewBox=\"0 0 475.558 475.558\"\n style=\"enable-background:new 0 0 475.558 475.558;\" xml:space=\"preserve\">\n <circle style=\"fill:#ffffff;\" cx=\"237.779\" cy=\"237.779\" r=\"237.779\" />\n <path style=\"fill:#000000;\" d=\"M214.181,240.332c29.429-29.425,58.857-58.853,88.278-88.278\n c25.666-25.663-14.316-65.341-40.039-39.615c-36.029,36.029-72.055,72.055-108.084,108.084\n c-10.888,10.885-10.588,29.023,0.214,39.829c36.029,36.029,72.055,72.058,108.084,108.087\n c25.666,25.666,65.345-14.316,39.615-40.043C272.888,299.039,243.535,269.686,214.181,240.332z\" />\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n </svg>\n </span>\n </div>\n <div *ngIf=\"indicators\" class=\"indicators\">\n <ol class=\"carousel-buttons\">\n <li *ngFor=\"let img of images; let i = index\" (click)=\"goTo($event,i)\" [class.active]=\"x===i*100\"></li>\n </ol>\n </div>\n <span *ngIf=\"isFullScreen\" class=\"buttons close\" (click)=\"closeFullScreen($event)\">\n <svg version=\"1.1\" id=\"Capa_1\" xmlns=\"http://www.w3.org/2000/svg\" xmlns:xlink=\"http://www.w3.org/1999/xlink\"\n x=\"0px\" y=\"0px\" viewBox=\"0 0 252 252\" style=\"enable-background:new 0 0 252 252;\" xml:space=\"preserve\">\n <g>\n <path d=\"M126,0C56.523,0,0,56.523,0,126s56.523,126,126,126s126-56.523,126-126S195.477,0,126,0z M126,234\n\t\tc-59.551,0-108-48.449-108-108S66.449,18,126,18s108,48.449,108,108S185.551,234,126,234z\" />\n <path d=\"M164.612,87.388c-3.515-3.515-9.213-3.515-12.728,0L126,113.272l-25.885-25.885c-3.515-3.515-9.213-3.515-12.728,0\n\t\tc-3.515,3.515-3.515,9.213,0,12.728L113.272,126l-25.885,25.885c-3.515,3.515-3.515,9.213,0,12.728\n\t\tc1.757,1.757,4.061,2.636,6.364,2.636s4.606-0.879,6.364-2.636L126,138.728l25.885,25.885c1.757,1.757,4.061,2.636,6.364,2.636\n\t\ts4.606-0.879,6.364-2.636c3.515-3.515,3.515-9.213,0-12.728L138.728,126l25.885-25.885\n\t\tC168.127,96.601,168.127,90.902,164.612,87.388z\" />\n </g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n <g></g>\n </svg>\n\n </span>\n</div>", styles: [".main{overflow:hidden;position:relative}img{width:100%}.carousel{display:flex;width:100%}.indicators{position:absolute;display:flex;align-items:center;justify-content:center;width:100%;bottom:10%}.carousel-buttons li:before{position:absolute;top:-10px;left:0;display:inline-block;width:100%;height:10px;content:\"\"}.carousel-buttons li:after{position:absolute;bottom:-10px;left:0;display:inline-block;width:100%;height:10px;content:\"\"}.carousel-buttons li{position:relative;flex:0 1 auto;width:40px;height:5px;margin-right:3px;margin-left:3px;text-indent:-999px;background-color:#ffffff80;cursor:pointer}.carousel-buttons{list-style:none;display:flex}.carousel-buttons li.active{background-color:#fff}.buttons:hover{opacity:1!important}.controls{display:flex;align-items:center;justify-content:space-between;position:absolute;width:100%;height:100%;top:0}.buttons{filter:invert(100%);transition:opacity .3s;opacity:.5;cursor:pointer;width:5%;height:10%;background-size:contain;background-repeat:no-repeat}.next{transform:rotateY(180deg)}.close{position:absolute;top:5%;right:2.5%}.buttons.close{width:4%;height:8%}\n"] }] }], propDecorators: { carousel: [{ type: ViewChild, args: ["carousel", { read: ElementRef }] }], images: [{ type: Input }], delay: [{ type: Input }], pauseOnHover: [{ type: Input }], width: [{ type: Input }], height: [{ type: Input }], indicators: [{ type: Input }], controls: [{ type: Input }], clickToFullScreen: [{ type: Input }], preserveRatioOnFullScreen: [{ type: Input }] } }); //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmd4LW0tY2Fyb3VzZWwuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vcHJvamVjdHMvbmd4LW0tY2Fyb3VzZWwvc3JjL2xpYi9uZ3gtbS1jYXJvdXNlbC5jb21wb25lbnQudHMiLCIuLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtbS1jYXJvdXNlbC9zcmMvbGliL25neC1tLWNhcm91c2VsLmNvbXBvbmVudC5odG1sIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxPQUFPLEVBQUUsS0FBSyxFQUFFLEtBQUssRUFBRSxVQUFVLEVBQUUsT0FBTyxFQUFFLE1BQU0scUJBQXFCLENBQUM7QUFDakYsT0FBTyxFQUFFLFNBQVMsRUFBRSxVQUFVLEVBQUUsS0FBSyxFQUFVLFNBQVMsRUFBRSxNQUFNLGVBQWUsQ0FBQzs7O0FBMENoRixNQUFNLE9BQU8scUJBQXFCO0lBeENsQztRQTRDVyxXQUFNLEdBQWtCLEVBQUUsQ0FBQztRQUMzQixVQUFLLEdBQVcsSUFBSSxDQUFDO1FBQ3JCLGlCQUFZLEdBQVksS0FBSyxDQUFDO1FBQzlCLFVBQUssR0FBVyxNQUFNLENBQUM7UUFDdkIsV0FBTSxHQUFXLE1BQU0sQ0FBQztRQUN4QixlQUFVLEdBQVksSUFBSSxDQUFDO1FBQzNCLGFBQVEsR0FBWSxJQUFJLENBQUM7UUFDekIsc0JBQWlCLEdBQVksSUFBSSxDQUFDO1FBQ2xDLDhCQUF5QixHQUFZLEtBQUssQ0FBQztRQUNwRCxVQUFLLEdBQVcsV0FBVyxDQUFDO1FBQzVCLE1BQUMsR0FBVyxDQUFDLENBQUM7UUFFZCxpQkFBWSxHQUFZLEtBQUssQ0FBQztLQTZEL0I7SUEzREMsUUFBUTtRQUNOLElBQUksQ0FBQyxNQUFNLEVBQUUsQ0FBQztJQUNoQixDQUFDO0lBRUQsTUFBTTtRQUNKLElBQUksQ0FBQyxPQUFPLEdBQUcsVUFBVSxDQUFDLEdBQUcsRUFBRTtZQUM3QixJQUFJLElBQUksQ0FBQyxDQUFDLEdBQUcs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QUNHLEtBQUs7c0JBQWIsS0FBSztnQkFDRyxNQUFNO3NCQUFkLEtBQUs7Z0JBQ0csVUFBVTtzQkFBbEIsS0FBSztnQkFDRyxRQUFRO3NCQUFoQixLQUFLO2dCQUNHLGlCQUFpQjtzQkFBekIsS0FBSztnQkFDRyx5QkFBeUI7c0JBQWpDLEtBQUsiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyB0cmlnZ2VyLCBzdGF0ZSwgc3R5bGUsIHRyYW5zaXRpb24sIGFuaW1hdGUgfSBmcm9tICdAYW5ndWxhci9hbmltYXRpb25zJztcbmltcG9ydCB7IENvbXBvbmVudCwgRWxlbWVudFJlZiwgSW5wdXQsIE9uSW5pdCwgVmlld0NoaWxkIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ25neC1tLWNhcm91c2VsJyxcbiAgdGVtcGxhdGVVcmw6ICcuL25neC1tLWNhcm91c2VsLmNvbXBvbmVudC5odG1sJyxcbiAgc3R5bGVVcmxzOiBbXG4gICAgJy4vbmd4LW0tY2Fyb3VzZWwuY29tcG9uZW50LmNzcydcbiAgXSxcbiAgYW5pbWF0aW9uczogW1xuICAgIHRyaWdnZXIoJ3NsaWRlJywgW1xuICAgICAgc3RhdGUoJ3NsaWRlT25lJywgc3R5bGUoe1xuICAgICAgICB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKC17e3RyYW5zbGF0ZVZhbHVlfX0lKSdcbiAgICAgIH0pLFxuICAgICAgICB7IHBhcmFtczogeyB0cmFuc2xhdGVWYWx1ZTogMCB9IH1cbiAgICAgICksXG4gICAgICBzdGF0ZSgnc2xpZGVUd28nLCBzdHlsZSh7XG4gICAgICAgIHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoLXt7dHJhbnNsYXRlVmFsdWV9fSUpJ1xuICAgICAgfSksXG4gICAgICAgIHsgcGFyYW1zOiB7IHRyYW5zbGF0ZVZhbHVlOiAwIH0gfVxuICAgICAgKSxcbiAgICAgIHN0YXRlKCdzbGlkZVplcm8nLCBzdHlsZSh7XG4gICAgICB9KSxcbiAgICAgICAgeyBwYXJhbXM6IHsgdHJhbnNsYXRlVmFsdWU6IDAgfSB9XG4gICAgICApLFxuICAgICAgc3RhdGUoJ3NsaWRlQmFjaycsIHN0eWxlKHtcbiAgICAgICAgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCh7e3RyYW5zbGF0ZVZhbHVlfX0lKSdcbiAgICAgIH0pLFxuICAgICAgICB7IHBhcmFtczogeyB0cmFuc2xhdGVWYWx1ZTogMCB9IH1cbiAgICAgICksXG4gICAgICB0cmFuc2l0aW9uKCcqPT5zbGlkZU9uZScsIFtcbiAgICAgICAgYW5pbWF0ZSgnMTAwMG1zIGVhc2Utb3V0JylcbiAgICAgIF0pLFxuICAgICAgdHJhbnNpdGlvbignKj0+c2xpZGVUd28nLCBbXG4gICAgICAgIGFuaW1hdGUoJzEwMDBtcyBlYXNlLW91dCcpXG4gICAgICBdKSxcbiAgICAgIHRyYW5zaXRpb24oJyo9PnNsaWRlWmVybycsIFtcbiAgICAgICAgc3R5bGUoeyBvcGFjaXR5OiAwLCB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDApJyB9KSxcbiAgICAgICAgYW5pbWF0ZSgnMTUwMG1zIGVhc2Utb3V0Jywgc3R5bGUoeyBvcGFjaXR5OiAxIH0pKVxuICAgICAgXSlcbiAgICBdKSxcbiAgXVxufSlcbmV4cG9ydCBjbGFzcyBOZ3hNQ2Fyb3VzZWxDb21wb25lbnQgaW1wbGVtZW50cyBPbkluaXQge1xuXG4gIEBWaWV3Q2hpbGQoXCJjYXJvdXNlbFwiLCB7IHJlYWQ6IEVsZW1lbnRSZWYgfSkgY2Fyb3VzZWwhOiBFbGVtZW50UmVmO1xuXG4gIEBJbnB1dCgpIGltYWdlczogQXJyYXk8U3RyaW5nPiA9IFtdO1xuICBASW5wdXQoKSBkZWxheTogbnVtYmVyID0gNTAwMDtcbiAgQElucHV0KCkgcGF1c2VPbkhvdmVyOiBib29sZWFuID0gZmFsc2U7XG4gIEBJbnB1dCgpIHdpZHRoOiBTdHJpbmcgPSAnMTAwJSc7XG4gIEBJbnB1dCgpIGhlaWdodDogU3RyaW5nID0gJzEwMCUnO1xuICBASW5wdXQoKSBpbmRpY2F0b3JzOiBib29sZWFuID0gdHJ1ZTtcbiAgQElucHV0KCkgY29udHJvbHM6IGJvb2xlYW4gPSB0cnVlO1xuICBASW5wdXQoKSBjbGlja1RvRnVsbFNjcmVlbjogYm9vbGVhbiA9IHRydWU7XG4gIEBJbnB1dCgpIHByZXNlcnZlUmF0aW9PbkZ1bGxTY3JlZW46IGJvb2xlYW4gPSBmYWxzZTtcbiAgc2xpZGU6IHN0cmluZyA9ICdzbGlkZVplcm8nO1xuICB4OiBudW1iZXIgPSAwO1xuICBoYW5kbGVyOiBhbnk7XG4gIGlzRnVsbFNjcmVlbjogYm9vbGVhbiA9IGZhbHNlO1xuXG4gIG5nT25Jbml0KCkge1xuICAgIHRoaXMudG9nZ2xlKCk7XG4gIH1cblxuICB0b2dnbGUoKSB7XG4gICAgdGhpcy5oYW5kbGVyID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICBpZiAodGhpcy54IDwgKHRoaXMuaW1hZ2VzLmxlbmd0aCAtIDEpICogMTAwKSB7XG4gICAgICAgIHRoaXMueCA9IHRoaXMueCArIDEwMDtcbiAgICAgICAgdGhpcy5zbGlkZSA9IHRoaXMuc2xpZGUgPT0gXCJzbGlkZU9uZVwiID8gXCJzbGlkZVR3b1wiIDogXCJzbGlkZU9uZVwiO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdGhpcy5zbGlkZSA9IFwic2xpZGVaZXJvXCI7XG4gICAgICAgIHRoaXMueCA9IDA7XG4gICAgICB9XG4gICAgICB0aGlzLnRvZ2dsZSgpO1xuICAgIH0sIHRoaXMuZGVsYXkpO1xuICB9XG5cbiAgZ29UbyhldmVudDogRXZlbnQsIHg6IG51bWJlcikge1xuICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpO1xuICAgIHRoaXMueCA9IHggKiAxMDA7XG4gICAgdGhpcy5zbGlkZSA9IHRoaXMuc2xpZGUgPT0gXCJzbGlkZU9uZVwiID8gXCJzbGlkZVR3b1wiIDogXCJzbGlkZU9uZVwiO1xuICAgIHdpbmRvdy5jbGVhclRpbWVvdXQodGhpcy5oYW5kbGVyKTtcbiAgICB0aGlzLnRvZ2dsZSgpO1xuICAgIHRoaXMub25Ib3ZlcigpO1xuICB9XG5cbiAgb25Ib3ZlcigpIHtcbiAgICBpZiAodGhpcy5wYXVzZU9uSG92ZXIpIHdpbmRvdy5jbGVhclRpbWVvdXQodGhpcy5oYW5kbGVyKTtcbiAgfVxuXG4gIG9uTGVhdmUoKSB7XG4gICAgaWYgKHRoaXMucGF1c2VPbkhvdmVyKSB0aGlzLnRvZ2dsZSgpO1xuICB9XG5cbiAgb3BlbkZ1bGxzY3JlZW4oKSB7XG4gICAgaWYgKHRoaXMuY2xpY2tUb0Z1bGxTY3JlZW4pIHtcbiAgICAgIHRoaXMuaXNGdWxsU2NyZWVuID0gdHJ1ZTtcbiAgICAgIGlmICh0aGlzLmNhcm91c2VsPy5uYXRpdmVFbGVtZW50LnJlcXVlc3RGdWxsc2NyZWVuKSB7XG4gICAgICAgIHRoaXMuY2Fyb3VzZWw/Lm5hdGl2ZUVsZW1lbnQucmVxdWVzdEZ1bGxzY3JlZW4oKTtcbiAgICAgIH0gZWxzZSBpZiAodGhpcy5jYXJvdXNlbD8ubmF0aXZlRWxlbWVudC53ZWJraXRSZXF1ZXN0RnVsbHNjcmVlbikgeyAvKiBTYWZhcmkgKi9cbiAgICAgICAgdGhpcy5jYXJvdXNlbD8ubmF0aXZlRWxlbWVudC53ZWJraXRSZXF1ZXN0RnVsbHNjcmVlbigpO1xuICAgICAgfSBlbHNlIGlmICh0aGlzLmNhcm91c2VsPy5uYXRpdmVFbGVtZW50Lm1zUmVxdWVzdEZ1bGxzY3JlZW4pIHsgLyogSUUxMSAqL1xuICAgICAgICB0aGlzLmNhcm91c2VsPy5uYXRpdmVFbGVtZW50Lm1zUmVxdWVzdEZ1bGxzY3JlZW4oKTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICBjbG9zZUZ1bGxTY3JlZW4oZXZlbnQ6IEV2ZW50KSB7XG4gICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgdGhpcy5pc0Z1bGxTY3JlZW4gPSBmYWxzZTtcbiAgICBpZiAodGhpcy5pc0Z1bGxTY3JlZW4gJiYgZG9jdW1lbnQuZXhpdEZ1bGxzY3JlZW4pIHtcbiAgICAgIGRvY3VtZW50LmV4aXRGdWxsc2NyZWVuKCk7XG4gICAgfSBlbHNlIGlmICgoZG9jdW1lbnQgYXMgYW55KS53ZWJraXRFeGl0RnVsbHNjcmVlbikgeyAvKiBTYWZhcmkgKi9cbiAgICAgIChkb2N1bWVudCBhcyBhbnkpLndlYmtpdEV4aXRGdWxsc2NyZWVuKCk7XG4gICAgfSBlbHNlIGlmICgoZG9jdW1lbnQgYXMgYW55KS5tc0V4aXRGdWxsc2NyZWVuKSB7IC8qIElFMTEgKi9cbiAgICAgIChkb2N1bWVudCBhcyBhbnkpLm1zRXhpdEZ1bGxzY3JlZW4oKTtcbiAgICB9XG4gIH1cblxufVxuIiwiPGRpdiAjY2Fyb3VzZWwgKGNsaWNrKT1cIm9wZW5GdWxsc2NyZWVuKClcIiAobW91c2VlbnRlcik9XCJvbkhvdmVyKClcIiAobW91c2VsZWF2ZSk9XCJvbkxlYXZlKClcIiBjbGFzcz1cIm1haW5cIlxuICAgIFtzdHlsZS53aWR0aF09XCJ3aWR0aFwiIFtzdHlsZS5oZWlnaHRdPVwiaGVpZ2h0XCIgW3N0eWxlLmRpc3BsYXldPVwiaXNGdWxsU2NyZWVuPydmbGV4JzonYmxvY2snXCI+XG4gICAgPGRpdiBbQHNsaWRlXT1cInt2YWx1ZTogc2xpZGUsIHBhcmFtczoge3RyYW5zbGF0ZVZhbHVlOiB4fX1cIiBjbGFzcz1cImNhcm91c2VsXCI+XG4gICAgICAgIDxpbWcgKm5nRm9yPVwibGV0IGltZyBvZiBpbWFnZXNcIiBbc3JjXT1cImltZ1wiPlxuICAgIDwvZGl2PlxuICAgIDxkaXYgKm5nSWY9XCJjb250cm9sc1wiIGNsYXNzPVwiY29udHJvbHNcIj5cbiAgICAgICAgPHNwYW4gKGNsaWNrKT1cImdvVG8oJGV2ZW50LCh4LzEwMCk+MD8oeC8xMDApLTE6aW1hZ2VzLmxlbmd0aC0xKVwiIGNsYXNzPVwiYnV0dG9ucyBwcmV2XCI+XG4gICAgICAgICAgICA8c3ZnIHZlcnNpb249XCIxLjFcIiBpZD1cIkxheWVyXzFcIiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCJcbiAgICAgICAgICAgICAgICB4bWxuczp4bGluaz1cImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmtcIiB4PVwiMHB4XCIgeT1cIjBweFwiIHZpZXdCb3g9XCIwIDAgNDc1LjU1OCA0NzUuNTU4XCJcbiAgICAgICAgICAgICAgICBzdHlsZT1cImVuYWJsZS1iYWNrZ3JvdW5kOm5ldyAwIDAgNDc1LjU1OCA0NzUuNTU4O1wiIHhtbDpzcGFjZT1cInByZXNlcnZlXCI+XG4gICAgICAgICAgICAgICAgPGNpcmNsZSBzdHlsZT1cImZpbGw6I2ZmZmZmZjtcIiBjeD1cIjIzNy43NzlcIiBjeT1cIjIzNy43NzlcIiByPVwiMjM3Ljc3OVwiIC8+XG4gICAgICAgICAgICAgICAgPHBhdGggc3R5bGU9XCJmaWxsOiMwMDAwMDA7XCIgZD1cIk0yMTQuMTgxLDI0MC4zMzJjMjkuNDI5LTI5LjQyNSw1OC44NTctNTguODUzLDg4LjI3OC04OC4yNzhcbiAgIGMyNS42NjYtMjUuNjYzLTE0LjMxNi02NS4zNDEtNDAuMDM5LTM5LjYxNWMtMzYuMDI5LDM2LjAyOS03Mi4wNTUsNzIuMDU1LTEwOC4wODQsMTA4LjA4NFxuICAgYy0xMC44ODgsMTAuODg1LTEwLjU4OCwyOS4wMjMsMC4yMTQsMzkuODI5YzM2LjAyOSwzNi4wMjksNzIuMDU1LDcyLjA1OCwxMDguMDg0LDEwOC4wODdcbiAgIGMyNS42NjYsMjUuNjY2LDY1LjM0NS0xNC4zMTYsMzkuNjE1LTQwLjA0M0MyNzIuODg4LDI5OS4wMzksMjQzLjUzNSwyNjkuNjg2LDIxNC4xODEsMjQwLjMzMnpcIiAvPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPC9zdmc+XG4gICAgICAgIDwvc3Bhbj5cbiAgICAgICAgPHNwYW4gKGNsaWNrKT1cImdvVG8oJGV2ZW50LCh4LzEwMCk8aW1hZ2VzLmxlbmd0aC0xPyh4LzEwMCkrMTowKVwiIGNsYXNzPVwiYnV0dG9ucyBuZXh0XCI+XG4gICAgICAgICAgICA8c3ZnIHZlcnNpb249XCIxLjFcIiBpZD1cIkxheWVyXzFcIiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCJcbiAgICAgICAgICAgICAgICB4bWxuczp4bGluaz1cImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmtcIiB4PVwiMHB4XCIgeT1cIjBweFwiIHZpZXdCb3g9XCIwIDAgNDc1LjU1OCA0NzUuNTU4XCJcbiAgICAgICAgICAgICAgICBzdHlsZT1cImVuYWJsZS1iYWNrZ3JvdW5kOm5ldyAwIDAgNDc1LjU1OCA0NzUuNTU4O1wiIHhtbDpzcGFjZT1cInByZXNlcnZlXCI+XG4gICAgICAgICAgICAgICAgPGNpcmNsZSBzdHlsZT1cImZpbGw6I2ZmZmZmZjtcIiBjeD1cIjIzNy43NzlcIiBjeT1cIjIzNy43NzlcIiByPVwiMjM3Ljc3OVwiIC8+XG4gICAgICAgICAgICAgICAgPHBhdGggc3R5bGU9XCJmaWxsOiMwMDAwMDA7XCIgZD1cIk0yMTQuMTgxLDI0MC4zMzJjMjkuNDI5LTI5LjQyNSw1OC44NTctNTguODUzLDg4LjI3OC04OC4yNzhcbiAgIGMyNS42NjYtMjUuNjYzLTE0LjMxNi02NS4zNDEtNDAuMDM5LTM5LjYxNWMtMzYuMDI5LDM2LjAyOS03Mi4wNTUsNzIuMDU1LTEwOC4wODQsMTA4LjA4NFxuICAgYy0xMC44ODgsMTAuODg1LTEwLjU4OCwyOS4wMjMsMC4yMTQsMzkuODI5YzM2LjAyOSwzNi4wMjksNzIuMDU1LDcyLjA1OCwxMDguMDg0LDEwOC4wODdcbiAgIGMyNS42NjYsMjUuNjY2LDY1LjM0NS0xNC4zMTYsMzkuNjE1LTQwLjA0M0MyNzIuODg4LDI5OS4wMzksMjQzLjUzNSwyNjkuNjg2LDIxNC4xODEsMjQwLjMzMnpcIiAvPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgICAgIDxnPjwvZz5cbiAgICAgICAgICAgICAgICA8Zz48L2c+XG4gICAgICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPC9zdmc+XG4gICAgICAgIDwvc3Bhbj5cbiAgICA8L2Rpdj5cbiAgICA8ZGl2ICpuZ0lmPVwiaW5kaWNhdG9yc1wiIGNsYXNzPVwiaW5kaWNhdG9yc1wiPlxuICAgICAgICA8b2wgY2xhc3M9XCJjYXJvdXNlbC1idXR0b25zXCI+XG4gICAgICAgICAgICA8bGkgKm5nRm9yPVwibGV0IGltZyBvZiBpbWFnZXM7IGxldCBpID0gaW5kZXhcIiAoY2xpY2spPVwiZ29UbygkZXZlbnQsaSlcIiBbY2xhc3MuYWN0aXZlXT1cIng9PT1pKjEwMFwiPjwvbGk+XG4gICAgICAgIDwvb2w+XG4gICAgPC9kaXY+XG4gICAgPHNwYW4gKm5nSWY9XCJpc0Z1bGxTY3JlZW5cIiBjbGFzcz1cImJ1dHRvbnMgY2xvc2VcIiAoY2xpY2spPVwiY2xvc2VGdWxsU2NyZWVuKCRldmVudClcIj5cbiAgICAgICAgPHN2ZyB2ZXJzaW9uPVwiMS4xXCIgaWQ9XCJDYXBhXzFcIiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgeG1sbnM6eGxpbms9XCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rXCJcbiAgICAgICAgICAgIHg9XCIwcHhcIiB5PVwiMHB4XCIgdmlld0JveD1cIjAgMCAyNTIgMjUyXCIgc3R5bGU9XCJlbmFibGUtYmFja2dyb3VuZDpuZXcgMCAwIDI1MiAyNTI7XCIgeG1sOnNwYWNlPVwicHJlc2VydmVcIj5cbiAgICAgICAgICAgIDxnPlxuICAgICAgICAgICAgICAgIDxwYXRoIGQ9XCJNMTI2LDBDNTYuNTIzLDAsMCw1Ni41MjMsMCwxMjZzNTYuNTIzLDEyNiwxMjYsMTI2czEyNi01Ni41MjMsMTI2LTEyNlMxOTUuNDc3LDAsMTI2LDB6IE0xMjYsMjM0XG5cdFx0Yy01OS41NTEsMC0xMDgtNDguNDQ5LTEwOC0xMDhTNjYuNDQ5LDE4LDEyNiwxOHMxMDgsNDguNDQ5LDEwOCwxMDhTMTg1LjU1MSwyMzQsMTI2LDIzNHpcIiAvPlxuICAgICAgICAgICAgICAgIDxwYXRoIGQ9XCJNMTY0LjYxMiw4Ny4zODhjLTMuNTE1LTMuNTE1LTkuMjEzLTMuNTE1LTEyLjcyOCwwTDEyNiwxMTMuMjcybC0yNS44ODUtMjUuODg1Yy0zLjUxNS0zLjUxNS05LjIxMy0zLjUxNS0xMi43MjgsMFxuXHRcdGMtMy41MTUsMy41MTUtMy41MTUsOS4yMTMsMCwxMi43MjhMMTEzLjI3MiwxMjZsLTI1Ljg4NSwyNS44ODVjLTMuNTE1LDMuNTE1LTMuNTE1LDkuMjEzLDAsMTIuNzI4XG5cdFx0YzEuNzU3LDEuNzU3LDQuMDYxLDIuNjM2LDYuMzY0LDIuNjM2czQuNjA2LTAuODc5LDYuMzY0LTIuNjM2TDEyNiwxMzguNzI4bDI1Ljg4NSwyNS44ODVjMS43NTcsMS43NTcsNC4wNjEsMi42MzYsNi4zNjQsMi42MzZcblx0XHRzNC42MDYtMC44NzksNi4zNjQtMi42MzZjMy41MTUtMy41MTUsMy41MTUtOS4yMTMsMC0xMi43MjhMMTM4LjcyOCwxMjZsMjUuODg1LTI1Ljg4NVxuXHRcdEMxNjguMTI3LDk2LjYwMSwxNjguMTI3LDkwLjkwMiwxNjQuNjEyLDg3LjM4OHpcIiAvPlxuICAgICAgICAgICAgPC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICAgICAgPGc+PC9nPlxuICAgICAgICA8L3N2Zz5cblxuICAgIDwvc3Bhbj5cbjwvZGl2PiJdfQ==