ng-zorro-antd
Version:
An enterprise-class UI components based on Ant Design and Angular
263 lines • 38 kB
JavaScript
/**
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://github.com/NG-ZORRO/ng-zorro-antd/blob/master/LICENSE
*/
import { DOCUMENT } from '@angular/common';
import { ChangeDetectionStrategy, Component, Input, inject, numberAttribute } from '@angular/core';
import { getPixelRatio, getStyleStr, reRendering, rotateWatermark } from './util';
import * as i0 from "@angular/core";
/**
* Base size of the canvas, 1 for parallel layout and 2 for alternate layout
* Only alternate layout is currently supported
*/
const BaseSize = 2;
const FontGap = 3;
export class NzWaterMarkComponent {
constructor(el, cdr) {
this.el = el;
this.cdr = cdr;
this.nzWidth = 120;
this.nzHeight = 64;
this.nzRotate = -22;
this.nzZIndex = 9;
this.nzImage = '';
this.nzContent = '';
this.nzFont = {};
this.nzGap = [100, 100];
this.nzOffset = [this.nzGap[0] / 2, this.nzGap[1] / 2];
this.document = inject(DOCUMENT);
this.waterMarkElement = this.document.createElement('div');
this.stopObservation = false;
this.observer = new MutationObserver(mutations => {
if (this.stopObservation) {
return;
}
mutations.forEach(mutation => {
if (reRendering(mutation, this.waterMarkElement)) {
this.destroyWatermark();
this.renderWatermark();
}
});
});
}
ngOnInit() {
this.observer.observe(this.el.nativeElement, {
subtree: true,
childList: true,
attributeFilter: ['style', 'class']
});
}
ngAfterViewInit() {
this.renderWatermark();
}
ngOnChanges(changes) {
const { nzRotate, nzZIndex, nzWidth, nzHeight, nzImage, nzContent, nzFont, gapX, gapY, offsetLeft, offsetTop } = changes;
if (nzRotate ||
nzZIndex ||
nzWidth ||
nzHeight ||
nzImage ||
nzContent ||
nzFont ||
gapX ||
gapY ||
offsetLeft ||
offsetTop) {
this.renderWatermark();
}
}
getFont() {
const font = {
color: 'rgba(0,0,0,.15)',
fontSize: 16,
fontWeight: 'normal',
fontFamily: 'sans-serif',
fontStyle: 'normal'
};
this.nzFont = { ...font, ...this.nzFont };
this.cdr.markForCheck();
}
getMarkStyle() {
const markStyle = {
zIndex: this.nzZIndex,
position: 'absolute',
left: 0,
top: 0,
width: '100%',
height: '100%',
pointerEvents: 'none',
backgroundRepeat: 'repeat',
visibility: 'visible'
};
/** Calculate the style of the nzOffset */
let positionLeft = (this.nzOffset?.[0] ?? this.nzGap[0] / 2) - this.nzGap[0] / 2;
let positionTop = (this.nzOffset?.[1] ?? this.nzGap[1] / 2) - this.nzGap[1] / 2;
if (positionLeft > 0) {
markStyle.left = `${positionLeft}px`;
markStyle.width = `calc(100% - ${positionLeft}px)`;
positionLeft = 0;
}
if (positionTop > 0) {
markStyle.top = `${positionTop}px`;
markStyle.height = `calc(100% - ${positionTop}px)`;
positionTop = 0;
}
markStyle.backgroundPosition = `${positionLeft}px ${positionTop}px`;
return markStyle;
}
destroyWatermark() {
if (this.waterMarkElement) {
this.waterMarkElement.remove();
}
}
appendWatermark(base64Url, markWidth) {
this.stopObservation = true;
this.waterMarkElement.setAttribute('style', getStyleStr({
...this.getMarkStyle(),
backgroundImage: `url('${base64Url}')`,
backgroundSize: `${(this.nzGap[0] + markWidth) * BaseSize}px`
}));
this.el.nativeElement.append(this.waterMarkElement);
this.cdr.markForCheck();
// Delayed execution
setTimeout(() => {
this.stopObservation = false;
this.cdr.markForCheck();
});
}
getMarkSize(ctx) {
let defaultWidth = 120;
let defaultHeight = 64;
if (!this.nzImage && ctx.measureText) {
ctx.font = `${Number(this.nzFont.fontSize)}px ${this.nzFont.fontFamily}`;
const contents = Array.isArray(this.nzContent) ? this.nzContent : [this.nzContent];
const widths = contents.map(item => ctx.measureText(item).width);
defaultWidth = Math.ceil(Math.max(...widths));
defaultHeight = Number(this.nzFont.fontSize) * contents.length + (contents.length - 1) * FontGap;
}
return [this.nzWidth ?? defaultWidth, this.nzHeight ?? defaultHeight];
}
fillTexts(ctx, drawX, drawY, drawWidth, drawHeight) {
const ratio = getPixelRatio();
const mergedFontSize = Number(this.nzFont.fontSize) * ratio;
ctx.font = `${this.nzFont.fontStyle} normal ${this.nzFont.fontWeight} ${mergedFontSize}px/${drawHeight}px ${this.nzFont.fontFamily}`;
if (this.nzFont.color)
ctx.fillStyle = this.nzFont.color;
ctx.textAlign = 'center';
ctx.textBaseline = 'top';
ctx.translate(drawWidth / 2, 0);
const contents = Array.isArray(this.nzContent) ? this.nzContent : [this.nzContent];
contents?.forEach((item, index) => {
ctx.fillText(item ?? '', drawX, drawY + index * (mergedFontSize + FontGap * ratio));
});
}
drawText(canvas, ctx, drawX, drawY, drawWidth, drawHeight, alternateRotateX, alternateRotateY, alternateDrawX, alternateDrawY, markWidth) {
this.fillTexts(ctx, drawX, drawY, drawWidth, drawHeight);
/** Fill the interleaved text after rotation */
ctx.restore();
rotateWatermark(ctx, alternateRotateX, alternateRotateY, this.nzRotate);
this.fillTexts(ctx, alternateDrawX, alternateDrawY, drawWidth, drawHeight);
this.appendWatermark(canvas.toDataURL(), markWidth);
}
renderWatermark() {
if (!this.nzContent && !this.nzImage) {
return;
}
const canvas = this.document.createElement('canvas');
const ctx = canvas.getContext('2d');
if (ctx) {
if (!this.waterMarkElement) {
this.waterMarkElement = this.document.createElement('div');
}
this.getFont();
const ratio = getPixelRatio();
const [markWidth, markHeight] = this.getMarkSize(ctx);
const canvasWidth = (this.nzGap[0] + markWidth) * ratio;
const canvasHeight = (this.nzGap[1] + markHeight) * ratio;
canvas.setAttribute('width', `${canvasWidth * BaseSize}px`);
canvas.setAttribute('height', `${canvasHeight * BaseSize}px`);
const drawX = (this.nzGap[0] * ratio) / 2;
const drawY = (this.nzGap[1] * ratio) / 2;
const drawWidth = markWidth * ratio;
const drawHeight = markHeight * ratio;
const rotateX = (drawWidth + this.nzGap[0] * ratio) / 2;
const rotateY = (drawHeight + this.nzGap[1] * ratio) / 2;
/** Alternate drawing parameters */
const alternateDrawX = drawX + canvasWidth;
const alternateDrawY = drawY + canvasHeight;
const alternateRotateX = rotateX + canvasWidth;
const alternateRotateY = rotateY + canvasHeight;
ctx.save();
rotateWatermark(ctx, rotateX, rotateY, this.nzRotate);
if (this.nzImage) {
const img = new Image();
const onLoad = () => {
cleanup();
ctx.drawImage(img, drawX, drawY, drawWidth, drawHeight);
/** Draw interleaved pictures after rotation */
ctx.restore();
rotateWatermark(ctx, alternateRotateX, alternateRotateY, this.nzRotate);
ctx.drawImage(img, alternateDrawX, alternateDrawY, drawWidth, drawHeight);
this.appendWatermark(canvas.toDataURL(), markWidth);
};
const onError = () => {
cleanup();
this.drawText(canvas, ctx, drawX, drawY, drawWidth, drawHeight, alternateRotateX, alternateRotateY, alternateDrawX, alternateDrawY, markWidth);
};
const cleanup = () => {
img.removeEventListener('load', onLoad);
img.removeEventListener('error', onError);
};
img.addEventListener('load', onLoad);
img.addEventListener('error', onError);
img.crossOrigin = 'anonymous';
img.referrerPolicy = 'no-referrer';
img.src = this.nzImage;
}
else {
this.drawText(canvas, ctx, drawX, drawY, drawWidth, drawHeight, alternateRotateX, alternateRotateY, alternateDrawX, alternateDrawY, markWidth);
}
}
}
ngOnDestroy() {
this.observer.disconnect();
}
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.1", ngImport: i0, type: NzWaterMarkComponent, deps: [{ token: i0.ElementRef }, { token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component }); }
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "16.1.0", version: "18.2.1", type: NzWaterMarkComponent, isStandalone: true, selector: "nz-water-mark", inputs: { nzWidth: ["nzWidth", "nzWidth", numberAttribute], nzHeight: ["nzHeight", "nzHeight", numberAttribute], nzRotate: ["nzRotate", "nzRotate", numberAttribute], nzZIndex: ["nzZIndex", "nzZIndex", numberAttribute], nzImage: "nzImage", nzContent: "nzContent", nzFont: "nzFont", nzGap: "nzGap", nzOffset: "nzOffset" }, host: { classAttribute: "ant-water-mark" }, exportAs: ["NzWaterMark"], usesOnChanges: true, ngImport: i0, template: ` <ng-content></ng-content> `, isInline: true, changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.1", ngImport: i0, type: NzWaterMarkComponent, decorators: [{
type: Component,
args: [{
selector: 'nz-water-mark',
standalone: true,
exportAs: 'NzWaterMark',
changeDetection: ChangeDetectionStrategy.OnPush,
template: ` <ng-content></ng-content> `,
host: {
class: 'ant-water-mark'
}
}]
}], ctorParameters: () => [{ type: i0.ElementRef }, { type: i0.ChangeDetectorRef }], propDecorators: { nzWidth: [{
type: Input,
args: [{ transform: numberAttribute }]
}], nzHeight: [{
type: Input,
args: [{ transform: numberAttribute }]
}], nzRotate: [{
type: Input,
args: [{ transform: numberAttribute }]
}], nzZIndex: [{
type: Input,
args: [{ transform: numberAttribute }]
}], nzImage: [{
type: Input
}], nzContent: [{
type: Input
}], nzFont: [{
type: Input
}], nzGap: [{
type: Input
}], nzOffset: [{
type: Input
}] } });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoid2F0ZXItbWFyay5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9jb21wb25lbnRzL3dhdGVyLW1hcmsvd2F0ZXItbWFyay5jb21wb25lbnQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUE7OztHQUdHO0FBRUgsT0FBTyxFQUFFLFFBQVEsRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBQzNDLE9BQU8sRUFFTCx1QkFBdUIsRUFFdkIsU0FBUyxFQUVULEtBQUssRUFLTCxNQUFNLEVBQ04sZUFBZSxFQUNoQixNQUFNLGVBQWUsQ0FBQztBQUd2QixPQUFPLEVBQUUsYUFBYSxFQUFFLFdBQVcsRUFBRSxXQUFXLEVBQUUsZUFBZSxFQUFFLE1BQU0sUUFBUSxDQUFDOztBQUVsRjs7O0dBR0c7QUFDSCxNQUFNLFFBQVEsR0FBRyxDQUFDLENBQUM7QUFDbkIsTUFBTSxPQUFPLEdBQUcsQ0FBQyxDQUFDO0FBWWxCLE1BQU0sT0FBTyxvQkFBb0I7SUE0Qi9CLFlBQ1UsRUFBYyxFQUNkLEdBQXNCO1FBRHRCLE9BQUUsR0FBRixFQUFFLENBQVk7UUFDZCxRQUFHLEdBQUgsR0FBRyxDQUFtQjtRQTdCTyxZQUFPLEdBQVcsR0FBRyxDQUFDO1FBQ3RCLGFBQVEsR0FBVyxFQUFFLENBQUM7UUFDdEIsYUFBUSxHQUFXLENBQUMsRUFBRSxDQUFDO1FBQ3ZCLGFBQVEsR0FBVyxDQUFDLENBQUM7UUFDbkQsWUFBTyxHQUFXLEVBQUUsQ0FBQztRQUNyQixjQUFTLEdBQXNCLEVBQUUsQ0FBQztRQUNsQyxXQUFNLEdBQWEsRUFBRSxDQUFDO1FBQ3RCLFVBQUssR0FBcUIsQ0FBQyxHQUFHLEVBQUUsR0FBRyxDQUFDLENBQUM7UUFDckMsYUFBUSxHQUFxQixDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxFQUFFLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUM7UUFFckUs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QUFwQixvQkFBb0IsMkZBQ1gsZUFBZSxzQ0FDZixlQUFlLHNDQUNmLGVBQWUsc0NBQ2YsZUFBZSw2TkFUekIsNkJBQTZCOzsyRkFLNUIsb0JBQW9CO2tCQVZoQyxTQUFTO21CQUFDO29CQUNULFFBQVEsRUFBRSxlQUFlO29CQUN6QixVQUFVLEVBQUUsSUFBSTtvQkFDaEIsUUFBUSxFQUFFLGFBQWE7b0JBQ3ZCLGVBQWUsRUFBRSx1QkFBdUIsQ0FBQyxNQUFNO29CQUMvQyxRQUFRLEVBQUUsNkJBQTZCO29CQUN2QyxJQUFJLEVBQUU7d0JBQ0osS0FBSyxFQUFFLGdCQUFnQjtxQkFDeEI7aUJBQ0Y7K0dBRXdDLE9BQU87c0JBQTdDLEtBQUs7dUJBQUMsRUFBRSxTQUFTLEVBQUUsZUFBZSxFQUFFO2dCQUNFLFFBQVE7c0JBQTlDLEtBQUs7dUJBQUMsRUFBRSxTQUFTLEVBQUUsZUFBZSxFQUFFO2dCQUNFLFFBQVE7c0JBQTlDLEtBQUs7dUJBQUMsRUFBRSxTQUFTLEVBQUUsZUFBZSxFQUFFO2dCQUNFLFFBQVE7c0JBQTlDLEtBQUs7dUJBQUMsRUFBRSxTQUFTLEVBQUUsZUFBZSxFQUFFO2dCQUM1QixPQUFPO3NCQUFmLEtBQUs7Z0JBQ0csU0FBUztzQkFBakIsS0FBSztnQkFDRyxNQUFNO3NCQUFkLEtBQUs7Z0JBQ0csS0FBSztzQkFBYixLQUFLO2dCQUNHLFFBQVE7c0JBQWhCLEtBQUsiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIFVzZSBvZiB0aGlzIHNvdXJjZSBjb2RlIGlzIGdvdmVybmVkIGJ5IGFuIE1JVC1zdHlsZSBsaWNlbnNlIHRoYXQgY2FuIGJlXG4gKiBmb3VuZCBpbiB0aGUgTElDRU5TRSBmaWxlIGF0IGh0dHBzOi8vZ2l0aHViLmNvbS9ORy1aT1JSTy9uZy16b3Jyby1hbnRkL2Jsb2IvbWFzdGVyL0xJQ0VOU0VcbiAqL1xuXG5pbXBvcnQgeyBET0NVTUVOVCB9IGZyb20gJ0Bhbmd1bGFyL2NvbW1vbic7XG5pbXBvcnQge1xuICBBZnRlclZpZXdJbml0LFxuICBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneSxcbiAgQ2hhbmdlRGV0ZWN0b3JSZWYsXG4gIENvbXBvbmVudCxcbiAgRWxlbWVudFJlZixcbiAgSW5wdXQsXG4gIE9uQ2hhbmdlcyxcbiAgT25EZXN0cm95LFxuICBPbkluaXQsXG4gIFNpbXBsZUNoYW5nZXMsXG4gIGluamVjdCxcbiAgbnVtYmVyQXR0cmlidXRlXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuXG5pbXBvcnQgeyBGb250VHlwZSwgTWFya1N0eWxlVHlwZSB9IGZyb20gJy4vdHlwaW5ncyc7XG5pbXBvcnQgeyBnZXRQaXhlbFJhdGlvLCBnZXRTdHlsZVN0ciwgcmVSZW5kZXJpbmcsIHJvdGF0ZVdhdGVybWFyayB9IGZyb20gJy4vdXRpbCc7XG5cbi8qKlxuICogQmFzZSBzaXplIG9mIHRoZSBjYW52YXMsIDEgZm9yIHBhcmFsbGVsIGxheW91dCBhbmQgMiBmb3IgYWx0ZXJuYXRlIGxheW91dFxuICogT25seSBhbHRlcm5hdGUgbGF5b3V0IGlzIGN1cnJlbnRseSBzdXBwb3J0ZWRcbiAqL1xuY29uc3QgQmFzZVNpemUgPSAyO1xuY29uc3QgRm9udEdhcCA9IDM7XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ256LXdhdGVyLW1hcmsnLFxuICBzdGFuZGFsb25lOiB0cnVlLFxuICBleHBvcnRBczogJ056V2F0ZXJNYXJrJyxcbiAgY2hhbmdlRGV0ZWN0aW9uOiBDaGFuZ2VEZXRlY3Rpb25TdHJhdGVneS5PblB1c2gsXG4gIHRlbXBsYXRlOiBgIDxuZy1jb250ZW50PjwvbmctY29udGVudD4gYCxcbiAgaG9zdDoge1xuICAgIGNsYXNzOiAnYW50LXdhdGVyLW1hcmsnXG4gIH1cbn0pXG5leHBvcnQgY2xhc3MgTnpXYXRlck1hcmtDb21wb25lbnQgaW1wbGVtZW50cyBBZnRlclZpZXdJbml0LCBPbkluaXQsIE9uQ2hhbmdlcywgT25EZXN0cm95IHtcbiAgQElucHV0KHsgdHJhbnNmb3JtOiBudW1iZXJBdHRyaWJ1dGUgfSkgbnpXaWR0aDogbnVtYmVyID0gMTIwO1xuICBASW5wdXQoeyB0cmFuc2Zvcm06IG51bWJlckF0dHJpYnV0ZSB9KSBuekhlaWdodDogbnVtYmVyID0gNjQ7XG4gIEBJbnB1dCh7IHRyYW5zZm9ybTogbnVtYmVyQXR0cmlidXRlIH0pIG56Um90YXRlOiBudW1iZXIgPSAtMjI7XG4gIEBJbnB1dCh7IHRyYW5zZm9ybTogbnVtYmVyQXR0cmlidXRlIH0pIG56WkluZGV4OiBudW1iZXIgPSA5O1xuICBASW5wdXQoKSBuekltYWdlOiBzdHJpbmcgPSAnJztcbiAgQElucHV0KCkgbnpDb250ZW50OiBzdHJpbmcgfCBzdHJpbmdbXSA9ICcnO1xuICBASW5wdXQoKSBuekZvbnQ6IEZvbnRUeXBlID0ge307XG4gIEBJbnB1dCgpIG56R2FwOiBbbnVtYmVyLCBudW1iZXJdID0gWzEwMCwgMTAwXTtcbiAgQElucHV0KCkgbnpPZmZzZXQ6IFtudW1iZXIsIG51bWJlcl0gPSBbdGhpcy5uekdhcFswXSAvIDIsIHRoaXMubnpHYXBbMV0gLyAyXTtcblxuICBwcml2YXRlIGRvY3VtZW50OiBEb2N1bWVudCA9IGluamVjdChET0NVTUVOVCk7XG5cbiAgd2F0ZXJNYXJrRWxlbWVudDogSFRNTERpdkVsZW1lbnQgPSB0aGlzLmRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xuICBzdG9wT2JzZXJ2YXRpb246IGJvb2xlYW4gPSBmYWxzZTtcblxuICBvYnNlcnZlciA9IG5ldyBNdXRhdGlvbk9ic2VydmVyKG11dGF0aW9ucyA9PiB7XG4gICAgaWYgKHRoaXMuc3RvcE9ic2VydmF0aW9uKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIG11dGF0aW9ucy5mb3JFYWNoKG11dGF0aW9uID0+IHtcbiAgICAgIGlmIChyZVJlbmRlcmluZyhtdXRhdGlvbiwgdGhpcy53YXRlck1hcmtFbGVtZW50KSkge1xuICAgICAgICB0aGlzLmRlc3Ryb3lXYXRlcm1hcmsoKTtcbiAgICAgICAgdGhpcy5yZW5kZXJXYXRlcm1hcmsoKTtcbiAgICAgIH1cbiAgICB9KTtcbiAgfSk7XG5cbiAgY29uc3RydWN0b3IoXG4gICAgcHJpdmF0ZSBlbDogRWxlbWVudFJlZixcbiAgICBwcml2YXRlIGNkcjogQ2hhbmdlRGV0ZWN0b3JSZWZcbiAgKSB7fVxuXG4gIG5nT25Jbml0KCk6IHZvaWQge1xuICAgIHRoaXMub2JzZXJ2ZXIub2JzZXJ2ZSh0aGlzLmVsLm5hdGl2ZUVsZW1lbnQsIHtcbiAgICAgIHN1YnRyZWU6IHRydWUsXG4gICAgICBjaGlsZExpc3Q6IHRydWUsXG4gICAgICBhdHRyaWJ1dGVGaWx0ZXI6IFsnc3R5bGUnLCAnY2xhc3MnXVxuICAgIH0pO1xuICB9XG5cbiAgbmdBZnRlclZpZXdJbml0KCk6IHZvaWQge1xuICAgIHRoaXMucmVuZGVyV2F0ZXJtYXJrKCk7XG4gIH1cblxuICBuZ09uQ2hhbmdlcyhjaGFuZ2VzOiBTaW1wbGVDaGFuZ2VzKTogdm9pZCB7XG4gICAgY29uc3QgeyBuelJvdGF0ZSwgbnpaSW5kZXgsIG56V2lkdGgsIG56SGVpZ2h0LCBuekltYWdlLCBuekNvbnRlbnQsIG56Rm9udCwgZ2FwWCwgZ2FwWSwgb2Zmc2V0TGVmdCwgb2Zmc2V0VG9wIH0gPVxuICAgICAgY2hhbmdlcztcblxuICAgIGlmIChcbiAgICAgIG56Um90YXRlIHx8XG4gICAgICBuelpJbmRleCB8fFxuICAgICAgbnpXaWR0aCB8fFxuICAgICAgbnpIZWlnaHQgfHxcbiAgICAgIG56SW1hZ2UgfHxcbiAgICAgIG56Q29udGVudCB8fFxuICAgICAgbnpGb250IHx8XG4gICAgICBnYXBYIHx8XG4gICAgICBnYXBZIHx8XG4gICAgICBvZmZzZXRMZWZ0IHx8XG4gICAgICBvZmZzZXRUb3BcbiAgICApIHtcbiAgICAgIHRoaXMucmVuZGVyV2F0ZXJtYXJrKCk7XG4gICAgfVxuICB9XG5cbiAgZ2V0Rm9udCgpOiB2b2lkIHtcbiAgICBjb25zdCBmb250OiBGb250VHlwZSA9IHtcbiAgICAgIGNvbG9yOiAncmdiYSgwLDAsMCwuMTUpJyxcbiAgICAgIGZvbnRTaXplOiAxNixcbiAgICAgIGZvbnRXZWlnaHQ6ICdub3JtYWwnLFxuICAgICAgZm9udEZhbWlseTogJ3NhbnMtc2VyaWYnLFxuICAgICAgZm9udFN0eWxlOiAnbm9ybWFsJ1xuICAgIH07XG5cbiAgICB0aGlzLm56Rm9udCA9IHsgLi4uZm9udCwgLi4udGhpcy5uekZvbnQgfTtcbiAgICB0aGlzLmNkci5tYXJrRm9yQ2hlY2soKTtcbiAgfVxuXG4gIGdldE1hcmtTdHlsZSgpOiBNYXJrU3R5bGVUeXBlIHtcbiAgICBjb25zdCBtYXJrU3R5bGU6IE1hcmtTdHlsZVR5cGUgPSB7XG4gICAgICB6SW5kZXg6IHRoaXMubnpaSW5kZXgsXG4gICAgICBwb3NpdGlvbjogJ2Fic29sdXRlJyxcbiAgICAgIGxlZnQ6IDAsXG4gICAgICB0b3A6IDAsXG4gICAgICB3aWR0aDogJzEwMCUnLFxuICAgICAgaGVpZ2h0OiAnMTAwJScsXG4gICAgICBwb2ludGVyRXZlbnRzOiAnbm9uZScsXG4gICAgICBiYWNrZ3JvdW5kUmVwZWF0OiAncmVwZWF0JyxcbiAgICAgIHZpc2liaWxpdHk6ICd2aXNpYmxlJ1xuICAgIH07XG5cbiAgICAvKiogQ2FsY3VsYXRlIHRoZSBzdHlsZSBvZiB0aGUgbnpPZmZzZXQgKi9cbiAgICBsZXQgcG9zaXRpb25MZWZ0ID0gKHRoaXMubnpPZmZzZXQ/LlswXSA/PyB0aGlzLm56R2FwWzBdIC8gMikgLSB0aGlzLm56R2FwWzBdIC8gMjtcbiAgICBsZXQgcG9zaXRpb25Ub3AgPSAodGhpcy5uek9mZnNldD8uWzFdID8/IHRoaXMubnpHYXBbMV0gLyAyKSAtIHRoaXMubnpHYXBbMV0gLyAyO1xuICAgIGlmIChwb3NpdGlvbkxlZnQgPiAwKSB7XG4gICAgICBtYXJrU3R5bGUubGVmdCA9IGAke3Bvc2l0aW9uTGVmdH1weGA7XG4gICAgICBtYXJrU3R5bGUud2lkdGggPSBgY2FsYygxMDAlIC0gJHtwb3NpdGlvbkxlZnR9cHgpYDtcbiAgICAgIHBvc2l0aW9uTGVmdCA9IDA7XG4gICAgfVxuICAgIGlmIChwb3NpdGlvblRvcCA+IDApIHtcbiAgICAgIG1hcmtTdHlsZS50b3AgPSBgJHtwb3NpdGlvblRvcH1weGA7XG4gICAgICBtYXJrU3R5bGUuaGVpZ2h0ID0gYGNhbGMoMTAwJSAtICR7cG9zaXRpb25Ub3B9cHgpYDtcbiAgICAgIHBvc2l0aW9uVG9wID0gMDtcbiAgICB9XG4gICAgbWFya1N0eWxlLmJhY2tncm91bmRQb3NpdGlvbiA9IGAke3Bvc2l0aW9uTGVmdH1weCAke3Bvc2l0aW9uVG9wfXB4YDtcblxuICAgIHJldHVybiBtYXJrU3R5bGU7XG4gIH1cblxuICBkZXN0cm95V2F0ZXJtYXJrKCk6IHZvaWQge1xuICAgIGlmICh0aGlzLndhdGVyTWFya0VsZW1lbnQpIHtcbiAgICAgIHRoaXMud2F0ZXJNYXJrRWxlbWVudC5yZW1vdmUoKTtcbiAgICB9XG4gIH1cblxuICBhcHBlbmRXYXRlcm1hcmsoYmFzZTY0VXJsOiBzdHJpbmcsIG1hcmtXaWR0aDogbnVtYmVyKTogdm9pZCB7XG4gICAgdGhpcy5zdG9wT2JzZXJ2YXRpb24gPSB0cnVlO1xuICAgIHRoaXMud2F0ZXJNYXJrRWxlbWVudC5zZXRBdHRyaWJ1dGUoXG4gICAgICAnc3R5bGUnLFxuICAgICAgZ2V0U3R5bGVTdHIoe1xuICAgICAgICAuLi50aGlzLmdldE1hcmtTdHlsZSgpLFxuICAgICAgICBiYWNrZ3JvdW5kSW1hZ2U6IGB1cmwoJyR7YmFzZTY0VXJsfScpYCxcbiAgICAgICAgYmFja2dyb3VuZFNpemU6IGAkeyh0aGlzLm56R2FwWzBdICsgbWFya1dpZHRoKSAqIEJhc2VTaXplfXB4YFxuICAgICAgfSlcbiAgICApO1xuICAgIHRoaXMuZWwubmF0aXZlRWxlbWVudC5hcHBlbmQodGhpcy53YXRlck1hcmtFbGVtZW50KTtcbiAgICB0aGlzLmNkci5tYXJrRm9yQ2hlY2soKTtcblxuICAgIC8vIERlbGF5ZWQgZXhlY3V0aW9uXG4gICAgc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICB0aGlzLnN0b3BPYnNlcnZhdGlvbiA9IGZhbHNlO1xuICAgICAgdGhpcy5jZHIubWFya0ZvckNoZWNrKCk7XG4gICAgfSk7XG4gIH1cblxuICBnZXRNYXJrU2l6ZShjdHg6IENhbnZhc1JlbmRlcmluZ0NvbnRleHQyRCk6IFtudW1iZXIsIG51bWJlcl0ge1xuICAgIGxldCBkZWZhdWx0V2lkdGggPSAxMjA7XG4gICAgbGV0IGRlZmF1bHRIZWlnaHQgPSA2NDtcbiAgICBpZiAoIXRoaXMubnpJbWFnZSAmJiBjdHgubWVhc3VyZVRleHQpIHtcbiAgICAgIGN0eC5mb250ID0gYCR7TnVtYmVyKHRoaXMubnpGb250LmZvbnRTaXplKX1weCAke3RoaXMubnpGb250LmZvbnRGYW1pbHl9YDtcbiAgICAgIGNvbnN0IGNvbnRlbnRzID0gQXJyYXkuaXNBcnJheSh0aGlzLm56Q29udGVudCkgPyB0aGlzLm56Q29udGVudCA6IFt0aGlzLm56Q29udGVudF07XG4gICAgICBjb25zdCB3aWR0aHMgPSBjb250ZW50cy5tYXAoaXRlbSA9PiBjdHgubWVhc3VyZVRleHQoaXRlbSEpLndpZHRoKTtcbiAgICAgIGRlZmF1bHRXaWR0aCA9IE1hdGguY2VpbChNYXRoLm1heCguLi53aWR0aHMpKTtcbiAgICAgIGRlZmF1bHRIZWlnaHQgPSBOdW1iZXIodGhpcy5uekZvbnQuZm9udFNpemUpICogY29udGVudHMubGVuZ3RoICsgKGNvbnRlbnRzLmxlbmd0aCAtIDEpICogRm9udEdhcDtcbiAgICB9XG4gICAgcmV0dXJuIFt0aGlzLm56V2lkdGggPz8gZGVmYXVsdFdpZHRoLCB0aGlzLm56SGVpZ2h0ID8/IGRlZmF1bHRIZWlnaHRdO1xuICB9XG5cbiAgZmlsbFRleHRzKGN0eDogQ2FudmFzUmVuZGVyaW5nQ29udGV4dDJELCBkcmF3WDogbnVtYmVyLCBkcmF3WTogbnVtYmVyLCBkcmF3V2lkdGg6IG51bWJlciwgZHJhd0hlaWdodDogbnVtYmVyKTogdm9pZCB7XG4gICAgY29uc3QgcmF0aW8gPSBnZXRQaXhlbFJhdGlvKCk7XG4gICAgY29uc3QgbWVyZ2VkRm9udFNpemUgPSBOdW1iZXIodGhpcy5uekZvbnQuZm9udFNpemUpICogcmF0aW87XG4gICAgY3R4LmZvbnQgPSBgJHt0aGlzLm56Rm9udC5mb250U3R5bGV9IG5vcm1hbCAke3RoaXMubnpGb250LmZvbnRXZWlnaHR9ICR7bWVyZ2VkRm9udFNpemV9cHgvJHtkcmF3SGVpZ2h0fXB4ICR7dGhpcy5uekZvbnQuZm9udEZhbWlseX1gO1xuICAgIGlmICh0aGlzLm56Rm9udC5jb2xvcikgY3R4LmZpbGxTdHlsZSA9IHRoaXMubnpGb250LmNvbG9yO1xuICAgIGN0eC50ZXh0QWxpZ24gPSAnY2VudGVyJztcbiAgICBjdHgudGV4dEJhc2VsaW5lID0gJ3RvcCc7XG4gICAgY3R4LnRyYW5zbGF0ZShkcmF3V2lkdGggLyAyLCAwKTtcbiAgICBjb25zdCBjb250ZW50cyA9IEFycmF5LmlzQXJyYXkodGhpcy5uekNvbnRlbnQpID8gdGhpcy5uekNvbnRlbnQgOiBbdGhpcy5uekNvbnRlbnRdO1xuICAgIGNvbnRlbnRzPy5mb3JFYWNoKChpdGVtLCBpbmRleCkgPT4ge1xuICAgICAgY3R4LmZpbGxUZXh0KGl0ZW0gPz8gJycsIGRyYXdYLCBkcmF3WSArIGluZGV4ICogKG1lcmdlZEZvbnRTaXplICsgRm9udEdhcCAqIHJhdGlvKSk7XG4gICAgfSk7XG4gIH1cblxuICBkcmF3VGV4dChcbiAgICBjYW52YXM6IEhUTUxDYW52YXNFbGVtZW50LFxuICAgIGN0eDogQ2FudmFzUmVuZGVyaW5nQ29udGV4dDJELFxuICAgIGRyYXdYOiBudW1iZXIsXG4gICAgZHJhd1k6IG51bWJlcixcbiAgICBkcmF3V2lkdGg6IG51bWJlcixcbiAgICBkcmF3SGVpZ2h0OiBudW1iZXIsXG4gICAgYWx0ZXJuYXRlUm90YXRlWDogbnVtYmVyLFxuICAgIGFsdGVybmF0ZVJvdGF0ZVk6IG51bWJlcixcbiAgICBhbHRlcm5hdGVEcmF3WDogbnVtYmVyLFxuICAgIGFsdGVybmF0ZURyYXdZOiBudW1iZXIsXG4gICAgbWFya1dpZHRoOiBudW1iZXJcbiAgKTogdm9pZCB7XG4gICAgdGhpcy5maWxsVGV4dHMoY3R4LCBkcmF3WCwgZHJhd1ksIGRyYXdXaWR0aCwgZHJhd0hlaWdodCk7XG5cbiAgICAvKiogRmlsbCB0aGUgaW50ZXJsZWF2ZWQgdGV4dCBhZnRlciByb3RhdGlvbiAqL1xuICAgIGN0eC5yZXN0b3JlKCk7XG4gICAgcm90YXRlV2F0ZXJtYXJrKGN0eCwgYWx0ZXJuYXRlUm90YXRlWCwgYWx0ZXJuYXRlUm90YXRlWSwgdGhpcy5uelJvdGF0ZSk7XG4gICAgdGhpcy5maWxsVGV4dHMoY3R4LCBhbHRlcm5hdGVEcmF3WCwgYWx0ZXJuYXRlRHJhd1ksIGRyYXdXaWR0aCwgZHJhd0hlaWdodCk7XG4gICAgdGhpcy5hcHBlbmRXYXRlcm1hcmsoY2FudmFzLnRvRGF0YVVSTCgpLCBtYXJrV2lkdGgpO1xuICB9XG5cbiAgcmVuZGVyV2F0ZXJtYXJrKCk6IHZvaWQge1xuICAgIGlmICghdGhpcy5uekNvbnRlbnQgJiYgIXRoaXMubnpJbWFnZSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBjb25zdCBjYW52YXM6IEhUTUxDYW52YXNFbGVtZW50ID0gdGhpcy5kb2N1bWVudC5jcmVhdGVFbGVtZW50KCdjYW52YXMnKTtcbiAgICBjb25zdCBjdHggPSBjYW52YXMuZ2V0Q29udGV4dCgnMmQnKSBhcyBDYW52YXNSZW5kZXJpbmdDb250ZXh0MkQ7XG5cbiAgICBpZiAoY3R4KSB7XG4gICAgICBpZiAoIXRoaXMud2F0ZXJNYXJrRWxlbWVudCkge1xuICAgICAgICB0aGlzLndhdGVyTWFya0VsZW1lbnQgPSB0aGlzLmRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xuICAgICAgfVxuICAgICAgdGhpcy5nZXRGb250KCk7XG4gICAgICBjb25zdCByYXRpbyA9IGdldFBpeGVsUmF0aW8oKTtcbiAgICAgIGNvbnN0IFttYXJrV2lkdGgsIG1hcmtIZWlnaHRdID0gdGhpcy5nZXRNYXJrU2l6ZShjdHgpO1xuICAgICAgY29uc3QgY2FudmFzV2lkdGggPSAodGhpcy5uekdhcFswXSArIG1hcmtXaWR0aCkgKiByYXRpbztcbiAgICAgIGNvbnN0IGNhbnZhc0hlaWdodCA9ICh0aGlzLm56R2FwWzFdICsgbWFya0hlaWdodCkgKiByYXRpbztcbiAgICAgIGNhbnZhcy5zZXRBdHRyaWJ1dGUoJ3dpZHRoJywgYCR7Y2FudmFzV2lkdGggKiBCYXNlU2l6ZX1weGApO1xuICAgICAgY2FudmFzLnNldEF0dHJpYnV0ZSgnaGVpZ2h0JywgYCR7Y2FudmFzSGVpZ2h0ICogQmFzZVNpemV9cHhgKTtcblxuICAgICAgY29uc3QgZHJhd1ggPSAodGhpcy5uekdhcFswXSAqIHJhdGlvKSAvIDI7XG4gICAgICBjb25zdCBkcmF3WSA9ICh0aGlzLm56R2FwWzFdICogcmF0aW8pIC8gMjtcbiAgICAgIGNvbnN0IGRyYXdXaWR0aCA9IG1hcmtXaWR0aCAqIHJhdGlvO1xuICAgICAgY29uc3QgZHJhd0hlaWdodCA9IG1hcmtIZWlnaHQgKiByYXRpbztcbiAgICAgIGNvbnN0IHJvdGF0ZVggPSAoZHJhd1dpZHRoICsgdGhpcy5uekdhcFswXSAqIHJhdGlvKSAvIDI7XG4gICAgICBjb25zdCByb3RhdGVZID0gKGRyYXdIZWlnaHQgKyB0aGlzLm56R2FwWzFdICogcmF0aW8pIC8gMjtcblxuICAgICAgLyoqIEFsdGVybmF0ZSBkcmF3aW5nIHBhcmFtZXRlcnMgKi9cbiAgICAgIGNvbnN0IGFsdGVybmF0ZURyYXdYID0gZHJhd1ggKyBjYW52YXNXaWR0aDtcbiAgICAgIGNvbnN0IGFsdGVybmF0ZURyYXdZID0gZHJhd1kgKyBjYW52YXNIZWlnaHQ7XG4gICAgICBjb25zdCBhbHRlcm5hdGVSb3RhdGVYID0gcm90YXRlWCArIGNhbnZhc1dpZHRoO1xuICAgICAgY29uc3QgYWx0ZXJuYXRlUm90YXRlWSA9IHJvdGF0ZVkgKyBjYW52YXNIZWlnaHQ7XG5cbiAgICAgIGN0eC5zYXZlKCk7XG4gICAgICByb3RhdGVXYXRlcm1hcmsoY3R4LCByb3RhdGVYLCByb3RhdGVZLCB0aGlzLm56Um90YXRlKTtcblxuICAgICAgaWYgKHRoaXMubnpJbWFnZSkge1xuICAgICAgICBjb25zdCBpbWcgPSBuZXcgSW1hZ2UoKTtcblxuICAgICAgICBjb25zdCBvbkxvYWQgPSAoKTogdm9pZCA9PiB7XG4gICAgICAgICAgY2xlYW51cCgpO1xuXG4gICAgICAgICAgY3R4LmRyYXdJbWFnZShpbWcsIGRyYXdYLCBkcmF3WSwgZHJhd1dpZHRoLCBkcmF3SGVpZ2h0KTtcblxuICAgICAgICAgIC8qKiBEcmF3IGludGVybGVhdmVkIHBpY3R1cmVzIGFmdGVyIHJvdGF0aW9uICovXG4gICAgICAgICAgY3R4LnJlc3RvcmUoKTtcbiAgICAgICAgICByb3RhdGVXYXRlcm1hcmsoY3R4LCBhbHRlcm5hdGVSb3RhdGVYLCBhbHRlcm5hdGVSb3RhdGVZLCB0aGlzLm56Um90YXRlKTtcbiAgICAgICAgICBjdHguZHJhd0ltYWdlKGltZywgYWx0ZXJuYXRlRHJhd1gsIGFsdGVybmF0ZURyYXdZLCBkcmF3V2lkdGgsIGRyYXdIZWlnaHQpO1xuICAgICAgICAgIHRoaXMuYXBwZW5kV2F0ZXJtYXJrKGNhbnZhcy50b0RhdGFVUkwoKSwgbWFya1dpZHRoKTtcbiAgICAgICAgfTtcblxuICAgICAgICBjb25zdCBvbkVycm9yID0gKCk6IHZvaWQgPT4ge1xuICAgICAgICAgIGNsZWFudXAoKTtcblxuICAgICAgICAgIHRoaXMuZHJhd1RleHQoXG4gICAgICAgICAgICBjYW52YXMsXG4gICAgICAgICAgICBjdHgsXG4gICAgICAgICAgICBkcmF3WCxcbiAgICAgICAgICAgIGRyYXdZLFxuICAgICAgICAgICAgZHJhd1dpZHRoLFxuICAgICAgICAgICAgZHJhd0hlaWdodCxcbiAgICAgICAgICAgIGFsdGVybmF0ZVJvdGF0ZVgsXG4gICAgICAgICAgICBhbHRlcm5hdGVSb3RhdGVZLFxuICAgICAgICAgICAgYWx0ZXJuYXRlRHJhd1gsXG4gICAgICAgICAgICBhbHRlcm5hdGVEcmF3WSxcbiAgICAgICAgICAgIG1hcmtXaWR0aFxuICAgICAgICAgICk7XG4gICAgICAgIH07XG5cbiAgICAgICAgY29uc3QgY2xlYW51cCA9ICgpOiB2b2lkID0+IHtcbiAgICAgICAgICBpbWcucmVtb3ZlRXZlbnRMaXN0ZW5lcignbG9hZCcsIG9uTG9hZCk7XG4gICAgICAgICAgaW1nLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ2Vycm9yJywgb25FcnJvcik7XG4gICAgICAgIH07XG5cbiAgICAgICAgaW1nLmFkZEV2ZW50TGlzdGVuZXIoJ2xvYWQnLCBvbkxvYWQpO1xuICAgICAgICBpbWcuYWRkRXZlbnRMaXN0ZW5lcignZXJyb3InLCBvbkVycm9yKTtcblxuICAgICAgICBpbWcuY3Jvc3NPcmlnaW4gPSAnYW5vbnltb3VzJztcbiAgICAgICAgaW1nLnJlZmVycmVyUG9saWN5ID0gJ25vLXJlZmVycmVyJztcbiAgICAgICAgaW1nLnNyYyA9IHRoaXMubnpJbWFnZTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRoaXMuZHJhd1RleHQoXG4gICAgICAgICAgY2FudmFzLFxuICAgICAgICAgIGN0eCxcbiAgICAgICAgICBkcmF3WCxcbiAgICAgICAgICBkcmF3WSxcbiAgICAgICAgICBkcmF3V2lkdGgsXG4gICAgICAgICAgZHJhd0hlaWdodCxcbiAgICAgICAgICBhbHRlcm5hdGVSb3RhdGVYLFxuICAgICAgICAgIGFsdGVybmF0ZVJvdGF0ZVksXG4gICAgICAgICAgYWx0ZXJuYXRlRHJhd1gsXG4gICAgICAgICAgYWx0ZXJuYXRlRHJhd1ksXG4gICAgICAgICAgbWFya1dpZHRoXG4gICAgICAgICk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgbmdPbkRlc3Ryb3koKTogdm9pZCB7XG4gICAgdGhpcy5vYnNlcnZlci5kaXNjb25uZWN0KCk7XG4gIH1cbn1cbiJdfQ==