@syncfusion/ej2-treemap 19.2.55 → 19.4.38
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintrc.json +1 -1
- package/.github/PULL_REQUEST_TEMPLATE/Bug.md +72 -0
- package/.github/PULL_REQUEST_TEMPLATE/Feature.md +49 -0
- package/CHANGELOG.md +0 -14
- package/dist/ej2-treemap.umd.min.js +2 -2
- package/dist/ej2-treemap.umd.min.js.map +1 -1
- package/dist/es6/ej2-treemap.es2015.js +108 -191
- package/dist/es6/ej2-treemap.es2015.js.map +1 -1
- package/dist/es6/ej2-treemap.es5.js +108 -191
- package/dist/es6/ej2-treemap.es5.js.map +1 -1
- package/dist/global/ej2-treemap.min.js +2 -2
- package/dist/global/ej2-treemap.min.js.map +1 -1
- package/dist/global/index.d.ts +1 -1
- package/dist/ts/treemap/layout/legend.ts +991 -0
- package/dist/ts/treemap/layout/render-panel.ts +717 -0
- package/dist/ts/treemap/model/base.ts +800 -0
- package/dist/ts/treemap/model/constants.ts +118 -0
- package/dist/ts/treemap/model/image-export.ts +109 -0
- package/dist/ts/treemap/model/interface.ts +554 -0
- package/dist/ts/treemap/model/pdf-export.ts +103 -0
- package/dist/ts/treemap/model/print.ts +93 -0
- package/dist/ts/treemap/model/theme.ts +202 -0
- package/dist/ts/treemap/treemap.ts +1571 -0
- package/dist/ts/treemap/user-interaction/highlight-selection.ts +530 -0
- package/dist/ts/treemap/user-interaction/tooltip.ts +199 -0
- package/dist/ts/treemap/utils/enum.ts +218 -0
- package/dist/ts/treemap/utils/helper.ts +1181 -0
- package/package.json +11 -11
- package/src/treemap/layout/legend.js +1 -18
- package/src/treemap/layout/render-panel.js +1 -16
- package/src/treemap/model/base-model.d.ts +0 -2
- package/src/treemap/model/base.d.ts +0 -2
- package/src/treemap/model/pdf-export.js +1 -1
- package/src/treemap/model/theme.js +68 -0
- package/src/treemap/treemap-model.d.ts +1 -19
- package/src/treemap/treemap.d.ts +0 -20
- package/src/treemap/treemap.js +17 -98
- package/src/treemap/user-interaction/highlight-selection.js +5 -39
- package/src/treemap/user-interaction/tooltip.js +4 -21
- package/src/treemap/utils/enum.d.ts +5 -1
- package/src/treemap/utils/helper.d.ts +1 -0
- package/src/treemap/utils/helper.js +13 -0
|
@@ -0,0 +1,1181 @@
|
|
|
1
|
+
/* eslint-disable @typescript-eslint/explicit-member-accessibility */
|
|
2
|
+
/* eslint-disable @typescript-eslint/dot-notation */
|
|
3
|
+
/* eslint-disable max-len */
|
|
4
|
+
import { BorderModel, FontModel, ColorMappingModel, LeafItemSettingsModel } from '../model/base-model';
|
|
5
|
+
import { createElement, compile, merge, isNullOrUndefined, remove } from '@syncfusion/ej2-base';
|
|
6
|
+
import { SvgRenderer } from '@syncfusion/ej2-svg-base';
|
|
7
|
+
import { Alignment, LabelPosition } from '../utils/enum';
|
|
8
|
+
import { TreeMap } from '../treemap';
|
|
9
|
+
import { IShapes } from '../model/interface';
|
|
10
|
+
import { ExportType } from '../utils/enum';
|
|
11
|
+
/**
|
|
12
|
+
* Create the class for size
|
|
13
|
+
*/
|
|
14
|
+
export class Size {
|
|
15
|
+
/**
|
|
16
|
+
* height of the size
|
|
17
|
+
*/
|
|
18
|
+
public height: number;
|
|
19
|
+
/**
|
|
20
|
+
* width of the size
|
|
21
|
+
*/
|
|
22
|
+
public width: number;
|
|
23
|
+
constructor(width: number, height: number) {
|
|
24
|
+
this.width = width;
|
|
25
|
+
this.height = height;
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export function stringToNumber(value: string, containerSize: number): number {
|
|
30
|
+
if (value !== null && value !== undefined) {
|
|
31
|
+
return value.indexOf('%') !== -1 ? (containerSize / 100) * parseInt(value, 10) : parseInt(value, 10);
|
|
32
|
+
}
|
|
33
|
+
return null;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* Internal use of type rect
|
|
38
|
+
*
|
|
39
|
+
* @private
|
|
40
|
+
*/
|
|
41
|
+
export class Rect {
|
|
42
|
+
public x: number;
|
|
43
|
+
public y: number;
|
|
44
|
+
public height: number;
|
|
45
|
+
public width: number;
|
|
46
|
+
constructor(x: number, y: number, width: number, height: number) {
|
|
47
|
+
this.x = x;
|
|
48
|
+
this.y = y;
|
|
49
|
+
this.width = width;
|
|
50
|
+
this.height = height;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* Internal use of rectangle options
|
|
56
|
+
*
|
|
57
|
+
* @private
|
|
58
|
+
*/
|
|
59
|
+
export class RectOption {
|
|
60
|
+
public id: string;
|
|
61
|
+
public fill: string;
|
|
62
|
+
public x: number;
|
|
63
|
+
public y: number;
|
|
64
|
+
public height: number;
|
|
65
|
+
public width: number;
|
|
66
|
+
public opacity: number;
|
|
67
|
+
public stroke: string;
|
|
68
|
+
public ['stroke-width']: number;
|
|
69
|
+
public ['stroke-dasharray']: string;
|
|
70
|
+
constructor(
|
|
71
|
+
id: string, fill: string, border: BorderModel, opacity: number, rect: Rect, dashArray?: string
|
|
72
|
+
) {
|
|
73
|
+
this.y = rect.y;
|
|
74
|
+
this.x = rect.x;
|
|
75
|
+
this.height = rect.height;
|
|
76
|
+
this.width = rect.width;
|
|
77
|
+
this.id = id;
|
|
78
|
+
this.fill = fill;
|
|
79
|
+
this.opacity = opacity;
|
|
80
|
+
this.stroke = border.color;
|
|
81
|
+
this['stroke-width'] = border.width;
|
|
82
|
+
this['stroke-dasharray'] = dashArray;
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
export class PathOption {
|
|
87
|
+
public id: string;
|
|
88
|
+
public opacity: number;
|
|
89
|
+
public fill: string;
|
|
90
|
+
public stroke: string;
|
|
91
|
+
public ['stroke-width']: number;
|
|
92
|
+
public ['stroke-dasharray']: string;
|
|
93
|
+
public d: string;
|
|
94
|
+
constructor(
|
|
95
|
+
id: string, fill: string, width: number, color: string, opacity?: number,
|
|
96
|
+
dashArray?: string, d?: string
|
|
97
|
+
) {
|
|
98
|
+
this.id = id;
|
|
99
|
+
this.opacity = opacity;
|
|
100
|
+
this.fill = fill;
|
|
101
|
+
this.stroke = color;
|
|
102
|
+
this['stroke-width'] = width;
|
|
103
|
+
this['stroke-dasharray'] = dashArray;
|
|
104
|
+
this.d = d;
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
/**
|
|
109
|
+
* Function to measure the height and width of the text.
|
|
110
|
+
*
|
|
111
|
+
* @param {string} text - Specifies the text.
|
|
112
|
+
* @param {FontModel} font - Specifies the font.
|
|
113
|
+
* @param {string} id - Specifies the id.
|
|
114
|
+
* @returns {Size} - Returns the size.
|
|
115
|
+
* @private
|
|
116
|
+
*/
|
|
117
|
+
export function measureText(text: string, font: FontModel): Size {
|
|
118
|
+
let measureObject: HTMLElement = document.getElementById('treeMapMeasureText');
|
|
119
|
+
if (measureObject === null) {
|
|
120
|
+
measureObject = createElement('text', { id: 'treeMapMeasureText' });
|
|
121
|
+
document.body.appendChild(measureObject);
|
|
122
|
+
}
|
|
123
|
+
measureObject.innerHTML = text;
|
|
124
|
+
measureObject.style.position = 'absolute';
|
|
125
|
+
measureObject.style.fontSize = font.size;
|
|
126
|
+
measureObject.style.fontWeight = font.fontWeight;
|
|
127
|
+
measureObject.style.fontStyle = font.fontStyle;
|
|
128
|
+
measureObject.style.fontFamily = font.fontFamily;
|
|
129
|
+
measureObject.style.visibility = 'hidden';
|
|
130
|
+
measureObject.style.top = '-100';
|
|
131
|
+
measureObject.style.left = '0';
|
|
132
|
+
measureObject.style.whiteSpace = 'nowrap';
|
|
133
|
+
// For bootstrap line height issue
|
|
134
|
+
measureObject.style.lineHeight = 'normal';
|
|
135
|
+
return new Size(measureObject.clientWidth, measureObject.clientHeight);
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
/**
|
|
139
|
+
* Internal use of text options
|
|
140
|
+
*
|
|
141
|
+
* @private
|
|
142
|
+
*/
|
|
143
|
+
export class TextOption {
|
|
144
|
+
public anchor: string;
|
|
145
|
+
public id: string;
|
|
146
|
+
public transform: string = '';
|
|
147
|
+
public x: number;
|
|
148
|
+
public y: number;
|
|
149
|
+
public text: string | string[];
|
|
150
|
+
public baseLine: string = 'auto';
|
|
151
|
+
public connectorText: string;
|
|
152
|
+
constructor(
|
|
153
|
+
id?: string, x?: number, y?: number, anchor?: string, text?: string | string[], transform: string = '',
|
|
154
|
+
baseLine?: string, connectorText?: string
|
|
155
|
+
) {
|
|
156
|
+
this.id = id;
|
|
157
|
+
this.text = text;
|
|
158
|
+
this.transform = transform;
|
|
159
|
+
this.anchor = anchor;
|
|
160
|
+
this.x = x;
|
|
161
|
+
this.y = y;
|
|
162
|
+
this.baseLine = baseLine;
|
|
163
|
+
this.connectorText = connectorText;
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
|
|
168
|
+
/**
|
|
169
|
+
* Trim the title text
|
|
170
|
+
*
|
|
171
|
+
* @param {number} maxWidth - Specifies the maximum width
|
|
172
|
+
* @param {string} text - Specifies the text
|
|
173
|
+
* @param {FontModel} font - Specifies the font
|
|
174
|
+
* @returns {string} - Returns the string
|
|
175
|
+
* @private
|
|
176
|
+
*/
|
|
177
|
+
export function textTrim(maxWidth: number, text: string, font: FontModel): string {
|
|
178
|
+
let label: string = text;
|
|
179
|
+
let size: number = measureText(text, font).width;
|
|
180
|
+
if (size > maxWidth) {
|
|
181
|
+
const textLength: number = text.length;
|
|
182
|
+
for (let i: number = textLength - 1; i >= 0; --i) {
|
|
183
|
+
label = text.substring(0, i) + '...';
|
|
184
|
+
size = measureText(label, font).width;
|
|
185
|
+
if (size <= maxWidth || label.length < 4) {
|
|
186
|
+
if (label.length < 4) {
|
|
187
|
+
label = ' ';
|
|
188
|
+
}
|
|
189
|
+
return label;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
return label;
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
/**
|
|
197
|
+
* Map internal class for Point
|
|
198
|
+
*/
|
|
199
|
+
|
|
200
|
+
export class Location {
|
|
201
|
+
/**
|
|
202
|
+
* To calculate x value for location
|
|
203
|
+
*/
|
|
204
|
+
public x: number;
|
|
205
|
+
/**
|
|
206
|
+
* To calculate y value for location
|
|
207
|
+
*/
|
|
208
|
+
public y: number;
|
|
209
|
+
constructor(x: number, y: number) {
|
|
210
|
+
this.x = x;
|
|
211
|
+
this.y = y;
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
/**
|
|
216
|
+
* Method to calculate x position of title
|
|
217
|
+
*/
|
|
218
|
+
|
|
219
|
+
export function findPosition(location: Rect, alignment: Alignment, textSize: Size, type: string): Location {
|
|
220
|
+
let x: number;
|
|
221
|
+
switch (alignment) {
|
|
222
|
+
case 'Near':
|
|
223
|
+
x = location.x;
|
|
224
|
+
break;
|
|
225
|
+
case 'Center':
|
|
226
|
+
x = (type === 'title') ? (location.width / 2 - textSize.width / 2) :
|
|
227
|
+
((location.x + (location.width / 2)) - textSize.width / 2);
|
|
228
|
+
break;
|
|
229
|
+
case 'Far':
|
|
230
|
+
x = (type === 'title') ? (location.width - location.y - textSize.width) :
|
|
231
|
+
((location.x + location.width) - textSize.width);
|
|
232
|
+
break;
|
|
233
|
+
}
|
|
234
|
+
const y: number = (type === 'title') ? location.y + (textSize.height / 2) : ((location.y + location.height / 2) + textSize.height / 2);
|
|
235
|
+
return new Location(x, y);
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
export function createTextStyle(
|
|
239
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
240
|
+
renderer: SvgRenderer, renderOptions: any, text: string
|
|
241
|
+
): HTMLElement {
|
|
242
|
+
const htmlObject: HTMLElement = <HTMLElement>renderer.createText(renderOptions, text);
|
|
243
|
+
htmlObject.setAttributeNS('http://www.w3.org/XML/1998/namespace', 'xml:space', 'preserve');
|
|
244
|
+
htmlObject.style['user-select'] = 'none';
|
|
245
|
+
htmlObject.style['-moz-user-select'] = 'none';
|
|
246
|
+
htmlObject.style['-webkit-touch-callout'] = 'none';
|
|
247
|
+
htmlObject.style['-webkit-user-select'] = 'none';
|
|
248
|
+
htmlObject.style['-khtml-user-select'] = 'none';
|
|
249
|
+
htmlObject.style['-ms-user-select'] = 'none';
|
|
250
|
+
htmlObject.style['-o-user-select'] = 'none';
|
|
251
|
+
return htmlObject;
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
/**
|
|
255
|
+
* Internal rendering of text
|
|
256
|
+
*
|
|
257
|
+
* @param {TextOption} options - Specifies the text option
|
|
258
|
+
* @param {FontModel} font - Specifies the font model
|
|
259
|
+
* @param {string} color - Specifies the color
|
|
260
|
+
* @param {HTMLElement | Element} parent - Specifes the html element
|
|
261
|
+
* @param {boolean} isMinus - Specifies the boolean value
|
|
262
|
+
* @returns {Element} - Returns the element
|
|
263
|
+
* @private
|
|
264
|
+
*/
|
|
265
|
+
export function renderTextElement(
|
|
266
|
+
options: TextOption, font: FontModel, color: string, parent: HTMLElement | Element, isMinus: boolean = false
|
|
267
|
+
): Element {
|
|
268
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
269
|
+
const renderOptions: any = {
|
|
270
|
+
'font-size': font.size,
|
|
271
|
+
'font-style': font.fontStyle,
|
|
272
|
+
'font-family': font.fontFamily,
|
|
273
|
+
'font-weight': font.fontWeight,
|
|
274
|
+
'text-anchor': options.anchor,
|
|
275
|
+
'transform': options.transform,
|
|
276
|
+
'opacity': font.opacity,
|
|
277
|
+
'dominant-baseline': options.baseLine,
|
|
278
|
+
'id': options.id,
|
|
279
|
+
'x': options.x,
|
|
280
|
+
'y': options.y,
|
|
281
|
+
'fill': color
|
|
282
|
+
};
|
|
283
|
+
const text: string = typeof options.text === 'string' ? options.text : isMinus ? options.text[options.text.length - 1] : options.text[0];
|
|
284
|
+
let tspanElement: Element;
|
|
285
|
+
const renderer: SvgRenderer = new SvgRenderer('');
|
|
286
|
+
let height: number; let htmlObject: HTMLElement;
|
|
287
|
+
const breadCrumbText: boolean = !isNullOrUndefined(text) && !isNullOrUndefined(options.connectorText) ?
|
|
288
|
+
(text.search(options.connectorText[1]) >= 0) : false;
|
|
289
|
+
if (breadCrumbText) {
|
|
290
|
+
const drilledLabel: string = text;
|
|
291
|
+
const spacing: number = 5;
|
|
292
|
+
const drillLevelText: string[] = drilledLabel.split('#');
|
|
293
|
+
for (let z: number = 0; z < drillLevelText.length; z++) {
|
|
294
|
+
let drillText: string = (drillLevelText[z].search(options.connectorText) !== -1 && !isNullOrUndefined(options.connectorText)) ?
|
|
295
|
+
options.connectorText : drillLevelText[z];
|
|
296
|
+
renderOptions['id'] = options.id + '_' + z;
|
|
297
|
+
htmlObject = createTextStyle(renderer, renderOptions, drillText);
|
|
298
|
+
if (z % 2 === 0 && z !== 0) {
|
|
299
|
+
const re: RegExp = /\s+/g;
|
|
300
|
+
drillText = drillText.replace(re, ' ');
|
|
301
|
+
}
|
|
302
|
+
const size: Size = measureText(drillText, font);
|
|
303
|
+
renderOptions['x'] = z !== 0 ? renderOptions['x'] + size.width : renderOptions['x'] + size.width + spacing;
|
|
304
|
+
parent.appendChild(htmlObject);
|
|
305
|
+
}
|
|
306
|
+
} else {
|
|
307
|
+
htmlObject = createTextStyle(renderer, renderOptions, text);
|
|
308
|
+
parent.appendChild(htmlObject);
|
|
309
|
+
}
|
|
310
|
+
if (typeof options.text !== 'string' && options.text.length > 1) {
|
|
311
|
+
for (let i: number = 1, len: number = options.text.length; i < len; i++) {
|
|
312
|
+
height = (measureText(options.text[i], font).height);
|
|
313
|
+
tspanElement = renderer.createTSpan(
|
|
314
|
+
{
|
|
315
|
+
'x': options.x, 'id': options.id,
|
|
316
|
+
'y': (options.y) + (i * height)
|
|
317
|
+
},
|
|
318
|
+
options.text[i]);
|
|
319
|
+
htmlObject.appendChild(tspanElement);
|
|
320
|
+
}
|
|
321
|
+
parent.appendChild(htmlObject);
|
|
322
|
+
}
|
|
323
|
+
return htmlObject;
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
export function setItemTemplateContent(targetId: string, targetElement: Element, contentItemTemplate: string): void {
|
|
327
|
+
const itemSelect: string = targetId.split('_RectPath')[0];
|
|
328
|
+
let itemTemplate: Element;
|
|
329
|
+
if (targetId.indexOf('_LabelTemplate') > -1) {
|
|
330
|
+
itemTemplate = targetElement;
|
|
331
|
+
} else {
|
|
332
|
+
itemTemplate = document.querySelector('#' + itemSelect + '_LabelTemplate');
|
|
333
|
+
}
|
|
334
|
+
if (!isNullOrUndefined(itemTemplate)) {
|
|
335
|
+
itemTemplate.innerHTML = contentItemTemplate;
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
|
|
339
|
+
export function getElement(id: string): Element {
|
|
340
|
+
return document.getElementById(id);
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
344
|
+
export function itemsToOrder(a: any, b: any): number {
|
|
345
|
+
return a['weight'] === b['weight'] ? 0 : a['weight'] < b['weight'] ? 1 : -1;
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
349
|
+
export function isContainsData(source: string[], pathName: string, processData: any, treemap: TreeMap): boolean {
|
|
350
|
+
let isExist: boolean = false; let name: string = ''; let path: string;
|
|
351
|
+
const leaf: LeafItemSettingsModel = treemap.leafItemSettings; for (let i: number = 0; i < source.length; i++) {
|
|
352
|
+
path = treemap.levels[i] ? treemap.levels[i].groupPath : leaf.labelPath ? leaf.labelPath : treemap.weightValuePath;
|
|
353
|
+
const data: string = processData[path] || 'undefined';
|
|
354
|
+
if (source[i] === data) {
|
|
355
|
+
name += data + (i === source.length - 1 ? '' : '#');
|
|
356
|
+
if (name === pathName) {
|
|
357
|
+
isExist = true;
|
|
358
|
+
break;
|
|
359
|
+
}
|
|
360
|
+
}
|
|
361
|
+
}
|
|
362
|
+
return isExist;
|
|
363
|
+
}
|
|
364
|
+
|
|
365
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
366
|
+
export function findChildren(data: any): any {
|
|
367
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
368
|
+
let children: any;
|
|
369
|
+
if (data) {
|
|
370
|
+
const keys: string[] = Object.keys(data);
|
|
371
|
+
children = {};
|
|
372
|
+
for (let i: number = 0; i < keys.length; i++) {
|
|
373
|
+
if (data[keys[i]] instanceof Array) {
|
|
374
|
+
children['values'] = data[keys[i]];
|
|
375
|
+
children['key'] = keys[i];
|
|
376
|
+
break;
|
|
377
|
+
}
|
|
378
|
+
}
|
|
379
|
+
}
|
|
380
|
+
return children;
|
|
381
|
+
}
|
|
382
|
+
|
|
383
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
384
|
+
export function findHightLightItems(data: any, items: string[], mode: string, treeMap: TreeMap): string[] {
|
|
385
|
+
if (mode === 'Child') {
|
|
386
|
+
items.push(data['levelOrderName']);
|
|
387
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
388
|
+
const children: any[] = findChildren(data)['values'];
|
|
389
|
+
if (children && children.length > 0) {
|
|
390
|
+
for (let i: number = 0; i < children.length; i++) {
|
|
391
|
+
if (items.indexOf(children[i]['levelOrderName']) === -1) {
|
|
392
|
+
items.push(children[i]['levelOrderName']);
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
for (let j: number = 0; j < children.length; j++) {
|
|
396
|
+
findHightLightItems(children[j], items, mode, treeMap);
|
|
397
|
+
}
|
|
398
|
+
}
|
|
399
|
+
} else if (mode === 'Parent') {
|
|
400
|
+
if (typeof data['levelOrderName'] === 'string' && items.indexOf(data['levelOrderName']) === -1) {
|
|
401
|
+
items.push(data['levelOrderName']);
|
|
402
|
+
findHightLightItems(data['parent'], items, mode, treeMap);
|
|
403
|
+
}
|
|
404
|
+
} else if (mode === 'All') {
|
|
405
|
+
const parentName: string = (data['levelOrderName'] as string).split('#')[0];
|
|
406
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
407
|
+
let currentItem: any;
|
|
408
|
+
for (let i: number = 0; i < treeMap.layout.renderItems.length; i++) {
|
|
409
|
+
currentItem = treeMap.layout.renderItems[i];
|
|
410
|
+
if ((currentItem['levelOrderName']).indexOf(parentName) > -1 && items.indexOf(currentItem['levelOrderName']) === -1) {
|
|
411
|
+
items.push(currentItem['levelOrderName']);
|
|
412
|
+
}
|
|
413
|
+
}
|
|
414
|
+
} else {
|
|
415
|
+
items.push(data['levelOrderName']);
|
|
416
|
+
}
|
|
417
|
+
return items;
|
|
418
|
+
}
|
|
419
|
+
|
|
420
|
+
/**
|
|
421
|
+
* Function to compile the template function for maps.
|
|
422
|
+
*
|
|
423
|
+
* @param {string} template - Specifies the template
|
|
424
|
+
* @returns {Function} - Returns the template function
|
|
425
|
+
* @private
|
|
426
|
+
*/
|
|
427
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
428
|
+
export function getTemplateFunction(template: string): any {
|
|
429
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
430
|
+
let templateFn: any = null;
|
|
431
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
432
|
+
let e: any;
|
|
433
|
+
try {
|
|
434
|
+
if (document.querySelectorAll(template).length) {
|
|
435
|
+
templateFn = compile(document.querySelector(template).innerHTML.trim());
|
|
436
|
+
}
|
|
437
|
+
} catch (e) {
|
|
438
|
+
templateFn = compile(template);
|
|
439
|
+
}
|
|
440
|
+
return templateFn;
|
|
441
|
+
}
|
|
442
|
+
|
|
443
|
+
/**
|
|
444
|
+
* @private
|
|
445
|
+
* @param {HTMLCollection} element - Specifies the element
|
|
446
|
+
* @param {string} labelId - Specifies the label id
|
|
447
|
+
* @param {Object} data - Specifies the data
|
|
448
|
+
* @returns {HTMLElement} - Returns the element
|
|
449
|
+
*/
|
|
450
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
451
|
+
export function convertElement(element: HTMLCollection, labelId: string, data: any): HTMLElement {
|
|
452
|
+
const childElement: HTMLElement = createElement('div', {
|
|
453
|
+
id: labelId,
|
|
454
|
+
styles: 'position: absolute;pointer-events: auto;'
|
|
455
|
+
});
|
|
456
|
+
let elementLength: number = element.length;
|
|
457
|
+
while (elementLength > 0) {
|
|
458
|
+
childElement.appendChild(element[0]);
|
|
459
|
+
elementLength--;
|
|
460
|
+
}
|
|
461
|
+
let templateHtml: string = childElement.innerHTML;
|
|
462
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
463
|
+
const keys: any[] = Object.keys(data);
|
|
464
|
+
for (let i: number = 0; i < keys.length; i++) {
|
|
465
|
+
templateHtml = templateHtml.replace(new RegExp('{{:' + <string>keys[i] + '}}', 'g'), data[keys[i].toString()]);
|
|
466
|
+
}
|
|
467
|
+
childElement.innerHTML = templateHtml;
|
|
468
|
+
return childElement;
|
|
469
|
+
}
|
|
470
|
+
|
|
471
|
+
export function findLabelLocation(rect: Rect, position: LabelPosition, labelSize: Size, type: string, treemap: TreeMap): Location {
|
|
472
|
+
const location: Location = new Location(0, 0);
|
|
473
|
+
const padding: number = 5;
|
|
474
|
+
const paddings: number = 2;
|
|
475
|
+
const elementRect: ClientRect = treemap.element.getBoundingClientRect();
|
|
476
|
+
const x: number = (type === 'Template') ? treemap.areaRect.x : 0;
|
|
477
|
+
const y: number = (type === 'Template') ? treemap.areaRect.y : 0;
|
|
478
|
+
location.x = (Math.abs(x - ((position.indexOf('Left') > -1) ? rect.x + padding : !(position.indexOf('Right') > -1) ?
|
|
479
|
+
rect.x + ((rect.width / 2) - (labelSize.width / 2)) : (rect.x + rect.width) - labelSize.width))) - paddings;
|
|
480
|
+
if (treemap.enableDrillDown && (treemap.renderDirection === 'BottomLeftTopRight'
|
|
481
|
+
|| treemap.renderDirection === 'BottomRightTopLeft')) {
|
|
482
|
+
location.y = Math.abs((rect.y + rect.height) - labelSize.height + padding);
|
|
483
|
+
} else {
|
|
484
|
+
location.y = Math.abs(y - ((position.indexOf('Top') > -1) ? (type === 'Template' ? rect.y : rect.y + labelSize.height) :
|
|
485
|
+
!(position.indexOf('Bottom') > -1) ? type === 'Template' ? (rect.y + ((rect.height / 2) - (labelSize.height / 2))) :
|
|
486
|
+
(rect.y + (rect.height / 2) + labelSize.height / 4) : (rect.y + rect.height) - labelSize.height));
|
|
487
|
+
}
|
|
488
|
+
|
|
489
|
+
return location;
|
|
490
|
+
}
|
|
491
|
+
|
|
492
|
+
export function measureElement(element: HTMLElement, parentElement: HTMLElement): Size {
|
|
493
|
+
const size: Size = new Size(0, 0);
|
|
494
|
+
parentElement.appendChild(element);
|
|
495
|
+
size.height = element.offsetHeight;
|
|
496
|
+
size.width = element.offsetWidth;
|
|
497
|
+
const measureElementId: HTMLElement = document.getElementById(element.id);
|
|
498
|
+
measureElementId.parentNode.removeChild(measureElementId);
|
|
499
|
+
return size;
|
|
500
|
+
}
|
|
501
|
+
|
|
502
|
+
export function getArea(rect: Rect): number {
|
|
503
|
+
return (rect.width - rect.x) * (rect.height - rect.y);
|
|
504
|
+
}
|
|
505
|
+
|
|
506
|
+
export function getShortestEdge(input: Rect): number {
|
|
507
|
+
const container: Rect = convertToContainer(input);
|
|
508
|
+
const width: number = container.width;
|
|
509
|
+
const height: number = container.height;
|
|
510
|
+
const result: number = Math.min(width, height);
|
|
511
|
+
return result;
|
|
512
|
+
}
|
|
513
|
+
|
|
514
|
+
export function convertToContainer(rect: Rect): Rect {
|
|
515
|
+
const x: number = rect.x;
|
|
516
|
+
const y: number = rect.y;
|
|
517
|
+
const width: number = rect.width;
|
|
518
|
+
const height: number = rect.height;
|
|
519
|
+
return {
|
|
520
|
+
x: x,
|
|
521
|
+
y: y,
|
|
522
|
+
width: width - x,
|
|
523
|
+
height: height - y
|
|
524
|
+
};
|
|
525
|
+
}
|
|
526
|
+
|
|
527
|
+
export function convertToRect(container: Rect): Rect {
|
|
528
|
+
const xOffset: number = container.x;
|
|
529
|
+
const yOffset: number = container.y;
|
|
530
|
+
const width: number = container.width;
|
|
531
|
+
const height: number = container.height;
|
|
532
|
+
return {
|
|
533
|
+
x: xOffset,
|
|
534
|
+
y: yOffset,
|
|
535
|
+
width: xOffset + width,
|
|
536
|
+
height: yOffset + height
|
|
537
|
+
};
|
|
538
|
+
}
|
|
539
|
+
|
|
540
|
+
export function getMousePosition(pageX: number, pageY: number, element: Element): Location {
|
|
541
|
+
const elementRect: ClientRect = element.getBoundingClientRect();
|
|
542
|
+
const pageXOffset: number = element.ownerDocument.defaultView.pageXOffset;
|
|
543
|
+
const pageYOffset: number = element.ownerDocument.defaultView.pageYOffset;
|
|
544
|
+
const clientTop: number = element.ownerDocument.documentElement.clientTop;
|
|
545
|
+
const clientLeft: number = element.ownerDocument.documentElement.clientLeft;
|
|
546
|
+
const positionX: number = elementRect.left + pageXOffset - clientLeft;
|
|
547
|
+
const positionY: number = elementRect.top + pageYOffset - clientTop;
|
|
548
|
+
return new Location((pageX - positionX), (pageY - positionY));
|
|
549
|
+
}
|
|
550
|
+
export function colorMap(
|
|
551
|
+
colorMapping: ColorMappingModel[], equalValue: string,
|
|
552
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
553
|
+
value: number | string, weightValuePath: number): any {
|
|
554
|
+
let fill: string; const paths: string[] = []; let opacity: string;
|
|
555
|
+
if (isNullOrUndefined(equalValue) && (isNullOrUndefined(value) && isNaN(<number>value))) {
|
|
556
|
+
return null;
|
|
557
|
+
}
|
|
558
|
+
for (let i: number = 0; i < colorMapping.length; i++) {
|
|
559
|
+
let isEqualColor: boolean = false; const dataValue: number = <number>value;
|
|
560
|
+
if (!isNullOrUndefined(colorMapping[i].from) && !isNullOrUndefined(colorMapping[i].to)
|
|
561
|
+
&& !isNullOrUndefined(colorMapping[i].value)) {
|
|
562
|
+
if ((value >= colorMapping[i].from && colorMapping[i].to >= value) && (colorMapping[i].value === equalValue)) {
|
|
563
|
+
isEqualColor = true;
|
|
564
|
+
if (Object.prototype.toString.call(colorMapping[i].color) === '[object Array]') {
|
|
565
|
+
fill = !isEqualColor ? colorCollections(colorMapping[i], dataValue) : colorMapping[i].color[0];
|
|
566
|
+
} else {
|
|
567
|
+
fill = <string>colorMapping[i].color;
|
|
568
|
+
}
|
|
569
|
+
}
|
|
570
|
+
} else if ((!isNullOrUndefined(colorMapping[i].from) && !isNullOrUndefined(colorMapping[i].to))
|
|
571
|
+
|| !isNullOrUndefined((colorMapping[i].value))) {
|
|
572
|
+
if ((value >= colorMapping[i].from && colorMapping[i].to >= value) || (colorMapping[i].value === equalValue)) {
|
|
573
|
+
if (colorMapping[i].value === equalValue) {
|
|
574
|
+
isEqualColor = true;
|
|
575
|
+
}
|
|
576
|
+
if (Object.prototype.toString.call(colorMapping[i].color) === '[object Array]') {
|
|
577
|
+
fill = !isEqualColor ? colorCollections(colorMapping[i], dataValue) : colorMapping[i].color[0];
|
|
578
|
+
} else {
|
|
579
|
+
fill = <string>colorMapping[i].color;
|
|
580
|
+
}
|
|
581
|
+
}
|
|
582
|
+
}
|
|
583
|
+
if (((value >= colorMapping[i].from && value <= colorMapping[i].to) || (colorMapping[i].value === equalValue))
|
|
584
|
+
&& !isNullOrUndefined(colorMapping[i].minOpacity) && !isNullOrUndefined(colorMapping[i].maxOpacity) && fill) {
|
|
585
|
+
opacity = deSaturationColor(weightValuePath, colorMapping[i], fill, value as number);
|
|
586
|
+
}
|
|
587
|
+
if ((fill === '' || isNullOrUndefined(fill))
|
|
588
|
+
&& isNullOrUndefined(colorMapping[i].from) && isNullOrUndefined(colorMapping[i].to)
|
|
589
|
+
&& isNullOrUndefined(colorMapping[i].minOpacity) && isNullOrUndefined(colorMapping[i].maxOpacity)
|
|
590
|
+
&& isNullOrUndefined(colorMapping[i].value)) {
|
|
591
|
+
fill = (Object.prototype.toString.call(colorMapping[i].color) === '[object Array]') ?
|
|
592
|
+
<string>colorMapping[i].color[0] : <string>colorMapping[i].color;
|
|
593
|
+
}
|
|
594
|
+
opacity = !isNullOrUndefined(opacity) ? opacity : '1';
|
|
595
|
+
paths.push(fill);
|
|
596
|
+
}
|
|
597
|
+
for (let j: number = paths.length - 1; j >= 0; j--) {
|
|
598
|
+
fill = paths[j];
|
|
599
|
+
j = (fill) ? -1 : j;
|
|
600
|
+
}
|
|
601
|
+
return { fill: fill, opacity: opacity };
|
|
602
|
+
}
|
|
603
|
+
|
|
604
|
+
|
|
605
|
+
export function deSaturationColor(
|
|
606
|
+
weightValuePath: number, colorMapping: ColorMappingModel, color: string, rangeValue: number): string {
|
|
607
|
+
let opacity: number = 1;
|
|
608
|
+
if ((rangeValue >= colorMapping.from && rangeValue <= colorMapping.to)) {
|
|
609
|
+
const ratio: number = (rangeValue - colorMapping.from) / (colorMapping.to - colorMapping.from);
|
|
610
|
+
opacity = (ratio * (colorMapping.maxOpacity - colorMapping.minOpacity)) + colorMapping.minOpacity;
|
|
611
|
+
}
|
|
612
|
+
return opacity.toString();
|
|
613
|
+
}
|
|
614
|
+
|
|
615
|
+
export function colorCollections(colorMap: ColorMappingModel, value: number): string {
|
|
616
|
+
const gradientFill: string = getColorByValue(colorMap, value);
|
|
617
|
+
return gradientFill;
|
|
618
|
+
}
|
|
619
|
+
|
|
620
|
+
export function rgbToHex(r: number, g: number, b: number): string {
|
|
621
|
+
return '#' + componentToHex(r) + componentToHex(g) + componentToHex(b);
|
|
622
|
+
}
|
|
623
|
+
|
|
624
|
+
export function getColorByValue(colorMap: ColorMappingModel, value: number): string {
|
|
625
|
+
let color: string = '';
|
|
626
|
+
let rbg: ColorValue;
|
|
627
|
+
if (Number(value) === colorMap.from) {
|
|
628
|
+
color = colorMap.color[0];
|
|
629
|
+
} else if (Number(value) === colorMap.to) {
|
|
630
|
+
color = colorMap.color[colorMap.color.length - 1];
|
|
631
|
+
} else {
|
|
632
|
+
rbg = getGradientColor(Number(value), colorMap);
|
|
633
|
+
color = rgbToHex(rbg.r, rbg.g, rbg.b);
|
|
634
|
+
}
|
|
635
|
+
return color;
|
|
636
|
+
}
|
|
637
|
+
|
|
638
|
+
export function getGradientColor(value: number, colorMap: ColorMappingModel): ColorValue {
|
|
639
|
+
const previousOffset: number = colorMap.from;
|
|
640
|
+
const nextOffset: number = colorMap.to;
|
|
641
|
+
let percent: number = 0; let prev1: string;
|
|
642
|
+
const full: number = nextOffset - previousOffset; let midColor: string; let midreturn: ColorValue;
|
|
643
|
+
percent = (value - previousOffset) / full; let previousColor: string; let nextColor: string;
|
|
644
|
+
if (colorMap.color.length <= 2) {
|
|
645
|
+
previousColor = colorMap.color[0].charAt(0) === '#' ? colorMap.color[0] : colorNameToHex(colorMap.color[0]);
|
|
646
|
+
nextColor = colorMap.color[colorMap.color.length - 1].charAt(0) === '#' ?
|
|
647
|
+
colorMap.color[colorMap.color.length - 1] : colorNameToHex(colorMap.color[colorMap.color.length - 1]);
|
|
648
|
+
} else {
|
|
649
|
+
previousColor = colorMap.color[0].charAt(0) === '#' ? colorMap.color[0] : colorNameToHex(colorMap.color[0]);
|
|
650
|
+
nextColor = colorMap.color[colorMap.color.length - 1].charAt(0) === '#' ?
|
|
651
|
+
colorMap.color[colorMap.color.length - 1] : colorNameToHex(colorMap.color[colorMap.color.length - 1]);
|
|
652
|
+
const a: number = full / (colorMap.color.length - 1); let b: number; let c: number;
|
|
653
|
+
|
|
654
|
+
const length: number = colorMap.color.length - 1;
|
|
655
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
656
|
+
const splitColorValueOffset: any[] = []; let splitColor: any = {};
|
|
657
|
+
for (let j: number = 1; j < length; j++) {
|
|
658
|
+
c = j * a;
|
|
659
|
+
b = previousOffset + c;
|
|
660
|
+
splitColor = { b: b, color: colorMap.color[j] };
|
|
661
|
+
splitColorValueOffset.push(splitColor);
|
|
662
|
+
}
|
|
663
|
+
for (let i: number = 0; i < splitColorValueOffset.length; i++) {
|
|
664
|
+
if (previousOffset <= value && value <= splitColorValueOffset[i]['b'] && i === 0) {
|
|
665
|
+
midColor = splitColorValueOffset[i]['color'].charAt(0) === '#' ?
|
|
666
|
+
splitColorValueOffset[i]['color'] : colorNameToHex(splitColorValueOffset[i]['color']);
|
|
667
|
+
nextColor = midColor;
|
|
668
|
+
percent = value < splitColorValueOffset[i]['b'] ? 1 - Math.abs((value - splitColorValueOffset[i]['b']) / a)
|
|
669
|
+
: (value - splitColorValueOffset[i]['b']) / a;
|
|
670
|
+
} else if (splitColorValueOffset[i]['b'] <= value && value <= nextOffset && i === (splitColorValueOffset.length - 1)) {
|
|
671
|
+
midColor = splitColorValueOffset[i]['color'].charAt(0) === '#' ?
|
|
672
|
+
splitColorValueOffset[i]['color'] : colorNameToHex(splitColorValueOffset[i]['color']);
|
|
673
|
+
previousColor = midColor;
|
|
674
|
+
percent = value < splitColorValueOffset[i]['b'] ?
|
|
675
|
+
1 - Math.abs((value - splitColorValueOffset[i]['b']) / a) : (value - splitColorValueOffset[i]['b']) / a;
|
|
676
|
+
}
|
|
677
|
+
if (i !== splitColorValueOffset.length - 1 && i < splitColorValueOffset.length) {
|
|
678
|
+
if (splitColorValueOffset[i]['b'] <= value && value <= splitColorValueOffset[i + 1]['b']) {
|
|
679
|
+
midColor = splitColorValueOffset[i]['color'].charAt(0) === '#' ?
|
|
680
|
+
splitColorValueOffset[i]['color'] : colorNameToHex(splitColorValueOffset[i]['color']);
|
|
681
|
+
previousColor = midColor;
|
|
682
|
+
nextColor = splitColorValueOffset[i + 1]['color'].charAt(0) === '#' ?
|
|
683
|
+
splitColorValueOffset[i + 1]['color'] : colorNameToHex(splitColorValueOffset[i + 1]['color']);
|
|
684
|
+
percent = Math.abs((value - splitColorValueOffset[i + 1]['b'])) / a;
|
|
685
|
+
}
|
|
686
|
+
}
|
|
687
|
+
}
|
|
688
|
+
}
|
|
689
|
+
return getPercentageColor(percent, previousColor, nextColor);
|
|
690
|
+
}
|
|
691
|
+
|
|
692
|
+
export function getPercentageColor(percent: number, previous: string, next: string): ColorValue {
|
|
693
|
+
const nextColor: string = next.split('#')[1];
|
|
694
|
+
const prevColor: string = previous.split('#')[1];
|
|
695
|
+
const r: number = getPercentage(percent, parseInt(prevColor.substr(0, 2), 16), parseInt(nextColor.substr(0, 2), 16));
|
|
696
|
+
const g: number = getPercentage(percent, parseInt(prevColor.substr(2, 2), 16), parseInt(nextColor.substr(2, 2), 16));
|
|
697
|
+
const b: number = getPercentage(percent, parseInt(prevColor.substr(4, 2), 16), parseInt(nextColor.substr(4, 2), 16));
|
|
698
|
+
return new ColorValue(r, g, b);
|
|
699
|
+
}
|
|
700
|
+
|
|
701
|
+
export function getPercentage(percent: number, previous: number, next: number): number {
|
|
702
|
+
const full: number = next - previous;
|
|
703
|
+
return Math.round((previous + (full * percent)));
|
|
704
|
+
}
|
|
705
|
+
|
|
706
|
+
export function wordWrap(maximumWidth: number, dataLabel: string, font: FontModel): string[] {
|
|
707
|
+
const textCollection: string[] = dataLabel.split(' ');
|
|
708
|
+
let label: string = '';
|
|
709
|
+
const labelCollection: string[] = [];
|
|
710
|
+
let text: string;
|
|
711
|
+
for (let i: number = 0, len: number = textCollection.length; i < len; i++) {
|
|
712
|
+
text = textCollection[i];
|
|
713
|
+
if (measureText(label.concat(text), font).width < maximumWidth) {
|
|
714
|
+
label = label.concat((label === '' ? '' : ' ') + text);
|
|
715
|
+
} else {
|
|
716
|
+
if (label !== '') {
|
|
717
|
+
labelCollection.push(textTrim(maximumWidth, label, font));
|
|
718
|
+
label = text;
|
|
719
|
+
} else {
|
|
720
|
+
labelCollection.push(textTrim(maximumWidth, text, font));
|
|
721
|
+
text = '';
|
|
722
|
+
}
|
|
723
|
+
}
|
|
724
|
+
if (label && i === len - 1) {
|
|
725
|
+
labelCollection.push(textTrim(maximumWidth, label, font));
|
|
726
|
+
}
|
|
727
|
+
}
|
|
728
|
+
return labelCollection;
|
|
729
|
+
}
|
|
730
|
+
export function textWrap(maxWidth: number, label: string, font: FontModel): string[] {
|
|
731
|
+
const text: string = label;
|
|
732
|
+
const resultText: string[] = [];
|
|
733
|
+
let currentLength: number = 0;
|
|
734
|
+
let totalWidth: number = measureText(label, font).width;
|
|
735
|
+
const totalLength: number = label.length;
|
|
736
|
+
if (maxWidth >= totalWidth) {
|
|
737
|
+
resultText.push(label);
|
|
738
|
+
return resultText;
|
|
739
|
+
} else {
|
|
740
|
+
for (let i: number = label.length; i > currentLength; i--) {
|
|
741
|
+
const sliceString: string = label.slice(currentLength, i);
|
|
742
|
+
totalWidth = measureText(sliceString, font).width;
|
|
743
|
+
if (totalWidth <= maxWidth) {
|
|
744
|
+
resultText.push(sliceString);
|
|
745
|
+
currentLength += sliceString.length;
|
|
746
|
+
if (totalLength === currentLength) {
|
|
747
|
+
return resultText;
|
|
748
|
+
}
|
|
749
|
+
i = totalLength + 1;
|
|
750
|
+
}
|
|
751
|
+
}
|
|
752
|
+
}
|
|
753
|
+
return resultText;
|
|
754
|
+
}
|
|
755
|
+
/**
|
|
756
|
+
* hide function
|
|
757
|
+
*
|
|
758
|
+
* @param {number} maxWidth - Specifies the maximum width
|
|
759
|
+
* @param {number} maxHeight - Specifies the maximum height
|
|
760
|
+
* @param {string} text - Specifies the text
|
|
761
|
+
* @param {FontModel} font - Specifies the font
|
|
762
|
+
* @returns {string} - Returns the hideText
|
|
763
|
+
*/
|
|
764
|
+
export function hide(maxWidth: number, maxHeight: number, text: string, font: FontModel): string {
|
|
765
|
+
let hideText: string = text;
|
|
766
|
+
const textSize: Size = measureText(text, font);
|
|
767
|
+
hideText = (textSize.width > maxWidth || textSize.height > maxHeight) ? ' ' : text;
|
|
768
|
+
return hideText;
|
|
769
|
+
}
|
|
770
|
+
|
|
771
|
+
export function orderByArea(a: number, b: number): number {
|
|
772
|
+
if (a['itemArea'] === b['itemArea']) {
|
|
773
|
+
return 0;
|
|
774
|
+
} else if (a['itemArea'] < b['itemArea']) {
|
|
775
|
+
return 1;
|
|
776
|
+
}
|
|
777
|
+
return -1;
|
|
778
|
+
}
|
|
779
|
+
|
|
780
|
+
export function maintainSelection(treemap: TreeMap, element: Element, className: string): void {
|
|
781
|
+
const elementId: string[] = treemap.levelSelection;
|
|
782
|
+
if (elementId) {
|
|
783
|
+
for (let index: number = 0; index < elementId.length; index++) {
|
|
784
|
+
if (element.getAttribute('id') === elementId[index]) {
|
|
785
|
+
if (element.childElementCount > 0) {
|
|
786
|
+
element.children[0].setAttribute('class', className);
|
|
787
|
+
applyOptions(
|
|
788
|
+
element.childNodes[0] as SVGPathElement,
|
|
789
|
+
{
|
|
790
|
+
border: treemap.selectionSettings.border, fill: treemap.selectionSettings.fill,
|
|
791
|
+
opacity: treemap.selectionSettings.opacity
|
|
792
|
+
}
|
|
793
|
+
);
|
|
794
|
+
}
|
|
795
|
+
} else {
|
|
796
|
+
element.setAttribute('class', '');
|
|
797
|
+
}
|
|
798
|
+
}
|
|
799
|
+
}
|
|
800
|
+
}
|
|
801
|
+
|
|
802
|
+
export function legendMaintain(treemap: TreeMap, legendGroup: Element): void {
|
|
803
|
+
const elementId: string[] = treemap.legendId;
|
|
804
|
+
if (elementId) {
|
|
805
|
+
for (let i: number = 0; i < elementId.length; i++) {
|
|
806
|
+
for (let j: number = 0; j < legendGroup.childElementCount; j++) {
|
|
807
|
+
if (legendGroup.childNodes[j]['id'] === elementId[i]) {
|
|
808
|
+
(legendGroup.childNodes[j] as SVGRectElement).setAttribute('fill', treemap.selectionSettings.fill);
|
|
809
|
+
(legendGroup.childNodes[j] as SVGRectElement).setAttribute('stroke', treemap.selectionSettings.border.color);
|
|
810
|
+
(legendGroup.childNodes[j] as SVGRectElement).setAttribute('stroke-width',
|
|
811
|
+
(treemap.selectionSettings.border.width).toString());
|
|
812
|
+
(legendGroup.childNodes[j] as SVGRectElement).setAttribute('opacity', treemap.selectionSettings.opacity);
|
|
813
|
+
}
|
|
814
|
+
}
|
|
815
|
+
}
|
|
816
|
+
}
|
|
817
|
+
}
|
|
818
|
+
|
|
819
|
+
export function removeClassNames(elements: HTMLCollection, type: string, treemap: TreeMap): void {
|
|
820
|
+
let opacity: string; const process: boolean = true; let element: SVGPathElement;
|
|
821
|
+
let stroke: string; let strokeWidth: string; let fill: string;
|
|
822
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
823
|
+
let options: any = {};
|
|
824
|
+
for (let j: number = 0; j < elements.length; j++) {
|
|
825
|
+
element = isNullOrUndefined(elements[j].childNodes[0] as SVGPathElement) ? elements[j] as SVGPathElement :
|
|
826
|
+
elements[j].childNodes[0] as SVGPathElement;
|
|
827
|
+
options = treemap.layout.renderItems[element.id.split('_')[6]]['options'];
|
|
828
|
+
applyOptions(element, options);
|
|
829
|
+
elements[j].classList.remove(type);
|
|
830
|
+
j -= 1;
|
|
831
|
+
}
|
|
832
|
+
}
|
|
833
|
+
|
|
834
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
835
|
+
export function applyOptions(element: SVGPathElement, options: any): void {
|
|
836
|
+
element.setAttribute('opacity', options['opacity']);
|
|
837
|
+
if (!isNullOrUndefined(options['fill'])) {
|
|
838
|
+
element.setAttribute('fill', options['fill']);
|
|
839
|
+
}
|
|
840
|
+
element.setAttribute('stroke', options['border']['color']);
|
|
841
|
+
element.setAttribute('stroke-width', options['border']['width']);
|
|
842
|
+
}
|
|
843
|
+
|
|
844
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
845
|
+
export function textFormatter(format: string, data: any, treemap: TreeMap): string {
|
|
846
|
+
if (isNullOrUndefined(format)) {
|
|
847
|
+
return null;
|
|
848
|
+
}
|
|
849
|
+
const keys: string[] = Object.keys(data);
|
|
850
|
+
for (const key of keys) {
|
|
851
|
+
format = format.split('${' + key + '}').join(formatValue(data[key], treemap).toString());
|
|
852
|
+
}
|
|
853
|
+
return format;
|
|
854
|
+
}
|
|
855
|
+
|
|
856
|
+
export function formatValue(value: number, treemap: TreeMap): string | number {
|
|
857
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
858
|
+
let formatValue: string | number; let formatFunction: any;
|
|
859
|
+
if (treemap.format && !isNaN(Number(value))) {
|
|
860
|
+
formatFunction = treemap.intl.getNumberFormat(
|
|
861
|
+
{ format: treemap.format, useGrouping: treemap.useGroupingSeparator });
|
|
862
|
+
formatValue = formatFunction(Number(value));
|
|
863
|
+
} else {
|
|
864
|
+
formatValue = value;
|
|
865
|
+
}
|
|
866
|
+
return formatValue ? formatValue : '';
|
|
867
|
+
}
|
|
868
|
+
|
|
869
|
+
/**
|
|
870
|
+
* @private
|
|
871
|
+
*/
|
|
872
|
+
export class ColorValue {
|
|
873
|
+
public r: number;
|
|
874
|
+
public g: number;
|
|
875
|
+
public b: number;
|
|
876
|
+
constructor(r?: number, g?: number, b?: number) {
|
|
877
|
+
this.r = r;
|
|
878
|
+
this.g = g;
|
|
879
|
+
this.b = b;
|
|
880
|
+
}
|
|
881
|
+
}
|
|
882
|
+
|
|
883
|
+
/**
|
|
884
|
+
* @param {ColorValue} value - Specfies the color value
|
|
885
|
+
* @returns {string} - Returns the string
|
|
886
|
+
* @private
|
|
887
|
+
*/
|
|
888
|
+
export function convertToHexCode(value: ColorValue): string {
|
|
889
|
+
return '#' + componentToHex(value.r) + componentToHex(value.g) + componentToHex(value.b);
|
|
890
|
+
}
|
|
891
|
+
|
|
892
|
+
/**
|
|
893
|
+
* @param {number} value - Specifes the value
|
|
894
|
+
* @returns {string} - Returns the string
|
|
895
|
+
* @private */
|
|
896
|
+
export function componentToHex(value: number): string {
|
|
897
|
+
const hex: string = value.toString(16);
|
|
898
|
+
return hex.length === 1 ? '0' + hex : hex;
|
|
899
|
+
}
|
|
900
|
+
|
|
901
|
+
/**
|
|
902
|
+
* @param {string} hex - Specifies the hex value
|
|
903
|
+
* @returns {ColorValue} - Returns the color value
|
|
904
|
+
* @private
|
|
905
|
+
*/
|
|
906
|
+
export function convertHexToColor(hex: string): ColorValue {
|
|
907
|
+
const result: RegExpExecArray = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex);
|
|
908
|
+
return result ? new ColorValue(parseInt(result[1], 16), parseInt(result[2], 16), parseInt(result[3], 16)) :
|
|
909
|
+
new ColorValue(255, 255, 255);
|
|
910
|
+
}
|
|
911
|
+
|
|
912
|
+
/**
|
|
913
|
+
* @param {string} color - Specifies the color
|
|
914
|
+
* @returns {string} - Returns the string
|
|
915
|
+
* @private
|
|
916
|
+
*/
|
|
917
|
+
export function colorNameToHex(color: string): string {
|
|
918
|
+
color = color === 'transparent' ? 'white' : color;
|
|
919
|
+
const element: HTMLElement = document.getElementById('treeMapMeasureText');
|
|
920
|
+
element.style.color = color;
|
|
921
|
+
color = window.getComputedStyle(element).color;
|
|
922
|
+
const exp: RegExp = /^(rgb|hsl)(a?)[(]\s*([\d.]+\s*%?)\s*,\s*([\d.]+\s*%?)\s*,\s*([\d.]+\s*%?)\s*(?:,\s*([\d.]+)\s*)?[)]$/;
|
|
923
|
+
const isRGBValue: RegExpExecArray = exp.exec(color);
|
|
924
|
+
return convertToHexCode(
|
|
925
|
+
new ColorValue(parseInt(isRGBValue[3], 10), parseInt(isRGBValue[4], 10), parseInt(isRGBValue[5], 10))
|
|
926
|
+
);
|
|
927
|
+
}
|
|
928
|
+
|
|
929
|
+
/**
|
|
930
|
+
* @param {Location} location - Specifies the location
|
|
931
|
+
* @param {string} shape - Specifies the shape
|
|
932
|
+
* @param {Size} size - Specifies the size
|
|
933
|
+
* @param {string} url - Specifies the url
|
|
934
|
+
* @param {PathOption} options - Specifies the options
|
|
935
|
+
* @param {string} label - Specifies the label
|
|
936
|
+
* @returns {Element} - Returns the element
|
|
937
|
+
* @private
|
|
938
|
+
*/
|
|
939
|
+
export function drawSymbol(location: Location, shape: string, size: Size, url: string, options: PathOption, label: string): Element {
|
|
940
|
+
const functionName: string = 'Path';
|
|
941
|
+
const svgRenderer: SvgRenderer = new SvgRenderer('');
|
|
942
|
+
const temp: IShapes = renderLegendShape(location, size, shape, options, url);
|
|
943
|
+
const htmlElement: Element = svgRenderer['draw' + temp.functionName](temp.renderOption);
|
|
944
|
+
htmlElement.setAttribute('aria-label', label);
|
|
945
|
+
return htmlElement;
|
|
946
|
+
}
|
|
947
|
+
/**
|
|
948
|
+
* @param {Location} location - Specifies the location
|
|
949
|
+
* @param {Size} size - Specifies the size
|
|
950
|
+
* @param {string} shape - Specifies the shape
|
|
951
|
+
* @param {PathOption} options - Specifies the path option
|
|
952
|
+
* @param {string} url - Specifies the string
|
|
953
|
+
* @returns {IShapes} - Returns the shapes
|
|
954
|
+
* @private
|
|
955
|
+
*/
|
|
956
|
+
export function renderLegendShape(location: Location, size: Size, shape: string, options: PathOption, url: string): IShapes {
|
|
957
|
+
let renderPath: string;
|
|
958
|
+
let functionName: string = 'Path';
|
|
959
|
+
const shapeWidth: number = size.width;
|
|
960
|
+
const shapeHeight: number = size.height;
|
|
961
|
+
const shapeX: number = location.x;
|
|
962
|
+
const shapeY: number = location.y;
|
|
963
|
+
const x: number = location.x + (-shapeWidth / 2);
|
|
964
|
+
const y: number = location.y + (-shapeHeight / 2);
|
|
965
|
+
switch (shape) {
|
|
966
|
+
case 'Circle':
|
|
967
|
+
case 'Bubble':
|
|
968
|
+
functionName = 'Ellipse';
|
|
969
|
+
merge(options, { 'rx': shapeWidth / 2, 'ry': shapeHeight / 2, 'cx': shapeX, 'cy': shapeY });
|
|
970
|
+
break;
|
|
971
|
+
case 'VerticalLine':
|
|
972
|
+
renderPath = 'M' + ' ' + shapeX + ' ' + (shapeY + (shapeHeight / 2)) + ' ' + 'L' + ' ' + shapeX + ' '
|
|
973
|
+
+ (shapeY + (-shapeHeight / 2));
|
|
974
|
+
merge(options, { 'd': renderPath });
|
|
975
|
+
break;
|
|
976
|
+
case 'Diamond':
|
|
977
|
+
renderPath = 'M' + ' ' + x + ' ' + shapeY + ' ' +
|
|
978
|
+
'L' + ' ' + shapeX + ' ' + (shapeY + (-shapeHeight / 2)) + ' ' +
|
|
979
|
+
'L' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + shapeY + ' ' +
|
|
980
|
+
'L' + ' ' + shapeX + ' ' + (shapeY + (shapeHeight / 2)) + ' ' +
|
|
981
|
+
'L' + ' ' + x + ' ' + shapeY + ' z';
|
|
982
|
+
merge(options, { 'd': renderPath });
|
|
983
|
+
break;
|
|
984
|
+
case 'Rectangle':
|
|
985
|
+
renderPath = 'M' + ' ' + x + ' ' + (shapeY + (-shapeHeight / 2)) + ' ' +
|
|
986
|
+
'L' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + (shapeY + (-shapeHeight / 2)) + ' ' +
|
|
987
|
+
'L' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + (shapeY + (shapeHeight / 2)) + ' ' +
|
|
988
|
+
'L' + ' ' + x + ' ' + (shapeY + (shapeHeight / 2)) + ' ' +
|
|
989
|
+
'L' + ' ' + x + ' ' + (shapeY + (-shapeHeight / 2)) + ' z';
|
|
990
|
+
merge(options, { 'd': renderPath });
|
|
991
|
+
break;
|
|
992
|
+
case 'Triangle':
|
|
993
|
+
renderPath = 'M' + ' ' + x + ' ' + (shapeY + (shapeHeight / 2)) + ' ' +
|
|
994
|
+
'L' + ' ' + shapeX + ' ' + (shapeY + (-shapeHeight / 2)) + ' ' +
|
|
995
|
+
'L' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + (shapeY + (shapeHeight / 2)) + ' ' +
|
|
996
|
+
'L' + ' ' + x + ' ' + (shapeY + (shapeHeight / 2)) + ' z';
|
|
997
|
+
merge(options, { 'd': renderPath });
|
|
998
|
+
break;
|
|
999
|
+
case 'InvertedTriangle':
|
|
1000
|
+
renderPath = 'M' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + (shapeY - (shapeHeight / 2)) + ' ' +
|
|
1001
|
+
'L' + ' ' + shapeX + ' ' + (shapeY + (shapeHeight / 2)) + ' ' +
|
|
1002
|
+
'L' + ' ' + (shapeX - (shapeWidth / 2)) + ' ' + (shapeY - (shapeHeight / 2)) + ' ' +
|
|
1003
|
+
'L' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + (shapeY - (shapeHeight / 2)) + ' z';
|
|
1004
|
+
merge(options, { 'd': renderPath });
|
|
1005
|
+
break;
|
|
1006
|
+
case 'Pentagon':
|
|
1007
|
+
// eslint-disable-next-line no-case-declarations
|
|
1008
|
+
const eq: number = 72;
|
|
1009
|
+
// eslint-disable-next-line no-case-declarations
|
|
1010
|
+
let xValue: number;
|
|
1011
|
+
// eslint-disable-next-line no-case-declarations
|
|
1012
|
+
let yValue: number;
|
|
1013
|
+
for (let i: number = 0; i <= 5; i++) {
|
|
1014
|
+
xValue = (shapeWidth / 2) * Math.cos((Math.PI / 180) * (i * eq));
|
|
1015
|
+
yValue = (shapeWidth / 2) * Math.sin((Math.PI / 180) * (i * eq));
|
|
1016
|
+
if (i === 0) {
|
|
1017
|
+
renderPath = 'M' + ' ' + (shapeX + xValue) + ' ' + (shapeY + yValue) + ' ';
|
|
1018
|
+
} else {
|
|
1019
|
+
renderPath = renderPath.concat('L' + ' ' + (shapeX + xValue) + ' ' + (shapeY + yValue) + ' ');
|
|
1020
|
+
}
|
|
1021
|
+
}
|
|
1022
|
+
renderPath = renderPath.concat('Z');
|
|
1023
|
+
merge(options, { 'd': renderPath });
|
|
1024
|
+
break;
|
|
1025
|
+
case 'Star':
|
|
1026
|
+
renderPath = 'M ' + (location.x + size.width / 3) + ' ' + (location.y - size.height / 2) + ' L ' + (location.x - size.width / 2)
|
|
1027
|
+
+ ' ' + (location.y + size.height / 6) + ' L ' + (location.x + size.width / 2) + ' ' + (location.y + size.height / 6)
|
|
1028
|
+
+ ' L ' + (location.x - size.width / 3) + ' ' + (location.y - size.height / 2) + ' L ' + location.x + ' ' +
|
|
1029
|
+
(location.y + size.height / 2) + ' L ' + (location.x + size.width / 3) + ' ' + (location.y - size.height / 2) + ' Z';
|
|
1030
|
+
merge(options, { 'd': renderPath });
|
|
1031
|
+
break;
|
|
1032
|
+
case 'Cross':
|
|
1033
|
+
renderPath = 'M' + ' ' + x + ' ' + shapeY + ' ' + 'L' + ' ' + (shapeX + (shapeWidth / 2)) + ' ' + shapeY + ' ' +
|
|
1034
|
+
'M' + ' ' + shapeX + ' ' + (shapeY + (shapeHeight / 2)) + ' ' + 'L' + ' ' + shapeX + ' ' +
|
|
1035
|
+
(shapeY + (-shapeHeight / 2));
|
|
1036
|
+
merge(options, { 'd': renderPath });
|
|
1037
|
+
break;
|
|
1038
|
+
case 'Image':
|
|
1039
|
+
functionName = 'Image';
|
|
1040
|
+
merge(options, { 'href': url, 'height': shapeHeight, 'width': shapeWidth, x: x, y: y });
|
|
1041
|
+
break;
|
|
1042
|
+
}
|
|
1043
|
+
return { renderOption: options, functionName: functionName };
|
|
1044
|
+
}
|
|
1045
|
+
|
|
1046
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1047
|
+
export function isParentItem(data: any[], item: any): boolean {
|
|
1048
|
+
let isParentItem: boolean = false;
|
|
1049
|
+
for (let j: number = 0; j < data.length; j++) {
|
|
1050
|
+
if (item['levelOrderName'] === data[j]['levelOrderName']) {
|
|
1051
|
+
isParentItem = true;
|
|
1052
|
+
break;
|
|
1053
|
+
}
|
|
1054
|
+
}
|
|
1055
|
+
return isParentItem;
|
|
1056
|
+
}
|
|
1057
|
+
/**
|
|
1058
|
+
* Ajax support for treemap
|
|
1059
|
+
*/
|
|
1060
|
+
export class TreeMapAjax {
|
|
1061
|
+
/** options for data */
|
|
1062
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1063
|
+
public dataOptions: string | any;
|
|
1064
|
+
/** type of data */
|
|
1065
|
+
public type: string;
|
|
1066
|
+
/** async value */
|
|
1067
|
+
public async: boolean;
|
|
1068
|
+
/** type of the content */
|
|
1069
|
+
public contentType: string;
|
|
1070
|
+
/** sending data */
|
|
1071
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1072
|
+
public sendData: string | any;
|
|
1073
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1074
|
+
constructor(options: string | any, type?: string, async?: boolean, contentType?: string, sendData?: string | any) {
|
|
1075
|
+
this.dataOptions = options;
|
|
1076
|
+
this.type = type || 'GET';
|
|
1077
|
+
this.async = async || true;
|
|
1078
|
+
this.contentType = contentType;
|
|
1079
|
+
this.sendData = sendData;
|
|
1080
|
+
}
|
|
1081
|
+
}
|
|
1082
|
+
|
|
1083
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1084
|
+
export function removeShape(collection: any[], value: string): void {
|
|
1085
|
+
if (collection.length > 0) {
|
|
1086
|
+
for (let i: number = 0; i < collection.length; i++) {
|
|
1087
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1088
|
+
const item: any = collection[i];
|
|
1089
|
+
setColor(item['legendEle'], item['oldFill'], item['oldOpacity'], item['oldBorderColor'], item['oldBorderWidth']);
|
|
1090
|
+
}
|
|
1091
|
+
}
|
|
1092
|
+
}
|
|
1093
|
+
|
|
1094
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1095
|
+
export function removeLegend(collection: any[], value: string): void {
|
|
1096
|
+
if (collection.length > 0) {
|
|
1097
|
+
for (let j: number = 0; j < collection.length; j++) {
|
|
1098
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1099
|
+
const item: any = collection[j];
|
|
1100
|
+
setColor(item['legendEle'], item['oldFill'], item['oldOpacity'], item['oldBorderColor'], item['oldBorderWidth']);
|
|
1101
|
+
const dataCount: number = item['ShapeCollection']['Elements'].length;
|
|
1102
|
+
for (let k: number = 0; k < dataCount; k++) {
|
|
1103
|
+
setColor(
|
|
1104
|
+
item['ShapeCollection']['Elements'][k], item['shapeOldFill'], item['shapeOldOpacity'],
|
|
1105
|
+
item['shapeOldBorderColor'], item['shapeOldBorderWidth']);
|
|
1106
|
+
}
|
|
1107
|
+
}
|
|
1108
|
+
}
|
|
1109
|
+
}
|
|
1110
|
+
|
|
1111
|
+
export function setColor(element: Element, fill: string, opacity: string, borderColor: string, borderWidth: string): void {
|
|
1112
|
+
element.setAttribute('fill', fill);
|
|
1113
|
+
element.setAttribute('opacity', opacity);
|
|
1114
|
+
element.setAttribute('stroke', borderColor);
|
|
1115
|
+
element.setAttribute('stroke-width', borderWidth);
|
|
1116
|
+
}
|
|
1117
|
+
|
|
1118
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1119
|
+
export function removeSelectionWithHighlight(collection: any[], element: any[], treemap: TreeMap): void {
|
|
1120
|
+
removeShape(collection, 'highlight');
|
|
1121
|
+
element = [];
|
|
1122
|
+
removeClassNames(document.getElementsByClassName('treeMapHighLight'), 'treeMapHighLight', treemap);
|
|
1123
|
+
}
|
|
1124
|
+
|
|
1125
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1126
|
+
export function getLegendIndex(length: number, item: any, treemap: TreeMap): number {
|
|
1127
|
+
let index: number;
|
|
1128
|
+
for (let i: number = 0; i < length; i++) {
|
|
1129
|
+
const dataLength: number = treemap.treeMapLegendModule.legendCollections[i]['legendData'].length;
|
|
1130
|
+
for (let j: number = 0; j < dataLength; j++) {
|
|
1131
|
+
if (treemap.treeMapLegendModule.legendCollections[i]['legendData'][j]['levelOrderName'] === item['levelOrderName']) {
|
|
1132
|
+
index = i;
|
|
1133
|
+
break;
|
|
1134
|
+
}
|
|
1135
|
+
}
|
|
1136
|
+
}
|
|
1137
|
+
return index;
|
|
1138
|
+
}
|
|
1139
|
+
|
|
1140
|
+
export function pushCollection(
|
|
1141
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1142
|
+
collection: any[], index: number, number: number, legendElement: Element, shapeElement: Element,
|
|
1143
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1144
|
+
renderItems: any[], legendCollection: any[]): void {
|
|
1145
|
+
collection.push({
|
|
1146
|
+
legendEle: legendElement, oldFill: legendCollection[index]['legendFill'],
|
|
1147
|
+
oldOpacity: legendCollection[index]['opacity'], oldBorderColor: legendCollection[index]['borderColor'],
|
|
1148
|
+
oldBorderWidth: legendCollection[index]['borderWidth'],
|
|
1149
|
+
shapeElement: shapeElement, shapeOldFill: renderItems[number]['options']['fill'],
|
|
1150
|
+
shapeOldOpacity: renderItems[number]['options']['opacity'],
|
|
1151
|
+
shapeOldBorderColor: renderItems[number]['options']['border']['color'],
|
|
1152
|
+
shapeOldBorderWidth: renderItems[number]['options']['border']['width']
|
|
1153
|
+
});
|
|
1154
|
+
}
|
|
1155
|
+
|
|
1156
|
+
/**
|
|
1157
|
+
* To trigger the download element
|
|
1158
|
+
*
|
|
1159
|
+
* @param {string} fileName - Specifies the file name
|
|
1160
|
+
* @param {ExportType} type - Specifies the type
|
|
1161
|
+
* @param {string} url - Specifies the url
|
|
1162
|
+
* @param {boolean} isDownload - Specifies the boolean value
|
|
1163
|
+
* @returns {void}
|
|
1164
|
+
*/
|
|
1165
|
+
export function triggerDownload(fileName: string, type: ExportType, url: string, isDownload: boolean): void {
|
|
1166
|
+
createElement('a', {
|
|
1167
|
+
attrs: {
|
|
1168
|
+
'download': fileName + '.' + (type as string).toLocaleLowerCase(),
|
|
1169
|
+
'href': url
|
|
1170
|
+
}
|
|
1171
|
+
}).dispatchEvent(new MouseEvent(isDownload ? 'click' : 'move', {
|
|
1172
|
+
view: window,
|
|
1173
|
+
bubbles: false,
|
|
1174
|
+
cancelable: true
|
|
1175
|
+
}));
|
|
1176
|
+
}
|
|
1177
|
+
|
|
1178
|
+
export function removeElement(id: string): void {
|
|
1179
|
+
const element: Element = document.getElementById(id);
|
|
1180
|
+
return element ? remove(element) : null;
|
|
1181
|
+
}
|