@qrvey/utils 1.15.0-2 → 1.15.0-20

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 (115) hide show
  1. package/dist/cjs/elements/helpers/fixed.d.ts +85 -0
  2. package/dist/cjs/elements/helpers/fixed.js +188 -0
  3. package/dist/cjs/elements/helpers/gridStrategy.d.ts +28 -0
  4. package/dist/cjs/elements/helpers/gridStrategy.js +81 -0
  5. package/dist/cjs/elements/helpers/index.d.ts +1 -0
  6. package/dist/cjs/elements/helpers/index.js +17 -0
  7. package/dist/cjs/elements/helpers/responsive.d.ts +87 -0
  8. package/dist/cjs/elements/helpers/responsive.js +166 -0
  9. package/dist/cjs/elements/index.d.ts +2 -0
  10. package/dist/cjs/elements/index.js +18 -0
  11. package/dist/cjs/elements/interfaces/ICanvasGrid.d.ts +5 -0
  12. package/dist/cjs/elements/interfaces/ICanvasGrid.js +9 -0
  13. package/dist/cjs/elements/interfaces/IFixedPosition.d.ts +5 -0
  14. package/dist/cjs/elements/interfaces/IFixedPosition.js +2 -0
  15. package/dist/cjs/elements/interfaces/IVemCore.d.ts +29 -0
  16. package/dist/cjs/elements/interfaces/IVemCore.js +3 -0
  17. package/dist/cjs/elements/interfaces/IVemPosition.d.ts +44 -0
  18. package/dist/cjs/elements/interfaces/IVemPosition.js +8 -0
  19. package/dist/cjs/elements/interfaces/index.d.ts +4 -0
  20. package/dist/cjs/elements/interfaces/index.js +20 -0
  21. package/dist/cjs/elements/utils/element.d.ts +4 -0
  22. package/dist/cjs/elements/utils/element.js +28 -0
  23. package/dist/cjs/elements/utils/general.d.ts +15 -0
  24. package/dist/cjs/elements/utils/general.js +20 -0
  25. package/dist/cjs/elements/utils/overlap.d.ts +63 -0
  26. package/dist/cjs/elements/utils/overlap.js +99 -0
  27. package/dist/cjs/elements/utils/position.d.ts +4 -0
  28. package/dist/cjs/elements/utils/position.js +5 -0
  29. package/dist/cjs/filters/adapters/FDToLogic.js +2 -1
  30. package/dist/cjs/filters/helpers/backend/buildFilters.d.ts +5 -0
  31. package/dist/cjs/filters/helpers/backend/buildFilters.js +23 -1
  32. package/dist/cjs/filters/helpers/common/getDateProperties.d.ts +6 -0
  33. package/dist/cjs/filters/helpers/common/getDateProperties.js +2 -1
  34. package/dist/cjs/filters/helpers/settings/getFilterSettings.js +1 -1
  35. package/dist/cjs/filters/interfaces/common/IFSScopeID.d.ts +4 -0
  36. package/dist/cjs/general/array/howManyByParam.d.ts +8 -0
  37. package/dist/cjs/general/array/howManyByParam.js +21 -0
  38. package/dist/cjs/general/array/index.d.ts +2 -0
  39. package/dist/cjs/general/array/index.js +2 -0
  40. package/dist/cjs/general/string/index.d.ts +4 -0
  41. package/dist/cjs/general/string/index.js +4 -0
  42. package/dist/cjs/general/string/secureHTML.d.ts +8 -0
  43. package/dist/cjs/general/string/secureHTML.js +13 -0
  44. package/dist/cjs/general/string/strategies/XSSEstrictedSanitizer.d.ts +8 -0
  45. package/dist/cjs/general/string/strategies/XSSEstrictedSanitizer.js +23 -0
  46. package/dist/cjs/general/string/strategies/XSSSanitizer.d.ts +8 -0
  47. package/dist/cjs/general/string/strategies/XSSSanitizer.js +19 -0
  48. package/dist/cjs/general/string/urlValidator.d.ts +10 -0
  49. package/dist/cjs/general/string/urlValidator.js +38 -0
  50. package/dist/cjs/globalization/interfaces/export/II18nExportingModal.d.ts +20 -0
  51. package/dist/cjs/globalization/interfaces/filters/II18nFilterDisplay.d.ts +1 -0
  52. package/dist/cjs/globalization/labels/export/I18N_EXPORT_MODAL.js +20 -0
  53. package/dist/cjs/globalization/labels/filters/I18N_FILTER_DISPLAY.js +1 -0
  54. package/dist/cjs/index.d.ts +1 -0
  55. package/dist/cjs/index.js +1 -0
  56. package/dist/cjs/interfaces/SatinizerStrategy.d.ts +3 -0
  57. package/dist/cjs/interfaces/SatinizerStrategy.js +2 -0
  58. package/dist/elements/helpers/fixed.d.ts +85 -0
  59. package/dist/elements/helpers/fixed.js +177 -0
  60. package/dist/elements/helpers/gridStrategy.d.ts +28 -0
  61. package/dist/elements/helpers/gridStrategy.js +76 -0
  62. package/dist/elements/helpers/index.d.ts +1 -0
  63. package/dist/elements/helpers/index.js +1 -0
  64. package/dist/elements/helpers/responsive.d.ts +87 -0
  65. package/dist/elements/helpers/responsive.js +155 -0
  66. package/dist/elements/index.d.ts +2 -0
  67. package/dist/elements/index.js +2 -0
  68. package/dist/elements/interfaces/ICanvasGrid.d.ts +5 -0
  69. package/dist/elements/interfaces/ICanvasGrid.js +6 -0
  70. package/dist/elements/interfaces/IFixedPosition.d.ts +5 -0
  71. package/dist/elements/interfaces/IFixedPosition.js +1 -0
  72. package/dist/elements/interfaces/IVemCore.d.ts +29 -0
  73. package/dist/elements/interfaces/IVemCore.js +1 -0
  74. package/dist/elements/interfaces/IVemPosition.d.ts +44 -0
  75. package/dist/elements/interfaces/IVemPosition.js +5 -0
  76. package/dist/elements/interfaces/index.d.ts +4 -0
  77. package/dist/elements/interfaces/index.js +4 -0
  78. package/dist/elements/utils/element.d.ts +4 -0
  79. package/dist/elements/utils/element.js +24 -0
  80. package/dist/elements/utils/general.d.ts +15 -0
  81. package/dist/elements/utils/general.js +16 -0
  82. package/dist/elements/utils/overlap.d.ts +63 -0
  83. package/dist/elements/utils/overlap.js +95 -0
  84. package/dist/elements/utils/position.d.ts +4 -0
  85. package/dist/elements/utils/position.js +1 -0
  86. package/dist/filters/adapters/FDToLogic.js +2 -1
  87. package/dist/filters/helpers/backend/buildFilters.d.ts +5 -0
  88. package/dist/filters/helpers/backend/buildFilters.js +23 -1
  89. package/dist/filters/helpers/common/getDateProperties.d.ts +6 -0
  90. package/dist/filters/helpers/common/getDateProperties.js +1 -1
  91. package/dist/filters/helpers/settings/getFilterSettings.js +1 -1
  92. package/dist/filters/interfaces/common/IFSScopeID.d.ts +4 -0
  93. package/dist/general/array/howManyByParam.d.ts +8 -0
  94. package/dist/general/array/howManyByParam.js +17 -0
  95. package/dist/general/array/index.d.ts +2 -0
  96. package/dist/general/array/index.js +2 -0
  97. package/dist/general/string/index.d.ts +4 -0
  98. package/dist/general/string/index.js +4 -0
  99. package/dist/general/string/secureHTML.d.ts +8 -0
  100. package/dist/general/string/secureHTML.js +9 -0
  101. package/dist/general/string/strategies/XSSEstrictedSanitizer.d.ts +8 -0
  102. package/dist/general/string/strategies/XSSEstrictedSanitizer.js +19 -0
  103. package/dist/general/string/strategies/XSSSanitizer.d.ts +8 -0
  104. package/dist/general/string/strategies/XSSSanitizer.js +15 -0
  105. package/dist/general/string/urlValidator.d.ts +10 -0
  106. package/dist/general/string/urlValidator.js +34 -0
  107. package/dist/globalization/interfaces/export/II18nExportingModal.d.ts +20 -0
  108. package/dist/globalization/interfaces/filters/II18nFilterDisplay.d.ts +1 -0
  109. package/dist/globalization/labels/export/I18N_EXPORT_MODAL.js +20 -0
  110. package/dist/globalization/labels/filters/I18N_FILTER_DISPLAY.js +1 -0
  111. package/dist/index.d.ts +1 -0
  112. package/dist/index.js +1 -0
  113. package/dist/interfaces/SatinizerStrategy.d.ts +3 -0
  114. package/dist/interfaces/SatinizerStrategy.js +1 -0
  115. package/package.json +3 -2
@@ -0,0 +1,23 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.XSSEstrictedSanitizer = void 0;
4
+ const xss_1 = require("xss");
5
+ class XSSEstrictedSanitizer {
6
+ constructor(options, attributesBlackList = []) {
7
+ this.attributesBlackList = attributesBlackList;
8
+ this.options = Object.assign({ css: false, onIgnoreTagAttr: (_tag, name, value) => {
9
+ if (this.attributesBlackList.includes(name)) {
10
+ return ""; // Elimina el atributo si está en la lista negra
11
+ }
12
+ return `${name}="${value}"`; // Mantiene el atributo si no está en la lista negra
13
+ }, onIgnoreTag: (tag, _html, _options) => {
14
+ if (["script", "iframe"].includes(tag)) {
15
+ return ""; // Elimina los <script>
16
+ }
17
+ }, escapeHtml: (str) => str }, options);
18
+ }
19
+ sanitize(html) {
20
+ return (0, xss_1.filterXSS)(html, this.options);
21
+ }
22
+ }
23
+ exports.XSSEstrictedSanitizer = XSSEstrictedSanitizer;
@@ -0,0 +1,8 @@
1
+ import { IFilterXSSOptions } from "xss";
2
+ import { SanitizerStrategy } from "../../../interfaces/SatinizerStrategy";
3
+ export declare class XSSSanitizer implements SanitizerStrategy {
4
+ private attributesBlackList;
5
+ private options;
6
+ constructor(options?: IFilterXSSOptions, attributesBlackList?: string[]);
7
+ sanitize(html: string): string;
8
+ }
@@ -0,0 +1,19 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.XSSSanitizer = void 0;
4
+ const xss_1 = require("xss");
5
+ class XSSSanitizer {
6
+ constructor(options, attributesBlackList = []) {
7
+ this.attributesBlackList = attributesBlackList;
8
+ this.options = Object.assign({ css: false, onIgnoreTagAttr: (tag, name, value) => {
9
+ if (!this.attributesBlackList.includes(name)) {
10
+ return `${name}="${value}"`;
11
+ }
12
+ return "";
13
+ } }, options);
14
+ }
15
+ sanitize(html) {
16
+ return (0, xss_1.filterXSS)(html, this.options);
17
+ }
18
+ }
19
+ exports.XSSSanitizer = XSSSanitizer;
@@ -0,0 +1,10 @@
1
+ export declare class URLValidator {
2
+ private validDomains;
3
+ private validProtocols;
4
+ constructor(domains?: string[], protocols?: string[]);
5
+ setValidDomains(domains?: string[]): this;
6
+ setValidProtocols(protocols?: string[]): this;
7
+ validate(url: string): boolean;
8
+ private isValidProtocol;
9
+ private isValidDomain;
10
+ }
@@ -0,0 +1,38 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.URLValidator = void 0;
4
+ class URLValidator {
5
+ constructor(domains = [], protocols = ["http", "https"]) {
6
+ this.validDomains = domains;
7
+ this.validProtocols = protocols;
8
+ }
9
+ setValidDomains(domains = []) {
10
+ this.validDomains = domains;
11
+ return this;
12
+ }
13
+ setValidProtocols(protocols = []) {
14
+ this.validProtocols = protocols;
15
+ return this;
16
+ }
17
+ validate(url) {
18
+ try {
19
+ const urlObj = new URL(url);
20
+ return (this.isValidProtocol(urlObj.protocol) &&
21
+ (this.validDomains.length === 0 || this.isValidDomain(urlObj.hostname)));
22
+ }
23
+ catch (_a) {
24
+ return false;
25
+ }
26
+ }
27
+ isValidProtocol(protocol) {
28
+ const normalizedProtocol = protocol.replace(":", "").toLowerCase();
29
+ return this.validProtocols.includes(normalizedProtocol);
30
+ }
31
+ isValidDomain(domain) {
32
+ if (this.validDomains.length === 0) {
33
+ return true;
34
+ }
35
+ return this.validDomains.some((validDomain) => domain.endsWith(validDomain));
36
+ }
37
+ }
38
+ exports.URLValidator = URLValidator;
@@ -16,6 +16,26 @@ export interface I18nExportingModal {
16
16
  failed_scheduling: string;
17
17
  successful_scheduling: string;
18
18
  };
19
+ pivoting_export: {
20
+ dataset_label: string;
21
+ filter_label: string;
22
+ pivoting: {
23
+ title: string;
24
+ yes_label: string;
25
+ no_label: string;
26
+ };
27
+ search_placeholder: string;
28
+ columns_section: {
29
+ title: string;
30
+ subtitle: string;
31
+ select_all_label: string;
32
+ dataset_columns: string;
33
+ pivot_columns_label: string;
34
+ pivot_columns_sublabel: string;
35
+ };
36
+ columns_to_export_label: string;
37
+ no_results_found: string;
38
+ };
19
39
  schedule: {
20
40
  chart_download_ready: string;
21
41
  page_download_ready: string;
@@ -3,4 +3,5 @@ export interface II18nFilterDisplay {
3
3
  edit: string;
4
4
  remove: string;
5
5
  title: string;
6
+ dataset_title?: string;
6
7
  }
@@ -27,6 +27,26 @@ exports.EXPORTING_MODAL = {
27
27
  failed_scheduling: "The export could not be scheduled at this time.",
28
28
  successful_scheduling: "The export of {{fileName}} has been scheduled successfully.",
29
29
  },
30
+ pivoting_export: {
31
+ dataset_label: "Dataset",
32
+ filter_label: "Filter",
33
+ pivoting: {
34
+ title: "Pivoting",
35
+ yes_label: "Yes",
36
+ no_label: "No",
37
+ },
38
+ search_placeholder: "Search",
39
+ columns_section: {
40
+ title: "Columns",
41
+ subtitle: "(Select columns to export)",
42
+ select_all_label: "Add All Columns",
43
+ dataset_columns: "Dataset Columns",
44
+ pivot_columns_label: "Pivot Columns",
45
+ pivot_columns_sublabel: "Displaying only the first 100 results.",
46
+ },
47
+ columns_to_export_label: "Columns to export",
48
+ no_results_found: "No results found",
49
+ },
30
50
  schedule: {
31
51
  chart_download_ready: "Chart is ready to download",
32
52
  page_download_ready: "Dashboard is ready to download",
@@ -9,4 +9,5 @@ exports.I18N_FILTER_DISPLAY = {
9
9
  edit: "Edit",
10
10
  remove: "Remove",
11
11
  title: "Filters affecting this chart",
12
+ dataset_title: "Filters affecting this dataset",
12
13
  };
@@ -16,3 +16,4 @@ export * from "./typescript/index";
16
16
  export * from "./tokens/index";
17
17
  export * from "./column_format/index";
18
18
  export * from "./themes/index";
19
+ export * from "./elements/index";
package/dist/cjs/index.js CHANGED
@@ -32,3 +32,4 @@ __exportStar(require("./typescript/index"), exports);
32
32
  __exportStar(require("./tokens/index"), exports);
33
33
  __exportStar(require("./column_format/index"), exports);
34
34
  __exportStar(require("./themes/index"), exports);
35
+ __exportStar(require("./elements/index"), exports);
@@ -0,0 +1,3 @@
1
+ export interface SanitizerStrategy {
2
+ sanitize(html: string): string;
3
+ }
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,85 @@
1
+ import { CanvasDevice } from "../interfaces/ICanvasGrid";
2
+ import { FindAvailablePositionOptions } from "../interfaces/IFixedPosition";
3
+ import { VemFixed } from "../interfaces/IVemCore";
4
+ import { VemPositionFixed } from "../interfaces/IVemPosition";
5
+ /**
6
+ * update the position for a specific device
7
+ * @param element element to be updated
8
+ * @param newDevicePosition new position attributes for the element
9
+ * @param device device for the update
10
+ * @returns new element with its position updated
11
+ */
12
+ export declare function updateFixedPosition(element: VemFixed, newDevicePosition: Partial<VemPositionFixed>, device: CanvasDevice): VemFixed;
13
+ /**
14
+ * Finds the first available position within a canvas where a new element can be placed without overlapping existing elements.
15
+ * @param canvasWidth - The width of the canvas in pixels.
16
+ * @param newElement - The new element to be placed, with fixed position properties.
17
+ * @param elements - The list of existing elements on the canvas.
18
+ * @param device - The device type (e.g., desktop, tablet, mobile) for determining element positions.
19
+ * @param [options] - Additional options for position finding.
20
+ * @param [options.canvasHeight] - The maximum height of the canvas in pixels. Defaults to `Infinity`.
21
+ * @param [options.findRightToLeft] - Whether to search for positions from right to left. Defaults to `false`.
22
+ * @param [options.initialY] - The initial Y-coordinate to start the search. Defaults to `0`.
23
+ * @returns - The x and y coordinates of the first available position.
24
+ * @throws {Error} - Throws an error if no valid position is found and `canvasHeight` is not specified.
25
+ */
26
+ export declare function findAvailablePosition(canvasWidth: number, newElement: VemFixed, elements: VemFixed[], device: CanvasDevice, options?: FindAvailablePositionOptions): {
27
+ x: number;
28
+ y: number;
29
+ };
30
+ export declare const getFixedPositionByDevice: (item: VemFixed, device: CanvasDevice) => VemPositionFixed | undefined;
31
+ /**
32
+ * Finds available positions for multiple new elements within a canvas, ensuring they do not overlap with existing elements.
33
+ * @param canvasWidth - The width of the canvas in pixels.
34
+ * @param newElements - The list of new elements to be positioned, each with fixed position properties.
35
+ * @param elements - The list of existing elements on the canvas.
36
+ * @param device - The device type (e.g., desktop, tablet, mobile) for determining element positions.
37
+ * @param [startWithPositionY] - Whether to start the position search for each new element based on its initial Y-coordinate. Defaults to `false`.
38
+ * @param [findRightToLeft] - Whether to search for positions from right to left. Defaults to `false`.
39
+ * @param [canvasHeight] - The maximum height of the canvas in pixels. If not provided, the search height is unlimited.
40
+ * @returns
41
+ */
42
+ export declare function findFixedAvailablePositions(canvasWidth: number, newElements: VemFixed[], elements: VemFixed[], device: CanvasDevice, startWithPositionY?: boolean, findRightToLeft?: boolean, canvasHeight?: number): VemFixed[];
43
+ /**
44
+ * Adjusts the `width` of a responsive element to fit within the specified canvas width and updates its position.
45
+ * @param element - The fixed element to adjust.
46
+ * @param canvasWidth - The width of the canvas in grid columns.
47
+ * @param canvasDevice - The target device type (e.g., desktop, tablet, mobile).
48
+ * @returns - The updated responsive element with an adjusted `width`.
49
+ */
50
+ export declare function calculateWidth(element: VemFixed, canvasWidth: number, canvasDevice: CanvasDevice): VemFixed;
51
+ /**
52
+ * @param elements elements to calculate
53
+ * @param device current device
54
+ * @returns height
55
+ */
56
+ export declare const getFixedGridElementsBottomLimit: (elements: VemFixed[], device: CanvasDevice) => number;
57
+ /**
58
+ * Calculates distances of elements from a given reference point on the canvas device.
59
+ * @param elements - Array of `VemFixed` elements to calculate distances for.
60
+ * @param device - Canvas device providing the coordinates of the elements.
61
+ * @param referencePoint - The reference point to calculate distances from.
62
+ * @param referencePoint.x
63
+ * @param referencePoint.y
64
+ * @returns An array of objects containing the original elements and their calculated distances from the reference point.
65
+ */
66
+ export declare const calculateDistancesToReferencePoint: (elements: VemFixed[], device: CanvasDevice, referencePoint: {
67
+ x: number;
68
+ y: number;
69
+ }) => {
70
+ distance: number;
71
+ element: VemFixed;
72
+ }[];
73
+ /**
74
+ * Sorts elements based on their distance from a reference point on the canvas.
75
+ * @param elements - Array of `VemFixed` elements to be sorted.
76
+ * @param device - Canvas device providing the coordinates of the elements.
77
+ * @param referencePoint - The reference point to calculate distances from.
78
+ * @param referencePoint.x
79
+ * @param referencePoint.y
80
+ * @returns An array of `VemFixed` elements sorted by their distance from the reference point (0, 0).
81
+ */
82
+ export declare const sortElementsFromReferencePoint: (elements: VemFixed<unknown>[], device: CanvasDevice, referencePoint: {
83
+ x: number;
84
+ y: number;
85
+ }) => VemFixed<unknown>[];
@@ -0,0 +1,177 @@
1
+ import { VemPositionType } from "../interfaces/IVemPosition";
2
+ import { sortByDistanceFunction } from "../utils/general";
3
+ import { OverlapIntervalTree } from "../utils/overlap";
4
+ import { setElementPosition } from "../utils/position";
5
+ const SPACE_DELTA = 10;
6
+ /**
7
+ * update the position for a specific device
8
+ * @param element element to be updated
9
+ * @param newDevicePosition new position attributes for the element
10
+ * @param device device for the update
11
+ * @returns new element with its position updated
12
+ */
13
+ export function updateFixedPosition(element, newDevicePosition, device) {
14
+ var _a;
15
+ return Object.assign(Object.assign({}, element), { position: Object.assign(Object.assign({}, element.position), { fixed: Object.assign(Object.assign({}, element.position.fixed), { [device]: Object.assign(Object.assign({}, (_a = element.position.fixed) === null || _a === void 0 ? void 0 : _a[device]), newDevicePosition) }) }) });
16
+ }
17
+ /**
18
+ * Finds the first available position within a canvas where a new element can be placed without overlapping existing elements.
19
+ * @param canvasWidth - The width of the canvas in pixels.
20
+ * @param newElement - The new element to be placed, with fixed position properties.
21
+ * @param elements - The list of existing elements on the canvas.
22
+ * @param device - The device type (e.g., desktop, tablet, mobile) for determining element positions.
23
+ * @param [options] - Additional options for position finding.
24
+ * @param [options.canvasHeight] - The maximum height of the canvas in pixels. Defaults to `Infinity`.
25
+ * @param [options.findRightToLeft] - Whether to search for positions from right to left. Defaults to `false`.
26
+ * @param [options.initialY] - The initial Y-coordinate to start the search. Defaults to `0`.
27
+ * @returns - The x and y coordinates of the first available position.
28
+ * @throws {Error} - Throws an error if no valid position is found and `canvasHeight` is not specified.
29
+ */
30
+ export function findAvailablePosition(canvasWidth, newElement, elements, device, options = {}) {
31
+ var _a, _b;
32
+ const { width: newWidth, height: newHeight } = getFixedPositionByDevice(newElement, device);
33
+ const canvasHeight = (_a = options.canvasHeight) !== null && _a !== void 0 ? _a : Infinity;
34
+ const sortedElements = options.findRightToLeft
35
+ ? elements
36
+ .slice()
37
+ .sort((b, a) => b.position.fixed[device].x - a.position.fixed[device].x)
38
+ : elements
39
+ .slice()
40
+ .sort((a, b) => a.position.fixed[device].y - b.position.fixed[device].y);
41
+ const intervalTree = new OverlapIntervalTree();
42
+ for (const element of sortedElements) {
43
+ const elemPosition = element.position.fixed[device];
44
+ intervalTree.insert(elemPosition.x, elemPosition.x + elemPosition.width, elemPosition.y, elemPosition.y + elemPosition.height);
45
+ }
46
+ let startX = options.findRightToLeft ? canvasWidth - newWidth : 0;
47
+ const initialY = (_b = options.initialY) !== null && _b !== void 0 ? _b : 0;
48
+ let increment = options.findRightToLeft ? -SPACE_DELTA : SPACE_DELTA;
49
+ for (let y = initialY; y <= canvasHeight - newHeight; y += SPACE_DELTA) {
50
+ let x = startX;
51
+ while (x >= 0 && x <= canvasWidth - newWidth) {
52
+ if (!intervalTree.overlaps(x, x + newWidth, y, y + newHeight)) {
53
+ return { x, y };
54
+ }
55
+ x += increment;
56
+ }
57
+ if (options.findRightToLeft) {
58
+ startX = 0;
59
+ increment = SPACE_DELTA;
60
+ }
61
+ }
62
+ if (options.canvasHeight)
63
+ return { x: 0, y: 0 };
64
+ throw new Error("No valid position found");
65
+ }
66
+ export const getFixedPositionByDevice = (item, device) => {
67
+ const fixedPosition = item.position.fixed;
68
+ const devicePosition = fixedPosition[device];
69
+ return isValidPosition(devicePosition) ? devicePosition : undefined;
70
+ };
71
+ const isValidPosition = (position) => {
72
+ return ((position === null || position === void 0 ? void 0 : position.y) !== undefined &&
73
+ position.x !== undefined &&
74
+ position.z !== undefined &&
75
+ position.height !== undefined &&
76
+ position.width !== undefined);
77
+ };
78
+ /**
79
+ * Finds available positions for multiple new elements within a canvas, ensuring they do not overlap with existing elements.
80
+ * @param canvasWidth - The width of the canvas in pixels.
81
+ * @param newElements - The list of new elements to be positioned, each with fixed position properties.
82
+ * @param elements - The list of existing elements on the canvas.
83
+ * @param device - The device type (e.g., desktop, tablet, mobile) for determining element positions.
84
+ * @param [startWithPositionY] - Whether to start the position search for each new element based on its initial Y-coordinate. Defaults to `false`.
85
+ * @param [findRightToLeft] - Whether to search for positions from right to left. Defaults to `false`.
86
+ * @param [canvasHeight] - The maximum height of the canvas in pixels. If not provided, the search height is unlimited.
87
+ * @returns
88
+ */
89
+ export function findFixedAvailablePositions(canvasWidth, newElements, elements, device, startWithPositionY = false, findRightToLeft = false, canvasHeight) {
90
+ const processedElements = elements.slice();
91
+ const resultElems = [];
92
+ newElements.forEach((nElement) => {
93
+ const initialY = startWithPositionY
94
+ ? nElement.position.fixed[device].y
95
+ : 0;
96
+ const newElement = calculateWidth(nElement, canvasWidth, device);
97
+ const availablePosition = findAvailablePosition(canvasWidth, newElement, processedElements, device, { initialY, findRightToLeft, canvasHeight });
98
+ const newElemWithPosition = updateFixedPosition(newElement, availablePosition, device);
99
+ resultElems.push(newElemWithPosition);
100
+ processedElements.push(newElemWithPosition);
101
+ });
102
+ return resultElems;
103
+ }
104
+ /**
105
+ * Adjusts the `width` of a responsive element to fit within the specified canvas width and updates its position.
106
+ * @param element - The fixed element to adjust.
107
+ * @param canvasWidth - The width of the canvas in grid columns.
108
+ * @param canvasDevice - The target device type (e.g., desktop, tablet, mobile).
109
+ * @returns - The updated responsive element with an adjusted `width`.
110
+ */
111
+ export function calculateWidth(element, canvasWidth, canvasDevice) {
112
+ const currentPosition = element.position.fixed[canvasDevice];
113
+ const fixedWidth = Math.min(currentPosition.width, canvasWidth);
114
+ const position = Object.assign(Object.assign({}, currentPosition), { width: fixedWidth });
115
+ return setElementPosition(element, VemPositionType.FIXED, canvasDevice, position);
116
+ }
117
+ const getFixedGridElementY = (element, device, allowNegative = false) => {
118
+ var _a;
119
+ const position = element.position.fixed[device];
120
+ const itemY = (_a = position === null || position === void 0 ? void 0 : position.y) !== null && _a !== void 0 ? _a : 0;
121
+ if (!allowNegative) {
122
+ return itemY >= 0 ? itemY : 0;
123
+ }
124
+ return itemY;
125
+ };
126
+ const getFixedGridElementHeight = (element, device) => {
127
+ const position = element.position.fixed[device];
128
+ return position === null || position === void 0 ? void 0 : position.height;
129
+ };
130
+ /**
131
+ * @param elements elements to calculate
132
+ * @param device current device
133
+ * @returns height
134
+ */
135
+ export const getFixedGridElementsBottomLimit = (elements, device) => {
136
+ if (!elements.length)
137
+ return 0;
138
+ return Math.max(...elements.map((element) => getFixedGridElementY(element, device) +
139
+ getFixedGridElementHeight(element, device)));
140
+ };
141
+ /**
142
+ * Calculates distances of elements from a given reference point on the canvas device.
143
+ * @param elements - Array of `VemFixed` elements to calculate distances for.
144
+ * @param device - Canvas device providing the coordinates of the elements.
145
+ * @param referencePoint - The reference point to calculate distances from.
146
+ * @param referencePoint.x
147
+ * @param referencePoint.y
148
+ * @returns An array of objects containing the original elements and their calculated distances from the reference point.
149
+ */
150
+ export const calculateDistancesToReferencePoint = (elements, device, referencePoint) => {
151
+ return elements.map((element) => {
152
+ const elementPosition = getFixedPositionByDevice(element, device);
153
+ if (!elementPosition) {
154
+ throw new Error(`Position for device ${device} is undefined for element with Id ${element.elementId}.`);
155
+ }
156
+ const distance = Math.pow(referencePoint.x - elementPosition.x, 2) +
157
+ Math.pow(referencePoint.y - elementPosition.y, 2);
158
+ return {
159
+ distance,
160
+ element,
161
+ };
162
+ });
163
+ };
164
+ /**
165
+ * Sorts elements based on their distance from a reference point on the canvas.
166
+ * @param elements - Array of `VemFixed` elements to be sorted.
167
+ * @param device - Canvas device providing the coordinates of the elements.
168
+ * @param referencePoint - The reference point to calculate distances from.
169
+ * @param referencePoint.x
170
+ * @param referencePoint.y
171
+ * @returns An array of `VemFixed` elements sorted by their distance from the reference point (0, 0).
172
+ */
173
+ export const sortElementsFromReferencePoint = (elements, device, referencePoint) => {
174
+ const calculatedElements = calculateDistancesToReferencePoint(elements, device, referencePoint);
175
+ const sortedElements = [...calculatedElements].sort(sortByDistanceFunction);
176
+ return sortedElements.map((element) => element.element);
177
+ };
@@ -0,0 +1,28 @@
1
+ import { CanvasDevice, Vem } from "../interfaces";
2
+ interface RecalculateOptions {
3
+ canvasHeight?: number;
4
+ sort?: CanvasDevice;
5
+ allowCopy?: boolean;
6
+ }
7
+ /**
8
+ * Recalculates the positions of elements on a canvas based on the canvas type.
9
+ * @param newElements - The list of elements to be recalculated. Each element has properties based on its type.
10
+ * @param currentElements - The list of elements to be recalculated. Each element has properties based on its type.
11
+ * @param canvasWidth - The width of the canvas in pixels.
12
+ * @param canvasType - The type of canvas (e.g., "fixed") that determines how positions are recalculated.
13
+ * @param device - The device type (e.g., desktop, tablet, mobile) for determining element positions.
14
+ * @param canvasHeight - variable for the canvas with header component
15
+ * @param options
16
+ * @returns - A list of elements with updated positions if the canvas type is "fixed" or "responsive".
17
+ */
18
+ export declare function recalculateElements(newElements: Vem[], currentElements: Vem[], canvasWidth: number, canvasType: string, device: CanvasDevice, options?: RecalculateOptions): Vem[];
19
+ /**
20
+ * The calculation is delegated to a specific strategy based on the `canvasType`.
21
+ * @param elements - The list of elements in the canvas.
22
+ * @param canvasType - The type of canvas (e.g., "fixed", "responsive").
23
+ * @param device - The target device type (e.g., desktop, tablet, mobile).
24
+ * @param [rowGap] - The optional gap (in pixels) between rows in the canvas.
25
+ * @returns - The calculated canvas height based on the selected strategy. Returns an empty array if no strategy is found.
26
+ */
27
+ export declare function calculateCanvasHeight(elements: Vem[], canvasType: string, device: CanvasDevice, rowGap?: number): number;
28
+ export {};
@@ -0,0 +1,76 @@
1
+ import { findFixedAvailablePositions, getFixedGridElementsBottomLimit, sortElementsFromReferencePoint, } from "./fixed";
2
+ import { findResponsiveAvailablePositions, getResponsiveGridElementsBottomLimit, sortResponsiveElements, } from "./responsive";
3
+ import { CanvasDevice, VemPositionType, } from "../interfaces";
4
+ import { copyDesktopPositionToDevice } from "../utils/element";
5
+ const recalculateStrategies = {
6
+ fixed: (elements, currentElements, canvasWidth, device, options) => {
7
+ const isSorted = !currentElements.length;
8
+ const changedElements = (options.allowCopy
9
+ ? copyDesktopPositionToDevice(elements, device, VemPositionType.FIXED)
10
+ : elements);
11
+ // sort elements
12
+ const orderedElements = isSorted
13
+ ? sortElementsFromReferencePoint(changedElements, options.sort, {
14
+ x: 0,
15
+ y: 0,
16
+ })
17
+ : changedElements;
18
+ return findFixedAvailablePositions(canvasWidth, orderedElements, currentElements, device, false, false, options === null || options === void 0 ? void 0 : options.canvasHeight);
19
+ },
20
+ responsive: (elements, currentElements, canvasWidth, device, options) => {
21
+ const isSorted = !currentElements.length;
22
+ const changedElements = (options.allowCopy
23
+ ? copyDesktopPositionToDevice(elements, device, VemPositionType.RESPONSIVE)
24
+ : elements);
25
+ const orderedElements = isSorted
26
+ ? sortResponsiveElements(changedElements, options.sort)
27
+ : changedElements;
28
+ return findResponsiveAvailablePositions(canvasWidth, orderedElements, currentElements, device);
29
+ },
30
+ };
31
+ const calculateCanvasHeightStrategies = {
32
+ fixed: (elements, device) => {
33
+ return getFixedGridElementsBottomLimit(elements, device);
34
+ },
35
+ responsive: (elements, device, rowGap) => {
36
+ return getResponsiveGridElementsBottomLimit(elements, device, rowGap);
37
+ },
38
+ };
39
+ /**
40
+ * Recalculates the positions of elements on a canvas based on the canvas type.
41
+ * @param newElements - The list of elements to be recalculated. Each element has properties based on its type.
42
+ * @param currentElements - The list of elements to be recalculated. Each element has properties based on its type.
43
+ * @param canvasWidth - The width of the canvas in pixels.
44
+ * @param canvasType - The type of canvas (e.g., "fixed") that determines how positions are recalculated.
45
+ * @param device - The device type (e.g., desktop, tablet, mobile) for determining element positions.
46
+ * @param canvasHeight - variable for the canvas with header component
47
+ * @param options
48
+ * @returns - A list of elements with updated positions if the canvas type is "fixed" or "responsive".
49
+ */
50
+ export function recalculateElements(newElements, currentElements, canvasWidth, canvasType, device, options) {
51
+ const strategy = recalculateStrategies[canvasType];
52
+ if (!strategy) {
53
+ return [];
54
+ }
55
+ const defaultOptions = {
56
+ sort: CanvasDevice.DESKTOP,
57
+ allowCopy: true,
58
+ };
59
+ const calculatedOptions = Object.assign(Object.assign({}, defaultOptions), options);
60
+ return strategy(newElements, currentElements, canvasWidth, device, calculatedOptions);
61
+ }
62
+ /**
63
+ * The calculation is delegated to a specific strategy based on the `canvasType`.
64
+ * @param elements - The list of elements in the canvas.
65
+ * @param canvasType - The type of canvas (e.g., "fixed", "responsive").
66
+ * @param device - The target device type (e.g., desktop, tablet, mobile).
67
+ * @param [rowGap] - The optional gap (in pixels) between rows in the canvas.
68
+ * @returns - The calculated canvas height based on the selected strategy. Returns an empty array if no strategy is found.
69
+ */
70
+ export function calculateCanvasHeight(elements, canvasType, device, rowGap) {
71
+ const strategy = calculateCanvasHeightStrategies[canvasType];
72
+ if (!strategy) {
73
+ return 0;
74
+ }
75
+ return strategy(elements, device, rowGap);
76
+ }
@@ -0,0 +1 @@
1
+ export * from "./gridStrategy";
@@ -0,0 +1 @@
1
+ export * from "./gridStrategy";
@@ -0,0 +1,87 @@
1
+ import { CanvasDevice } from "../interfaces/ICanvasGrid";
2
+ import { VemResponsive } from "../interfaces/IVemCore";
3
+ import { VemPositionResponsive } from "../interfaces/IVemPosition";
4
+ /**
5
+ * Finds the first available position for a new responsive element within a canvas.
6
+ * @param canvasWidth - The width of the canvas in terms of columns.
7
+ * @param newElement - The new responsive element to place on the canvas.
8
+ * @param elements - The existing elements on the canvas.
9
+ * @param device - The target device type (e.g., desktop, tablet, mobile) to calculate responsive positions.
10
+ * @returns - The column and row start positions for the new element, or `undefined` if no valid position is found.
11
+ */
12
+ export declare function findAvailablePosition(canvasWidth: number, newElement: VemResponsive, elements: VemResponsive[], device: CanvasDevice): {
13
+ colStart: number;
14
+ rowStart: number;
15
+ } | undefined;
16
+ /**
17
+ * Updates the responsive position of a given element for a specified device.
18
+ * @param element - The responsive element to update.
19
+ * @param newPosition - The new position values to update for the element.
20
+ * @param device - The target device type (e.g., desktop, tablet, mobile) for which the position is updated.
21
+ * @returns - A new `VemResponsive` object with the updated responsive position for the specified device.
22
+ */
23
+ export declare function updateResponsivePosition(element: VemResponsive, newPosition: Partial<VemPositionResponsive>, device: CanvasDevice): VemResponsive;
24
+ /**
25
+ * Finds available positions for a list of responsive elements on a canvas and updates their positions.
26
+ * @param canvasWidth - The width of the canvas in grid columns.
27
+ * @param newElements - The list of new responsive elements to position.
28
+ * @param elements - The list of existing responsive elements already positioned on the canvas.
29
+ * @param device - The target device type (e.g., desktop, tablet, mobile) for which positions are calculated.
30
+ * @returns - A list of responsive elements with updated positions for the specified device.
31
+ */
32
+ export declare function findResponsiveAvailablePositions(canvasWidth: number, newElements: VemResponsive[], elements: VemResponsive[], device: CanvasDevice): VemResponsive[];
33
+ /**
34
+ * Adjusts the `colSpan` of a responsive element to fit within the specified canvas width and updates its position.
35
+ * @param element - The responsive element to adjust.
36
+ * @param canvasWidth - The width of the canvas in grid columns.
37
+ * @param canvasDevice - The target device type (e.g., desktop, tablet, mobile).
38
+ * @returns - The updated responsive element with an adjusted `colSpan`.
39
+ */
40
+ export declare function calculateColSpan(element: VemResponsive, canvasWidth: number, canvasDevice: CanvasDevice): VemResponsive;
41
+ export declare const getResponsiveGridElementsBottomLimit: (elements: VemResponsive[], device: CanvasDevice, rowGap: number) => number;
42
+ /**
43
+ * Calculates the distances of elements from a reference point and returns a list of objects
44
+ * containing the calculated distance and the corresponding element.
45
+ * @param elements - An array of `VemResponsive` objects. Each object represents an element with
46
+ * a `position` property that contains responsive positions for various devices.
47
+ * @param device - The specific device type (key of `CanvasDevice`) to determine the responsive position.
48
+ * @param referencePoint - An object representing the reference point with `x` and `y` coordinates.
49
+ * @param referencePoint.x
50
+ * @param referencePoint.y
51
+ * @returns - An array of objects, where each object contains:
52
+ * - `distance`: The squared Euclidean distance from the reference point.
53
+ * - `element`: The corresponding `VemResponsive` object.
54
+ */
55
+ export declare const calculateDistancesToReferencePoint: (elements: VemResponsive[], device: CanvasDevice, referencePoint: {
56
+ x: number;
57
+ y: number;
58
+ }) => {
59
+ distance: number;
60
+ element: VemResponsive;
61
+ }[];
62
+ /**
63
+ /**
64
+ Sorts objects containing a `distance` and `element` by distance in ascending order.
65
+ If two objects have the same distance, it resolves the tie by comparing the `colStart` property
66
+ of their responsive positions for the `DESKTOP` device.
67
+ * @param a - An object containing:
68
+ * - `distance`: The calculated distance from a reference point.
69
+ * - `element`: A `VemResponsive` object with responsive position data.
70
+ * @param b - Another object with the same structure as `a`.
71
+ * @param a.element
72
+ * @param a.distance
73
+ * @param _device - The device type (of type `CanvasDevice`). Currently unused in this function.
74
+ * @param b.distance
75
+ * @param b.element
76
+ * @returns - A negative number if `a` should come before `b`,
77
+ * a positive number if `a` should come after `b`,
78
+ * or 0 if they have the same distance and `colStart` values.
79
+ */
80
+ export declare const sortByDistanceInResponsiveFunction: (a: {
81
+ distance: number;
82
+ element: VemResponsive;
83
+ }, b: {
84
+ distance: number;
85
+ element: VemResponsive;
86
+ }, _device: CanvasDevice) => number;
87
+ export declare const sortResponsiveElements: (elements: VemResponsive<unknown>[], sortByDevice?: CanvasDevice) => VemResponsive<unknown>[];