fabric 6.0.2 → 6.2.0
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/CHANGELOG.md +15 -0
- package/dist/index.js +250 -101
- package/dist/index.js.map +1 -1
- package/dist/index.min.js +1 -1
- package/dist/index.min.js.map +1 -1
- package/dist/index.min.mjs +1 -1
- package/dist/index.min.mjs.map +1 -1
- package/dist/index.mjs +250 -101
- package/dist/index.mjs.map +1 -1
- package/dist/index.node.cjs +250 -101
- package/dist/index.node.cjs.map +1 -1
- package/dist/index.node.mjs +250 -101
- package/dist/index.node.mjs.map +1 -1
- package/dist/package.json.min.mjs +1 -1
- package/dist/package.json.mjs +1 -1
- package/dist/src/ClassRegistry.d.ts +1 -0
- package/dist/src/ClassRegistry.d.ts.map +1 -1
- package/dist/src/ClassRegistry.min.mjs +1 -1
- package/dist/src/ClassRegistry.min.mjs.map +1 -1
- package/dist/src/ClassRegistry.mjs +3 -0
- package/dist/src/ClassRegistry.mjs.map +1 -1
- package/dist/src/Collection.d.ts +3 -3
- package/dist/src/Collection.d.ts.map +1 -1
- package/dist/src/EventTypeDefs.d.ts +19 -11
- package/dist/src/EventTypeDefs.d.ts.map +1 -1
- package/dist/src/LayoutManager/LayoutManager.d.ts.map +1 -1
- package/dist/src/LayoutManager/LayoutManager.min.mjs +1 -1
- package/dist/src/LayoutManager/LayoutManager.min.mjs.map +1 -1
- package/dist/src/LayoutManager/LayoutManager.mjs +2 -2
- package/dist/src/LayoutManager/LayoutManager.mjs.map +1 -1
- package/dist/src/Shadow.d.ts.map +1 -1
- package/dist/src/Shadow.min.mjs +1 -1
- package/dist/src/Shadow.min.mjs.map +1 -1
- package/dist/src/Shadow.mjs +1 -5
- package/dist/src/Shadow.mjs.map +1 -1
- package/dist/src/canvas/DOMManagers/util.d.ts.map +1 -1
- package/dist/src/canvas/DOMManagers/util.min.mjs +1 -1
- package/dist/src/canvas/DOMManagers/util.min.mjs.map +1 -1
- package/dist/src/canvas/DOMManagers/util.mjs +9 -15
- package/dist/src/canvas/DOMManagers/util.mjs.map +1 -1
- package/dist/src/canvas/SelectableCanvas.d.ts.map +1 -1
- package/dist/src/canvas/SelectableCanvas.min.mjs +1 -1
- package/dist/src/canvas/SelectableCanvas.min.mjs.map +1 -1
- package/dist/src/canvas/SelectableCanvas.mjs +3 -0
- package/dist/src/canvas/SelectableCanvas.mjs.map +1 -1
- package/dist/src/canvas/StaticCanvas.d.ts +20 -24
- package/dist/src/canvas/StaticCanvas.d.ts.map +1 -1
- package/dist/src/color/util.d.ts.map +1 -1
- package/dist/src/constants.d.ts +1 -0
- package/dist/src/constants.d.ts.map +1 -1
- package/dist/src/constants.min.mjs +1 -1
- package/dist/src/constants.min.mjs.map +1 -1
- package/dist/src/constants.mjs +2 -1
- package/dist/src/constants.mjs.map +1 -1
- package/dist/src/controls/controlRendering.d.ts +1 -1
- package/dist/src/controls/controlRendering.d.ts.map +1 -1
- package/dist/src/controls/controlRendering.min.mjs.map +1 -1
- package/dist/src/controls/controlRendering.mjs.map +1 -1
- package/dist/src/controls/fireEvent.d.ts +2 -2
- package/dist/src/controls/fireEvent.d.ts.map +1 -1
- package/dist/src/controls/fireEvent.min.mjs.map +1 -1
- package/dist/src/controls/fireEvent.mjs.map +1 -1
- package/dist/src/controls/index.d.ts +1 -0
- package/dist/src/controls/index.d.ts.map +1 -1
- package/dist/src/controls/index.min.mjs +1 -1
- package/dist/src/controls/index.mjs +1 -0
- package/dist/src/controls/index.mjs.map +1 -1
- package/dist/src/controls/pathControl.d.ts +12 -0
- package/dist/src/controls/pathControl.d.ts.map +1 -0
- package/dist/src/controls/pathControl.min.mjs +2 -0
- package/dist/src/controls/pathControl.min.mjs.map +1 -0
- package/dist/src/controls/pathControl.mjs +156 -0
- package/dist/src/controls/pathControl.mjs.map +1 -0
- package/dist/src/controls/polyControl.d.ts.map +1 -1
- package/dist/src/controls/polyControl.min.mjs +1 -1
- package/dist/src/controls/polyControl.min.mjs.map +1 -1
- package/dist/src/controls/polyControl.mjs +1 -9
- package/dist/src/controls/polyControl.mjs.map +1 -1
- package/dist/src/controls/util.d.ts +1 -1
- package/dist/src/controls/wrapWithFireEvent.d.ts +5 -3
- package/dist/src/controls/wrapWithFireEvent.d.ts.map +1 -1
- package/dist/src/controls/wrapWithFireEvent.min.mjs +1 -1
- package/dist/src/controls/wrapWithFireEvent.min.mjs.map +1 -1
- package/dist/src/controls/wrapWithFireEvent.mjs +7 -4
- package/dist/src/controls/wrapWithFireEvent.mjs.map +1 -1
- package/dist/src/controls/wrapWithFixedAnchor.d.ts.map +1 -1
- package/dist/src/env/index.d.ts.map +1 -1
- package/dist/src/env/node.d.ts.map +1 -1
- package/dist/src/filters/BaseFilter.d.ts.map +1 -1
- package/dist/src/filters/BaseFilter.min.mjs.map +1 -1
- package/dist/src/filters/BaseFilter.mjs +0 -1
- package/dist/src/filters/BaseFilter.mjs.map +1 -1
- package/dist/src/filters/ColorMatrix.d.ts.map +1 -1
- package/dist/src/filters/ColorMatrixFilters.d.ts +8 -96
- package/dist/src/filters/ColorMatrixFilters.d.ts.map +1 -1
- package/dist/src/filters/Convolute.d.ts +2 -1
- package/dist/src/filters/Convolute.d.ts.map +1 -1
- package/dist/src/filters/shaders/baseFilter.d.ts +1 -1
- package/dist/src/filters/shaders/baseFilter.d.ts.map +1 -1
- package/dist/src/filters/utils.d.ts.map +1 -1
- package/dist/src/parser/normalizeAttr.d.ts.map +1 -1
- package/dist/src/parser/parseStyleString.d.ts.map +1 -1
- package/dist/src/parser/parseStyleString.min.mjs +1 -1
- package/dist/src/parser/parseStyleString.min.mjs.map +1 -1
- package/dist/src/parser/parseStyleString.mjs +1 -0
- package/dist/src/parser/parseStyleString.mjs.map +1 -1
- package/dist/src/parser/parseUseDirectives.d.ts.map +1 -1
- package/dist/src/parser/parseUseDirectives.min.mjs +1 -1
- package/dist/src/parser/parseUseDirectives.min.mjs.map +1 -1
- package/dist/src/parser/parseUseDirectives.mjs +61 -43
- package/dist/src/parser/parseUseDirectives.mjs.map +1 -1
- package/dist/src/shapes/Group.d.ts +20 -20
- package/dist/src/shapes/Group.d.ts.map +1 -1
- package/dist/src/shapes/IText/DraggableTextDelegate.d.ts.map +1 -1
- package/dist/src/shapes/IText/ITextBehavior.d.ts.map +1 -1
- package/dist/src/shapes/IText/ITextBehavior.min.mjs.map +1 -1
- package/dist/src/shapes/IText/ITextBehavior.mjs +0 -1
- package/dist/src/shapes/IText/ITextBehavior.mjs.map +1 -1
- package/dist/src/shapes/Image.d.ts.map +1 -1
- package/dist/src/shapes/Image.min.mjs.map +1 -1
- package/dist/src/shapes/Image.mjs +0 -2
- package/dist/src/shapes/Image.mjs.map +1 -1
- package/dist/src/shapes/Path.d.ts +9 -9
- package/dist/src/shapes/Path.d.ts.map +1 -1
- package/dist/src/shapes/Polyline.d.ts +1 -1
- package/dist/src/shapes/Rect.d.ts +1 -1
- package/dist/src/shapes/Text/Text.d.ts +1 -1
- package/dist/src/shapes/Text/Text.d.ts.map +1 -1
- package/dist/src/shapes/Text/TextSVGExportMixin.d.ts.map +1 -1
- package/dist/src/shapes/Text/TextSVGExportMixin.min.mjs.map +1 -1
- package/dist/src/shapes/Text/TextSVGExportMixin.mjs +0 -2
- package/dist/src/shapes/Text/TextSVGExportMixin.mjs.map +1 -1
- package/dist/src/shapes/Textbox.d.ts.map +1 -1
- package/dist/src/shapes/Textbox.min.mjs.map +1 -1
- package/dist/src/shapes/Textbox.mjs +0 -2
- package/dist/src/shapes/Textbox.mjs.map +1 -1
- package/dist/src/util/applyMixins.d.ts.map +1 -1
- package/dist/src/util/dom_misc.d.ts.map +1 -1
- package/dist/src/util/dom_misc.min.mjs +1 -1
- package/dist/src/util/dom_misc.min.mjs.map +1 -1
- package/dist/src/util/dom_misc.mjs +7 -9
- package/dist/src/util/dom_misc.mjs.map +1 -1
- package/dist/src/util/internals/cloneDeep.d.ts.map +1 -1
- package/dist/src/util/internals/console.d.ts +1 -1
- package/dist/src/util/internals/findRight.d.ts.map +1 -1
- package/dist/src/util/internals/removeFromArray.d.ts.map +1 -1
- package/dist/src/util/misc/dom.d.ts.map +1 -1
- package/dist/src/util/misc/groupSVGElements.d.ts.map +1 -1
- package/dist/src/util/misc/matrix.d.ts.map +1 -1
- package/dist/src/util/misc/objectEnlive.d.ts +1 -1
- package/dist/src/util/misc/objectEnlive.d.ts.map +1 -1
- package/dist/src/util/misc/objectEnlive.min.mjs +1 -1
- package/dist/src/util/misc/objectEnlive.min.mjs.map +1 -1
- package/dist/src/util/misc/objectEnlive.mjs +7 -11
- package/dist/src/util/misc/objectEnlive.mjs.map +1 -1
- package/dist/src/util/misc/objectTransforms.d.ts.map +1 -1
- package/dist/src/util/misc/pick.d.ts.map +1 -1
- package/dist/src/util/misc/planeChange.d.ts.map +1 -1
- package/dist/src/util/misc/svgParsing.d.ts.map +1 -1
- package/dist/src/util/misc/textStyles.d.ts.map +1 -1
- package/dist/src/util/path/index.d.ts +0 -1
- package/dist/src/util/path/index.d.ts.map +1 -1
- package/dist/src/util/path/index.min.mjs +1 -1
- package/dist/src/util/path/index.min.mjs.map +1 -1
- package/dist/src/util/path/index.mjs +1 -2
- package/dist/src/util/path/index.mjs.map +1 -1
- package/dist/src/util/path/typedefs.d.ts +1 -0
- package/dist/src/util/path/typedefs.d.ts.map +1 -1
- package/dist/src/util/typeAssertions.d.ts +2 -2
- package/dist/src/util/typeAssertions.d.ts.map +1 -1
- package/lib/aligning_guidelines.js +76 -1
- package/lib/centering_guidelines.js +3 -1
- package/package.json +3 -3
- package/src/ClassRegistry.spec.ts +39 -0
- package/src/ClassRegistry.ts +4 -0
- package/src/EventTypeDefs.ts +22 -10
- package/src/LayoutManager/ActiveSelectionLayoutManager.spec.ts +1 -0
- package/src/LayoutManager/LayoutManager.spec.ts +1 -0
- package/src/LayoutManager/LayoutManager.ts +2 -0
- package/src/Shadow.ts +1 -6
- package/src/canvas/DOMManagers/util.ts +11 -15
- package/src/canvas/SelectableCanvas.spec.ts +18 -0
- package/src/canvas/SelectableCanvas.ts +3 -0
- package/src/constants.ts +1 -0
- package/src/controls/controlRendering.ts +4 -2
- package/src/controls/fireEvent.ts +2 -2
- package/src/controls/index.ts +1 -0
- package/src/controls/pathControl.spec.ts +75 -0
- package/src/controls/pathControl.ts +293 -0
- package/src/controls/polyControl.ts +1 -1
- package/src/controls/wrapWithFireEvent.ts +14 -5
- package/src/filters/BaseFilter.ts +1 -2
- package/src/parser/parseStyleString.ts +1 -0
- package/src/parser/parseUseDirectives.test.ts +113 -0
- package/src/parser/parseUseDirectives.ts +64 -58
- package/src/shapes/IText/ITextBehavior.ts +4 -2
- package/src/shapes/Image.ts +0 -2
- package/src/shapes/Text/TextSVGExportMixin.ts +0 -2
- package/src/shapes/Textbox.ts +0 -2
- package/src/util/dom_misc.ts +17 -10
- package/src/util/misc/objectEnlive.spec.ts +68 -0
- package/src/util/misc/objectEnlive.ts +7 -13
- package/src/util/path/__snapshots__/index.spec.ts.snap +327 -0
- package/src/util/path/index.spec.ts +13 -2
- package/src/util/path/index.ts +2 -4
- package/src/util/path/typedefs.ts +2 -0
- package/.gitmodules +0 -3
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,21 @@
|
|
|
2
2
|
|
|
3
3
|
## [next]
|
|
4
4
|
|
|
5
|
+
## [6.2.0]
|
|
6
|
+
|
|
7
|
+
- fix(): Parse use directive attribute issues [#10053](https://github.com/fabricjs/fabric.js/pull/10053)
|
|
8
|
+
- fix(parseUseDirectives): Fix style tag processing in use tag when reference also has a style [#10050](https://github.com/fabricjs/fabric.js/pull/10050)
|
|
9
|
+
- fix(): Fix path Arc parsing regression issue [#10048](https://github.com/fabricjs/fabric.js/pull/10048)
|
|
10
|
+
- chore(TS): Update TS to latest [#10044](https://github.com/fabricjs/fabric.js/pull/10044)
|
|
11
|
+
- feat(): Add has method to classRegistry to allow to check if a class exists. (fixes #10001)
|
|
12
|
+
|
|
13
|
+
## [6.1.0]
|
|
14
|
+
|
|
15
|
+
- fix(): Avoid errors on restoring custom properties that pass the lazy detection of shadow,gradient,pattern and clipPath. [#10001](https://github.com/fabricjs/fabric.js/issues/10001)
|
|
16
|
+
- fix(): When deselecting an active selection remove its reference from hoveredTarget [#9961](https://github.com/fabricjs/fabric.js/pull/9961)
|
|
17
|
+
- feat(): Path controls utility [#9998](https://github.com/fabricjs/fabric.js/pull/9998)
|
|
18
|
+
- chore(): Removed website submodule
|
|
19
|
+
|
|
5
20
|
## [6.0.2]
|
|
6
21
|
|
|
7
22
|
- fix(TS): Type fixes and improved JSDOCS. [#9978](https://github.com/fabricjs/fabric.js/pull/9978)
|
package/dist/index.js
CHANGED
|
@@ -407,7 +407,7 @@
|
|
|
407
407
|
}
|
|
408
408
|
const cache = new Cache();
|
|
409
409
|
|
|
410
|
-
var version = "6.0
|
|
410
|
+
var version = "6.2.0";
|
|
411
411
|
|
|
412
412
|
// use this syntax so babel plugin see this import here
|
|
413
413
|
const VERSION = version;
|
|
@@ -436,6 +436,7 @@
|
|
|
436
436
|
const SKEWING = 'skewing';
|
|
437
437
|
const RESIZING = 'resizing';
|
|
438
438
|
const MODIFY_POLY = 'modifyPoly';
|
|
439
|
+
const MODIFY_PATH = 'modifyPath';
|
|
439
440
|
const CHANGED = 'changed';
|
|
440
441
|
const SCALE = 'scale';
|
|
441
442
|
const SCALE_X = 'scaleX';
|
|
@@ -465,6 +466,9 @@
|
|
|
465
466
|
this[JSON$1] = new Map();
|
|
466
467
|
this[SVG] = new Map();
|
|
467
468
|
}
|
|
469
|
+
has(classType) {
|
|
470
|
+
return this[JSON$1].has(classType);
|
|
471
|
+
}
|
|
468
472
|
getClass(classType) {
|
|
469
473
|
const constructor = this[JSON$1].get(classType);
|
|
470
474
|
if (!constructor) {
|
|
@@ -1959,8 +1963,13 @@
|
|
|
1959
1963
|
if (!value) {
|
|
1960
1964
|
return value;
|
|
1961
1965
|
}
|
|
1962
|
-
|
|
1963
|
-
|
|
1966
|
+
/**
|
|
1967
|
+
* clipPath or shadow or gradient or text on a path or a pattern,
|
|
1968
|
+
* or the backgroundImage or overlayImage of canvas
|
|
1969
|
+
* If we have a type and there is a classe registered for it, we enlive it.
|
|
1970
|
+
* If there is no class registered for it we return the value as is
|
|
1971
|
+
* */
|
|
1972
|
+
if (value.type && classRegistry.has(value.type)) {
|
|
1964
1973
|
return enlivenObjects([value], {
|
|
1965
1974
|
signal
|
|
1966
1975
|
}).then(_ref => {
|
|
@@ -1969,15 +1978,6 @@
|
|
|
1969
1978
|
return enlived;
|
|
1970
1979
|
});
|
|
1971
1980
|
}
|
|
1972
|
-
// pattern
|
|
1973
|
-
if (value.source) {
|
|
1974
|
-
return classRegistry.getClass('pattern').fromObject(value, {
|
|
1975
|
-
signal
|
|
1976
|
-
}).then(pattern => {
|
|
1977
|
-
instances.push(pattern);
|
|
1978
|
-
return pattern;
|
|
1979
|
-
});
|
|
1980
|
-
}
|
|
1981
1981
|
return value;
|
|
1982
1982
|
});
|
|
1983
1983
|
const keys = Object.keys(serializedObject);
|
|
@@ -2851,6 +2851,7 @@
|
|
|
2851
2851
|
top
|
|
2852
2852
|
};
|
|
2853
2853
|
}
|
|
2854
|
+
let elementLoop = element;
|
|
2854
2855
|
const docElement = doc.documentElement,
|
|
2855
2856
|
body = doc.body || {
|
|
2856
2857
|
scrollLeft: 0,
|
|
@@ -2860,19 +2861,16 @@
|
|
|
2860
2861
|
// to account for ShadowDOM. We still want to traverse up out of ShadowDOM,
|
|
2861
2862
|
// but the .parentNode of a root ShadowDOM node will always be null, instead
|
|
2862
2863
|
// it should be accessed through .host. See http://stackoverflow.com/a/24765528/4383938
|
|
2863
|
-
|
|
2864
|
-
|
|
2865
|
-
|
|
2866
|
-
element = element.parentNode || element.host;
|
|
2867
|
-
// @ts-expect-error because element is typed as HTMLElement but it can go up to document
|
|
2868
|
-
if (element === doc) {
|
|
2864
|
+
while (elementLoop && (elementLoop.parentNode || elementLoop.host)) {
|
|
2865
|
+
elementLoop = elementLoop.parentNode || elementLoop.host;
|
|
2866
|
+
if (elementLoop === doc) {
|
|
2869
2867
|
left = body.scrollLeft || docElement.scrollLeft || 0;
|
|
2870
2868
|
top = body.scrollTop || docElement.scrollTop || 0;
|
|
2871
2869
|
} else {
|
|
2872
|
-
left +=
|
|
2873
|
-
top +=
|
|
2870
|
+
left += elementLoop.scrollLeft || 0;
|
|
2871
|
+
top += elementLoop.scrollTop || 0;
|
|
2874
2872
|
}
|
|
2875
|
-
if (
|
|
2873
|
+
if (elementLoop.nodeType === 1 && elementLoop.style.position === 'fixed') {
|
|
2876
2874
|
break;
|
|
2877
2875
|
}
|
|
2878
2876
|
}
|
|
@@ -2945,29 +2943,23 @@
|
|
|
2945
2943
|
*/
|
|
2946
2944
|
function getElementOffset(element) {
|
|
2947
2945
|
var _getWindowFromElement;
|
|
2948
|
-
let box = {
|
|
2949
|
-
left: 0,
|
|
2950
|
-
top: 0
|
|
2951
|
-
};
|
|
2952
2946
|
const doc = element && getDocumentFromElement(element),
|
|
2953
2947
|
offset = {
|
|
2954
2948
|
left: 0,
|
|
2955
2949
|
top: 0
|
|
2956
|
-
},
|
|
2957
|
-
offsetAttributes = {
|
|
2958
|
-
borderLeftWidth: LEFT,
|
|
2959
|
-
borderTopWidth: TOP,
|
|
2960
|
-
paddingLeft: LEFT,
|
|
2961
|
-
paddingTop: TOP
|
|
2962
2950
|
};
|
|
2963
2951
|
if (!doc) {
|
|
2964
2952
|
return offset;
|
|
2965
2953
|
}
|
|
2966
2954
|
const elemStyle = ((_getWindowFromElement = getWindowFromElement(element)) === null || _getWindowFromElement === void 0 ? void 0 : _getWindowFromElement.getComputedStyle(element, null)) || {};
|
|
2967
|
-
|
|
2968
|
-
|
|
2969
|
-
|
|
2970
|
-
|
|
2955
|
+
offset.left += parseInt(elemStyle.borderLeftWidth, 10) || 0;
|
|
2956
|
+
offset.top += parseInt(elemStyle.borderTopWidth, 10) || 0;
|
|
2957
|
+
offset.left += parseInt(elemStyle.paddingLeft, 10) || 0;
|
|
2958
|
+
offset.top += parseInt(elemStyle.paddingTop, 10) || 0;
|
|
2959
|
+
let box = {
|
|
2960
|
+
left: 0,
|
|
2961
|
+
top: 0
|
|
2962
|
+
};
|
|
2971
2963
|
const docElem = doc.documentElement;
|
|
2972
2964
|
if (typeof element.getBoundingClientRect !== 'undefined') {
|
|
2973
2965
|
box = element.getBoundingClientRect();
|
|
@@ -6743,11 +6735,7 @@
|
|
|
6743
6735
|
|
|
6744
6736
|
constructor(arg0) {
|
|
6745
6737
|
const options = typeof arg0 === 'string' ? Shadow.parseShadow(arg0) : arg0;
|
|
6746
|
-
Object.assign(this, Shadow.ownDefaults);
|
|
6747
|
-
for (const prop in options) {
|
|
6748
|
-
// @ts-expect-error for loops are so messy in TS
|
|
6749
|
-
this[prop] = options[prop];
|
|
6750
|
-
}
|
|
6738
|
+
Object.assign(this, Shadow.ownDefaults, options);
|
|
6751
6739
|
this.id = uid();
|
|
6752
6740
|
}
|
|
6753
6741
|
|
|
@@ -8196,14 +8184,16 @@
|
|
|
8196
8184
|
|
|
8197
8185
|
/**
|
|
8198
8186
|
* Wrap an action handler with firing an event if the action is performed
|
|
8199
|
-
* @param {
|
|
8200
|
-
* @
|
|
8187
|
+
* @param {TModificationEvents} eventName the event we want to fire
|
|
8188
|
+
* @param {TransformActionHandler<T>} actionHandler the function to wrap
|
|
8189
|
+
* @param {object} extraEventInfo extra information to pas to the event handler
|
|
8190
|
+
* @return {TransformActionHandler<T>} a function with an action handler signature
|
|
8201
8191
|
*/
|
|
8202
|
-
const wrapWithFireEvent = (eventName, actionHandler) => {
|
|
8192
|
+
const wrapWithFireEvent = (eventName, actionHandler, extraEventInfo) => {
|
|
8203
8193
|
return (eventData, transform, x, y) => {
|
|
8204
8194
|
const actionPerformed = actionHandler(eventData, transform, x, y);
|
|
8205
8195
|
if (actionPerformed) {
|
|
8206
|
-
fireEvent(eventName, commonEventInfo(eventData, transform, x, y));
|
|
8196
|
+
fireEvent(eventName, _objectSpread2(_objectSpread2({}, commonEventInfo(eventData, transform, x, y)), extraEventInfo));
|
|
8207
8197
|
}
|
|
8208
8198
|
return actionPerformed;
|
|
8209
8199
|
};
|
|
@@ -10675,6 +10665,7 @@
|
|
|
10675
10665
|
*/
|
|
10676
10666
|
function parseStyleString(style, oStyle) {
|
|
10677
10667
|
style.replace(/;\s*$/, '').split(';').forEach(chunk => {
|
|
10668
|
+
if (!chunk) return;
|
|
10678
10669
|
const [attr, value] = chunk.split(':');
|
|
10679
10670
|
oStyle[attr.trim().toLowerCase()] = value.trim();
|
|
10680
10671
|
});
|
|
@@ -11104,7 +11095,7 @@
|
|
|
11104
11095
|
const {
|
|
11105
11096
|
target
|
|
11106
11097
|
} = context;
|
|
11107
|
-
return [MODIFIED, MOVING, RESIZING, ROTATING, SCALING, SKEWING, CHANGED, MODIFY_POLY].map(key => object.on(key, e => this.performLayout(key === MODIFIED ? {
|
|
11098
|
+
return [MODIFIED, MOVING, RESIZING, ROTATING, SCALING, SKEWING, CHANGED, MODIFY_POLY, MODIFY_PATH].map(key => object.on(key, e => this.performLayout(key === MODIFIED ? {
|
|
11108
11099
|
type: LAYOUT_TYPE_OBJECT_MODIFIED,
|
|
11109
11100
|
trigger: key,
|
|
11110
11101
|
e,
|
|
@@ -12041,7 +12032,7 @@
|
|
|
12041
12032
|
|
|
12042
12033
|
// Convert into cubic bezier segments <= 90deg
|
|
12043
12034
|
const segments = Math.ceil(Math.abs(dtheta / PI * 2)),
|
|
12044
|
-
result =
|
|
12035
|
+
result = [],
|
|
12045
12036
|
mDelta = dtheta / segments,
|
|
12046
12037
|
mT = 8 / 3 * Math.sin(mDelta / 4) * Math.sin(mDelta / 4) / Math.sin(mDelta / 2);
|
|
12047
12038
|
let th3 = mTheta + mDelta;
|
|
@@ -12592,7 +12583,6 @@
|
|
|
12592
12583
|
* ['Q', 3, 5, 2, 1, 4, 0],
|
|
12593
12584
|
* ['Q', 9, 12, 2, 1, 4, 0],
|
|
12594
12585
|
* ];
|
|
12595
|
-
*
|
|
12596
12586
|
*/
|
|
12597
12587
|
const parsePath = pathString => {
|
|
12598
12588
|
// clean the string
|
|
@@ -14052,6 +14042,9 @@
|
|
|
14052
14042
|
if (this._currentTransform && this._currentTransform.target === obj) {
|
|
14053
14043
|
this.endCurrentTransform(e);
|
|
14054
14044
|
}
|
|
14045
|
+
if (isActiveSelection(obj) && obj === this._hoveredTarget) {
|
|
14046
|
+
this._hoveredTarget = undefined;
|
|
14047
|
+
}
|
|
14055
14048
|
this._activeObject = undefined;
|
|
14056
14049
|
return true;
|
|
14057
14050
|
}
|
|
@@ -18713,8 +18706,6 @@
|
|
|
18713
18706
|
* @return {String}
|
|
18714
18707
|
*/
|
|
18715
18708
|
getSvgStyles(skipShadow) {
|
|
18716
|
-
// cant use ts-expect-error because of ts 5.3 cross check
|
|
18717
|
-
// @ts-ignore TS doesn't respect this type casting
|
|
18718
18709
|
return "".concat(super.getSvgStyles(skipShadow), " white-space: pre;");
|
|
18719
18710
|
}
|
|
18720
18711
|
|
|
@@ -20667,7 +20658,6 @@
|
|
|
20667
20658
|
} : undefined);
|
|
20668
20659
|
this._fireSelectionChanged();
|
|
20669
20660
|
if (this.canvas) {
|
|
20670
|
-
// @ts-expect-error in reality it is an IText instance
|
|
20671
20661
|
this.canvas.fire('text:editing:entered', {
|
|
20672
20662
|
target: this,
|
|
20673
20663
|
e
|
|
@@ -23163,8 +23153,6 @@
|
|
|
23163
23153
|
* @param {Array} [propertiesToInclude] Any properties that you might want to additionally include in the output
|
|
23164
23154
|
* @return {Object} object representation of an instance
|
|
23165
23155
|
*/
|
|
23166
|
-
// cant use ts-expect-error because of ts 5.3 cross check
|
|
23167
|
-
// @ts-ignore TS this typing limitations
|
|
23168
23156
|
toObject() {
|
|
23169
23157
|
let propertiesToInclude = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];
|
|
23170
23158
|
return super.toObject(['minWidth', 'splitByGrapheme', ...propertiesToInclude]);
|
|
@@ -24356,8 +24344,6 @@
|
|
|
24356
24344
|
*/
|
|
24357
24345
|
drawCacheOnCanvas(ctx) {
|
|
24358
24346
|
ctx.imageSmoothingEnabled = this.imageSmoothing;
|
|
24359
|
-
// cant use ts-expect-error because of ts 5.3 cross check
|
|
24360
|
-
// @ts-ignore TS doesn't respect this type casting
|
|
24361
24347
|
super.drawCacheOnCanvas(ctx);
|
|
24362
24348
|
}
|
|
24363
24349
|
|
|
@@ -24747,65 +24733,82 @@
|
|
|
24747
24733
|
|
|
24748
24734
|
function parseUseDirectives(doc) {
|
|
24749
24735
|
const nodelist = getMultipleNodes(doc, ['use', 'svg:use']);
|
|
24750
|
-
|
|
24751
|
-
|
|
24752
|
-
const
|
|
24753
|
-
|
|
24754
|
-
|
|
24736
|
+
const skipAttributes = ['x', 'y', 'xlink:href', 'href', 'transform'];
|
|
24737
|
+
for (const useElement of nodelist) {
|
|
24738
|
+
const useAttributes = useElement.attributes;
|
|
24739
|
+
const useAttrMap = {};
|
|
24740
|
+
for (const attr of useAttributes) {
|
|
24741
|
+
attr.value && (useAttrMap[attr.name] = attr.value);
|
|
24742
|
+
}
|
|
24743
|
+
const xlink = (useAttrMap['xlink:href'] || useAttrMap.href || '').slice(1);
|
|
24744
|
+
if (xlink === '') {
|
|
24755
24745
|
return;
|
|
24756
24746
|
}
|
|
24757
|
-
const
|
|
24758
|
-
|
|
24759
|
-
const y = el.getAttribute('y') || 0;
|
|
24760
|
-
const el2Orig = doc.getElementById(xlink);
|
|
24761
|
-
if (el2Orig === null) {
|
|
24747
|
+
const referencedElement = doc.getElementById(xlink);
|
|
24748
|
+
if (referencedElement === null) {
|
|
24762
24749
|
// if we can't find the target of the xlink, consider this use tag bad, similar to no xlink
|
|
24763
24750
|
return;
|
|
24764
24751
|
}
|
|
24765
|
-
let
|
|
24766
|
-
|
|
24767
|
-
const
|
|
24768
|
-
const
|
|
24769
|
-
|
|
24770
|
-
if (/^svg$/i.test(el2.nodeName)) {
|
|
24771
|
-
const el3 = el2.ownerDocument.createElementNS(namespace, 'g');
|
|
24772
|
-
for (let j = 0, attrs = el2.attributes, len = attrs.length; j < len; j++) {
|
|
24773
|
-
const attr = attrs.item(j);
|
|
24774
|
-
attr && el3.setAttributeNS(namespace, attr.nodeName, attr.nodeValue);
|
|
24775
|
-
}
|
|
24776
|
-
// el2.firstChild != null
|
|
24777
|
-
while (el2.firstChild) {
|
|
24778
|
-
el3.appendChild(el2.firstChild);
|
|
24779
|
-
}
|
|
24780
|
-
el2 = el3;
|
|
24752
|
+
let clonedOriginal = referencedElement.cloneNode(true);
|
|
24753
|
+
const originalAttributes = clonedOriginal.attributes;
|
|
24754
|
+
const originalAttrMap = {};
|
|
24755
|
+
for (const attr of originalAttributes) {
|
|
24756
|
+
attr.value && (originalAttrMap[attr.name] = attr.value);
|
|
24781
24757
|
}
|
|
24782
|
-
|
|
24783
|
-
|
|
24758
|
+
|
|
24759
|
+
// Transform attribute needs to be merged in a particular way
|
|
24760
|
+
const {
|
|
24761
|
+
x = 0,
|
|
24762
|
+
y = 0,
|
|
24763
|
+
transform = ''
|
|
24764
|
+
} = useAttrMap;
|
|
24765
|
+
const currentTrans = "".concat(transform, " ").concat(originalAttrMap.transform || '', " translate(").concat(x, ", ").concat(y, ")");
|
|
24766
|
+
applyViewboxTransform(clonedOriginal);
|
|
24767
|
+
if (/^svg$/i.test(clonedOriginal.nodeName)) {
|
|
24768
|
+
// if is an SVG, create a group and apply all the attributes on top of it
|
|
24769
|
+
const el3 = clonedOriginal.ownerDocument.createElementNS(svgNS, 'g');
|
|
24770
|
+
Object.entries(originalAttrMap).forEach(_ref => {
|
|
24771
|
+
let [name, value] = _ref;
|
|
24772
|
+
return el3.setAttributeNS(svgNS, name, value);
|
|
24773
|
+
});
|
|
24774
|
+
el3.append(...clonedOriginal.childNodes);
|
|
24775
|
+
clonedOriginal = el3;
|
|
24776
|
+
}
|
|
24777
|
+
for (const attr of useAttributes) {
|
|
24784
24778
|
if (!attr) {
|
|
24785
24779
|
continue;
|
|
24786
24780
|
}
|
|
24787
24781
|
const {
|
|
24788
|
-
|
|
24789
|
-
|
|
24782
|
+
name,
|
|
24783
|
+
value
|
|
24790
24784
|
} = attr;
|
|
24791
|
-
if (
|
|
24785
|
+
if (skipAttributes.includes(name)) {
|
|
24792
24786
|
continue;
|
|
24793
24787
|
}
|
|
24794
|
-
if (
|
|
24795
|
-
|
|
24788
|
+
if (name === 'style') {
|
|
24789
|
+
// when use has a style, merge the two styles, with the ref being priority (not use)
|
|
24790
|
+
// priority is by feature. an attribute for fill on the original element
|
|
24791
|
+
// will overwrite the fill in style or attribute for tha use
|
|
24792
|
+
const styleRecord = {};
|
|
24793
|
+
parseStyleString(value, styleRecord);
|
|
24794
|
+
// cleanup styleRecord from attributes of original
|
|
24795
|
+
Object.entries(originalAttrMap).forEach(_ref2 => {
|
|
24796
|
+
let [name, value] = _ref2;
|
|
24797
|
+
styleRecord[name] = value;
|
|
24798
|
+
});
|
|
24799
|
+
// now we can put in the style of the original that will overwrite the original attributes
|
|
24800
|
+
parseStyleString(originalAttrMap.style || '', styleRecord);
|
|
24801
|
+
const mergedStyles = Object.entries(styleRecord).map(entry => entry.join(':')).join(';');
|
|
24802
|
+
clonedOriginal.setAttribute(name, mergedStyles);
|
|
24796
24803
|
} else {
|
|
24797
|
-
|
|
24804
|
+
// set the attribute from use element only if the original does not have it already
|
|
24805
|
+
!originalAttrMap[name] && clonedOriginal.setAttribute(name, value);
|
|
24798
24806
|
}
|
|
24799
24807
|
}
|
|
24800
|
-
|
|
24801
|
-
|
|
24802
|
-
|
|
24803
|
-
|
|
24804
|
-
parentNode.replaceChild(el2, el);
|
|
24805
|
-
// some browsers do not shorten nodelist after replaceChild (IE8)
|
|
24806
|
-
if (nodelist.length === oldLength) {
|
|
24807
|
-
i++;
|
|
24808
|
-
}
|
|
24808
|
+
clonedOriginal.setAttribute('transform', currentTrans);
|
|
24809
|
+
clonedOriginal.setAttribute('instantiated_by_use', '1');
|
|
24810
|
+
clonedOriginal.removeAttribute('id');
|
|
24811
|
+
useElement.parentNode.replaceChild(clonedOriginal, useElement);
|
|
24809
24812
|
}
|
|
24810
24813
|
}
|
|
24811
24814
|
|
|
@@ -25162,7 +25165,7 @@
|
|
|
25162
25165
|
});
|
|
25163
25166
|
}
|
|
25164
25167
|
|
|
25165
|
-
const ACTION_NAME = MODIFY_POLY;
|
|
25168
|
+
const ACTION_NAME$1 = MODIFY_POLY;
|
|
25166
25169
|
/**
|
|
25167
25170
|
* This function locates the controls.
|
|
25168
25171
|
* It'll be used both for drawing and for interaction.
|
|
@@ -25214,13 +25217,13 @@
|
|
|
25214
25217
|
return actionPerformed;
|
|
25215
25218
|
};
|
|
25216
25219
|
};
|
|
25217
|
-
const createPolyActionHandler = pointIndex => wrapWithFireEvent(ACTION_NAME, factoryPolyActionHandler(pointIndex, polyActionHandler));
|
|
25220
|
+
const createPolyActionHandler = pointIndex => wrapWithFireEvent(ACTION_NAME$1, factoryPolyActionHandler(pointIndex, polyActionHandler));
|
|
25218
25221
|
function createPolyControls(arg0) {
|
|
25219
25222
|
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
25220
25223
|
const controls = {};
|
|
25221
25224
|
for (let idx = 0; idx < (typeof arg0 === 'number' ? arg0 : arg0.points.length); idx++) {
|
|
25222
25225
|
controls["p".concat(idx)] = new Control(_objectSpread2({
|
|
25223
|
-
actionName: ACTION_NAME,
|
|
25226
|
+
actionName: ACTION_NAME$1,
|
|
25224
25227
|
positionHandler: createPolyPositionHandler(idx),
|
|
25225
25228
|
actionHandler: createPolyActionHandler(idx)
|
|
25226
25229
|
}, options));
|
|
@@ -25228,10 +25231,157 @@
|
|
|
25228
25231
|
return controls;
|
|
25229
25232
|
}
|
|
25230
25233
|
|
|
25234
|
+
const ACTION_NAME = 'modifyPath';
|
|
25235
|
+
const calcPathPointPosition = (pathObject, commandIndex, pointIndex) => {
|
|
25236
|
+
const {
|
|
25237
|
+
path,
|
|
25238
|
+
pathOffset
|
|
25239
|
+
} = pathObject;
|
|
25240
|
+
const command = path[commandIndex];
|
|
25241
|
+
return new Point(command[pointIndex] - pathOffset.x, command[pointIndex + 1] - pathOffset.y).transform(multiplyTransformMatrices(pathObject.getViewportTransform(), pathObject.calcTransformMatrix()));
|
|
25242
|
+
};
|
|
25243
|
+
const movePathPoint = (pathObject, x, y, commandIndex, pointIndex) => {
|
|
25244
|
+
const {
|
|
25245
|
+
path,
|
|
25246
|
+
pathOffset
|
|
25247
|
+
} = pathObject;
|
|
25248
|
+
const anchorCommand = path[(commandIndex > 0 ? commandIndex : path.length) - 1];
|
|
25249
|
+
const anchorPoint = new Point(anchorCommand[pointIndex], anchorCommand[pointIndex + 1]);
|
|
25250
|
+
const anchorPointInParentPlane = anchorPoint.subtract(pathOffset).transform(pathObject.calcOwnMatrix());
|
|
25251
|
+
const mouseLocalPosition = sendPointToPlane(new Point(x, y), undefined, pathObject.calcOwnMatrix());
|
|
25252
|
+
path[commandIndex][pointIndex] = mouseLocalPosition.x + pathOffset.x;
|
|
25253
|
+
path[commandIndex][pointIndex + 1] = mouseLocalPosition.y + pathOffset.y;
|
|
25254
|
+
pathObject.setDimensions();
|
|
25255
|
+
const newAnchorPointInParentPlane = anchorPoint.subtract(pathObject.pathOffset).transform(pathObject.calcOwnMatrix());
|
|
25256
|
+
const diff = newAnchorPointInParentPlane.subtract(anchorPointInParentPlane);
|
|
25257
|
+
pathObject.left -= diff.x;
|
|
25258
|
+
pathObject.top -= diff.y;
|
|
25259
|
+
pathObject.set('dirty', true);
|
|
25260
|
+
return true;
|
|
25261
|
+
};
|
|
25262
|
+
|
|
25263
|
+
/**
|
|
25264
|
+
* This function locates the controls.
|
|
25265
|
+
* It'll be used both for drawing and for interaction.
|
|
25266
|
+
*/
|
|
25267
|
+
function pathPositionHandler(dim, finalMatrix, pathObject) {
|
|
25268
|
+
const {
|
|
25269
|
+
commandIndex,
|
|
25270
|
+
pointIndex
|
|
25271
|
+
} = this;
|
|
25272
|
+
return calcPathPointPosition(pathObject, commandIndex, pointIndex);
|
|
25273
|
+
}
|
|
25274
|
+
|
|
25275
|
+
/**
|
|
25276
|
+
* This function defines what the control does.
|
|
25277
|
+
* It'll be called on every mouse move after a control has been clicked and is being dragged.
|
|
25278
|
+
* The function receives as argument the mouse event, the current transform object
|
|
25279
|
+
* and the current position in canvas coordinate `transform.target` is a reference to the
|
|
25280
|
+
* current object being transformed.
|
|
25281
|
+
*/
|
|
25282
|
+
function pathActionHandler(eventData, transform, x, y) {
|
|
25283
|
+
const {
|
|
25284
|
+
target
|
|
25285
|
+
} = transform;
|
|
25286
|
+
const {
|
|
25287
|
+
commandIndex,
|
|
25288
|
+
pointIndex
|
|
25289
|
+
} = this;
|
|
25290
|
+
const actionPerformed = movePathPoint(target, x, y, commandIndex, pointIndex);
|
|
25291
|
+
{
|
|
25292
|
+
fireEvent(this.actionName, _objectSpread2(_objectSpread2({}, commonEventInfo(eventData, transform, x, y)), {}, {
|
|
25293
|
+
commandIndex,
|
|
25294
|
+
pointIndex
|
|
25295
|
+
}));
|
|
25296
|
+
}
|
|
25297
|
+
return actionPerformed;
|
|
25298
|
+
}
|
|
25299
|
+
const indexFromPrevCommand = previousCommandType => previousCommandType === 'C' ? 5 : previousCommandType === 'Q' ? 3 : 1;
|
|
25300
|
+
class PathPointControl extends Control {
|
|
25301
|
+
constructor(options) {
|
|
25302
|
+
super(options);
|
|
25303
|
+
}
|
|
25304
|
+
render(ctx, left, top, styleOverride, fabricObject) {
|
|
25305
|
+
const overrides = _objectSpread2(_objectSpread2({}, styleOverride), {}, {
|
|
25306
|
+
cornerColor: this.controlFill,
|
|
25307
|
+
cornerStrokeColor: this.controlStroke,
|
|
25308
|
+
transparentCorners: !this.controlFill
|
|
25309
|
+
});
|
|
25310
|
+
super.render(ctx, left, top, overrides, fabricObject);
|
|
25311
|
+
}
|
|
25312
|
+
}
|
|
25313
|
+
class PathControlPointControl extends PathPointControl {
|
|
25314
|
+
constructor(options) {
|
|
25315
|
+
super(options);
|
|
25316
|
+
}
|
|
25317
|
+
render(ctx, left, top, styleOverride, fabricObject) {
|
|
25318
|
+
const {
|
|
25319
|
+
path
|
|
25320
|
+
} = fabricObject;
|
|
25321
|
+
const {
|
|
25322
|
+
commandIndex,
|
|
25323
|
+
pointIndex,
|
|
25324
|
+
connectToCommandIndex,
|
|
25325
|
+
connectToPointIndex
|
|
25326
|
+
} = this;
|
|
25327
|
+
ctx.save();
|
|
25328
|
+
ctx.strokeStyle = this.controlStroke;
|
|
25329
|
+
if (this.connectionDashArray) {
|
|
25330
|
+
ctx.setLineDash(this.connectionDashArray);
|
|
25331
|
+
}
|
|
25332
|
+
const [commandType] = path[commandIndex];
|
|
25333
|
+
const point = calcPathPointPosition(fabricObject, connectToCommandIndex, connectToPointIndex);
|
|
25334
|
+
if (commandType === 'Q') {
|
|
25335
|
+
// one control point connects to 2 points
|
|
25336
|
+
const point2 = calcPathPointPosition(fabricObject, commandIndex, pointIndex + 2);
|
|
25337
|
+
ctx.moveTo(point2.x, point2.y);
|
|
25338
|
+
ctx.lineTo(left, top);
|
|
25339
|
+
} else {
|
|
25340
|
+
ctx.moveTo(left, top);
|
|
25341
|
+
}
|
|
25342
|
+
ctx.lineTo(point.x, point.y);
|
|
25343
|
+
ctx.stroke();
|
|
25344
|
+
ctx.restore();
|
|
25345
|
+
super.render(ctx, left, top, styleOverride, fabricObject);
|
|
25346
|
+
}
|
|
25347
|
+
}
|
|
25348
|
+
const createControl = (commandIndexPos, pointIndexPos, isControlPoint, options, connectToCommandIndex, connectToPointIndex) => new (isControlPoint ? PathControlPointControl : PathPointControl)(_objectSpread2(_objectSpread2({
|
|
25349
|
+
commandIndex: commandIndexPos,
|
|
25350
|
+
pointIndex: pointIndexPos,
|
|
25351
|
+
actionName: ACTION_NAME,
|
|
25352
|
+
positionHandler: pathPositionHandler,
|
|
25353
|
+
actionHandler: pathActionHandler,
|
|
25354
|
+
connectToCommandIndex,
|
|
25355
|
+
connectToPointIndex
|
|
25356
|
+
}, options), isControlPoint ? options.controlPointStyle : options.pointStyle));
|
|
25357
|
+
function createPathControls(path) {
|
|
25358
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
25359
|
+
const controls = {};
|
|
25360
|
+
let previousCommandType = 'M';
|
|
25361
|
+
path.path.forEach((command, commandIndex) => {
|
|
25362
|
+
const commandType = command[0];
|
|
25363
|
+
if (commandType !== 'Z') {
|
|
25364
|
+
controls["c_".concat(commandIndex, "_").concat(commandType)] = createControl(commandIndex, command.length - 2, false, options);
|
|
25365
|
+
}
|
|
25366
|
+
switch (commandType) {
|
|
25367
|
+
case 'C':
|
|
25368
|
+
controls["c_".concat(commandIndex, "_C_CP_1")] = createControl(commandIndex, 1, true, options, commandIndex - 1, indexFromPrevCommand(previousCommandType));
|
|
25369
|
+
controls["c_".concat(commandIndex, "_C_CP_2")] = createControl(commandIndex, 3, true, options, commandIndex, 5);
|
|
25370
|
+
break;
|
|
25371
|
+
case 'Q':
|
|
25372
|
+
controls["c_".concat(commandIndex, "_Q_CP_1")] = createControl(commandIndex, 1, true, options, commandIndex, 3);
|
|
25373
|
+
break;
|
|
25374
|
+
}
|
|
25375
|
+
previousCommandType = commandType;
|
|
25376
|
+
});
|
|
25377
|
+
return controls;
|
|
25378
|
+
}
|
|
25379
|
+
|
|
25231
25380
|
var index = /*#__PURE__*/Object.freeze({
|
|
25232
25381
|
__proto__: null,
|
|
25233
25382
|
changeWidth: changeWidth,
|
|
25234
25383
|
createObjectDefaultControls: createObjectDefaultControls,
|
|
25384
|
+
createPathControls: createPathControls,
|
|
25235
25385
|
createPolyActionHandler: createPolyActionHandler,
|
|
25236
25386
|
createPolyControls: createPolyControls,
|
|
25237
25387
|
createPolyPositionHandler: createPolyPositionHandler,
|
|
@@ -25590,7 +25740,6 @@
|
|
|
25590
25740
|
return _objectSpread2({
|
|
25591
25741
|
type: this.type
|
|
25592
25742
|
}, defaultKeys.reduce((acc, key) => {
|
|
25593
|
-
//@ts-expect-error TS doesn't get i want an object that looks like this
|
|
25594
25743
|
acc[key] = this[key];
|
|
25595
25744
|
return acc;
|
|
25596
25745
|
}, {}));
|