@talrace/ngx-noder 0.0.8 → 0.0.9

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.
Files changed (93) hide show
  1. package/esm2022/lib/apart-components/add-link-dialog/add-link-dialog.component.mjs +15 -9
  2. package/esm2022/lib/apart-components/editor-toolbar/components/base-toolbar.component.mjs +8 -2
  3. package/esm2022/lib/apart-components/editor-toolbar/components/buttons/font/font.component.mjs +2 -2
  4. package/esm2022/lib/apart-components/editor-toolbar/components/buttons/font-size/font-size.component.mjs +3 -3
  5. package/esm2022/lib/apart-components/editor-toolbar/shared/toolbar-styles.helper.mjs +1 -8
  6. package/esm2022/lib/editor/components/edges/edge.component.mjs +2 -2
  7. package/esm2022/lib/editor/components/edges/edges.mjs +21 -2
  8. package/esm2022/lib/editor/components/image/input-handler/image-input.handler.mjs +18 -1
  9. package/esm2022/lib/editor/components/shared/services/custom-content.service.mjs +22 -56
  10. package/esm2022/lib/editor/components/table/components/table-cell.component.mjs +6 -6
  11. package/esm2022/lib/editor/components/table/components/table.component.mjs +13 -4
  12. package/esm2022/lib/editor/components/table/models/cell-data.model.mjs +3 -4
  13. package/esm2022/lib/editor/components/table/selection/table-selection.mjs +15 -5
  14. package/esm2022/lib/editor/content/constants/editor.const.mjs +9 -1
  15. package/esm2022/lib/editor/content/display-data/display-data.mjs +839 -0
  16. package/esm2022/lib/editor/content/display-data/general-properties.model.mjs +1 -1
  17. package/esm2022/lib/editor/content/display-data/models/paragraph-info.model.mjs +8 -0
  18. package/esm2022/lib/editor/content/display-data/paragraph.mjs +5 -1
  19. package/esm2022/lib/editor/content/display-data/text-line-info.mjs +2 -1
  20. package/esm2022/lib/editor/content/display-data/toolbar-styles.interface.mjs +1 -1
  21. package/esm2022/lib/editor/content/helpers/content-style.helper.mjs +12 -30
  22. package/esm2022/lib/editor/content/helpers/display-token.helper.mjs +62 -0
  23. package/esm2022/lib/editor/display/layers/cursor.layer.mjs +9 -8
  24. package/esm2022/lib/editor/display/layers/pages.layer.mjs +5 -5
  25. package/esm2022/lib/editor/display/layers/print.text.layer.mjs +2 -2
  26. package/esm2022/lib/editor/display/layers/selection.layer.mjs +15 -9
  27. package/esm2022/lib/editor/display/layers/text.layer.mjs +25 -27
  28. package/esm2022/lib/editor/display/print/print.renderer.mjs +8 -8
  29. package/esm2022/lib/editor/display/renderer.mjs +10 -10
  30. package/esm2022/lib/editor/display/rendering.helper.mjs +2 -4
  31. package/esm2022/lib/editor/display/virtual.renderer.mjs +5 -5
  32. package/esm2022/lib/editor/execution/edit.session.mjs +199 -755
  33. package/esm2022/lib/editor/execution/editor.mjs +116 -75
  34. package/esm2022/lib/editor/execution/helpers/format-style.helper.mjs +1 -33
  35. package/esm2022/lib/editor/execution/helpers/image.helpet.mjs +12 -0
  36. package/esm2022/lib/editor/execution/helpers/paragraph.helper.mjs +11 -3
  37. package/esm2022/lib/editor/execution/regulator.service.mjs +28 -20
  38. package/esm2022/lib/editor/gadgets/numbering/numbering-paragraph-style.model.mjs +13 -0
  39. package/esm2022/lib/editor/gadgets/numbering/numbering.helper.mjs +77 -10
  40. package/esm2022/lib/editor/gadgets/search/search.mjs +6 -6
  41. package/esm2022/lib/editor/interaction/editor.service.mjs +27 -6
  42. package/esm2022/lib/editor/interaction/input.handler.mjs +8 -5
  43. package/esm2022/lib/editor/interaction/mouse.handler.mjs +2 -1
  44. package/esm2022/lib/editor/operations/helpers/format-operations.helper.mjs +32 -2
  45. package/esm2022/lib/editor/operations/helpers/link-operations.helper.mjs +47 -12
  46. package/esm2022/lib/editor/operations/operations-helper.helper.mjs +13 -14
  47. package/esm2022/lib/editor/operations/save-commands.helper.mjs +2 -2
  48. package/esm2022/lib/editor/positioning/content.helper.mjs +15 -15
  49. package/esm2022/lib/editor/positioning/line-width.helper.mjs +5 -5
  50. package/esm2022/lib/editor/positioning/position.helper.mjs +34 -32
  51. package/esm2022/lib/editor/positioning/selection.mjs +42 -32
  52. package/esm2022/lib/editor/revision.helper.mjs +4 -3
  53. package/fesm2022/talrace-ngx-noder.mjs +3765 -3548
  54. package/fesm2022/talrace-ngx-noder.mjs.map +1 -1
  55. package/lib/apart-components/add-link-dialog/add-link-dialog.component.d.ts +0 -1
  56. package/lib/apart-components/editor-toolbar/shared/toolbar-styles.helper.d.ts +0 -2
  57. package/lib/editor/components/image/input-handler/image-input.handler.d.ts +3 -0
  58. package/lib/editor/components/shared/services/custom-content.service.d.ts +3 -5
  59. package/lib/editor/components/table/components/table-cell.component.d.ts +1 -1
  60. package/lib/editor/components/table/components/table.component.d.ts +1 -0
  61. package/lib/editor/components/table/models/cell-data.model.d.ts +1 -1
  62. package/lib/editor/components/table/selection/table-selection.d.ts +2 -0
  63. package/lib/editor/content/constants/editor.const.d.ts +2 -0
  64. package/lib/editor/content/display-data/display-data.d.ts +103 -0
  65. package/lib/editor/content/display-data/general-properties.model.d.ts +5 -0
  66. package/lib/editor/content/display-data/models/paragraph-info.model.d.ts +9 -0
  67. package/lib/editor/content/display-data/paragraph.d.ts +1 -0
  68. package/lib/editor/content/display-data/text-line-info.d.ts +1 -0
  69. package/lib/editor/content/display-data/toolbar-styles.interface.d.ts +1 -1
  70. package/lib/editor/content/helpers/content-style.helper.d.ts +1 -2
  71. package/lib/editor/content/helpers/display-token.helper.d.ts +6 -0
  72. package/lib/editor/display/layers/text.layer.d.ts +1 -2
  73. package/lib/editor/display/print/print.renderer.d.ts +0 -2
  74. package/lib/editor/execution/edit.session.d.ts +11 -59
  75. package/lib/editor/execution/editor.d.ts +9 -6
  76. package/lib/editor/execution/helpers/format-style.helper.d.ts +0 -2
  77. package/lib/editor/execution/helpers/image.helpet.d.ts +4 -0
  78. package/lib/editor/execution/regulator.service.d.ts +1 -1
  79. package/lib/editor/gadgets/numbering/numbering-paragraph-style.model.d.ts +6 -0
  80. package/lib/editor/gadgets/numbering/numbering.helper.d.ts +10 -3
  81. package/lib/editor/interaction/editor.service.d.ts +12 -3
  82. package/lib/editor/operations/helpers/link-operations.helper.d.ts +5 -3
  83. package/lib/editor/positioning/content.helper.d.ts +6 -5
  84. package/lib/editor/positioning/position.helper.d.ts +3 -3
  85. package/lib/editor/positioning/selection.d.ts +3 -0
  86. package/package.json +1 -1
  87. package/src/_ngx-noder.theme.scss +31 -2
  88. package/esm2022/lib/editor/content/display-data/document.mjs +0 -134
  89. package/esm2022/lib/editor/content/display-data/pages.wrap.mjs +0 -226
  90. package/esm2022/lib/editor/execution/helpers/delta.helper.mjs +0 -18
  91. package/lib/editor/content/display-data/document.d.ts +0 -56
  92. package/lib/editor/content/display-data/pages.wrap.d.ts +0 -42
  93. package/lib/editor/execution/helpers/delta.helper.d.ts +0 -6
@@ -76,8 +76,8 @@ export declare class EditorService {
76
76
  private _insertLink$;
77
77
  get endMousePress$(): Observable<void>;
78
78
  private _endMousePress$;
79
- get clearSelection$(): Observable<void>;
80
- private _clearSelection$;
79
+ get disableSelection$(): Observable<void>;
80
+ private _disableSelection$;
81
81
  get changedTableSize$(): Observable<{
82
82
  insertIndex: number;
83
83
  sessionId: number;
@@ -154,6 +154,12 @@ export declare class EditorService {
154
154
  private _removeSelected$;
155
155
  get keyDown$(): Observable<KeyboardEvent>;
156
156
  private _keyDown$;
157
+ get updateEdges$(): Observable<number>;
158
+ private _updateEdges$;
159
+ get insertText$(): Observable<string>;
160
+ private _insertText$;
161
+ get blurCustomComponent$(): Observable<void>;
162
+ private _blurCustomComponent$;
157
163
  setIsViewOnly(value: boolean): void;
158
164
  setHasSelection(value: boolean): void;
159
165
  setClipboardData(value: string): void;
@@ -168,7 +174,7 @@ export declare class EditorService {
168
174
  insertImage(imageData: ImageDataModel): void;
169
175
  insertLink(text: string, link: string): void;
170
176
  endMousePress(): void;
171
- clearSelection(): void;
177
+ disableSelection(): void;
172
178
  openElementSidenav(component: Type<ExternalSidenavInterface>, model: ElementModel, contentWidth: number): void;
173
179
  openSidenav(component: Type<any>): void;
174
180
  closeSidenav(): void;
@@ -195,6 +201,9 @@ export declare class EditorService {
195
201
  selectAll(): void;
196
202
  removeSelected(): void;
197
203
  keyDown(event: KeyboardEvent): void;
204
+ updateEdges(sessionId: number): void;
205
+ insertText(text: string): void;
206
+ blurCustomComponent(): void;
198
207
  static ɵfac: i0.ɵɵFactoryDeclaration<EditorService, never>;
199
208
  static ɵprov: i0.ɵɵInjectableDeclaration<EditorService>;
200
209
  }
@@ -1,6 +1,8 @@
1
1
  import { LinkModel } from '../../../models/generated/link.model';
2
2
  export declare class LinkOperationsHelper {
3
- static insertContent(links: LinkModel[], link: string, insertIndex: number, endIndex: number): void;
4
- static insertTextIntoLink(links: LinkModel[], text: string, insertIndex: number): void;
5
- static removeTextFromLink(links: LinkModel[], startIndex: number, endIndex: number): void;
3
+ static insert(links: LinkModel[], link: string, insertIndex: number, endIndex: number): void;
4
+ static insertContent(links: LinkModel[], insertIndex: number, textLength: number): void;
5
+ static removeContent(links: LinkModel[], startIndex: number, endIndex: number): void;
6
+ static restore(links: LinkModel[], startIndex: number, contentLength: number, newlinks: LinkModel[]): void;
7
+ static replaceContent(links: LinkModel[], startIndex: number, endIndex: number, length: number): void;
6
8
  }
@@ -1,14 +1,15 @@
1
1
  import { CursorParagraph } from './cursor-paragraph';
2
2
  import { InsertIndexInterface } from './insert-index.interface';
3
+ import { ParagraphInfoModel } from '../content/display-data/models/paragraph-info.model';
3
4
  import { Range } from './range';
4
5
  export declare class ContentHelper {
5
- static documentIndexToParagraphIndex(wrapParagraphIndex: number[], indexInDocument: number): CursorParagraph;
6
- static documentIndexToParagraphWithOffset(wrapParagraphIndex: number[], lines: string[], indexInDocument: number): CursorParagraph;
7
- static paragraphPositionToDocumentIndex(wrapParagraphIndex: number[], paragraph: CursorParagraph): number;
8
- static getSelectedPartDocumentIndexes(wrapParagraphIndex: number[], range: Range): {
6
+ static documentIndexToParagraphIndex(paragraphs: ParagraphInfoModel[], indexInDocument: number): CursorParagraph;
7
+ static documentIndexToParagraphWithOffset(paragraphs: ParagraphInfoModel[], indexInDocument: number): CursorParagraph;
8
+ static paragraphPositionToDocumentIndex(paragraphs: ParagraphInfoModel[], paragraph: CursorParagraph): number;
9
+ static getSelectedPartDocumentIndexes(paragraphs: ParagraphInfoModel[], range: Range): {
9
10
  startIndex: number;
10
11
  endIndex: number;
11
12
  };
12
- static paragraphToDocumentIndex(wrapParagraphIndex: number[], paragraph: number, index: number): number;
13
+ static paragraphToDocumentIndex(paragraphs: ParagraphInfoModel[], paragraph: number, index: number): number;
13
14
  static setIndexesElementsInInterval<T extends InsertIndexInterface>(elements: T[], elementIndexes: number[], startIndex: number, endIndex: number): void;
14
15
  }
@@ -1,8 +1,8 @@
1
1
  import { CursorParagraph } from './cursor-paragraph';
2
2
  import { CursorPosition } from './cursor-position.interface';
3
3
  import { EditSession } from '../execution/edit.session';
4
- import { Paragraph } from '../content/display-data/paragraph';
5
4
  import { ParagraphInfo } from '../content/display-data/paragraph-info.interface';
5
+ import { ParagraphInfoModel } from '../content/display-data/models/paragraph-info.model';
6
6
  export declare class PositionHelper {
7
7
  /**
8
8
  * Returns an object containing the `pageX` and `pageY` coordinates of the document position.
@@ -11,7 +11,7 @@ export declare class PositionHelper {
11
11
  /**
12
12
  * Get paragraph info (paragraph index, paragraph line index, line top offset and others) by row index
13
13
  **/
14
- static getParagraphInfoByRow(paragraphs: Paragraph[], row: number): ParagraphInfo;
14
+ static getParagraphInfoByRow(paragraphs: ParagraphInfoModel[], row: number): ParagraphInfo;
15
15
  static documentToScreen(session: EditSession, paragraph: number, indexInParagraph: number): CursorParagraph;
16
16
  static screenToDocument(session: EditSession, line: number, indexInLine: number): CursorParagraph;
17
17
  /**
@@ -25,7 +25,7 @@ export declare class PositionHelper {
25
25
  top: number;
26
26
  left: number;
27
27
  }): CursorParagraph;
28
- static findLineInParagraphs(paragraphs: Paragraph[], documentLine: number): {
28
+ static findLineInParagraphs(paragraphs: ParagraphInfoModel[], documentLine: number): {
29
29
  paragraphIndex: number;
30
30
  lineIndex: number;
31
31
  };
@@ -5,6 +5,7 @@ import { Range } from './range';
5
5
  export declare class Selection {
6
6
  anchor: CursorParagraph | null;
7
7
  cursor: CursorParagraph;
8
+ isDisabled: boolean;
8
9
  private keepLinePositionX;
9
10
  get isEmpty(): boolean;
10
11
  get isBackwards(): boolean;
@@ -14,6 +15,8 @@ export declare class Selection {
14
15
  placeSelection(cursor: CursorParagraph, anchor: CursorParagraph): void;
15
16
  moveSelection(position: CursorParagraph): void;
16
17
  clearSelection(): void;
18
+ disableSelection(): void;
19
+ enableSelection(): void;
17
20
  selectAll(model: ContentsInterface): void;
18
21
  selectUp(session: EditSession): void;
19
22
  navigateUp(session: EditSession): void;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@talrace/ngx-noder",
3
- "version": "0.0.8",
3
+ "version": "0.0.9",
4
4
  "license": "MIT",
5
5
  "peerDependencies": {
6
6
  "@angular/common": "^17.0.4",
@@ -11,19 +11,48 @@
11
11
  @import 'lib/editor/theme';
12
12
 
13
13
  @mixin ngx-noder-theme($theme) {
14
+ @include ngx-noder-add-link-theme($theme);
15
+ @include ngx-noder-text-format-theme($theme);
16
+ @include ngx-noder-confirm-theme($theme);
17
+ @include ngx-noder-title-theme($theme);
18
+ @include ngx-noder-toolbar-theme($theme);
19
+ @include ngx-noder-insert-table-theme($theme);
20
+ @include ngx-noder-editor-theme($theme);
21
+ }
22
+
23
+ @mixin ngx-noder-editor-theme($theme) {
24
+ @include editor-theme($theme);
25
+
14
26
  $font-family: roboto, helvetica, neue, 'Helvetica', Arial, sans-serif;
15
27
  $custom-typography: mat.define-typography-config(
16
28
  $font-family: $font-family
17
29
  );
30
+ @include mat.all-component-typographies($custom-typography);
31
+ }
32
+
33
+ @mixin ngx-noder-add-link-theme($theme) {
18
34
  @include add-link-dialog-component($theme);
19
35
  @include add-link-mobile-component($theme);
36
+ }
37
+
38
+ @mixin ngx-noder-text-format-theme($theme) {
20
39
  @include text-format-mobile-component($theme);
40
+ }
41
+
42
+ @mixin ngx-noder-confirm-theme($theme) {
21
43
  @include confirm-dialog-theme($theme);
22
- @include editor-theme($theme);
44
+ }
45
+
46
+ @mixin ngx-noder-title-theme($theme) {
23
47
  @include editor-title-component-theme($theme);
24
48
  @include editor-title-mobile-component-theme($theme);
49
+ }
50
+
51
+ @mixin ngx-noder-toolbar-theme($theme) {
25
52
  @include editor-toolbar-theme($theme);
53
+ }
54
+
55
+ @mixin ngx-noder-insert-table-theme($theme) {
26
56
  @include insert-table-component($theme);
27
57
  @include insert-table-mobile-component($theme);
28
- @include mat.all-component-typographies($custom-typography);
29
58
  }
@@ -1,134 +0,0 @@
1
- import { BreakTypes } from '../../gadgets/page-break/break-types.enum';
2
- import { CursorParagraph } from '../../positioning/cursor-paragraph';
3
- import { DeltaHelper } from '../../execution/helpers/delta.helper';
4
- import { NEW_LINE_MARKUP } from '../constants/editor.const';
5
- import { Range } from '../../positioning/range';
6
- export class Document {
7
- /**
8
- * Returns all the lines in the document as a single string, joined by the new line character.
9
- **/
10
- get text() {
11
- return this.lines.join(NEW_LINE_MARKUP);
12
- }
13
- get length() {
14
- return this.lines.length;
15
- }
16
- constructor(model, pageMargin, pagesSpace, pageWidth, pageHeight) {
17
- this.model = model;
18
- this.pageMargin = pageMargin;
19
- this.pagesSpace = pagesSpace;
20
- this.pageWidth = pageWidth;
21
- this.pageHeight = pageHeight;
22
- this.lines = [''];
23
- this.lines = DeltaHelper.splitByParagraphs(this.model.content);
24
- }
25
- insertText(position, text) {
26
- const endPoint = DeltaHelper.insertTextAndReturnEndCursorPosition(this.lines, text, position);
27
- return endPoint;
28
- }
29
- /**
30
- * Removes the `range` from the document.
31
- **/
32
- removeRange(range) {
33
- DeltaHelper.remove(this.lines, range.start, range.end);
34
- }
35
- getLine(lines, index) {
36
- return lines[index] || '';
37
- }
38
- getAllLines() {
39
- return this.getLines(0, this.getLinesCount());
40
- }
41
- getLinesCount() {
42
- return this.lines.length - 1;
43
- }
44
- getLines(firstRow, lastRow) {
45
- return this.lines.slice(firstRow, lastRow + 1);
46
- }
47
- /**
48
- * Returns all the text within `range` as an array of lines.
49
- **/
50
- getLinesForRange(range) {
51
- if (range.isSingleLine) {
52
- const line = this.getLine(this.lines, range.start.row);
53
- const linePartInRange = line.slice(range.start.column, range.end.column);
54
- return [linePartInRange];
55
- }
56
- const lines = this.getLines(range.start.row, range.end.row);
57
- lines[0] = (lines[0] || '').slice(range.start.column);
58
- const lastIndex = lines.length - 1;
59
- lines[lastIndex] = lines[lastIndex].slice(0, range.end.column);
60
- return lines;
61
- }
62
- /**
63
- * Returns all the text within `range` as a single string.
64
- **/
65
- getTextRange(range) {
66
- return this.getLinesForRange(range).join(NEW_LINE_MARKUP);
67
- }
68
- /**
69
- * Converts the position in a document to the character's index.
70
- */
71
- positionToIndex(position, startRow = 0) {
72
- let index = 0;
73
- const endRow = Math.min(position.row, this.lines.length);
74
- for (let i = startRow || 0; i < endRow; i++) {
75
- index += this.lines[i].length + 1;
76
- }
77
- return index + position.column;
78
- }
79
- /**
80
- * Converts an index position in a document to the position.
81
- * See 'positionToIndex' for more information.
82
- */
83
- indexToPosition(positionIndex, startRow) {
84
- const newlineLength = NEW_LINE_MARKUP.length;
85
- for (let lineIndex = startRow || 0; lineIndex < this.lines.length; lineIndex++) {
86
- positionIndex -= this.lines[lineIndex].length + newlineLength;
87
- if (positionIndex < 0) {
88
- const column = positionIndex + this.lines[lineIndex].length + newlineLength;
89
- return new CursorParagraph(lineIndex, column);
90
- }
91
- }
92
- const column = positionIndex + this.lines[this.lines.length - 1].length + newlineLength;
93
- return new CursorParagraph(this.lines.length - 1, column);
94
- }
95
- indexesToRange(startIndex, endIndex) {
96
- const startPoint = this.indexToPosition(startIndex, 0);
97
- const endPoint = this.indexToPosition(endIndex, 0);
98
- return new Range(startPoint, endPoint);
99
- }
100
- isNewLineSymbol(index) {
101
- const text = this.text;
102
- return !text || !text[index] || text[index] === NEW_LINE_MARKUP;
103
- }
104
- /**
105
- * Converts the selection range in a document to the selected paragraphs indexes (start and end of paragraphs).
106
- * start/end refers to the "absolute position" of a character in the document.
107
- */
108
- getSelectedParagraphsByRange(range) {
109
- const newlineLength = NEW_LINE_MARKUP.length;
110
- let start = 0;
111
- let end = 0;
112
- let i;
113
- const row = Math.min(range.end.row, this.lines.length - 1);
114
- for (i = 0; i < row; i++) {
115
- if (i < range.start.row) {
116
- start += this.lines[i].length + newlineLength;
117
- }
118
- end += this.lines[i].length + newlineLength;
119
- }
120
- if (i < this.lines.length) {
121
- end += this.lines[i].length;
122
- }
123
- return { start, end };
124
- }
125
- getPositionAfterBreak(position, breakType) {
126
- if (breakType === BreakTypes.TextWrapping) {
127
- return position;
128
- }
129
- const isLastColumn = position.column === this.lines[position.row].length;
130
- const isLastParagraph = position.row === this.lines.length - 1;
131
- return isLastColumn && !isLastParagraph ? new CursorParagraph(position.row + 1, 0) : position;
132
- }
133
- }
134
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZG9jdW1lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtbm9kZXIvc3JjL2xpYi9lZGl0b3IvY29udGVudC9kaXNwbGF5LWRhdGEvZG9jdW1lbnQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLDJDQUEyQyxDQUFDO0FBRXZFLE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxvQ0FBb0MsQ0FBQztBQUNyRSxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0sc0NBQXNDLENBQUM7QUFFbkUsT0FBTyxFQUFFLGVBQWUsRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBQzVELE9BQU8sRUFBRSxLQUFLLEVBQUUsTUFBTSx5QkFBeUIsQ0FBQztBQUVoRCxNQUFNLE9BQU8sUUFBUTtJQUdqQjs7UUFFSTtJQUNKLElBQUksSUFBSTtRQUNKLE9BQU8sSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsZUFBZSxDQUFDLENBQUM7SUFDNUMsQ0FBQztJQUVELElBQUksTUFBTTtRQUNOLE9BQU8sSUFBSSxDQUFDLEtBQUssQ0FBQyxNQUFNLENBQUM7SUFDN0IsQ0FBQztJQUVELFlBQ1ksS0FBd0IsRUFDekIsVUFBdUIsRUFDdkIsVUFBa0IsRUFDbEIsU0FBaUIsRUFDakIsVUFBbUI7UUFKbEIsVUFBSyxHQUFMLEtBQUssQ0FBbUI7UUFDekIsZUFBVSxHQUFWLFVBQVUsQ0FBYTtRQUN2QixlQUFVLEdBQVYsVUFBVSxDQUFRO1FBQ2xCLGNBQVMsR0FBVCxTQUFTLENBQVE7UUFDakIsZUFBVSxHQUFWLFVBQVUsQ0FBUztRQWxCOUIsVUFBSyxHQUFHLENBQUMsRUFBRSxDQUFDLENBQUM7UUFvQlQsSUFBSSxDQUFDLEtBQUssR0FBRyxXQUFXLENBQUMsaUJBQWlCLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsQ0FBQztJQUNuRSxDQUFDO0lBRUQs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QUFDO0lBQzFCLENBQUM7SUFFRCxxQkFBcUIsQ0FBQyxRQUF5QixFQUFFLFNBQXFCO1FBQ2xFLElBQUksU0FBUyxLQUFLLFVBQVUsQ0FBQyxZQUFZLEVBQUU7WUFDdkMsT0FBTyxRQUFRLENBQUM7U0FDbkI7UUFFRCxNQUFNLFlBQVksR0FBRyxRQUFRLENBQUMsTUFBTSxLQUFLLElBQUksQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxDQUFDLE1BQU0sQ0FBQztRQUN6RSxNQUFNLGVBQWUsR0FBRyxRQUFRLENBQUMsR0FBRyxLQUFLLElBQUksQ0FBQyxLQUFLLENBQUMsTUFBTSxHQUFHLENBQUMsQ0FBQztRQUMvRCxPQUFPLFlBQVksSUFBSSxDQUFDLGVBQWUsQ0FBQyxDQUFDLENBQUMsSUFBSSxlQUFlLENBQUMsUUFBUSxDQUFDLEdBQUcsR0FBRyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLFFBQVEsQ0FBQztJQUNsRyxDQUFDO0NBQ0oiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBCcmVha1R5cGVzIH0gZnJvbSAnLi4vLi4vZ2FkZ2V0cy9wYWdlLWJyZWFrL2JyZWFrLXR5cGVzLmVudW0nO1xuaW1wb3J0IHsgQ29udGVudHNJbnRlcmZhY2UgfSBmcm9tICcuLi9jb250ZW50cy5pbnRlcmZhY2UnO1xuaW1wb3J0IHsgQ3Vyc29yUGFyYWdyYXBoIH0gZnJvbSAnLi4vLi4vcG9zaXRpb25pbmcvY3Vyc29yLXBhcmFncmFwaCc7XG5pbXBvcnQgeyBEZWx0YUhlbHBlciB9IGZyb20gJy4uLy4uL2V4ZWN1dGlvbi9oZWxwZXJzL2RlbHRhLmhlbHBlcic7XG5pbXBvcnQgeyBNYXJnaW5Nb2RlbCB9IGZyb20gJy4uL21hcmdpbi5tb2RlbCc7XG5pbXBvcnQgeyBORVdfTElORV9NQVJLVVAgfSBmcm9tICcuLi9jb25zdGFudHMvZWRpdG9yLmNvbnN0JztcbmltcG9ydCB7IFJhbmdlIH0gZnJvbSAnLi4vLi4vcG9zaXRpb25pbmcvcmFuZ2UnO1xuXG5leHBvcnQgY2xhc3MgRG9jdW1lbnQge1xuICAgIGxpbmVzID0gWycnXTtcblxuICAgIC8qKlxuICAgICAqIFJldHVybnMgYWxsIHRoZSBsaW5lcyBpbiB0aGUgZG9jdW1lbnQgYXMgYSBzaW5nbGUgc3RyaW5nLCBqb2luZWQgYnkgdGhlIG5ldyBsaW5lIGNoYXJhY3Rlci5cbiAgICAgKiovXG4gICAgZ2V0IHRleHQoKTogc3RyaW5nIHtcbiAgICAgICAgcmV0dXJuIHRoaXMubGluZXMuam9pbihORVdfTElORV9NQVJLVVApO1xuICAgIH1cblxuICAgIGdldCBsZW5ndGgoKTogbnVtYmVyIHtcbiAgICAgICAgcmV0dXJuIHRoaXMubGluZXMubGVuZ3RoO1xuICAgIH1cblxuICAgIGNvbnN0cnVjdG9yKFxuICAgICAgICBwcml2YXRlIG1vZGVsOiBDb250ZW50c0ludGVyZmFjZSxcbiAgICAgICAgcHVibGljIHBhZ2VNYXJnaW46IE1hcmdpbk1vZGVsLFxuICAgICAgICBwdWJsaWMgcGFnZXNTcGFjZTogbnVtYmVyLFxuICAgICAgICBwdWJsaWMgcGFnZVdpZHRoOiBudW1iZXIsXG4gICAgICAgIHB1YmxpYyBwYWdlSGVpZ2h0PzogbnVtYmVyXG4gICAgKSB7XG4gICAgICAgIHRoaXMubGluZXMgPSBEZWx0YUhlbHBlci5zcGxpdEJ5UGFyYWdyYXBocyh0aGlzLm1vZGVsLmNvbnRlbnQpO1xuICAgIH1cblxuICAgIGluc2VydFRleHQocG9zaXRpb246IEN1cnNvclBhcmFncmFwaCwgdGV4dDogc3RyaW5nKTogQ3Vyc29yUGFyYWdyYXBoIHtcbiAgICAgICAgY29uc3QgZW5kUG9pbnQgPSBEZWx0YUhlbHBlci5pbnNlcnRUZXh0QW5kUmV0dXJuRW5kQ3Vyc29yUG9zaXRpb24odGhpcy5saW5lcywgdGV4dCwgcG9zaXRpb24pO1xuICAgICAgICByZXR1cm4gZW5kUG9pbnQ7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogUmVtb3ZlcyB0aGUgYHJhbmdlYCBmcm9tIHRoZSBkb2N1bWVudC5cbiAgICAgKiovXG4gICAgcmVtb3ZlUmFuZ2UocmFuZ2U6IFJhbmdlKTogdm9pZCB7XG4gICAgICAgIERlbHRhSGVscGVyLnJlbW92ZSh0aGlzLmxpbmVzLCByYW5nZS5zdGFydCwgcmFuZ2UuZW5kKTtcbiAgICB9XG5cbiAgICBnZXRMaW5lKGxpbmVzOiBzdHJpbmdbXSwgaW5kZXg6IG51bWJlcik6IHN0cmluZyB7XG4gICAgICAgIHJldHVybiBsaW5lc1tpbmRleF0gfHwgJyc7XG4gICAgfVxuXG4gICAgZ2V0QWxsTGluZXMoKTogc3RyaW5nW10ge1xuICAgICAgICByZXR1cm4gdGhpcy5nZXRMaW5lcygwLCB0aGlzLmdldExpbmVzQ291bnQoKSk7XG4gICAgfVxuXG4gICAgZ2V0TGluZXNDb3VudCgpOiBudW1iZXIge1xuICAgICAgICByZXR1cm4gdGhpcy5saW5lcy5sZW5ndGggLSAxO1xuICAgIH1cblxuICAgIGdldExpbmVzKGZpcnN0Um93OiBudW1iZXIsIGxhc3RSb3c6IG51bWJlcik6IHN0cmluZ1tdIHtcbiAgICAgICAgcmV0dXJuIHRoaXMubGluZXMuc2xpY2UoZmlyc3RSb3csIGxhc3RSb3cgKyAxKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBSZXR1cm5zIGFsbCB0aGUgdGV4dCB3aXRoaW4gYHJhbmdlYCBhcyBhbiBhcnJheSBvZiBsaW5lcy5cbiAgICAgKiovXG4gICAgZ2V0TGluZXNGb3JSYW5nZShyYW5nZTogUmFuZ2UpOiBzdHJpbmdbXSB7XG4gICAgICAgIGlmIChyYW5nZS5pc1NpbmdsZUxpbmUpIHtcbiAgICAgICAgICAgIGNvbnN0IGxpbmUgPSB0aGlzLmdldExpbmUodGhpcy5saW5lcywgcmFuZ2Uuc3RhcnQucm93KTtcbiAgICAgICAgICAgIGNvbnN0IGxpbmVQYXJ0SW5SYW5nZSA9IGxpbmUuc2xpY2UocmFuZ2Uuc3RhcnQuY29sdW1uLCByYW5nZS5lbmQuY29sdW1uKTtcblxuICAgICAgICAgICAgcmV0dXJuIFtsaW5lUGFydEluUmFuZ2VdO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3QgbGluZXMgPSB0aGlzLmdldExpbmVzKHJhbmdlLnN0YXJ0LnJvdywgcmFuZ2UuZW5kLnJvdyk7XG4gICAgICAgIGxpbmVzWzBdID0gKGxpbmVzWzBdIHx8ICcnKS5zbGljZShyYW5nZS5zdGFydC5jb2x1bW4pO1xuICAgICAgICBjb25zdCBsYXN0SW5kZXggPSBsaW5lcy5sZW5ndGggLSAxO1xuICAgICAgICBsaW5lc1tsYXN0SW5kZXhdID0gbGluZXNbbGFzdEluZGV4XS5zbGljZSgwLCByYW5nZS5lbmQuY29sdW1uKTtcblxuICAgICAgICByZXR1cm4gbGluZXM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogUmV0dXJucyBhbGwgdGhlIHRleHQgd2l0aGluIGByYW5nZWAgYXMgYSBzaW5nbGUgc3RyaW5nLlxuICAgICAqKi9cbiAgICBnZXRUZXh0UmFuZ2UocmFuZ2U6IFJhbmdlKTogc3RyaW5nIHtcbiAgICAgICAgcmV0dXJuIHRoaXMuZ2V0TGluZXNGb3JSYW5nZShyYW5nZSkuam9pbihORVdfTElORV9NQVJLVVApO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIENvbnZlcnRzIHRoZSBwb3NpdGlvbiBpbiBhIGRvY3VtZW50IHRvIHRoZSBjaGFyYWN0ZXIncyBpbmRleC5cbiAgICAgKi9cbiAgICBwb3NpdGlvblRvSW5kZXgocG9zaXRpb246IEN1cnNvclBhcmFncmFwaCwgc3RhcnRSb3cgPSAwKTogbnVtYmVyIHtcbiAgICAgICAgbGV0IGluZGV4ID0gMDtcbiAgICAgICAgY29uc3QgZW5kUm93ID0gTWF0aC5taW4ocG9zaXRpb24ucm93LCB0aGlzLmxpbmVzLmxlbmd0aCk7XG4gICAgICAgIGZvciAobGV0IGkgPSBzdGFydFJvdyB8fCAwOyBpIDwgZW5kUm93OyBpKyspIHtcbiAgICAgICAgICAgIGluZGV4ICs9IHRoaXMubGluZXNbaV0ubGVuZ3RoICsgMTtcbiAgICAgICAgfVxuXG4gICAgICAgIHJldHVybiBpbmRleCArIHBvc2l0aW9uLmNvbHVtbjtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBDb252ZXJ0cyBhbiBpbmRleCBwb3NpdGlvbiBpbiBhIGRvY3VtZW50IHRvIHRoZSBwb3NpdGlvbi5cbiAgICAgKiBTZWUgJ3Bvc2l0aW9uVG9JbmRleCcgZm9yIG1vcmUgaW5mb3JtYXRpb24uXG4gICAgICovXG4gICAgaW5kZXhUb1Bvc2l0aW9uKHBvc2l0aW9uSW5kZXg6IG51bWJlciwgc3RhcnRSb3c6IG51bWJlcik6IEN1cnNvclBhcmFncmFwaCB7XG4gICAgICAgIGNvbnN0IG5ld2xpbmVMZW5ndGggPSBORVdfTElORV9NQVJLVVAubGVuZ3RoO1xuICAgICAgICBmb3IgKGxldCBsaW5lSW5kZXggPSBzdGFydFJvdyB8fCAwOyBsaW5lSW5kZXggPCB0aGlzLmxpbmVzLmxlbmd0aDsgbGluZUluZGV4KyspIHtcbiAgICAgICAgICAgIHBvc2l0aW9uSW5kZXggLT0gdGhpcy5saW5lc1tsaW5lSW5kZXhdLmxlbmd0aCArIG5ld2xpbmVMZW5ndGg7XG4gICAgICAgICAgICBpZiAocG9zaXRpb25JbmRleCA8IDApIHtcbiAgICAgICAgICAgICAgICBjb25zdCBjb2x1bW4gPSBwb3NpdGlvbkluZGV4ICsgdGhpcy5saW5lc1tsaW5lSW5kZXhdLmxlbmd0aCArIG5ld2xpbmVMZW5ndGg7XG5cbiAgICAgICAgICAgICAgICByZXR1cm4gbmV3IEN1cnNvclBhcmFncmFwaChsaW5lSW5kZXgsIGNvbHVtbik7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCBjb2x1bW4gPSBwb3NpdGlvbkluZGV4ICsgdGhpcy5saW5lc1t0aGlzLmxpbmVzLmxlbmd0aCAtIDFdLmxlbmd0aCArIG5ld2xpbmVMZW5ndGg7XG5cbiAgICAgICAgcmV0dXJuIG5ldyBDdXJzb3JQYXJhZ3JhcGgodGhpcy5saW5lcy5sZW5ndGggLSAxLCBjb2x1bW4pO1xuICAgIH1cblxuICAgIGluZGV4ZXNUb1JhbmdlKHN0YXJ0SW5kZXg6IG51bWJlciwgZW5kSW5kZXg6IG51bWJlcik6IFJhbmdlIHtcbiAgICAgICAgY29uc3Qgc3RhcnRQb2ludCA9IHRoaXMuaW5kZXhUb1Bvc2l0aW9uKHN0YXJ0SW5kZXgsIDApO1xuICAgICAgICBjb25zdCBlbmRQb2ludCA9IHRoaXMuaW5kZXhUb1Bvc2l0aW9uKGVuZEluZGV4LCAwKTtcblxuICAgICAgICByZXR1cm4gbmV3IFJhbmdlKHN0YXJ0UG9pbnQsIGVuZFBvaW50KTtcbiAgICB9XG5cbiAgICBpc05ld0xpbmVTeW1ib2woaW5kZXg6IG51bWJlcik6IGJvb2xlYW4ge1xuICAgICAgICBjb25zdCB0ZXh0ID0gdGhpcy50ZXh0O1xuXG4gICAgICAgIHJldHVybiAhdGV4dCB8fCAhdGV4dFtpbmRleF0gfHwgdGV4dFtpbmRleF0gPT09IE5FV19MSU5FX01BUktVUDtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBDb252ZXJ0cyB0aGUgc2VsZWN0aW9uIHJhbmdlIGluIGEgZG9jdW1lbnQgdG8gdGhlIHNlbGVjdGVkIHBhcmFncmFwaHMgaW5kZXhlcyAoc3RhcnQgYW5kIGVuZCBvZiBwYXJhZ3JhcGhzKS5cbiAgICAgKiBzdGFydC9lbmQgcmVmZXJzIHRvIHRoZSBcImFic29sdXRlIHBvc2l0aW9uXCIgb2YgYSBjaGFyYWN0ZXIgaW4gdGhlIGRvY3VtZW50LlxuICAgICAqL1xuICAgIGdldFNlbGVjdGVkUGFyYWdyYXBoc0J5UmFuZ2UocmFuZ2U6IFJhbmdlKTogeyBzdGFydDogbnVtYmVyOyBlbmQ6IG51bWJlciB9IHtcbiAgICAgICAgY29uc3QgbmV3bGluZUxlbmd0aCA9IE5FV19MSU5FX01BUktVUC5sZW5ndGg7XG4gICAgICAgIGxldCBzdGFydCA9IDA7XG4gICAgICAgIGxldCBlbmQgPSAwO1xuICAgICAgICBsZXQgaTtcbiAgICAgICAgY29uc3Qgcm93ID0gTWF0aC5taW4ocmFuZ2UuZW5kLnJvdywgdGhpcy5saW5lcy5sZW5ndGggLSAxKTtcbiAgICAgICAgZm9yIChpID0gMDsgaSA8IHJvdzsgaSsrKSB7XG4gICAgICAgICAgICBpZiAoaSA8IHJhbmdlLnN0YXJ0LnJvdykge1xuICAgICAgICAgICAgICAgIHN0YXJ0ICs9IHRoaXMubGluZXNbaV0ubGVuZ3RoICsgbmV3bGluZUxlbmd0aDtcbiAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgZW5kICs9IHRoaXMubGluZXNbaV0ubGVuZ3RoICsgbmV3bGluZUxlbmd0aDtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChpIDwgdGhpcy5saW5lcy5sZW5ndGgpIHtcbiAgICAgICAgICAgIGVuZCArPSB0aGlzLmxpbmVzW2ldLmxlbmd0aDtcbiAgICAgICAgfVxuXG4gICAgICAgIHJldHVybiB7IHN0YXJ0LCBlbmQgfTtcbiAgICB9XG5cbiAgICBnZXRQb3NpdGlvbkFmdGVyQnJlYWsocG9zaXRpb246IEN1cnNvclBhcmFncmFwaCwgYnJlYWtUeXBlOiBCcmVha1R5cGVzKTogQ3Vyc29yUGFyYWdyYXBoIHtcbiAgICAgICAgaWYgKGJyZWFrVHlwZSA9PT0gQnJlYWtUeXBlcy5UZXh0V3JhcHBpbmcpIHtcbiAgICAgICAgICAgIHJldHVybiBwb3NpdGlvbjtcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IGlzTGFzdENvbHVtbiA9IHBvc2l0aW9uLmNvbHVtbiA9PT0gdGhpcy5saW5lc1twb3NpdGlvbi5yb3ddLmxlbmd0aDtcbiAgICAgICAgY29uc3QgaXNMYXN0UGFyYWdyYXBoID0gcG9zaXRpb24ucm93ID09PSB0aGlzLmxpbmVzLmxlbmd0aCAtIDE7XG4gICAgICAgIHJldHVybiBpc0xhc3RDb2x1bW4gJiYgIWlzTGFzdFBhcmFncmFwaCA/IG5ldyBDdXJzb3JQYXJhZ3JhcGgocG9zaXRpb24ucm93ICsgMSwgMCkgOiBwb3NpdGlvbjtcbiAgICB9XG59XG4iXX0=
@@ -1,226 +0,0 @@
1
- import { EdgeType } from '../../components/edges/edge-type.enum';
2
- import { EventEmitting } from '../../core/event-emitting';
3
- import { NumberingHelper } from '../../gadgets/numbering/numbering.helper';
4
- import { PageHelper } from '../../execution/helpers/page.helper';
5
- import { PageType } from '../../components/edges/page-type.enum';
6
- import { PageVerticalDataModel } from '../page-vertical-data.model';
7
- import { Paragraph } from './paragraph';
8
- import { ParagraphHelper } from '../../execution/helpers/paragraph.helper';
9
- export class PagesWrap extends EventEmitting {
10
- get defaultVerticalData() {
11
- return this.pagesVerticalData.find(x => x.pageType === PageType.Default);
12
- }
13
- constructor(pagesSpace, documentMargin, pageWidth, pageHeight = 0, customComponents) {
14
- super();
15
- this.pagesSpace = pagesSpace;
16
- this.documentMargin = documentMargin;
17
- this.pageWidth = pageWidth;
18
- this.pageHeight = pageHeight;
19
- this.customComponents = customComponents;
20
- this.allPagesHeight = 0;
21
- this.minHeight = 0;
22
- this.paragraphs = [];
23
- this.tabTokens = [];
24
- this.minHeight = this.pageHeight + 2 * this.pagesSpace;
25
- this.contentWidth = this.pageWidth - this.documentMargin.left - this.documentMargin.right;
26
- this.initPagesVerticalData();
27
- this.processTextLinesProperties = !this.pageHeight
28
- ? ParagraphHelper.processTextLinesPropertiesForSinglePage
29
- : ParagraphHelper.processTextLinesProperties;
30
- }
31
- getParagraphTop(index) {
32
- return this.paragraphs[index] ? this.paragraphs[index].distanceFromTop : 0;
33
- }
34
- getParagraphTopForPrint(index) {
35
- if (!this.paragraphs[index]) {
36
- return 0;
37
- }
38
- const paragraph = this.paragraphs[index];
39
- const pageNumber = paragraph.pageNumbers[0];
40
- let pageBreakHeight = 0;
41
- paragraph.textLinesInfo.forEach(linesInfo => {
42
- if (linesInfo.isAfterPageBreak) {
43
- pageBreakHeight = linesInfo.height;
44
- }
45
- });
46
- return paragraph.distanceFromTop - pageNumber * this.pagesSpace - pageBreakHeight;
47
- }
48
- getParagraphHeight(index) {
49
- return this.paragraphs[index] ? this.paragraphs[index].height : 0;
50
- }
51
- remove(index, length) {
52
- this.paragraphs.splice(index, length);
53
- }
54
- reset(paragraphsLength) {
55
- this.paragraphs.length = paragraphsLength;
56
- }
57
- set(row, lineInfos, numberings, docParagraphs) {
58
- if (!this.paragraphs[row]) {
59
- const numberingData = NumberingHelper.createDataModel(numberings, docParagraphs, row);
60
- this.paragraphs[row] = new Paragraph(numberingData, lineInfos[0].offsetBefore, this.processTextLinesProperties);
61
- }
62
- this.paragraphs[row].width = this.contentWidth;
63
- this.paragraphs[row].setTextLinesInfo(lineInfos);
64
- }
65
- getVisibleRange(offsetTop, scrollerHeight) {
66
- let start = this.paragraphs.findIndex(x => offsetTop <= x.distanceFromTop + x.height);
67
- if (start < 0) {
68
- start = 0;
69
- }
70
- let startLineInfo = null;
71
- const startParagraph = this.paragraphs[start];
72
- if (startParagraph) {
73
- const startParagraphOffsetTop = offsetTop - startParagraph.distanceFromTop;
74
- startLineInfo = ParagraphHelper.getVisibleLineInfo(startParagraph?.textLinesInfo, startParagraphOffsetTop, 1);
75
- }
76
- if (!startLineInfo) {
77
- return {
78
- startParagraph: 0,
79
- startLine: 0,
80
- startScreenLine: 0,
81
- startScreenFullLine: 0,
82
- endParagraph: 0,
83
- endLine: 0,
84
- endScreenLine: 0,
85
- endScreenFullLine: 0,
86
- pages: [1]
87
- };
88
- }
89
- let end = this.paragraphs.findIndex(x => offsetTop + scrollerHeight <= x.distanceFromTop + x.height);
90
- if (end < 0) {
91
- end = this.paragraphs.length - 1;
92
- }
93
- let endLineInfo = null;
94
- const endParagraph = this.paragraphs[end];
95
- if (endParagraph) {
96
- const endParagraphOffsetTop = offsetTop + scrollerHeight - endParagraph.distanceFromTop;
97
- endLineInfo = ParagraphHelper.getVisibleLineInfo(endParagraph?.textLinesInfo, endParagraphOffsetTop, -1);
98
- }
99
- const visiblePages = this.getVisiblePages(offsetTop, scrollerHeight);
100
- return {
101
- startParagraph: start,
102
- startLine: startLineInfo.index,
103
- startScreenLine: startLineInfo.screenIndex,
104
- startScreenFullLine: startLineInfo.visibleScreenIndex,
105
- endParagraph: end,
106
- endLine: endLineInfo.index,
107
- endScreenLine: endLineInfo.screenIndex,
108
- endScreenFullLine: endLineInfo.visibleScreenIndex,
109
- pages: visiblePages
110
- };
111
- }
112
- processParagraphsProperties(startParagraphIndex, wrapParagraphIndex) {
113
- this.setParagraphIndexes(wrapParagraphIndex);
114
- const pagesInfo = { pagesVerticalData: this.pagesVerticalData, pagesSpace: this.pagesSpace };
115
- let currentPage = startParagraphIndex === 0 ? 1 : this.paragraphs[startParagraphIndex - 1].lastPageNumber;
116
- let pageVerticalData = PageHelper.getVerticalData(currentPage, this.pagesVerticalData);
117
- for (let i = startParagraphIndex; i < this.paragraphs.length; i++) {
118
- const prevParagraphInfo = this.getPreviousParagraphInfo(i);
119
- const paragraph = this.paragraphs[i];
120
- paragraph.processParagraphProperties(prevParagraphInfo, pagesInfo, this.customComponents.tables);
121
- if (paragraph.firstPageNumber !== currentPage) {
122
- currentPage = paragraph.firstPageNumber;
123
- pageVerticalData = PageHelper.getVerticalData(paragraph.firstPageNumber, this.pagesVerticalData);
124
- }
125
- paragraph.distanceFromTop =
126
- (paragraph.firstPageNumber - 1) * this.pageHeight +
127
- this.pagesSpace * paragraph.firstPageNumber +
128
- pageVerticalData.marginTop +
129
- paragraph.pagePreviousContentHeight;
130
- }
131
- let pageHeight = this.pageHeight;
132
- if (!pageHeight) {
133
- pageHeight = this.getAllParagraphsHeight() + this.documentMargin.top + this.documentMargin.bottom;
134
- this.minHeight = pageHeight + 2 * this.pagesSpace;
135
- this.defaultVerticalData.contentHeight = pageHeight;
136
- }
137
- const lastPageNumber = this.paragraphs[this.paragraphs.length - 1].lastPageNumber;
138
- this.allPagesHeight = lastPageNumber * (pageHeight + this.pagesSpace) + this.pagesSpace;
139
- this.emit('pagesCountChanged', { pagesCount: lastPageNumber, pageHeight: pageHeight + 2 * this.pagesSpace });
140
- }
141
- getAllParagraphsHeight() {
142
- return this.paragraphs.reduce((sum, x) => sum + x.height, 0);
143
- }
144
- destroy() {
145
- this.removeAllListeners('pagesCountChanged');
146
- }
147
- updatePageVerticalData(edgeType, page, wrapParagraphIndex) {
148
- const pageVerticalData = PageHelper.getVerticalData(page, this.pagesVerticalData);
149
- const componentHeight = this.customComponents.edges.getComponentHeight(page, edgeType);
150
- if (edgeType === EdgeType.Header) {
151
- pageVerticalData.marginTop = componentHeight > this.documentMargin.top ? componentHeight : this.documentMargin.top;
152
- }
153
- else {
154
- pageVerticalData.marginBottom = componentHeight > this.documentMargin.bottom ? componentHeight : this.documentMargin.bottom;
155
- }
156
- const newContentHeight = this.pageHeight - pageVerticalData.marginTop - pageVerticalData.marginBottom;
157
- if (newContentHeight === pageVerticalData.contentHeight) {
158
- return;
159
- }
160
- pageVerticalData.contentHeight = newContentHeight;
161
- this.processParagraphsProperties(0, wrapParagraphIndex);
162
- }
163
- getPreviousParagraphInfo(row) {
164
- if (!row || !this.paragraphs.length) {
165
- return { lastPage: 1, paragraphHeight: 0, paragraphLastLine: -1 };
166
- }
167
- const prevParagraph = this.paragraphs[row - 1];
168
- return prevParagraph.getParagraphData();
169
- }
170
- getVisiblePages(offsetTop, containerHeight) {
171
- const visiblePages = [];
172
- let firstVisiblePage = offsetTop / (this.pageHeight + this.pagesSpace);
173
- if (firstVisiblePage % 1 === 0) {
174
- firstVisiblePage++;
175
- }
176
- let visiblePagesCount = containerHeight / (this.pageHeight + this.pagesSpace);
177
- const partialPageOnScreenPercent = Math.trunc(((visiblePagesCount % 1) + (firstVisiblePage % 1)) * 100);
178
- const pageSpaceHeightPercent = Math.trunc((this.pagesSpace / containerHeight) * 100);
179
- if (partialPageOnScreenPercent - pageSpaceHeightPercent > 100) {
180
- visiblePagesCount++;
181
- }
182
- visiblePagesCount = Math.ceil(visiblePagesCount);
183
- firstVisiblePage = Math.ceil(firstVisiblePage);
184
- const documentPagesCount = this.paragraphs[this.paragraphs.length - 1].lastPageNumber;
185
- if (firstVisiblePage + visiblePagesCount - 1 > documentPagesCount) {
186
- visiblePagesCount = documentPagesCount - firstVisiblePage + 1;
187
- }
188
- for (let i = 0; i < visiblePagesCount; i++) {
189
- visiblePages.push(firstVisiblePage + i);
190
- }
191
- return visiblePages;
192
- }
193
- initPagesVerticalData() {
194
- if (!this.customComponents.edges ||
195
- (!this.customComponents.edges.headersComponents.length && !this.customComponents.edges.footersComponents.length)) {
196
- this.pagesVerticalData = [
197
- new PageVerticalDataModel({
198
- marginTop: this.documentMargin.top,
199
- marginBottom: this.documentMargin.bottom,
200
- contentHeight: this.pageHeight - this.documentMargin.top - this.documentMargin.bottom,
201
- pageType: PageType.Default
202
- })
203
- ];
204
- return;
205
- }
206
- const pageTypes = this.customComponents.edges.getUniquePageTypes();
207
- this.pagesVerticalData = pageTypes.map(pageType => {
208
- const headerHeight = this.customComponents.edges.getComponentHeightByPageType(pageType, EdgeType.Header);
209
- const footerHeight = this.customComponents.edges.getComponentHeightByPageType(pageType, EdgeType.Footer);
210
- const marginTop = Math.max(headerHeight, this.documentMargin.top);
211
- const marginBottom = Math.max(footerHeight, this.documentMargin.bottom);
212
- return new PageVerticalDataModel({
213
- marginTop,
214
- marginBottom,
215
- contentHeight: this.pageHeight - marginTop - marginBottom,
216
- pageType
217
- });
218
- });
219
- }
220
- setParagraphIndexes(wrapParagraphIndex) {
221
- for (let i = 0; i < this.paragraphs.length; i++) {
222
- this.paragraphs[i].startInsertIndex = wrapParagraphIndex[i];
223
- }
224
- }
225
- }
226
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicGFnZXMud3JhcC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL25neC1ub2Rlci9zcmMvbGliL2VkaXRvci9jb250ZW50L2Rpc3BsYXktZGF0YS9wYWdlcy53cmFwLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUdBLE9BQU8sRUFBRSxRQUFRLEVBQUUsTUFBTSx1Q0FBdUMsQ0FBQztBQUNqRSxPQUFPLEVBQUUsYUFBYSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFLMUQsT0FBTyxFQUFFLGVBQWUsRUFBRSxNQUFNLDBDQUEwQyxDQUFDO0FBRTNFLE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSxxQ0FBcUMsQ0FBQztBQUNqRSxPQUFPLEVBQUUsUUFBUSxFQUFFLE1BQU0sdUNBQXVDLENBQUM7QUFDakUsT0FBTyxFQUFFLHFCQUFxQixFQUFFLE1BQU0sNkJBQTZCLENBQUM7QUFDcEUsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLGFBQWEsQ0FBQztBQUN4QyxPQUFPLEVBQUUsZUFBZSxFQUFFLE1BQU0sMENBQTBDLENBQUM7QUFJM0UsTUFBTSxPQUFPLFNBQVUsU0FBUSxhQUFhO0lBYXhDLElBQUksbUJBQW1CO1FBQ25CLE9BQU8sSUFBSSxDQUFDLGlCQUFpQixDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxRQUFRLEtBQUssUUFBUSxDQUFDLE9BQU8sQ0FBQyxDQUFDO0lBQzdFLENBQUM7SUFTRCxZQUNXLFVBQWtCLEVBQ2xCLGNBQTJCLEVBQzNCLFNBQWlCLEVBQ2pCLGFBQWEsQ0FBQyxFQUNkLGdCQUFtQztRQUUxQyxLQUFLLEVBQUUsQ0FBQztRQU5ELGVBQVUsR0FBVixVQUFVLENBQVE7UUFDbEIsbUJBQWMsR0FBZCxjQUFjLENBQWE7UUFDM0IsY0FBUyxHQUFULFNBQVMsQ0FBUTtRQUNqQixlQUFVLEdBQVYsVUFBVSxDQUFJO1FBQ2QscUJBQWdCLEdBQWhC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QyxNQUFNLFlBQVksR0FBRyxJQUFJLENBQUMsZ0JBQWdCLENBQUMsS0FBSyxDQUFDLDRCQUE0QixDQUFDLFFBQVEsRUFBRSxRQUFRLENBQUMsTUFBTSxDQUFDLENBQUM7WUFDekcsTUFBTSxZQUFZLEdBQUcsSUFBSSxDQUFDLGdCQUFnQixDQUFDLEtBQUssQ0FBQyw0QkFBNEIsQ0FBQyxRQUFRLEVBQUUsUUFBUSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1lBQ3pHLE1BQU0sU0FBUyxHQUFHLElBQUksQ0FBQyxHQUFHLENBQUMsWUFBWSxFQUFFLElBQUksQ0FBQyxjQUFjLENBQUMsR0FBRyxDQUFDLENBQUM7WUFDbEUsTUFBTSxZQUFZLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxZQUFZLEVBQUUsSUFBSSxDQUFDLGNBQWMsQ0FBQyxNQUFNLENBQUMsQ0FBQztZQUV4RSxPQUFPLElBQUkscUJBQXFCLENBQUM7Z0JBQzdCLFNBQVM7Z0JBQ1QsWUFBWTtnQkFDWixhQUFhLEVBQUUsSUFBSSxDQUFDLFVBQVUsR0FBRyxTQUFTLEdBQUcsWUFBWTtnQkFDekQsUUFBUTthQUNYLENBQUMsQ0FBQztRQUNQLENBQUMsQ0FBQyxDQUFDO0lBQ1AsQ0FBQztJQUVPLG1CQUFtQixDQUFDLGtCQUE0QjtRQUNwRCxLQUFLLElBQUksQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsSUFBSSxDQUFDLFVBQVUsQ0FBQyxNQUFNLEVBQUUsQ0FBQyxFQUFFLEVBQUU7WUFDN0MsSUFBSSxDQUFDLFVBQVUsQ0FBQyxDQUFDLENBQUMsQ0FBQyxnQkFBZ0IsR0FBRyxrQkFBa0IsQ0FBQyxDQUFDLENBQUMsQ0FBQztTQUMvRDtJQUNMLENBQUM7Q0FDSiIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IENvbXBvbmVudFJlZiB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuXG5pbXBvcnQgeyBEaXNwbGF5VG9rZW4gfSBmcm9tICcuL2Rpc3BsYXktdG9rZW4ubW9kZWwnO1xuaW1wb3J0IHsgRWRnZVR5cGUgfSBmcm9tICcuLi8uLi9jb21wb25lbnRzL2VkZ2VzL2VkZ2UtdHlwZS5lbnVtJztcbmltcG9ydCB7IEV2ZW50RW1pdHRpbmcgfSBmcm9tICcuLi8uLi9jb3JlL2V2ZW50LWVtaXR0aW5nJztcbmltcG9ydCB7IElDdXN0b21Db21wb25lbnRzIH0gZnJvbSAnLi4vLi4vY29tcG9uZW50cy9zaGFyZWQvY3VzdG9tLWNvbXBvbmVudHMuaW50ZXJmYWNlJztcbmltcG9ydCB7IExpbmVJbmZvTW9kZWwgfSBmcm9tICcuL2xpbmUtaW5mby5tb2RlbCc7XG5pbXBvcnQgeyBOb2RlclRhYmxlQ29tcG9uZW50IH0gZnJvbSAnLi4vLi4vY29tcG9uZW50cy90YWJsZS9jb21wb25lbnRzL3RhYmxlLmNvbXBvbmVudCc7XG5pbXBvcnQgeyBNYXJnaW5Nb2RlbCB9IGZyb20gJy4uL21hcmdpbi5tb2RlbCc7XG5pbXBvcnQgeyBOdW1iZXJpbmdIZWxwZXIgfSBmcm9tICcuLi8uLi9nYWRnZXRzL251bWJlcmluZy9udW1iZXJpbmcuaGVscGVyJztcbmltcG9ydCB7IE51bWJlcmluZ01vZGVsIH0gZnJvbSAnLi4vLi4vLi4vbW9kZWxzL2dlbmVyYXRlZC9udW1iZXJpbmcubW9kZWwnO1xuaW1wb3J0IHsgUGFnZUhlbHBlciB9IGZyb20gJy4uLy4uL2V4ZWN1dGlvbi9oZWxwZXJzL3BhZ2UuaGVscGVyJztcbmltcG9ydCB7IFBhZ2VUeXBlIH0gZnJvbSAnLi4vLi4vY29tcG9uZW50cy9lZGdlcy9wYWdlLXR5cGUuZW51bSc7XG5pbXBvcnQgeyBQYWdlVmVydGljYWxEYXRhTW9kZWwgfSBmcm9tICcuLi9wYWdlLXZlcnRpY2FsLWRhdGEubW9kZWwnO1xuaW1wb3J0IHsgUGFyYWdyYXBoIH0gZnJvbSAnLi9wYXJhZ3JhcGgnO1xuaW1wb3J0IHsgUGFyYWdyYXBoSGVscGVyIH0gZnJvbSAnLi4vLi4vZXhlY3V0aW9uL2hlbHBlcnMvcGFyYWdyYXBoLmhlbHBlcic7XG5pbXBvcnQgeyBQYXJhZ3JhcGhNb2RlbCB9IGZyb20gJy4uLy4uLy4uL21vZGVscy9nZW5lcmF0ZWQvcGFyYWdyYXBoLm1vZGVsJztcbmltcG9ydCB7IFZpc2libGVSYW5nZSB9IGZyb20gJy4uLy4uL2Rpc3BsYXkvdmlzaWJsZS1yYW5nZS5pbnRlcmZhY2UnO1xuXG5leHBvcnQgY2xhc3MgUGFnZXNXcmFwIGV4dGVuZHMgRXZlbnRFbWl0dGluZyB7XG4gICAgY29udGVudFdpZHRoOiBudW1iZXI7XG5cbiAgICBhbGxQYWdlc0hlaWdodCA9IDA7XG5cbiAgICBtaW5IZWlnaHQgPSAwO1xuXG4gICAgcGFyYWdyYXBoczogUGFyYWdyYXBoW10gPSBbXTtcblxuICAgIHRhYlRva2VuczogRGlzcGxheVRva2VuW10gPSBbXTtcblxuICAgIHBhZ2VzVmVydGljYWxEYXRhOiBQYWdlVmVydGljYWxEYXRhTW9kZWxbXTtcblxuICAgIGdldCBkZWZhdWx0VmVydGljYWxEYXRhKCk6IFBhZ2VWZXJ0aWNhbERhdGFNb2RlbCB7XG4gICAgICAgIHJldHVybiB0aGlzLnBhZ2VzVmVydGljYWxEYXRhLmZpbmQoeCA9PiB4LnBhZ2VUeXBlID09PSBQYWdlVHlwZS5EZWZhdWx0KTtcbiAgICB9XG5cbiAgICBwcml2YXRlIHByb2Nlc3NUZXh0TGluZXNQcm9wZXJ0aWVzOiAoXG4gICAgICAgIGN1cnJlbnRQYXJhZ3JhcGg6IFBhcmFncmFwaCxcbiAgICAgICAgcHJldlBhcmFncmFwaEluZm86IHsgbGFzdFBhZ2U6IG51bWJlcjsgcGFyYWdyYXBoSGVpZ2h0OiBudW1iZXI7IHBhcmFncmFwaExhc3RMaW5lOiBudW1iZXIgfSxcbiAgICAgICAgcGFnZXNJbmZvOiB7IHBhZ2VzVmVydGljYWxEYXRhOiBQYWdlVmVydGljYWxEYXRhTW9kZWxbXTsgcGFnZXNTcGFjZTogbnVtYmVyIH0sXG4gICAgICAgIHRhYmxlczogQ29tcG9uZW50UmVmPE5vZGVyVGFibGVDb21wb25lbnQ+W11cbiAgICApID0+IHZvaWQ7XG5cbiAgICBjb25zdHJ1Y3RvcihcbiAgICAgICAgcHVibGljIHBhZ2VzU3BhY2U6IG51bWJlcixcbiAgICAgICAgcHVibGljIGRvY3VtZW50TWFyZ2luOiBNYXJnaW5Nb2RlbCxcbiAgICAgICAgcHVibGljIHBhZ2VXaWR0aDogbnVtYmVyLFxuICAgICAgICBwdWJsaWMgcGFnZUhlaWdodCA9IDAsXG4gICAgICAgIHB1YmxpYyBjdXN0b21Db21wb25lbnRzOiBJQ3VzdG9tQ29tcG9uZW50c1xuICAgICkge1xuICAgICAgICBzdXBlcigpO1xuICAgICAgICB0aGlzLm1pbkhlaWdodCA9IHRoaXMucGFnZUhlaWdodCArIDIgKiB0aGlzLnBhZ2VzU3BhY2U7XG4gICAgICAgIHRoaXMuY29udGVudFdpZHRoID0gdGhpcy5wYWdlV2lkdGggLSB0aGlzLmRvY3VtZW50TWFyZ2luLmxlZnQgLSB0aGlzLmRvY3VtZW50TWFyZ2luLnJpZ2h0O1xuICAgICAgICB0aGlzLmluaXRQYWdlc1ZlcnRpY2FsRGF0YSgpO1xuXG4gICAgICAgIHRoaXMucHJvY2Vzc1RleHRMaW5lc1Byb3BlcnRpZXMgPSAhdGhpcy5wYWdlSGVpZ2h0XG4gICAgICAgICAgICA/IFBhcmFncmFwaEhlbHBlci5wcm9jZXNzVGV4dExpbmVzUHJvcGVydGllc0ZvclNpbmdsZVBhZ2VcbiAgICAgICAgICAgIDogUGFyYWdyYXBoSGVscGVyLnByb2Nlc3NUZXh0TGluZXNQcm9wZXJ0aWVzO1xuICAgIH1cblxuICAgIGdldFBhcmFncmFwaFRvcChpbmRleDogbnVtYmVyKTogbnVtYmVyIHtcbiAgICAgICAgcmV0dXJuIHRoaXMucGFyYWdyYXBoc1tpbmRleF0gPyB0aGlzLnBhcmFncmFwaHNbaW5kZXhdLmRpc3RhbmNlRnJvbVRvcCA6IDA7XG4gICAgfVxuXG4gICAgZ2V0UGFyYWdyYXBoVG9wRm9yUHJpbnQoaW5kZXg6IG51bWJlcik6IG51bWJlciB7XG4gICAgICAgIGlmICghdGhpcy5wYXJhZ3JhcGhzW2luZGV4XSkge1xuICAgICAgICAgICAgcmV0dXJuIDA7XG4gICAgICAgIH1cbiAgICAgICAgY29uc3QgcGFyYWdyYXBoID0gdGhpcy5wYXJhZ3JhcGhzW2luZGV4XTtcbiAgICAgICAgY29uc3QgcGFnZU51bWJlciA9IHBhcmFncmFwaC5wYWdlTnVtYmVyc1swXTtcbiAgICAgICAgbGV0IHBhZ2VCcmVha0hlaWdodCA9IDA7XG4gICAgICAgIHBhcmFncmFwaC50ZXh0TGluZXNJbmZvLmZvckVhY2gobGluZXNJbmZvID0+IHtcbiAgICAgICAgICAgIGlmIChsaW5lc0luZm8uaXNBZnRlclBhZ2VCcmVhaykge1xuICAgICAgICAgICAgICAgIHBhZ2VCcmVha0hlaWdodCA9IGxpbmVzSW5mby5oZWlnaHQ7XG4gICAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgICByZXR1cm4gcGFyYWdyYXBoLmRpc3RhbmNlRnJvbVRvcCAtIHBhZ2VOdW1iZXIgKiB0aGlzLnBhZ2VzU3BhY2UgLSBwYWdlQnJlYWtIZWlnaHQ7XG4gICAgfVxuXG4gICAgZ2V0UGFyYWdyYXBoSGVpZ2h0KGluZGV4OiBudW1iZXIpOiBudW1iZXIge1xuICAgICAgICByZXR1cm4gdGhpcy5wYXJhZ3JhcGhzW2luZGV4XSA/IHRoaXMucGFyYWdyYXBoc1tpbmRleF0uaGVpZ2h0IDogMDtcbiAgICB9XG5cbiAgICByZW1vdmUoaW5kZXg6IG51bWJlciwgbGVuZ3RoOiBudW1iZXIpOiB2b2lkIHtcbiAgICAgICAgdGhpcy5wYXJhZ3JhcGhzLnNwbGljZShpbmRleCwgbGVuZ3RoKTtcbiAgICB9XG5cbiAgICByZXNldChwYXJhZ3JhcGhzTGVuZ3RoOiBudW1iZXIpOiB2b2lkIHtcbiAgICAgICAgdGhpcy5wYXJhZ3JhcGhzLmxlbmd0aCA9IHBhcmFncmFwaHNMZW5ndGg7XG4gICAgfVxuXG4gICAgc2V0KHJvdzogbnVtYmVyLCBsaW5lSW5mb3M6IExpbmVJbmZvTW9kZWxbXSwgbnVtYmVyaW5nczogTnVtYmVyaW5nTW9kZWxbXSwgZG9jUGFyYWdyYXBoczogUGFyYWdyYXBoTW9kZWxbXSk6IHZvaWQge1xuICAgICAgICBpZiAoIXRoaXMucGFyYWdyYXBoc1tyb3ddKSB7XG4gICAgICAgICAgICBjb25zdCBudW1iZXJpbmdEYXRhID0gTnVtYmVyaW5nSGVscGVyLmNyZWF0ZURhdGFNb2RlbChudW1iZXJpbmdzLCBkb2NQYXJhZ3JhcGhzLCByb3cpO1xuICAgICAgICAgICAgdGhpcy5wYXJhZ3JhcGhzW3Jvd10gPSBuZXcgUGFyYWdyYXBoKG51bWJlcmluZ0RhdGEsIGxpbmVJbmZvc1swXS5vZmZzZXRCZWZvcmUsIHRoaXMucHJvY2Vzc1RleHRMaW5lc1Byb3BlcnRpZXMpO1xuICAgICAgICB9XG5cbiAgICAgICAgdGhpcy5wYXJhZ3JhcGhzW3Jvd10ud2lkdGggPSB0aGlzLmNvbnRlbnRXaWR0aDtcbiAgICAgICAgdGhpcy5wYXJhZ3JhcGhzW3Jvd10uc2V0VGV4dExpbmVzSW5mbyhsaW5lSW5mb3MpO1xuICAgIH1cblxuICAgIGdldFZpc2libGVSYW5nZShvZmZzZXRUb3A6IG51bWJlciwgc2Nyb2xsZXJIZWlnaHQ6IG51bWJlcik6IFZpc2libGVSYW5nZSB7XG4gICAgICAgIGxldCBzdGFydCA9IHRoaXMucGFyYWdyYXBocy5maW5kSW5kZXgoeCA9PiBvZmZzZXRUb3AgPD0geC5kaXN0YW5jZUZyb21Ub3AgKyB4LmhlaWdodCk7XG4gICAgICAgIGlmIChzdGFydCA8IDApIHtcbiAgICAgICAgICAgIHN0YXJ0ID0gMDtcbiAgICAgICAgfVxuXG4gICAgICAgIGxldCBzdGFydExpbmVJbmZvID0gbnVsbDtcbiAgICAgICAgY29uc3Qgc3RhcnRQYXJhZ3JhcGggPSB0aGlzLnBhcmFncmFwaHNbc3RhcnRdO1xuICAgICAgICBpZiAoc3RhcnRQYXJhZ3JhcGgpIHtcbiAgICAgICAgICAgIGNvbnN0IHN0YXJ0UGFyYWdyYXBoT2Zmc2V0VG9wID0gb2Zmc2V0VG9wIC0gc3RhcnRQYXJhZ3JhcGguZGlzdGFuY2VGcm9tVG9wO1xuICAgICAgICAgICAgc3RhcnRMaW5lSW5mbyA9IFBhcmFncmFwaEhlbHBlci5nZXRWaXNpYmxlTGluZUluZm8oc3RhcnRQYXJhZ3JhcGg/LnRleHRMaW5lc0luZm8sIHN0YXJ0UGFyYWdyYXBoT2Zmc2V0VG9wLCAxKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmICghc3RhcnRMaW5lSW5mbykge1xuICAgICAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgICAgICBzdGFydFBhcmFncmFwaDogMCxcbiAgICAgICAgICAgICAgICBzdGFydExpbmU6IDAsXG4gICAgICAgICAgICAgICAgc3RhcnRTY3JlZW5MaW5lOiAwLFxuICAgICAgICAgICAgICAgIHN0YXJ0U2NyZWVuRnVsbExpbmU6IDAsXG4gICAgICAgICAgICAgICAgZW5kUGFyYWdyYXBoOiAwLFxuICAgICAgICAgICAgICAgIGVuZExpbmU6IDAsXG4gICAgICAgICAgICAgICAgZW5kU2NyZWVuTGluZTogMCxcbiAgICAgICAgICAgICAgICBlbmRTY3JlZW5GdWxsTGluZTogMCxcbiAgICAgICAgICAgICAgICBwYWdlczogWzFdXG4gICAgICAgICAgICB9O1xuICAgICAgICB9XG5cbiAgICAgICAgbGV0IGVuZCA9IHRoaXMucGFyYWdyYXBocy5maW5kSW5kZXgoeCA9PiBvZmZzZXRUb3AgKyBzY3JvbGxlckhlaWdodCA8PSB4LmRpc3RhbmNlRnJvbVRvcCArIHguaGVpZ2h0KTtcbiAgICAgICAgaWYgKGVuZCA8IDApIHtcbiAgICAgICAgICAgIGVuZCA9IHRoaXMucGFyYWdyYXBocy5sZW5ndGggLSAxO1xuICAgICAgICB9XG5cbiAgICAgICAgbGV0IGVuZExpbmVJbmZvID0gbnVsbDtcbiAgICAgICAgY29uc3QgZW5kUGFyYWdyYXBoID0gdGhpcy5wYXJhZ3JhcGhzW2VuZF07XG4gICAgICAgIGlmIChlbmRQYXJhZ3JhcGgpIHtcbiAgICAgICAgICAgIGNvbnN0IGVuZFBhcmFncmFwaE9mZnNldFRvcCA9IG9mZnNldFRvcCArIHNjcm9sbGVySGVpZ2h0IC0gZW5kUGFyYWdyYXBoLmRpc3RhbmNlRnJvbVRvcDtcbiAgICAgICAgICAgIGVuZExpbmVJbmZvID0gUGFyYWdyYXBoSGVscGVyLmdldFZpc2libGVMaW5lSW5mbyhlbmRQYXJhZ3JhcGg/LnRleHRMaW5lc0luZm8sIGVuZFBhcmFncmFwaE9mZnNldFRvcCwgLTEpO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3QgdmlzaWJsZVBhZ2VzID0gdGhpcy5nZXRWaXNpYmxlUGFnZXMob2Zmc2V0VG9wLCBzY3JvbGxlckhlaWdodCk7XG5cbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgIHN0YXJ0UGFyYWdyYXBoOiBzdGFydCxcbiAgICAgICAgICAgIHN0YXJ0TGluZTogc3RhcnRMaW5lSW5mby5pbmRleCxcbiAgICAgICAgICAgIHN0YXJ0U2NyZWVuTGluZTogc3RhcnRMaW5lSW5mby5zY3JlZW5JbmRleCxcbiAgICAgICAgICAgIHN0YXJ0U2NyZWVuRnVsbExpbmU6IHN0YXJ0TGluZUluZm8udmlzaWJsZVNjcmVlbkluZGV4LFxuICAgICAgICAgICAgZW5kUGFyYWdyYXBoOiBlbmQsXG4gICAgICAgICAgICBlbmRMaW5lOiBlbmRMaW5lSW5mby5pbmRleCxcbiAgICAgICAgICAgIGVuZFNjcmVlbkxpbmU6IGVuZExpbmVJbmZvLnNjcmVlbkluZGV4LFxuICAgICAgICAgICAgZW5kU2NyZWVuRnVsbExpbmU6IGVuZExpbmVJbmZvLnZpc2libGVTY3JlZW5JbmRleCxcbiAgICAgICAgICAgIHBhZ2VzOiB2aXNpYmxlUGFnZXNcbiAgICAgICAgfTtcbiAgICB9XG5cbiAgICBwcm9jZXNzUGFyYWdyYXBoc1Byb3BlcnRpZXMoc3RhcnRQYXJhZ3JhcGhJbmRleDogbnVtYmVyLCB3cmFwUGFyYWdyYXBoSW5kZXg6IG51bWJlcltdKTogdm9pZCB7XG4gICAgICAgIHRoaXMuc2V0UGFyYWdyYXBoSW5kZXhlcyh3cmFwUGFyYWdyYXBoSW5kZXgpO1xuICAgICAgICBjb25zdCBwYWdlc0luZm8gPSB7IHBhZ2VzVmVydGljYWxEYXRhOiB0aGlzLnBhZ2VzVmVydGljYWxEYXRhLCBwYWdlc1NwYWNlOiB0aGlzLnBhZ2VzU3BhY2UgfTtcbiAgICAgICAgbGV0IGN1cnJlbnRQYWdlID0gc3RhcnRQYXJhZ3JhcGhJbmRleCA9PT0gMCA/IDEgOiB0aGlzLnBhcmFncmFwaHNbc3RhcnRQYXJhZ3JhcGhJbmRleCAtIDFdLmxhc3RQYWdlTnVtYmVyO1xuICAgICAgICBsZXQgcGFnZVZlcnRpY2FsRGF0YSA9IFBhZ2VIZWxwZXIuZ2V0VmVydGljYWxEYXRhKGN1cnJlbnRQYWdlLCB0aGlzLnBhZ2VzVmVydGljYWxEYXRhKTtcbiAgICAgICAgZm9yIChsZXQgaSA9IHN0YXJ0UGFyYWdyYXBoSW5kZXg7IGkgPCB0aGlzLnBhcmFncmFwaHMubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgICAgIGNvbnN0IHByZXZQYXJhZ3JhcGhJbmZvID0gdGhpcy5nZXRQcmV2aW91c1BhcmFncmFwaEluZm8oaSk7XG4gICAgICAgICAgICBjb25zdCBwYXJhZ3JhcGggPSB0aGlzLnBhcmFncmFwaHNbaV07XG4gICAgICAgICAgICBwYXJhZ3JhcGgucHJvY2Vzc1BhcmFncmFwaFByb3BlcnRpZXMocHJldlBhcmFncmFwaEluZm8sIHBhZ2VzSW5mbywgdGhpcy5jdXN0b21Db21wb25lbnRzLnRhYmxlcyk7XG4gICAgICAgICAgICBpZiAocGFyYWdyYXBoLmZpcnN0UGFnZU51bWJlciAhPT0gY3VycmVudFBhZ2UpIHtcbiAgICAgICAgICAgICAgICBjdXJyZW50UGFnZSA9IHBhcmFncmFwaC5maXJzdFBhZ2VOdW1iZXI7XG4gICAgICAgICAgICAgICAgcGFnZVZlcnRpY2FsRGF0YSA9IFBhZ2VIZWxwZXIuZ2V0VmVydGljYWxEYXRhKHBhcmFncmFwaC5maXJzdFBhZ2VOdW1iZXIsIHRoaXMucGFnZXNWZXJ0aWNhbERhdGEpO1xuICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICBwYXJhZ3JhcGguZGlzdGFuY2VGcm9tVG9wID1cbiAgICAgICAgICAgICAgICAocGFyYWdyYXBoLmZpcnN0UGFnZU51bWJlciAtIDEpICogdGhpcy5wYWdlSGVpZ2h0ICtcbiAgICAgICAgICAgICAgICB0aGlzLnBhZ2VzU3BhY2UgKiBwYXJhZ3JhcGguZmlyc3RQYWdlTnVtYmVyICtcbiAgICAgICAgICAgICAgICBwYWdlVmVydGljYWxEYXRhLm1hcmdpblRvcCArXG4gICAgICAgICAgICAgICAgcGFyYWdyYXBoLnBhZ2VQcmV2aW91c0NvbnRlbnRIZWlnaHQ7XG4gICAgICAgIH1cblxuICAgICAgICBsZXQgcGFnZUhlaWdodCA9IHRoaXMucGFnZUhlaWdodDtcbiAgICAgICAgaWYgKCFwYWdlSGVpZ2h0KSB7XG4gICAgICAgICAgICBwYWdlSGVpZ2h0ID0gdGhpcy5nZXRBbGxQYXJhZ3JhcGhzSGVpZ2h0KCkgKyB0aGlzLmRvY3VtZW50TWFyZ2luLnRvcCArIHRoaXMuZG9jdW1lbnRNYXJnaW4uYm90dG9tO1xuICAgICAgICAgICAgdGhpcy5taW5IZWlnaHQgPSBwYWdlSGVpZ2h0ICsgMiAqIHRoaXMucGFnZXNTcGFjZTtcbiAgICAgICAgICAgIHRoaXMuZGVmYXVsdFZlcnRpY2FsRGF0YS5jb250ZW50SGVpZ2h0ID0gcGFnZUhlaWdodDtcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IGxhc3RQYWdlTnVtYmVyID0gdGhpcy5wYXJhZ3JhcGhzW3RoaXMucGFyYWdyYXBocy5sZW5ndGggLSAxXS5sYXN0UGFnZU51bWJlcjtcbiAgICAgICAgdGhpcy5hbGxQYWdlc0hlaWdodCA9IGxhc3RQYWdlTnVtYmVyICogKHBhZ2VIZWlnaHQgKyB0aGlzLnBhZ2VzU3BhY2UpICsgdGhpcy5wYWdlc1NwYWNlO1xuICAgICAgICB0aGlzLmVtaXQoJ3BhZ2VzQ291bnRDaGFuZ2VkJywgeyBwYWdlc0NvdW50OiBsYXN0UGFnZU51bWJlciwgcGFnZUhlaWdodDogcGFnZUhlaWdodCArIDIgKiB0aGlzLnBhZ2VzU3BhY2UgfSk7XG4gICAgfVxuXG4gICAgZ2V0QWxsUGFyYWdyYXBoc0hlaWdodCgpOiBudW1iZXIge1xuICAgICAgICByZXR1cm4gdGhpcy5wYXJhZ3JhcGhzLnJlZHVjZSgoc3VtLCB4KSA9PiBzdW0gKyB4LmhlaWdodCwgMCk7XG4gICAgfVxuXG4gICAgZGVzdHJveSgpOiB2b2lkIHtcbiAgICAgICAgdGhpcy5yZW1vdmVBbGxMaXN0ZW5lcnMoJ3BhZ2VzQ291bnRDaGFuZ2VkJyk7XG4gICAgfVxuXG4gICAgdXBkYXRlUGFnZVZlcnRpY2FsRGF0YShlZGdlVHlwZTogRWRnZVR5cGUsIHBhZ2U6IG51bWJlciwgd3JhcFBhcmFncmFwaEluZGV4OiBudW1iZXJbXSk6IHZvaWQge1xuICAgICAgICBjb25zdCBwYWdlVmVydGljYWxEYXRhID0gUGFnZUhlbHBlci5nZXRWZXJ0aWNhbERhdGEocGFnZSwgdGhpcy5wYWdlc1ZlcnRpY2FsRGF0YSk7XG4gICAgICAgIGNvbnN0IGNvbXBvbmVudEhlaWdodCA9IHRoaXMuY3VzdG9tQ29tcG9uZW50cy5lZGdlcy5nZXRDb21wb25lbnRIZWlnaHQocGFnZSwgZWRnZVR5cGUpO1xuICAgICAgICBpZiAoZWRnZVR5cGUgPT09IEVkZ2VUeXBlLkhlYWRlcikge1xuICAgICAgICAgICAgcGFnZVZlcnRpY2FsRGF0YS5tYXJnaW5Ub3AgPSBjb21wb25lbnRIZWlnaHQgPiB0aGlzLmRvY3VtZW50TWFyZ2luLnRvcCA/IGNvbXBvbmVudEhlaWdodCA6IHRoaXMuZG9jdW1lbnRNYXJnaW4udG9wO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgcGFnZVZlcnRpY2FsRGF0YS5tYXJnaW5Cb3R0b20gPSBjb21wb25lbnRIZWlnaHQgPiB0aGlzLmRvY3VtZW50TWFyZ2luLmJvdHRvbSA/IGNvbXBvbmVudEhlaWdodCA6IHRoaXMuZG9jdW1lbnRNYXJnaW4uYm90dG9tO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3QgbmV3Q29udGVudEhlaWdodCA9IHRoaXMucGFnZUhlaWdodCAtIHBhZ2VWZXJ0aWNhbERhdGEubWFyZ2luVG9wIC0gcGFnZVZlcnRpY2FsRGF0YS5tYXJnaW5Cb3R0b207XG4gICAgICAgIGlmIChuZXdDb250ZW50SGVpZ2h0ID09PSBwYWdlVmVydGljYWxEYXRhLmNvbnRlbnRIZWlnaHQpIHtcbiAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgfVxuXG4gICAgICAgIHBhZ2VWZXJ0aWNhbERhdGEuY29udGVudEhlaWdodCA9IG5ld0NvbnRlbnRIZWlnaHQ7XG4gICAgICAgIHRoaXMucHJvY2Vzc1BhcmFncmFwaHNQcm9wZXJ0aWVzKDAsIHdyYXBQYXJhZ3JhcGhJbmRleCk7XG4gICAgfVxuXG4gICAgcHJpdmF0ZSBnZXRQcmV2aW91c1BhcmFncmFwaEluZm8ocm93OiBudW1iZXIpOiB7IGxhc3RQYWdlOiBudW1iZXI7IHBhcmFncmFwaEhlaWdodDogbnVtYmVyOyBwYXJhZ3JhcGhMYXN0TGluZTogbnVtYmVyIH0ge1xuICAgICAgICBpZiAoIXJvdyB8fCAhdGhpcy5wYXJhZ3JhcGhzLmxlbmd0aCkge1xuICAgICAgICAgICAgcmV0dXJuIHsgbGFzdFBhZ2U6IDEsIHBhcmFncmFwaEhlaWdodDogMCwgcGFyYWdyYXBoTGFzdExpbmU6IC0xIH07XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCBwcmV2UGFyYWdyYXBoID0gdGhpcy5wYXJhZ3JhcGhzW3JvdyAtIDFdO1xuICAgICAgICByZXR1cm4gcHJldlBhcmFncmFwaC5nZXRQYXJhZ3JhcGhEYXRhKCk7XG4gICAgfVxuXG4gICAgcHJpdmF0ZSBnZXRWaXNpYmxlUGFnZXMob2Zmc2V0VG9wOiBudW1iZXIsIGNvbnRhaW5lckhlaWdodDogbnVtYmVyKTogbnVtYmVyW10ge1xuICAgICAgICBjb25zdCB2aXNpYmxlUGFnZXM6IG51bWJlcltdID0gW107XG5cbiAgICAgICAgbGV0IGZpcnN0VmlzaWJsZVBhZ2UgPSBvZmZzZXRUb3AgLyAodGhpcy5wYWdlSGVpZ2h0ICsgdGhpcy5wYWdlc1NwYWNlKTtcbiAgICAgICAgaWYgKGZpcnN0VmlzaWJsZVBhZ2UgJSAxID09PSAwKSB7XG4gICAgICAgICAgICBmaXJzdFZpc2libGVQYWdlKys7XG4gICAgICAgIH1cblxuICAgICAgICBsZXQgdmlzaWJsZVBhZ2VzQ291bnQgPSBjb250YWluZXJIZWlnaHQgLyAodGhpcy5wYWdlSGVpZ2h0ICsgdGhpcy5wYWdlc1NwYWNlKTtcbiAgICAgICAgY29uc3QgcGFydGlhbFBhZ2VPblNjcmVlblBlcmNlbnQgPSBNYXRoLnRydW5jKCgodmlzaWJsZVBhZ2VzQ291bnQgJSAxKSArIChmaXJzdFZpc2libGVQYWdlICUgMSkpICogMTAwKTtcbiAgICAgICAgY29uc3QgcGFnZVNwYWNlSGVpZ2h0UGVyY2VudCA9IE1hdGgudHJ1bmMoKHRoaXMucGFnZXNTcGFjZSAvIGNvbnRhaW5lckhlaWdodCkgKiAxMDApO1xuICAgICAgICBpZiAocGFydGlhbFBhZ2VPblNjcmVlblBlcmNlbnQgLSBwYWdlU3BhY2VIZWlnaHRQZXJjZW50ID4gMTAwKSB7XG4gICAgICAgICAgICB2aXNpYmxlUGFnZXNDb3VudCsrO1xuICAgICAgICB9XG5cbiAgICAgICAgdmlzaWJsZVBhZ2VzQ291bnQgPSBNYXRoLmNlaWwodmlzaWJsZVBhZ2VzQ291bnQpO1xuICAgICAgICBmaXJzdFZpc2libGVQYWdlID0gTWF0aC5jZWlsKGZpcnN0VmlzaWJsZVBhZ2UpO1xuICAgICAgICBjb25zdCBkb2N1bWVudFBhZ2VzQ291bnQgPSB0aGlzLnBhcmFncmFwaHNbdGhpcy5wYXJhZ3JhcGhzLmxlbmd0aCAtIDFdLmxhc3RQYWdlTnVtYmVyO1xuICAgICAgICBpZiAoZmlyc3RWaXNpYmxlUGFnZSArIHZpc2libGVQYWdlc0NvdW50IC0gMSA+IGRvY3VtZW50UGFnZXNDb3VudCkge1xuICAgICAgICAgICAgdmlzaWJsZVBhZ2VzQ291bnQgPSBkb2N1bWVudFBhZ2VzQ291bnQgLSBmaXJzdFZpc2libGVQYWdlICsgMTtcbiAgICAgICAgfVxuXG4gICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgdmlzaWJsZVBhZ2VzQ291bnQ7IGkrKykge1xuICAgICAgICAgICAgdmlzaWJsZVBhZ2VzLnB1c2goZmlyc3RWaXNpYmxlUGFnZSArIGkpO1xuICAgICAgICB9XG5cbiAgICAgICAgcmV0dXJuIHZpc2libGVQYWdlcztcbiAgICB9XG5cbiAgICBwcml2YXRlIGluaXRQYWdlc1ZlcnRpY2FsRGF0YSgpOiB2b2lkIHtcbiAgICAgICAgaWYgKFxuICAgICAgICAgICAgIXRoaXMuY3VzdG9tQ29tcG9uZW50cy5lZGdlcyB8fFxuICAgICAgICAgICAgKCF0aGlzLmN1c3RvbUNvbXBvbmVudHMuZWRnZXMuaGVhZGVyc0NvbXBvbmVudHMubGVuZ3RoICYmICF0aGlzLmN1c3RvbUNvbXBvbmVudHMuZWRnZXMuZm9vdGVyc0NvbXBvbmVudHMubGVuZ3RoKVxuICAgICAgICApIHtcbiAgICAgICAgICAgIHRoaXMucGFnZXNWZXJ0aWNhbERhdGEgPSBbXG4gICAgICAgICAgICAgICAgbmV3IFBhZ2VWZXJ0aWNhbERhdGFNb2RlbCh7XG4gICAgICAgICAgICAgICAgICAgIG1hcmdpblRvcDogdGhpcy5kb2N1bWVudE1hcmdpbi50b3AsXG4gICAgICAgICAgICAgICAgICAgIG1hcmdpbkJvdHRvbTogdGhpcy5kb2N1bWVudE1hcmdpbi5ib3R0b20sXG4gICAgICAgICAgICAgICAgICAgIGNvbnRlbnRIZWlnaHQ6IHRoaXMucGFnZUhlaWdodCAtIHRoaXMuZG9jdW1lbnRNYXJnaW4udG9wIC0gdGhpcy5kb2N1bWVudE1hcmdpbi5ib3R0b20sXG4gICAgICAgICAgICAgICAgICAgIHBhZ2VUeXBlOiBQYWdlVHlwZS5EZWZhdWx0XG4gICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgIF07XG4gICAgICAgICAgICByZXR1cm47XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCBwYWdlVHlwZXMgPSB0aGlzLmN1c3RvbUNvbXBvbmVudHMuZWRnZXMuZ2V0VW5pcXVlUGFnZVR5cGVzKCk7XG4gICAgICAgIHRoaXMucGFnZXNWZXJ0aWNhbERhdGEgPSBwYWdlVHlwZXMubWFwKHBhZ2VUeXBlID0+IHtcbiAgICAgICAgICAgIGNvbnN0IGhlYWRlckhlaWdodCA9IHRoaXMuY3VzdG9tQ29tcG9uZW50cy5lZGdlcy5nZXRDb21wb25lbnRIZWlnaHRCeVBhZ2VUeXBlKHBhZ2VUeXBlLCBFZGdlVHlwZS5IZWFkZXIpO1xuICAgICAgICAgICAgY29uc3QgZm9vdGVySGVpZ2h0ID0gdGhpcy5jdXN0b21Db21wb25lbnRzLmVkZ2VzLmdldENvbXBvbmVudEhlaWdodEJ5UGFnZVR5cGUocGFnZVR5cGUsIEVkZ2VUeXBlLkZvb3Rlcik7XG4gICAgICAgICAgICBjb25zdCBtYXJnaW5Ub3AgPSBNYXRoLm1heChoZWFkZXJIZWlnaHQsIHRoaXMuZG9jdW1lbnRNYXJnaW4udG9wKTtcbiAgICAgICAgICAgIGNvbnN0IG1hcmdpbkJvdHRvbSA9IE1hdGgubWF4KGZvb3RlckhlaWdodCwgdGhpcy5kb2N1bWVudE1hcmdpbi5ib3R0b20pO1xuXG4gICAgICAgICAgICByZXR1cm4gbmV3IFBhZ2VWZXJ0aWNhbERhdGFNb2RlbCh7XG4gICAgICAgICAgICAgICAgbWFyZ2luVG9wLFxuICAgICAgICAgICAgICAgIG1hcmdpbkJvdHRvbSxcbiAgICAgICAgICAgICAgICBjb250ZW50SGVpZ2h0OiB0aGlzLnBhZ2VIZWlnaHQgLSBtYXJnaW5Ub3AgLSBtYXJnaW5Cb3R0b20sXG4gICAgICAgICAgICAgICAgcGFnZVR5cGVcbiAgICAgICAgICAgIH0pO1xuICAgICAgICB9KTtcbiAgICB9XG5cbiAgICBwcml2YXRlIHNldFBhcmFncmFwaEluZGV4ZXMod3JhcFBhcmFncmFwaEluZGV4OiBudW1iZXJbXSk6IHZvaWQge1xuICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHRoaXMucGFyYWdyYXBocy5sZW5ndGg7IGkrKykge1xuICAgICAgICAgICAgdGhpcy5wYXJhZ3JhcGhzW2ldLnN0YXJ0SW5zZXJ0SW5kZXggPSB3cmFwUGFyYWdyYXBoSW5kZXhbaV07XG4gICAgICAgIH1cbiAgICB9XG59XG4iXX0=