@leafer-ui/worker 1.0.0-rc.9 → 1.0.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/dist/worker.esm.js +1135 -839
- package/dist/worker.esm.min.js +1 -1
- package/dist/worker.js +7212 -6107
- package/dist/worker.min.js +1 -1
- package/dist/worker.module.js +7184 -6097
- package/dist/worker.module.min.js +1 -1
- package/package.json +9 -6
- package/src/index.ts +12 -1
- package/types/index.d.ts +1 -0
package/dist/worker.esm.js
CHANGED
|
@@ -1,8 +1,96 @@
|
|
|
1
|
-
import { LeafList, DataHelper, RenderEvent, ChildEvent, WatchEvent, PropertyEvent, LeafHelper, BranchHelper, Bounds, LeafBoundsHelper, Debug, LeafLevelList, LayoutEvent, Run, ImageManager,
|
|
1
|
+
import { LeaferCanvasBase, Platform, canvasPatch, Creator, LeaferImage, FileHelper, LeafList, DataHelper, RenderEvent, ChildEvent, WatchEvent, PropertyEvent, LeafHelper, BranchHelper, Bounds, LeafBoundsHelper, Debug, LeafLevelList, LayoutEvent, Run, ImageManager, AnimateEvent, ResizeEvent, BoundsHelper, Answer, MatrixHelper, AlignHelper, ImageEvent, AroundHelper, PointHelper, Direction4, TwoPointBoundsHelper, TaskProcessor, Matrix } from '@leafer/core';
|
|
2
2
|
export * from '@leafer/core';
|
|
3
3
|
export { LeaferImage } from '@leafer/core';
|
|
4
|
-
import {
|
|
4
|
+
import { InteractionBase, HitCanvasManager } from '@leafer-ui/core';
|
|
5
5
|
export * from '@leafer-ui/core';
|
|
6
|
+
import { PaintImage, ColorConvert, PaintGradient, Export, Group, TextConvert, Paint, Effect } from '@leafer-ui/draw';
|
|
7
|
+
|
|
8
|
+
class LeaferCanvas extends LeaferCanvasBase {
|
|
9
|
+
get allowBackgroundColor() { return true; }
|
|
10
|
+
init() {
|
|
11
|
+
this.__createView();
|
|
12
|
+
this.__createContext();
|
|
13
|
+
this.resize(this.config);
|
|
14
|
+
}
|
|
15
|
+
__createView() {
|
|
16
|
+
this.view = Platform.origin.createCanvas(1, 1);
|
|
17
|
+
}
|
|
18
|
+
updateViewSize() {
|
|
19
|
+
const { width, height, pixelRatio } = this;
|
|
20
|
+
this.view.width = Math.ceil(width * pixelRatio);
|
|
21
|
+
this.view.height = Math.ceil(height * pixelRatio);
|
|
22
|
+
this.clientBounds = this.bounds;
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
canvasPatch(OffscreenCanvasRenderingContext2D.prototype);
|
|
27
|
+
canvasPatch(Path2D.prototype);
|
|
28
|
+
|
|
29
|
+
const { mineType } = FileHelper;
|
|
30
|
+
Object.assign(Creator, {
|
|
31
|
+
canvas: (options, manager) => new LeaferCanvas(options, manager),
|
|
32
|
+
image: (options) => new LeaferImage(options)
|
|
33
|
+
});
|
|
34
|
+
function useCanvas(_canvasType, _power) {
|
|
35
|
+
Platform.origin = {
|
|
36
|
+
createCanvas: (width, height) => new OffscreenCanvas(width, height),
|
|
37
|
+
canvasToDataURL: (canvas, type, quality) => {
|
|
38
|
+
return new Promise((resolve, reject) => {
|
|
39
|
+
canvas.convertToBlob({ type: mineType(type), quality }).then((blob) => {
|
|
40
|
+
var reader = new FileReader();
|
|
41
|
+
reader.onload = (e) => resolve(e.target.result);
|
|
42
|
+
reader.onerror = (e) => reject(e);
|
|
43
|
+
reader.readAsDataURL(blob);
|
|
44
|
+
}).catch((e) => {
|
|
45
|
+
reject(e);
|
|
46
|
+
});
|
|
47
|
+
});
|
|
48
|
+
},
|
|
49
|
+
canvasToBolb: (canvas, type, quality) => canvas.convertToBlob({ type: mineType(type), quality }),
|
|
50
|
+
canvasSaveAs: (_canvas, _filename, _quality) => new Promise((resolve) => resolve()),
|
|
51
|
+
download(_url, _filename) { return undefined; },
|
|
52
|
+
loadImage(src) {
|
|
53
|
+
return new Promise((resolve, reject) => {
|
|
54
|
+
let req = new XMLHttpRequest();
|
|
55
|
+
req.open('GET', Platform.image.getRealURL(src), true);
|
|
56
|
+
req.responseType = "blob";
|
|
57
|
+
req.onload = () => {
|
|
58
|
+
createImageBitmap(req.response).then(img => {
|
|
59
|
+
resolve(img);
|
|
60
|
+
}).catch(e => {
|
|
61
|
+
reject(e);
|
|
62
|
+
});
|
|
63
|
+
};
|
|
64
|
+
req.onerror = (e) => reject(e);
|
|
65
|
+
req.send();
|
|
66
|
+
});
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
Platform.canvas = Creator.canvas();
|
|
70
|
+
Platform.conicGradientSupport = !!Platform.canvas.context.createConicGradient;
|
|
71
|
+
}
|
|
72
|
+
Platform.name = 'web';
|
|
73
|
+
Platform.isWorker = true;
|
|
74
|
+
Platform.requestRender = function (render) { requestAnimationFrame(render); };
|
|
75
|
+
Platform.devicePixelRatio = 1;
|
|
76
|
+
const { userAgent } = navigator;
|
|
77
|
+
if (userAgent.indexOf("Firefox") > -1) {
|
|
78
|
+
Platform.conicGradientRotate90 = true;
|
|
79
|
+
Platform.intWheelDeltaY = true;
|
|
80
|
+
}
|
|
81
|
+
else if (userAgent.indexOf("Safari") > -1 && userAgent.indexOf("Chrome") === -1) {
|
|
82
|
+
Platform.fullImageShadow = true;
|
|
83
|
+
}
|
|
84
|
+
if (userAgent.indexOf('Windows') > -1) {
|
|
85
|
+
Platform.os = 'Windows';
|
|
86
|
+
Platform.intWheelDeltaY = true;
|
|
87
|
+
}
|
|
88
|
+
else if (userAgent.indexOf('Mac') > -1) {
|
|
89
|
+
Platform.os = 'Mac';
|
|
90
|
+
}
|
|
91
|
+
else if (userAgent.indexOf('Linux') > -1) {
|
|
92
|
+
Platform.os = 'Linux';
|
|
93
|
+
}
|
|
6
94
|
|
|
7
95
|
class Watcher {
|
|
8
96
|
get childrenChanged() { return this.hasAdd || this.hasRemove || this.hasVisible; }
|
|
@@ -185,7 +273,7 @@ class LayoutBlockData {
|
|
|
185
273
|
}
|
|
186
274
|
|
|
187
275
|
const { updateAllMatrix, updateAllChange } = LeafHelper;
|
|
188
|
-
const debug$
|
|
276
|
+
const debug$2 = Debug.get('Layouter');
|
|
189
277
|
class Layouter {
|
|
190
278
|
constructor(target, userConfig) {
|
|
191
279
|
this.totalTimes = 0;
|
|
@@ -220,7 +308,7 @@ class Layouter {
|
|
|
220
308
|
target.emitEvent(new LayoutEvent(LayoutEvent.END, this.layoutedBlocks, this.times));
|
|
221
309
|
}
|
|
222
310
|
catch (e) {
|
|
223
|
-
debug$
|
|
311
|
+
debug$2.error(e);
|
|
224
312
|
}
|
|
225
313
|
this.layoutedBlocks = null;
|
|
226
314
|
}
|
|
@@ -234,9 +322,9 @@ class Layouter {
|
|
|
234
322
|
}
|
|
235
323
|
layoutOnce() {
|
|
236
324
|
if (this.layouting)
|
|
237
|
-
return debug$
|
|
325
|
+
return debug$2.warn('layouting');
|
|
238
326
|
if (this.times > 3)
|
|
239
|
-
return debug$
|
|
327
|
+
return debug$2.warn('layout max times');
|
|
240
328
|
this.times++;
|
|
241
329
|
this.totalTimes++;
|
|
242
330
|
this.layouting = true;
|
|
@@ -302,9 +390,11 @@ class Layouter {
|
|
|
302
390
|
updateAllChange(target);
|
|
303
391
|
}
|
|
304
392
|
addExtra(leaf) {
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
393
|
+
if (!this.__updatedList.has(leaf)) {
|
|
394
|
+
const { updatedList, beforeBounds } = this.extraBlock || (this.extraBlock = new LayoutBlockData([]));
|
|
395
|
+
updatedList.length ? beforeBounds.add(leaf.__world) : beforeBounds.set(leaf.__world);
|
|
396
|
+
updatedList.add(leaf);
|
|
397
|
+
}
|
|
308
398
|
}
|
|
309
399
|
createBlock(data) {
|
|
310
400
|
return new LayoutBlockData(data);
|
|
@@ -338,7 +428,7 @@ class Layouter {
|
|
|
338
428
|
}
|
|
339
429
|
}
|
|
340
430
|
|
|
341
|
-
const debug = Debug.get('Renderer');
|
|
431
|
+
const debug$1 = Debug.get('Renderer');
|
|
342
432
|
class Renderer {
|
|
343
433
|
get needFill() { return !!(!this.canvas.allowBackgroundColor && this.config.fill); }
|
|
344
434
|
constructor(target, canvas, userConfig) {
|
|
@@ -376,7 +466,7 @@ class Renderer {
|
|
|
376
466
|
const { target } = this;
|
|
377
467
|
this.times = 0;
|
|
378
468
|
this.totalBounds = new Bounds();
|
|
379
|
-
debug.log(target.innerName, '--->');
|
|
469
|
+
debug$1.log(target.innerName, '--->');
|
|
380
470
|
try {
|
|
381
471
|
this.emitRender(RenderEvent.START);
|
|
382
472
|
this.renderOnce(callback);
|
|
@@ -385,9 +475,9 @@ class Renderer {
|
|
|
385
475
|
}
|
|
386
476
|
catch (e) {
|
|
387
477
|
this.rendering = false;
|
|
388
|
-
debug.error(e);
|
|
478
|
+
debug$1.error(e);
|
|
389
479
|
}
|
|
390
|
-
debug.log('-------------|');
|
|
480
|
+
debug$1.log('-------------|');
|
|
391
481
|
}
|
|
392
482
|
renderAgain() {
|
|
393
483
|
if (this.rendering) {
|
|
@@ -399,9 +489,9 @@ class Renderer {
|
|
|
399
489
|
}
|
|
400
490
|
renderOnce(callback) {
|
|
401
491
|
if (this.rendering)
|
|
402
|
-
return debug.warn('rendering');
|
|
492
|
+
return debug$1.warn('rendering');
|
|
403
493
|
if (this.times > 3)
|
|
404
|
-
return debug.warn('render max times');
|
|
494
|
+
return debug$1.warn('render max times');
|
|
405
495
|
this.times++;
|
|
406
496
|
this.totalTimes++;
|
|
407
497
|
this.rendering = true;
|
|
@@ -414,6 +504,10 @@ class Renderer {
|
|
|
414
504
|
}
|
|
415
505
|
else {
|
|
416
506
|
this.requestLayout();
|
|
507
|
+
if (this.ignore) {
|
|
508
|
+
this.ignore = this.rendering = false;
|
|
509
|
+
return;
|
|
510
|
+
}
|
|
417
511
|
this.emitRender(RenderEvent.BEFORE);
|
|
418
512
|
if (this.config.usePartRender && this.totalTimes > 1) {
|
|
419
513
|
this.partRender();
|
|
@@ -434,7 +528,7 @@ class Renderer {
|
|
|
434
528
|
partRender() {
|
|
435
529
|
const { canvas, updateBlocks: list } = this;
|
|
436
530
|
if (!list)
|
|
437
|
-
return debug.warn('PartRender: need update attr');
|
|
531
|
+
return debug$1.warn('PartRender: need update attr');
|
|
438
532
|
this.mergeBlocks();
|
|
439
533
|
list.forEach(block => { if (canvas.bounds.hit(block) && !block.isEmpty())
|
|
440
534
|
this.clipRender(block); });
|
|
@@ -450,7 +544,7 @@ class Renderer {
|
|
|
450
544
|
canvas.clear();
|
|
451
545
|
}
|
|
452
546
|
else {
|
|
453
|
-
bounds.spread(
|
|
547
|
+
bounds.spread(10 + 1 / this.canvas.pixelRatio).ceil();
|
|
454
548
|
canvas.clearWorld(bounds, true);
|
|
455
549
|
canvas.clipWorld(bounds, true);
|
|
456
550
|
}
|
|
@@ -503,12 +597,12 @@ class Renderer {
|
|
|
503
597
|
const startTime = Date.now();
|
|
504
598
|
Platform.requestRender(() => {
|
|
505
599
|
this.FPS = Math.min(60, Math.ceil(1000 / (Date.now() - startTime)));
|
|
506
|
-
if (this.
|
|
507
|
-
|
|
600
|
+
if (this.running) {
|
|
601
|
+
this.target.emit(AnimateEvent.FRAME);
|
|
602
|
+
if (this.changed && this.canvas.view)
|
|
508
603
|
this.render();
|
|
604
|
+
this.target.emit(RenderEvent.NEXT);
|
|
509
605
|
}
|
|
510
|
-
if (this.running)
|
|
511
|
-
this.target.emit(AnimateEvent.FRAME);
|
|
512
606
|
if (this.target)
|
|
513
607
|
this.__requestRender();
|
|
514
608
|
});
|
|
@@ -521,9 +615,12 @@ class Renderer {
|
|
|
521
615
|
const bounds = new Bounds(0, 0, width, height);
|
|
522
616
|
if (!bounds.includes(this.target.__world) || this.needFill || !e.samePixelRatio) {
|
|
523
617
|
this.addBlock(this.canvas.bounds);
|
|
524
|
-
this.target.forceUpdate('
|
|
618
|
+
this.target.forceUpdate('surface');
|
|
619
|
+
return;
|
|
525
620
|
}
|
|
526
621
|
}
|
|
622
|
+
this.addBlock(new Bounds(0, 0, 1, 1));
|
|
623
|
+
this.changed = true;
|
|
527
624
|
}
|
|
528
625
|
__onLayoutEnd(event) {
|
|
529
626
|
if (event.data)
|
|
@@ -534,7 +631,7 @@ class Renderer {
|
|
|
534
631
|
empty = (!leaf.__world.width || !leaf.__world.height);
|
|
535
632
|
if (empty) {
|
|
536
633
|
if (!leaf.isLeafer)
|
|
537
|
-
debug.tip(leaf.innerName, ': empty');
|
|
634
|
+
debug$1.tip(leaf.innerName, ': empty');
|
|
538
635
|
empty = (!leaf.isBranch || leaf.isBranchLeaf);
|
|
539
636
|
}
|
|
540
637
|
return empty;
|
|
@@ -561,23 +658,13 @@ class Renderer {
|
|
|
561
658
|
if (this.target) {
|
|
562
659
|
this.stop();
|
|
563
660
|
this.__removeListenEvents();
|
|
564
|
-
this.target = null;
|
|
565
|
-
this.canvas = null;
|
|
566
|
-
this.config = null;
|
|
661
|
+
this.target = this.canvas = this.config = null;
|
|
567
662
|
}
|
|
568
663
|
}
|
|
569
664
|
}
|
|
570
665
|
|
|
571
|
-
var AnswerType;
|
|
572
|
-
(function (AnswerType) {
|
|
573
|
-
AnswerType[AnswerType["No"] = 0] = "No";
|
|
574
|
-
AnswerType[AnswerType["Yes"] = 1] = "Yes";
|
|
575
|
-
AnswerType[AnswerType["NoAndSkip"] = 2] = "NoAndSkip";
|
|
576
|
-
AnswerType[AnswerType["YesAndSkip"] = 3] = "YesAndSkip";
|
|
577
|
-
})(AnswerType || (AnswerType = {}));
|
|
578
|
-
|
|
579
666
|
const { hitRadiusPoint } = BoundsHelper;
|
|
580
|
-
class
|
|
667
|
+
class Picker {
|
|
581
668
|
constructor(target, selector) {
|
|
582
669
|
this.target = target;
|
|
583
670
|
this.selector = selector;
|
|
@@ -589,33 +676,41 @@ class Pather {
|
|
|
589
676
|
options = {};
|
|
590
677
|
const through = options.through || false;
|
|
591
678
|
const ignoreHittable = options.ignoreHittable || false;
|
|
679
|
+
const target = options.target || this.target;
|
|
592
680
|
this.exclude = options.exclude || null;
|
|
593
681
|
this.point = { x: hitPoint.x, y: hitPoint.y, radiusX: hitRadius, radiusY: hitRadius };
|
|
594
|
-
this.findList =
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
const
|
|
682
|
+
this.findList = new LeafList(options.findList);
|
|
683
|
+
if (!options.findList)
|
|
684
|
+
this.hitBranch(target);
|
|
685
|
+
const { list } = this.findList;
|
|
686
|
+
const leaf = this.getBestMatchLeaf(list, options.bottomList, ignoreHittable);
|
|
598
687
|
const path = ignoreHittable ? this.getPath(leaf) : this.getHitablePath(leaf);
|
|
599
688
|
this.clear();
|
|
600
|
-
return through ? { path, leaf, throughPath: list.length ? this.getThroughPath(list) : path } : { path, leaf };
|
|
689
|
+
return through ? { path, target: leaf, throughPath: list.length ? this.getThroughPath(list) : path } : { path, target: leaf };
|
|
601
690
|
}
|
|
602
|
-
getBestMatchLeaf() {
|
|
603
|
-
|
|
604
|
-
if (targets.length > 1) {
|
|
691
|
+
getBestMatchLeaf(list, bottomList, ignoreHittable) {
|
|
692
|
+
if (list.length) {
|
|
605
693
|
let find;
|
|
606
|
-
this.findList =
|
|
694
|
+
this.findList = new LeafList();
|
|
607
695
|
const { x, y } = this.point;
|
|
608
696
|
const point = { x, y, radiusX: 0, radiusY: 0 };
|
|
609
|
-
for (let i = 0, len =
|
|
610
|
-
find =
|
|
611
|
-
if (LeafHelper.worldHittable(find)) {
|
|
697
|
+
for (let i = 0, len = list.length; i < len; i++) {
|
|
698
|
+
find = list[i];
|
|
699
|
+
if (ignoreHittable || LeafHelper.worldHittable(find)) {
|
|
612
700
|
this.hitChild(find, point);
|
|
613
701
|
if (this.findList.length)
|
|
614
|
-
return this.findList[0];
|
|
702
|
+
return this.findList.list[0];
|
|
615
703
|
}
|
|
616
704
|
}
|
|
617
705
|
}
|
|
618
|
-
|
|
706
|
+
if (bottomList) {
|
|
707
|
+
for (let i = 0, len = bottomList.length; i < len; i++) {
|
|
708
|
+
this.hitChild(bottomList[i].target, this.point, bottomList[i].proxy);
|
|
709
|
+
if (this.findList.length)
|
|
710
|
+
return this.findList.list[0];
|
|
711
|
+
}
|
|
712
|
+
}
|
|
713
|
+
return list[0];
|
|
619
714
|
}
|
|
620
715
|
getPath(leaf) {
|
|
621
716
|
const path = new LeafList();
|
|
@@ -627,7 +722,7 @@ class Pather {
|
|
|
627
722
|
return path;
|
|
628
723
|
}
|
|
629
724
|
getHitablePath(leaf) {
|
|
630
|
-
const path = this.getPath(leaf);
|
|
725
|
+
const path = this.getPath(leaf && leaf.hittable ? leaf : null);
|
|
631
726
|
let item, hittablePath = new LeafList();
|
|
632
727
|
for (let i = path.list.length - 1; i > -1; i--) {
|
|
633
728
|
item = path.list[i];
|
|
@@ -657,12 +752,15 @@ class Pather {
|
|
|
657
752
|
}
|
|
658
753
|
return throughPath;
|
|
659
754
|
}
|
|
755
|
+
hitBranch(branch) {
|
|
756
|
+
this.eachFind(branch.children, branch.__onlyHitMask);
|
|
757
|
+
}
|
|
660
758
|
eachFind(children, hitMask) {
|
|
661
759
|
let child, hit;
|
|
662
760
|
const { point } = this, len = children.length;
|
|
663
761
|
for (let i = len - 1; i > -1; i--) {
|
|
664
762
|
child = children[i];
|
|
665
|
-
if (!child.__.visible || (hitMask && !child.__.
|
|
763
|
+
if (!child.__.visible || (hitMask && !child.__.mask))
|
|
666
764
|
continue;
|
|
667
765
|
hit = child.__.hitRadius ? true : hitRadiusPoint(child.__world, point);
|
|
668
766
|
if (child.isBranch) {
|
|
@@ -678,11 +776,15 @@ class Pather {
|
|
|
678
776
|
}
|
|
679
777
|
}
|
|
680
778
|
}
|
|
681
|
-
hitChild(child, point) {
|
|
779
|
+
hitChild(child, point, proxy) {
|
|
682
780
|
if (this.exclude && this.exclude.has(child))
|
|
683
781
|
return;
|
|
684
|
-
if (child.__hitWorld(point))
|
|
685
|
-
|
|
782
|
+
if (child.__hitWorld(point)) {
|
|
783
|
+
const { parent } = child;
|
|
784
|
+
if (parent && parent.__hasMask && !child.__.mask && !parent.children.some(item => item.__.mask && item.__hitWorld(point)))
|
|
785
|
+
return;
|
|
786
|
+
this.findList.add(proxy || child);
|
|
787
|
+
}
|
|
686
788
|
}
|
|
687
789
|
clear() {
|
|
688
790
|
this.point = null;
|
|
@@ -694,7 +796,8 @@ class Pather {
|
|
|
694
796
|
}
|
|
695
797
|
}
|
|
696
798
|
|
|
697
|
-
const { Yes, NoAndSkip, YesAndSkip } =
|
|
799
|
+
const { Yes, NoAndSkip, YesAndSkip } = Answer;
|
|
800
|
+
const idCondition = {}, classNameCondition = {}, tagCondition = {};
|
|
698
801
|
class Selector {
|
|
699
802
|
constructor(target, userConfig) {
|
|
700
803
|
this.config = {};
|
|
@@ -704,12 +807,13 @@ class Selector {
|
|
|
704
807
|
id: (leaf, name) => leaf.id === name ? (this.idMap[name] = leaf, 1) : 0,
|
|
705
808
|
innerId: (leaf, innerId) => leaf.innerId === innerId ? (this.innerIdMap[innerId] = leaf, 1) : 0,
|
|
706
809
|
className: (leaf, name) => leaf.className === name ? 1 : 0,
|
|
707
|
-
tag: (leaf, name) => leaf.__tag === name ? 1 : 0
|
|
810
|
+
tag: (leaf, name) => leaf.__tag === name ? 1 : 0,
|
|
811
|
+
tags: (leaf, nameMap) => nameMap[leaf.__tag] ? 1 : 0
|
|
708
812
|
};
|
|
709
813
|
this.target = target;
|
|
710
814
|
if (userConfig)
|
|
711
815
|
this.config = DataHelper.default(userConfig, this.config);
|
|
712
|
-
this.
|
|
816
|
+
this.picker = new Picker(target, this);
|
|
713
817
|
this.__listenEvents();
|
|
714
818
|
}
|
|
715
819
|
getBy(condition, branch, one, options) {
|
|
@@ -720,12 +824,25 @@ class Selector {
|
|
|
720
824
|
case 'string':
|
|
721
825
|
switch (condition[0]) {
|
|
722
826
|
case '#':
|
|
723
|
-
|
|
724
|
-
|
|
827
|
+
idCondition.id = condition.substring(1), condition = idCondition;
|
|
828
|
+
break;
|
|
725
829
|
case '.':
|
|
726
|
-
|
|
830
|
+
classNameCondition.className = condition.substring(1), condition = classNameCondition;
|
|
831
|
+
break;
|
|
727
832
|
default:
|
|
728
|
-
|
|
833
|
+
tagCondition.tag = condition, condition = tagCondition;
|
|
834
|
+
}
|
|
835
|
+
case 'object':
|
|
836
|
+
if (condition.id !== undefined) {
|
|
837
|
+
const leaf = this.getById(condition.id, branch);
|
|
838
|
+
return one ? leaf : (leaf ? [leaf] : []);
|
|
839
|
+
}
|
|
840
|
+
else if (condition.tag) {
|
|
841
|
+
const { tag } = condition, isArray = tag instanceof Array;
|
|
842
|
+
return this.getByMethod(isArray ? this.methods.tags : this.methods.tag, branch, one, isArray ? DataHelper.toMap(tag) : tag);
|
|
843
|
+
}
|
|
844
|
+
else {
|
|
845
|
+
return this.getByMethod(this.methods.className, branch, one, condition.className);
|
|
729
846
|
}
|
|
730
847
|
case 'function':
|
|
731
848
|
return this.getByMethod(condition, branch, one, options);
|
|
@@ -734,7 +851,7 @@ class Selector {
|
|
|
734
851
|
getByPoint(hitPoint, hitRadius, options) {
|
|
735
852
|
if (Platform.name === 'node')
|
|
736
853
|
this.target.emit(LayoutEvent.CHECK_UPDATE);
|
|
737
|
-
return this.
|
|
854
|
+
return this.picker.getByPoint(hitPoint, hitRadius, options);
|
|
738
855
|
}
|
|
739
856
|
getByInnerId(innerId, branch) {
|
|
740
857
|
const cache = this.innerIdMap[innerId];
|
|
@@ -810,7 +927,7 @@ class Selector {
|
|
|
810
927
|
destroy() {
|
|
811
928
|
if (this.__eventIds.length) {
|
|
812
929
|
this.__removeListenEvents();
|
|
813
|
-
this.
|
|
930
|
+
this.picker.destroy();
|
|
814
931
|
this.findLeaf = null;
|
|
815
932
|
this.innerIdMap = {};
|
|
816
933
|
this.idMap = {};
|
|
@@ -826,199 +943,428 @@ Object.assign(Creator, {
|
|
|
826
943
|
});
|
|
827
944
|
Platform.layout = Layouter.fullLayout;
|
|
828
945
|
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
const { width, height, pixelRatio } = this;
|
|
841
|
-
this.view.width = width * pixelRatio;
|
|
842
|
-
this.view.height = height * pixelRatio;
|
|
843
|
-
this.clientBounds = this.bounds;
|
|
844
|
-
}
|
|
845
|
-
}
|
|
846
|
-
|
|
847
|
-
canvasPatch(OffscreenCanvasRenderingContext2D.prototype);
|
|
848
|
-
canvasPatch(Path2D.prototype);
|
|
849
|
-
|
|
850
|
-
const { mineType } = FileHelper;
|
|
851
|
-
Object.assign(Creator, {
|
|
852
|
-
canvas: (options, manager) => new LeaferCanvas(options, manager),
|
|
853
|
-
image: (options) => new LeaferImage(options),
|
|
854
|
-
hitCanvas: (options, manager) => new LeaferCanvas(options, manager),
|
|
855
|
-
interaction: (target, canvas, selector, options) => new InteractionBase(target, canvas, selector, options),
|
|
856
|
-
});
|
|
857
|
-
function useCanvas(_canvasType, _power) {
|
|
858
|
-
Platform.origin = {
|
|
859
|
-
createCanvas: (width, height) => new OffscreenCanvas(width, height),
|
|
860
|
-
canvasToDataURL: (canvas, type, quality) => {
|
|
861
|
-
return new Promise((resolve, reject) => {
|
|
862
|
-
canvas.convertToBlob({ type: mineType(type), quality }).then((blob) => {
|
|
863
|
-
var reader = new FileReader();
|
|
864
|
-
reader.onload = (e) => resolve(e.target.result);
|
|
865
|
-
reader.onerror = (e) => reject(e);
|
|
866
|
-
reader.readAsDataURL(blob);
|
|
867
|
-
}).catch((e) => {
|
|
868
|
-
reject(e);
|
|
869
|
-
});
|
|
870
|
-
});
|
|
871
|
-
},
|
|
872
|
-
canvasToBolb: (canvas, type, quality) => canvas.convertToBlob({ type: mineType(type), quality }),
|
|
873
|
-
canvasSaveAs: (_canvas, _filename, _quality) => new Promise((resolve) => resolve()),
|
|
874
|
-
loadImage(src) {
|
|
875
|
-
return new Promise((resolve, reject) => {
|
|
876
|
-
if (!src.startsWith('data:') && Platform.image.suffix)
|
|
877
|
-
src += (src.includes("?") ? "&" : "?") + Platform.image.suffix;
|
|
878
|
-
let req = new XMLHttpRequest();
|
|
879
|
-
req.open('GET', src, true);
|
|
880
|
-
req.responseType = "blob";
|
|
881
|
-
req.onload = () => {
|
|
882
|
-
createImageBitmap(req.response).then(img => {
|
|
883
|
-
resolve(img);
|
|
884
|
-
}).catch(e => {
|
|
885
|
-
reject(e);
|
|
886
|
-
});
|
|
887
|
-
};
|
|
888
|
-
req.onerror = (e) => reject(e);
|
|
889
|
-
req.send();
|
|
946
|
+
function fillText(ui, canvas) {
|
|
947
|
+
let row;
|
|
948
|
+
const { rows, decorationY, decorationHeight } = ui.__.__textDrawData;
|
|
949
|
+
for (let i = 0, len = rows.length; i < len; i++) {
|
|
950
|
+
row = rows[i];
|
|
951
|
+
if (row.text) {
|
|
952
|
+
canvas.fillText(row.text, row.x, row.y);
|
|
953
|
+
}
|
|
954
|
+
else if (row.data) {
|
|
955
|
+
row.data.forEach(charData => {
|
|
956
|
+
canvas.fillText(charData.char, charData.x, row.y);
|
|
890
957
|
});
|
|
891
958
|
}
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
}
|
|
896
|
-
Platform.name = 'web';
|
|
897
|
-
Platform.isWorker = true;
|
|
898
|
-
Platform.requestRender = function (render) { requestAnimationFrame(render); };
|
|
899
|
-
Platform.devicePixelRatio = 1;
|
|
900
|
-
const { userAgent } = navigator;
|
|
901
|
-
if (userAgent.indexOf("Firefox") > -1) {
|
|
902
|
-
Platform.conicGradientRotate90 = true;
|
|
903
|
-
Platform.intWheelDeltaY = true;
|
|
904
|
-
}
|
|
905
|
-
else if (userAgent.indexOf("Safari") > -1 && userAgent.indexOf("Chrome") === -1) {
|
|
906
|
-
Platform.fullImageShadow = true;
|
|
907
|
-
}
|
|
908
|
-
if (userAgent.indexOf('Windows') > -1) {
|
|
909
|
-
Platform.os = 'Windows';
|
|
910
|
-
Platform.intWheelDeltaY = true;
|
|
911
|
-
}
|
|
912
|
-
else if (userAgent.indexOf('Mac') > -1) {
|
|
913
|
-
Platform.os = 'Mac';
|
|
914
|
-
}
|
|
915
|
-
else if (userAgent.indexOf('Linux') > -1) {
|
|
916
|
-
Platform.os = 'Linux';
|
|
959
|
+
if (decorationY)
|
|
960
|
+
canvas.fillRect(row.x, row.y + decorationY, row.width, decorationHeight);
|
|
961
|
+
}
|
|
917
962
|
}
|
|
918
963
|
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
const transform = get$4();
|
|
923
|
-
const swap = rotation && rotation !== 180;
|
|
924
|
-
const sw = box.width / (swap ? height : width);
|
|
925
|
-
const sh = box.height / (swap ? width : height);
|
|
926
|
-
const scale = mode === 'fit' ? Math.min(sw, sh) : Math.max(sw, sh);
|
|
927
|
-
const x = box.x + (box.width - width * scale) / 2;
|
|
928
|
-
const y = box.y + (box.height - height * scale) / 2;
|
|
929
|
-
translate$1(transform, x, y);
|
|
930
|
-
scaleHelper(transform, scale);
|
|
931
|
-
if (rotation)
|
|
932
|
-
rotateOfOuter$2(transform, { x: box.x + box.width / 2, y: box.y + box.height / 2 }, rotation);
|
|
933
|
-
data.scaleX = data.scaleY = scale;
|
|
934
|
-
data.transform = transform;
|
|
935
|
-
}
|
|
936
|
-
function clipMode(data, box, x, y, scaleX, scaleY, rotation) {
|
|
937
|
-
const transform = get$4();
|
|
938
|
-
translate$1(transform, box.x, box.y);
|
|
939
|
-
if (x || y)
|
|
940
|
-
translate$1(transform, x, y);
|
|
941
|
-
if (scaleX) {
|
|
942
|
-
scaleHelper(transform, scaleX, scaleY);
|
|
943
|
-
data.scaleX = transform.a;
|
|
944
|
-
data.scaleY = transform.d;
|
|
945
|
-
}
|
|
946
|
-
if (rotation)
|
|
947
|
-
rotate(transform, rotation);
|
|
948
|
-
data.transform = transform;
|
|
964
|
+
function fill(fill, ui, canvas) {
|
|
965
|
+
canvas.fillStyle = fill;
|
|
966
|
+
ui.__.__font ? fillText(ui, canvas) : (ui.__.windingRule ? canvas.fill(ui.__.windingRule) : canvas.fill());
|
|
949
967
|
}
|
|
950
|
-
function
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
968
|
+
function fills(fills, ui, canvas) {
|
|
969
|
+
let item;
|
|
970
|
+
const { windingRule, __font } = ui.__;
|
|
971
|
+
for (let i = 0, len = fills.length; i < len; i++) {
|
|
972
|
+
item = fills[i];
|
|
973
|
+
if (item.image && PaintImage.checkImage(ui, canvas, item, !__font))
|
|
974
|
+
continue;
|
|
975
|
+
if (item.style) {
|
|
976
|
+
canvas.fillStyle = item.style;
|
|
977
|
+
if (item.transform) {
|
|
978
|
+
canvas.save();
|
|
979
|
+
canvas.transform(item.transform);
|
|
980
|
+
if (item.blendMode)
|
|
981
|
+
canvas.blendMode = item.blendMode;
|
|
982
|
+
__font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
|
|
983
|
+
canvas.restore();
|
|
984
|
+
}
|
|
985
|
+
else {
|
|
986
|
+
if (item.blendMode) {
|
|
987
|
+
canvas.saveBlendMode(item.blendMode);
|
|
988
|
+
__font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
|
|
989
|
+
canvas.restoreBlendMode();
|
|
990
|
+
}
|
|
991
|
+
else {
|
|
992
|
+
__font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
|
|
993
|
+
}
|
|
994
|
+
}
|
|
964
995
|
}
|
|
965
996
|
}
|
|
966
|
-
origin.x = box.x;
|
|
967
|
-
origin.y = box.y;
|
|
968
|
-
if (x || y)
|
|
969
|
-
origin.x += x, origin.y += y;
|
|
970
|
-
translate$1(transform, origin.x, origin.y);
|
|
971
|
-
if (scaleX) {
|
|
972
|
-
scaleOfOuter$2(transform, origin, scaleX, scaleY);
|
|
973
|
-
data.scaleX = scaleX;
|
|
974
|
-
data.scaleY = scaleY;
|
|
975
|
-
}
|
|
976
|
-
data.transform = transform;
|
|
977
997
|
}
|
|
978
998
|
|
|
979
|
-
|
|
980
|
-
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
}
|
|
994
|
-
|
|
995
|
-
|
|
999
|
+
function strokeText(stroke, ui, canvas) {
|
|
1000
|
+
const { strokeAlign } = ui.__;
|
|
1001
|
+
const isStrokes = typeof stroke !== 'string';
|
|
1002
|
+
switch (strokeAlign) {
|
|
1003
|
+
case 'center':
|
|
1004
|
+
canvas.setStroke(isStrokes ? undefined : stroke, ui.__.strokeWidth, ui.__);
|
|
1005
|
+
isStrokes ? drawStrokesStyle(stroke, true, ui, canvas) : drawTextStroke(ui, canvas);
|
|
1006
|
+
break;
|
|
1007
|
+
case 'inside':
|
|
1008
|
+
drawAlignStroke('inside', stroke, isStrokes, ui, canvas);
|
|
1009
|
+
break;
|
|
1010
|
+
case 'outside':
|
|
1011
|
+
drawAlignStroke('outside', stroke, isStrokes, ui, canvas);
|
|
1012
|
+
break;
|
|
1013
|
+
}
|
|
1014
|
+
}
|
|
1015
|
+
function drawAlignStroke(align, stroke, isStrokes, ui, canvas) {
|
|
1016
|
+
const { __strokeWidth, __font } = ui.__;
|
|
1017
|
+
const out = canvas.getSameCanvas(true, true);
|
|
1018
|
+
out.setStroke(isStrokes ? undefined : stroke, __strokeWidth * 2, ui.__);
|
|
1019
|
+
out.font = __font;
|
|
1020
|
+
isStrokes ? drawStrokesStyle(stroke, true, ui, out) : drawTextStroke(ui, out);
|
|
1021
|
+
out.blendMode = align === 'outside' ? 'destination-out' : 'destination-in';
|
|
1022
|
+
fillText(ui, out);
|
|
1023
|
+
out.blendMode = 'normal';
|
|
1024
|
+
if (ui.__worldFlipped) {
|
|
1025
|
+
canvas.copyWorldByReset(out, ui.__nowWorld);
|
|
1026
|
+
}
|
|
1027
|
+
else {
|
|
1028
|
+
canvas.copyWorldToInner(out, ui.__nowWorld, ui.__layout.renderBounds);
|
|
1029
|
+
}
|
|
1030
|
+
out.recycle(ui.__nowWorld);
|
|
1031
|
+
}
|
|
1032
|
+
function drawTextStroke(ui, canvas) {
|
|
1033
|
+
let row;
|
|
1034
|
+
const { rows, decorationY, decorationHeight } = ui.__.__textDrawData;
|
|
1035
|
+
for (let i = 0, len = rows.length; i < len; i++) {
|
|
1036
|
+
row = rows[i];
|
|
1037
|
+
if (row.text) {
|
|
1038
|
+
canvas.strokeText(row.text, row.x, row.y);
|
|
1039
|
+
}
|
|
1040
|
+
else if (row.data) {
|
|
1041
|
+
row.data.forEach(charData => {
|
|
1042
|
+
canvas.strokeText(charData.char, charData.x, row.y);
|
|
1043
|
+
});
|
|
1044
|
+
}
|
|
1045
|
+
if (decorationY)
|
|
1046
|
+
canvas.strokeRect(row.x, row.y + decorationY, row.width, decorationHeight);
|
|
1047
|
+
}
|
|
1048
|
+
}
|
|
1049
|
+
function drawStrokesStyle(strokes, isText, ui, canvas) {
|
|
1050
|
+
let item;
|
|
1051
|
+
for (let i = 0, len = strokes.length; i < len; i++) {
|
|
1052
|
+
item = strokes[i];
|
|
1053
|
+
if (item.image && PaintImage.checkImage(ui, canvas, item, false))
|
|
1054
|
+
continue;
|
|
1055
|
+
if (item.style) {
|
|
1056
|
+
canvas.strokeStyle = item.style;
|
|
1057
|
+
if (item.blendMode) {
|
|
1058
|
+
canvas.saveBlendMode(item.blendMode);
|
|
1059
|
+
isText ? drawTextStroke(ui, canvas) : canvas.stroke();
|
|
1060
|
+
canvas.restoreBlendMode();
|
|
1061
|
+
}
|
|
1062
|
+
else {
|
|
1063
|
+
isText ? drawTextStroke(ui, canvas) : canvas.stroke();
|
|
1064
|
+
}
|
|
1065
|
+
}
|
|
1066
|
+
}
|
|
1067
|
+
}
|
|
1068
|
+
|
|
1069
|
+
function stroke(stroke, ui, canvas) {
|
|
1070
|
+
const options = ui.__;
|
|
1071
|
+
const { __strokeWidth, strokeAlign, __font } = options;
|
|
1072
|
+
if (!__strokeWidth)
|
|
1073
|
+
return;
|
|
1074
|
+
if (__font) {
|
|
1075
|
+
strokeText(stroke, ui, canvas);
|
|
1076
|
+
}
|
|
1077
|
+
else {
|
|
1078
|
+
switch (strokeAlign) {
|
|
1079
|
+
case 'center':
|
|
1080
|
+
canvas.setStroke(stroke, __strokeWidth, options);
|
|
1081
|
+
canvas.stroke();
|
|
1082
|
+
break;
|
|
1083
|
+
case 'inside':
|
|
1084
|
+
canvas.save();
|
|
1085
|
+
canvas.setStroke(stroke, __strokeWidth * 2, options);
|
|
1086
|
+
options.windingRule ? canvas.clip(options.windingRule) : canvas.clip();
|
|
1087
|
+
canvas.stroke();
|
|
1088
|
+
canvas.restore();
|
|
1089
|
+
break;
|
|
1090
|
+
case 'outside':
|
|
1091
|
+
const out = canvas.getSameCanvas(true, true);
|
|
1092
|
+
out.setStroke(stroke, __strokeWidth * 2, options);
|
|
1093
|
+
ui.__drawRenderPath(out);
|
|
1094
|
+
out.stroke();
|
|
1095
|
+
options.windingRule ? out.clip(options.windingRule) : out.clip();
|
|
1096
|
+
out.clearWorld(ui.__layout.renderBounds);
|
|
1097
|
+
if (ui.__worldFlipped) {
|
|
1098
|
+
canvas.copyWorldByReset(out, ui.__nowWorld);
|
|
1099
|
+
}
|
|
1100
|
+
else {
|
|
1101
|
+
canvas.copyWorldToInner(out, ui.__nowWorld, ui.__layout.renderBounds);
|
|
1102
|
+
}
|
|
1103
|
+
out.recycle(ui.__nowWorld);
|
|
1104
|
+
break;
|
|
1105
|
+
}
|
|
1106
|
+
}
|
|
1107
|
+
}
|
|
1108
|
+
function strokes(strokes, ui, canvas) {
|
|
1109
|
+
const options = ui.__;
|
|
1110
|
+
const { __strokeWidth, strokeAlign, __font } = options;
|
|
1111
|
+
if (!__strokeWidth)
|
|
1112
|
+
return;
|
|
1113
|
+
if (__font) {
|
|
1114
|
+
strokeText(strokes, ui, canvas);
|
|
1115
|
+
}
|
|
1116
|
+
else {
|
|
1117
|
+
switch (strokeAlign) {
|
|
1118
|
+
case 'center':
|
|
1119
|
+
canvas.setStroke(undefined, __strokeWidth, options);
|
|
1120
|
+
drawStrokesStyle(strokes, false, ui, canvas);
|
|
1121
|
+
break;
|
|
1122
|
+
case 'inside':
|
|
1123
|
+
canvas.save();
|
|
1124
|
+
canvas.setStroke(undefined, __strokeWidth * 2, options);
|
|
1125
|
+
options.windingRule ? canvas.clip(options.windingRule) : canvas.clip();
|
|
1126
|
+
drawStrokesStyle(strokes, false, ui, canvas);
|
|
1127
|
+
canvas.restore();
|
|
1128
|
+
break;
|
|
1129
|
+
case 'outside':
|
|
1130
|
+
const { renderBounds } = ui.__layout;
|
|
1131
|
+
const out = canvas.getSameCanvas(true, true);
|
|
1132
|
+
ui.__drawRenderPath(out);
|
|
1133
|
+
out.setStroke(undefined, __strokeWidth * 2, options);
|
|
1134
|
+
drawStrokesStyle(strokes, false, ui, out);
|
|
1135
|
+
options.windingRule ? out.clip(options.windingRule) : out.clip();
|
|
1136
|
+
out.clearWorld(renderBounds);
|
|
1137
|
+
if (ui.__worldFlipped) {
|
|
1138
|
+
canvas.copyWorldByReset(out, ui.__nowWorld);
|
|
1139
|
+
}
|
|
1140
|
+
else {
|
|
1141
|
+
canvas.copyWorldToInner(out, ui.__nowWorld, renderBounds);
|
|
1142
|
+
}
|
|
1143
|
+
out.recycle(ui.__nowWorld);
|
|
1144
|
+
break;
|
|
1145
|
+
}
|
|
1146
|
+
}
|
|
1147
|
+
}
|
|
1148
|
+
|
|
1149
|
+
const { getSpread, getOuterOf, getByMove, getIntersectData } = BoundsHelper;
|
|
1150
|
+
function shape(ui, current, options) {
|
|
1151
|
+
const canvas = current.getSameCanvas();
|
|
1152
|
+
const nowWorld = ui.__nowWorld;
|
|
1153
|
+
let bounds, fitMatrix, shapeBounds, worldCanvas;
|
|
1154
|
+
let { scaleX, scaleY } = nowWorld;
|
|
1155
|
+
if (scaleX < 0)
|
|
1156
|
+
scaleX = -scaleX;
|
|
1157
|
+
if (scaleY < 0)
|
|
1158
|
+
scaleY = -scaleY;
|
|
1159
|
+
if (current.bounds.includes(nowWorld)) {
|
|
1160
|
+
worldCanvas = canvas;
|
|
1161
|
+
bounds = shapeBounds = nowWorld;
|
|
1162
|
+
}
|
|
1163
|
+
else {
|
|
1164
|
+
const { renderShapeSpread: spread } = ui.__layout;
|
|
1165
|
+
const worldClipBounds = getIntersectData(spread ? getSpread(current.bounds, scaleX === scaleY ? spread * scaleX : [spread * scaleY, spread * scaleX]) : current.bounds, nowWorld);
|
|
1166
|
+
fitMatrix = current.bounds.getFitMatrix(worldClipBounds);
|
|
1167
|
+
let { a: fitScaleX, d: fitScaleY } = fitMatrix;
|
|
1168
|
+
if (fitMatrix.a < 1) {
|
|
1169
|
+
worldCanvas = current.getSameCanvas();
|
|
1170
|
+
ui.__renderShape(worldCanvas, options);
|
|
1171
|
+
scaleX *= fitScaleX;
|
|
1172
|
+
scaleY *= fitScaleY;
|
|
1173
|
+
}
|
|
1174
|
+
shapeBounds = getOuterOf(nowWorld, fitMatrix);
|
|
1175
|
+
bounds = getByMove(shapeBounds, -fitMatrix.e, -fitMatrix.f);
|
|
1176
|
+
if (options.matrix) {
|
|
1177
|
+
const { matrix } = options;
|
|
1178
|
+
fitMatrix.multiply(matrix);
|
|
1179
|
+
fitScaleX *= matrix.scaleX;
|
|
1180
|
+
fitScaleY *= matrix.scaleY;
|
|
1181
|
+
}
|
|
1182
|
+
options = Object.assign(Object.assign({}, options), { matrix: fitMatrix.withScale(fitScaleX, fitScaleY) });
|
|
1183
|
+
}
|
|
1184
|
+
ui.__renderShape(canvas, options);
|
|
1185
|
+
return {
|
|
1186
|
+
canvas, matrix: fitMatrix, bounds,
|
|
1187
|
+
worldCanvas, shapeBounds, scaleX, scaleY
|
|
1188
|
+
};
|
|
1189
|
+
}
|
|
1190
|
+
|
|
1191
|
+
let recycleMap;
|
|
1192
|
+
function compute(attrName, ui) {
|
|
1193
|
+
const data = ui.__, leafPaints = [];
|
|
1194
|
+
let paints = data.__input[attrName], hasOpacityPixel;
|
|
1195
|
+
if (!(paints instanceof Array))
|
|
1196
|
+
paints = [paints];
|
|
1197
|
+
recycleMap = PaintImage.recycleImage(attrName, data);
|
|
1198
|
+
for (let i = 0, len = paints.length, item; i < len; i++) {
|
|
1199
|
+
item = getLeafPaint(attrName, paints[i], ui);
|
|
1200
|
+
if (item)
|
|
1201
|
+
leafPaints.push(item);
|
|
1202
|
+
}
|
|
1203
|
+
data['_' + attrName] = leafPaints.length ? leafPaints : undefined;
|
|
1204
|
+
if (leafPaints.length && leafPaints[0].image)
|
|
1205
|
+
hasOpacityPixel = leafPaints[0].image.hasOpacityPixel;
|
|
1206
|
+
if (attrName === 'fill') {
|
|
1207
|
+
data.__pixelFill = hasOpacityPixel;
|
|
1208
|
+
}
|
|
1209
|
+
else {
|
|
1210
|
+
data.__pixelStroke = hasOpacityPixel;
|
|
1211
|
+
}
|
|
1212
|
+
}
|
|
1213
|
+
function getLeafPaint(attrName, paint, ui) {
|
|
1214
|
+
if (typeof paint !== 'object' || paint.visible === false || paint.opacity === 0)
|
|
1215
|
+
return undefined;
|
|
1216
|
+
const { boxBounds } = ui.__layout;
|
|
1217
|
+
switch (paint.type) {
|
|
1218
|
+
case 'solid':
|
|
1219
|
+
let { type, blendMode, color, opacity } = paint;
|
|
1220
|
+
return { type, blendMode, style: ColorConvert.string(color, opacity) };
|
|
1221
|
+
case 'image':
|
|
1222
|
+
return PaintImage.image(ui, attrName, paint, boxBounds, !recycleMap || !recycleMap[paint.url]);
|
|
1223
|
+
case 'linear':
|
|
1224
|
+
return PaintGradient.linearGradient(paint, boxBounds);
|
|
1225
|
+
case 'radial':
|
|
1226
|
+
return PaintGradient.radialGradient(paint, boxBounds);
|
|
1227
|
+
case 'angular':
|
|
1228
|
+
return PaintGradient.conicGradient(paint, boxBounds);
|
|
1229
|
+
default:
|
|
1230
|
+
return paint.r !== undefined ? { type: 'solid', style: ColorConvert.string(paint) } : undefined;
|
|
1231
|
+
}
|
|
1232
|
+
}
|
|
1233
|
+
|
|
1234
|
+
const PaintModule = {
|
|
1235
|
+
compute,
|
|
1236
|
+
fill,
|
|
1237
|
+
fills,
|
|
1238
|
+
fillText,
|
|
1239
|
+
stroke,
|
|
1240
|
+
strokes,
|
|
1241
|
+
strokeText,
|
|
1242
|
+
drawTextStroke,
|
|
1243
|
+
shape
|
|
1244
|
+
};
|
|
1245
|
+
|
|
1246
|
+
let origin = {};
|
|
1247
|
+
const { get: get$3, rotateOfOuter: rotateOfOuter$1, translate: translate$1, scaleOfOuter: scaleOfOuter$1, scale: scaleHelper, rotate } = MatrixHelper;
|
|
1248
|
+
function fillOrFitMode(data, box, x, y, scaleX, scaleY, rotation) {
|
|
1249
|
+
const transform = get$3();
|
|
1250
|
+
translate$1(transform, box.x + x, box.y + y);
|
|
1251
|
+
scaleHelper(transform, scaleX, scaleY);
|
|
1252
|
+
if (rotation)
|
|
1253
|
+
rotateOfOuter$1(transform, { x: box.x + box.width / 2, y: box.y + box.height / 2 }, rotation);
|
|
1254
|
+
data.transform = transform;
|
|
1255
|
+
}
|
|
1256
|
+
function clipMode(data, box, x, y, scaleX, scaleY, rotation) {
|
|
1257
|
+
const transform = get$3();
|
|
1258
|
+
translate$1(transform, box.x + x, box.y + y);
|
|
1259
|
+
if (scaleX)
|
|
1260
|
+
scaleHelper(transform, scaleX, scaleY);
|
|
1261
|
+
if (rotation)
|
|
1262
|
+
rotate(transform, rotation);
|
|
1263
|
+
data.transform = transform;
|
|
1264
|
+
}
|
|
1265
|
+
function repeatMode(data, box, width, height, x, y, scaleX, scaleY, rotation, align) {
|
|
1266
|
+
const transform = get$3();
|
|
1267
|
+
if (rotation) {
|
|
1268
|
+
if (align === 'center') {
|
|
1269
|
+
rotateOfOuter$1(transform, { x: width / 2, y: height / 2 }, rotation);
|
|
1270
|
+
}
|
|
1271
|
+
else {
|
|
1272
|
+
rotate(transform, rotation);
|
|
1273
|
+
switch (rotation) {
|
|
1274
|
+
case 90:
|
|
1275
|
+
translate$1(transform, height, 0);
|
|
1276
|
+
break;
|
|
1277
|
+
case 180:
|
|
1278
|
+
translate$1(transform, width, height);
|
|
1279
|
+
break;
|
|
1280
|
+
case 270:
|
|
1281
|
+
translate$1(transform, 0, width);
|
|
1282
|
+
break;
|
|
1283
|
+
}
|
|
1284
|
+
}
|
|
1285
|
+
}
|
|
1286
|
+
origin.x = box.x + x;
|
|
1287
|
+
origin.y = box.y + y;
|
|
1288
|
+
translate$1(transform, origin.x, origin.y);
|
|
1289
|
+
if (scaleX)
|
|
1290
|
+
scaleOfOuter$1(transform, origin, scaleX, scaleY);
|
|
1291
|
+
data.transform = transform;
|
|
1292
|
+
}
|
|
1293
|
+
|
|
1294
|
+
const { get: get$2, translate } = MatrixHelper;
|
|
1295
|
+
const tempBox = new Bounds();
|
|
1296
|
+
const tempPoint = {};
|
|
1297
|
+
function createData(leafPaint, image, paint, box) {
|
|
1298
|
+
const { blendMode } = paint;
|
|
1299
|
+
if (blendMode)
|
|
1300
|
+
leafPaint.blendMode = blendMode;
|
|
1301
|
+
leafPaint.data = getPatternData(paint, box, image);
|
|
1302
|
+
}
|
|
1303
|
+
function getPatternData(paint, box, image) {
|
|
1304
|
+
let { width, height } = image;
|
|
1305
|
+
if (paint.padding)
|
|
1306
|
+
box = tempBox.set(box).shrink(paint.padding);
|
|
1307
|
+
const { opacity, mode, align, offset, scale, size, rotation, repeat } = paint;
|
|
1308
|
+
const sameBox = box.width === width && box.height === height;
|
|
1309
|
+
const data = { mode };
|
|
1310
|
+
const swapSize = align !== 'center' && (rotation || 0) % 180 === 90;
|
|
1311
|
+
const swapWidth = swapSize ? height : width, swapHeight = swapSize ? width : height;
|
|
1312
|
+
let x = 0, y = 0, scaleX, scaleY;
|
|
1313
|
+
if (!mode || mode === 'cover' || mode === 'fit') {
|
|
1314
|
+
if (!sameBox || rotation) {
|
|
1315
|
+
const sw = box.width / swapWidth, sh = box.height / swapHeight;
|
|
1316
|
+
scaleX = scaleY = mode === 'fit' ? Math.min(sw, sh) : Math.max(sw, sh);
|
|
1317
|
+
x += (box.width - width * scaleX) / 2, y += (box.height - height * scaleY) / 2;
|
|
1318
|
+
}
|
|
1319
|
+
}
|
|
1320
|
+
else if (size) {
|
|
1321
|
+
scaleX = (typeof size === 'number' ? size : size.width) / width;
|
|
1322
|
+
scaleY = (typeof size === 'number' ? size : size.height) / height;
|
|
1323
|
+
}
|
|
1324
|
+
else if (scale) {
|
|
1325
|
+
scaleX = typeof scale === 'number' ? scale : scale.x;
|
|
996
1326
|
scaleY = typeof scale === 'number' ? scale : scale.y;
|
|
997
1327
|
}
|
|
1328
|
+
if (align) {
|
|
1329
|
+
const imageBounds = { x, y, width: swapWidth, height: swapHeight };
|
|
1330
|
+
if (scaleX)
|
|
1331
|
+
imageBounds.width *= scaleX, imageBounds.height *= scaleY;
|
|
1332
|
+
AlignHelper.toPoint(align, imageBounds, box, tempPoint, true);
|
|
1333
|
+
x += tempPoint.x, y += tempPoint.y;
|
|
1334
|
+
}
|
|
1335
|
+
if (offset)
|
|
1336
|
+
x += offset.x, y += offset.y;
|
|
998
1337
|
switch (mode) {
|
|
999
1338
|
case 'strench':
|
|
1000
1339
|
if (!sameBox)
|
|
1001
1340
|
width = box.width, height = box.height;
|
|
1002
|
-
if (box.x || box.y) {
|
|
1003
|
-
data.transform = get$3();
|
|
1004
|
-
translate(data.transform, box.x, box.y);
|
|
1005
|
-
}
|
|
1006
1341
|
break;
|
|
1342
|
+
case 'normal':
|
|
1007
1343
|
case 'clip':
|
|
1008
|
-
if (
|
|
1344
|
+
if (x || y || scaleX || rotation)
|
|
1009
1345
|
clipMode(data, box, x, y, scaleX, scaleY, rotation);
|
|
1010
1346
|
break;
|
|
1011
1347
|
case 'repeat':
|
|
1012
1348
|
if (!sameBox || scaleX || rotation)
|
|
1013
|
-
repeatMode(data, box, width, height, x, y, scaleX, scaleY, rotation);
|
|
1349
|
+
repeatMode(data, box, width, height, x, y, scaleX, scaleY, rotation, align);
|
|
1014
1350
|
if (!repeat)
|
|
1015
1351
|
data.repeat = 'repeat';
|
|
1016
1352
|
break;
|
|
1017
1353
|
case 'fit':
|
|
1018
1354
|
case 'cover':
|
|
1019
1355
|
default:
|
|
1020
|
-
if (
|
|
1021
|
-
fillOrFitMode(data,
|
|
1356
|
+
if (scaleX)
|
|
1357
|
+
fillOrFitMode(data, box, x, y, scaleX, scaleY, rotation);
|
|
1358
|
+
}
|
|
1359
|
+
if (!data.transform) {
|
|
1360
|
+
if (box.x || box.y) {
|
|
1361
|
+
data.transform = get$2();
|
|
1362
|
+
translate(data.transform, box.x, box.y);
|
|
1363
|
+
}
|
|
1364
|
+
}
|
|
1365
|
+
if (scaleX && mode !== 'strench') {
|
|
1366
|
+
data.scaleX = scaleX;
|
|
1367
|
+
data.scaleY = scaleY;
|
|
1022
1368
|
}
|
|
1023
1369
|
data.width = width;
|
|
1024
1370
|
data.height = height;
|
|
@@ -1026,112 +1372,108 @@ function createData(leafPaint, image, paint, box) {
|
|
|
1026
1372
|
data.opacity = opacity;
|
|
1027
1373
|
if (repeat)
|
|
1028
1374
|
data.repeat = typeof repeat === 'string' ? (repeat === 'x' ? 'repeat-x' : 'repeat-y') : 'repeat';
|
|
1375
|
+
return data;
|
|
1029
1376
|
}
|
|
1030
1377
|
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
|
|
1378
|
+
let cache, box = new Bounds();
|
|
1379
|
+
const { isSame } = BoundsHelper;
|
|
1380
|
+
function image(ui, attrName, paint, boxBounds, firstUse) {
|
|
1381
|
+
let leafPaint, event;
|
|
1382
|
+
const image = ImageManager.get(paint);
|
|
1383
|
+
if (cache && paint === cache.paint && isSame(boxBounds, cache.boxBounds)) {
|
|
1384
|
+
leafPaint = cache.leafPaint;
|
|
1385
|
+
}
|
|
1386
|
+
else {
|
|
1387
|
+
leafPaint = { type: paint.type, image };
|
|
1388
|
+
cache = image.use > 1 ? { leafPaint, paint, boxBounds: box.set(boxBounds) } : null;
|
|
1389
|
+
}
|
|
1390
|
+
if (firstUse || image.loading)
|
|
1391
|
+
event = { image, attrName, attrValue: paint };
|
|
1035
1392
|
if (image.ready) {
|
|
1036
|
-
|
|
1037
|
-
createData(leafPaint, image, attrValue, box);
|
|
1393
|
+
checkSizeAndCreateData(ui, attrName, paint, image, leafPaint, boxBounds);
|
|
1038
1394
|
if (firstUse) {
|
|
1039
|
-
|
|
1040
|
-
|
|
1395
|
+
onLoad(ui, event);
|
|
1396
|
+
onLoadSuccess(ui, event);
|
|
1041
1397
|
}
|
|
1042
1398
|
}
|
|
1043
1399
|
else if (image.error) {
|
|
1044
|
-
if (firstUse)
|
|
1045
|
-
ui.
|
|
1046
|
-
event.error = image.error;
|
|
1047
|
-
emit(ImageEvent.ERROR, event);
|
|
1048
|
-
}
|
|
1400
|
+
if (firstUse)
|
|
1401
|
+
onLoadError(ui, event, image.error);
|
|
1049
1402
|
}
|
|
1050
1403
|
else {
|
|
1404
|
+
ignoreRender(ui, true);
|
|
1051
1405
|
if (firstUse)
|
|
1052
|
-
|
|
1406
|
+
onLoad(ui, event);
|
|
1053
1407
|
leafPaint.loadId = image.load(() => {
|
|
1408
|
+
ignoreRender(ui, false);
|
|
1054
1409
|
if (!ui.destroyed) {
|
|
1055
|
-
if (
|
|
1056
|
-
|
|
1410
|
+
if (checkSizeAndCreateData(ui, attrName, paint, image, leafPaint, boxBounds)) {
|
|
1411
|
+
if (image.hasOpacityPixel)
|
|
1412
|
+
ui.__layout.hitCanvasChanged = true;
|
|
1057
1413
|
ui.forceUpdate('surface');
|
|
1058
1414
|
}
|
|
1059
|
-
|
|
1415
|
+
onLoadSuccess(ui, event);
|
|
1060
1416
|
}
|
|
1417
|
+
leafPaint.loadId = null;
|
|
1061
1418
|
}, (error) => {
|
|
1062
|
-
ui
|
|
1063
|
-
event
|
|
1064
|
-
|
|
1419
|
+
ignoreRender(ui, false);
|
|
1420
|
+
onLoadError(ui, event, error);
|
|
1421
|
+
leafPaint.loadId = null;
|
|
1065
1422
|
});
|
|
1066
1423
|
}
|
|
1067
1424
|
return leafPaint;
|
|
1068
1425
|
}
|
|
1069
|
-
function
|
|
1426
|
+
function checkSizeAndCreateData(ui, attrName, paint, image, leafPaint, boxBounds) {
|
|
1070
1427
|
if (attrName === 'fill' && !ui.__.__naturalWidth) {
|
|
1071
|
-
const
|
|
1072
|
-
|
|
1073
|
-
|
|
1074
|
-
if (
|
|
1428
|
+
const data = ui.__;
|
|
1429
|
+
data.__naturalWidth = image.width / data.pixelRatio;
|
|
1430
|
+
data.__naturalHeight = image.height / data.pixelRatio;
|
|
1431
|
+
if (data.__autoSide) {
|
|
1075
1432
|
ui.forceUpdate('width');
|
|
1076
1433
|
if (ui.__proxyData) {
|
|
1077
|
-
ui.setProxyAttr('width',
|
|
1078
|
-
ui.setProxyAttr('height',
|
|
1434
|
+
ui.setProxyAttr('width', data.width);
|
|
1435
|
+
ui.setProxyAttr('height', data.height);
|
|
1079
1436
|
}
|
|
1080
1437
|
return false;
|
|
1081
1438
|
}
|
|
1082
1439
|
}
|
|
1440
|
+
if (!leafPaint.data)
|
|
1441
|
+
createData(leafPaint, image, paint, boxBounds);
|
|
1083
1442
|
return true;
|
|
1084
1443
|
}
|
|
1085
|
-
function
|
|
1086
|
-
|
|
1087
|
-
|
|
1444
|
+
function onLoad(ui, event) {
|
|
1445
|
+
emit(ui, ImageEvent.LOAD, event);
|
|
1446
|
+
}
|
|
1447
|
+
function onLoadSuccess(ui, event) {
|
|
1448
|
+
emit(ui, ImageEvent.LOADED, event);
|
|
1449
|
+
}
|
|
1450
|
+
function onLoadError(ui, event, error) {
|
|
1451
|
+
event.error = error;
|
|
1452
|
+
ui.forceUpdate('surface');
|
|
1453
|
+
emit(ui, ImageEvent.ERROR, event);
|
|
1454
|
+
}
|
|
1455
|
+
function emit(ui, type, data) {
|
|
1456
|
+
if (ui.hasEvent(type))
|
|
1457
|
+
ui.emitEvent(new ImageEvent(type, data));
|
|
1458
|
+
}
|
|
1459
|
+
function ignoreRender(ui, value) {
|
|
1460
|
+
const { leafer } = ui;
|
|
1461
|
+
if (leafer && leafer.viewReady)
|
|
1462
|
+
leafer.renderer.ignore = value;
|
|
1088
1463
|
}
|
|
1089
1464
|
|
|
1090
|
-
|
|
1091
|
-
|
|
1092
|
-
|
|
1093
|
-
Permission to use, copy, modify, and/or distribute this software for any
|
|
1094
|
-
purpose with or without fee is hereby granted.
|
|
1095
|
-
|
|
1096
|
-
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
1097
|
-
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
1098
|
-
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
1099
|
-
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
1100
|
-
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
1101
|
-
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
1102
|
-
PERFORMANCE OF THIS SOFTWARE.
|
|
1103
|
-
***************************************************************************** */
|
|
1104
|
-
/* global Reflect, Promise, SuppressedError, Symbol */
|
|
1105
|
-
|
|
1106
|
-
|
|
1107
|
-
function __awaiter(thisArg, _arguments, P, generator) {
|
|
1108
|
-
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
1109
|
-
return new (P || (P = Promise))(function (resolve, reject) {
|
|
1110
|
-
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
1111
|
-
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
1112
|
-
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
1113
|
-
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
1114
|
-
});
|
|
1115
|
-
}
|
|
1116
|
-
|
|
1117
|
-
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
1118
|
-
var e = new Error(message);
|
|
1119
|
-
return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
|
|
1120
|
-
};
|
|
1121
|
-
|
|
1122
|
-
const Export$1 = {};
|
|
1123
|
-
|
|
1124
|
-
const { get: get$2, scale, copy: copy$1 } = MatrixHelper;
|
|
1465
|
+
const { get: get$1, scale, copy: copy$1 } = MatrixHelper;
|
|
1466
|
+
const { ceil, abs: abs$1 } = Math;
|
|
1125
1467
|
function createPattern(ui, paint, pixelRatio) {
|
|
1126
|
-
let { scaleX, scaleY } = ui.__world;
|
|
1468
|
+
let { scaleX, scaleY } = ImageManager.patternLocked ? ui.__world : ui.__nowWorld;
|
|
1127
1469
|
const id = scaleX + '-' + scaleY;
|
|
1128
1470
|
if (paint.patternId !== id && !ui.destroyed) {
|
|
1129
|
-
scaleX =
|
|
1130
|
-
scaleY =
|
|
1471
|
+
scaleX = abs$1(scaleX);
|
|
1472
|
+
scaleY = abs$1(scaleY);
|
|
1131
1473
|
const { image, data } = paint;
|
|
1132
1474
|
let imageScale, imageMatrix, { width, height, scaleX: sx, scaleY: sy, opacity, transform, repeat } = data;
|
|
1133
1475
|
if (sx) {
|
|
1134
|
-
imageMatrix = get$
|
|
1476
|
+
imageMatrix = get$1();
|
|
1135
1477
|
copy$1(imageMatrix, transform);
|
|
1136
1478
|
scale(imageMatrix, 1 / sx, 1 / sy);
|
|
1137
1479
|
scaleX *= sx;
|
|
@@ -1166,22 +1508,14 @@ function createPattern(ui, paint, pixelRatio) {
|
|
|
1166
1508
|
}
|
|
1167
1509
|
if (transform || scaleX !== 1 || scaleY !== 1) {
|
|
1168
1510
|
if (!imageMatrix) {
|
|
1169
|
-
imageMatrix = get$
|
|
1511
|
+
imageMatrix = get$1();
|
|
1170
1512
|
if (transform)
|
|
1171
1513
|
copy$1(imageMatrix, transform);
|
|
1172
1514
|
}
|
|
1173
1515
|
scale(imageMatrix, 1 / scaleX, 1 / scaleY);
|
|
1174
1516
|
}
|
|
1175
|
-
const
|
|
1176
|
-
|
|
1177
|
-
if (paint.transform)
|
|
1178
|
-
paint.transform = null;
|
|
1179
|
-
if (imageMatrix)
|
|
1180
|
-
pattern.setTransform ? pattern.setTransform(imageMatrix) : paint.transform = imageMatrix;
|
|
1181
|
-
}
|
|
1182
|
-
catch (_a) {
|
|
1183
|
-
paint.transform = imageMatrix;
|
|
1184
|
-
}
|
|
1517
|
+
const canvas = image.getCanvas(ceil(width) || 1, ceil(height) || 1, opacity);
|
|
1518
|
+
const pattern = image.getPattern(canvas, repeat || (Platform.origin.noRepeat || 'no-repeat'), imageMatrix, paint);
|
|
1185
1519
|
paint.style = pattern;
|
|
1186
1520
|
paint.patternId = id;
|
|
1187
1521
|
return true;
|
|
@@ -1191,9 +1525,41 @@ function createPattern(ui, paint, pixelRatio) {
|
|
|
1191
1525
|
}
|
|
1192
1526
|
}
|
|
1193
1527
|
|
|
1528
|
+
/******************************************************************************
|
|
1529
|
+
Copyright (c) Microsoft Corporation.
|
|
1530
|
+
|
|
1531
|
+
Permission to use, copy, modify, and/or distribute this software for any
|
|
1532
|
+
purpose with or without fee is hereby granted.
|
|
1533
|
+
|
|
1534
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
1535
|
+
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
1536
|
+
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
1537
|
+
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
1538
|
+
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
1539
|
+
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
1540
|
+
PERFORMANCE OF THIS SOFTWARE.
|
|
1541
|
+
***************************************************************************** */
|
|
1542
|
+
/* global Reflect, Promise, SuppressedError, Symbol */
|
|
1543
|
+
|
|
1544
|
+
|
|
1545
|
+
function __awaiter(thisArg, _arguments, P, generator) {
|
|
1546
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
1547
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
1548
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
1549
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
1550
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
1551
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
1552
|
+
});
|
|
1553
|
+
}
|
|
1554
|
+
|
|
1555
|
+
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
1556
|
+
var e = new Error(message);
|
|
1557
|
+
return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
|
|
1558
|
+
};
|
|
1559
|
+
|
|
1194
1560
|
const { abs } = Math;
|
|
1195
1561
|
function checkImage(ui, canvas, paint, allowPaint) {
|
|
1196
|
-
const { scaleX, scaleY } = ui.__world;
|
|
1562
|
+
const { scaleX, scaleY } = ImageManager.patternLocked ? ui.__world : ui.__nowWorld;
|
|
1197
1563
|
if (!paint.data || paint.patternId === scaleX + '-' + scaleY) {
|
|
1198
1564
|
return false;
|
|
1199
1565
|
}
|
|
@@ -1208,326 +1574,91 @@ function checkImage(ui, canvas, paint, allowPaint) {
|
|
|
1208
1574
|
width *= data.scaleX;
|
|
1209
1575
|
height *= data.scaleY;
|
|
1210
1576
|
}
|
|
1211
|
-
allowPaint = width * height > Platform.image.maxCacheSize;
|
|
1577
|
+
allowPaint = (width * height > Platform.image.maxCacheSize) || Export.running;
|
|
1212
1578
|
}
|
|
1213
1579
|
else {
|
|
1214
1580
|
allowPaint = false;
|
|
1215
1581
|
}
|
|
1216
1582
|
}
|
|
1217
|
-
if (allowPaint) {
|
|
1218
|
-
canvas.save();
|
|
1219
|
-
canvas.clip();
|
|
1220
|
-
if (paint.blendMode)
|
|
1221
|
-
canvas.blendMode = paint.blendMode;
|
|
1222
|
-
if (data.opacity)
|
|
1223
|
-
canvas.opacity *= data.opacity;
|
|
1224
|
-
if (data.transform)
|
|
1225
|
-
canvas.transform(data.transform);
|
|
1226
|
-
canvas.drawImage(paint.image.view, 0, 0, data.width, data.height);
|
|
1227
|
-
canvas.restore();
|
|
1228
|
-
return true;
|
|
1229
|
-
}
|
|
1230
|
-
else {
|
|
1231
|
-
if (!paint.style || Export
|
|
1232
|
-
createPattern(ui, paint, canvas.pixelRatio);
|
|
1233
|
-
}
|
|
1234
|
-
else {
|
|
1235
|
-
if (!paint.patternTask) {
|
|
1236
|
-
paint.patternTask = ImageManager.patternTasker.add(() => __awaiter(this, void 0, void 0, function* () {
|
|
1237
|
-
paint.patternTask = null;
|
|
1238
|
-
if (canvas.bounds.hit(ui.__world))
|
|
1239
|
-
createPattern(ui, paint, canvas.pixelRatio);
|
|
1240
|
-
ui.forceUpdate('surface');
|
|
1241
|
-
}), 300);
|
|
1242
|
-
}
|
|
1243
|
-
}
|
|
1244
|
-
return false;
|
|
1245
|
-
}
|
|
1246
|
-
}
|
|
1247
|
-
}
|
|
1248
|
-
|
|
1249
|
-
function recycleImage(attrName, data) {
|
|
1250
|
-
const paints = data['_' + attrName];
|
|
1251
|
-
if (paints instanceof Array) {
|
|
1252
|
-
let image, recycleMap, input, url;
|
|
1253
|
-
for (let i = 0, len = paints.length; i < len; i++) {
|
|
1254
|
-
image = paints[i].image;
|
|
1255
|
-
url = image && image.url;
|
|
1256
|
-
if (url) {
|
|
1257
|
-
if (!recycleMap)
|
|
1258
|
-
recycleMap = {};
|
|
1259
|
-
recycleMap[url] = true;
|
|
1260
|
-
ImageManager.recycle(image);
|
|
1261
|
-
if (image.loading) {
|
|
1262
|
-
if (!input) {
|
|
1263
|
-
input = (data.__input && data.__input[attrName]) || [];
|
|
1264
|
-
if (!(input instanceof Array))
|
|
1265
|
-
input = [input];
|
|
1266
|
-
}
|
|
1267
|
-
image.unload(paints[i].loadId, !input.some((item) => item.url === url));
|
|
1268
|
-
}
|
|
1269
|
-
}
|
|
1270
|
-
}
|
|
1271
|
-
return recycleMap;
|
|
1272
|
-
}
|
|
1273
|
-
return null;
|
|
1274
|
-
}
|
|
1275
|
-
|
|
1276
|
-
function fillText(ui, canvas) {
|
|
1277
|
-
let row;
|
|
1278
|
-
const { rows, decorationY, decorationHeight } = ui.__.__textDrawData;
|
|
1279
|
-
for (let i = 0, len = rows.length; i < len; i++) {
|
|
1280
|
-
row = rows[i];
|
|
1281
|
-
if (row.text) {
|
|
1282
|
-
canvas.fillText(row.text, row.x, row.y);
|
|
1283
|
-
}
|
|
1284
|
-
else if (row.data) {
|
|
1285
|
-
row.data.forEach(charData => {
|
|
1286
|
-
canvas.fillText(charData.char, charData.x, row.y);
|
|
1287
|
-
});
|
|
1288
|
-
}
|
|
1289
|
-
if (decorationY)
|
|
1290
|
-
canvas.fillRect(row.x, row.y + decorationY, row.width, decorationHeight);
|
|
1291
|
-
}
|
|
1292
|
-
}
|
|
1293
|
-
|
|
1294
|
-
function fill(fill, ui, canvas) {
|
|
1295
|
-
canvas.fillStyle = fill;
|
|
1296
|
-
ui.__.__font ? fillText(ui, canvas) : (ui.__.windingRule ? canvas.fill(ui.__.windingRule) : canvas.fill());
|
|
1297
|
-
}
|
|
1298
|
-
function fills(fills, ui, canvas) {
|
|
1299
|
-
let item;
|
|
1300
|
-
const { windingRule, __font } = ui.__;
|
|
1301
|
-
for (let i = 0, len = fills.length; i < len; i++) {
|
|
1302
|
-
item = fills[i];
|
|
1303
|
-
if (item.image && checkImage(ui, canvas, item, !__font))
|
|
1304
|
-
continue;
|
|
1305
|
-
if (item.style) {
|
|
1306
|
-
canvas.fillStyle = item.style;
|
|
1307
|
-
if (item.transform) {
|
|
1308
|
-
canvas.save();
|
|
1309
|
-
canvas.transform(item.transform);
|
|
1310
|
-
if (item.blendMode)
|
|
1311
|
-
canvas.blendMode = item.blendMode;
|
|
1312
|
-
__font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
|
|
1313
|
-
canvas.restore();
|
|
1314
|
-
}
|
|
1315
|
-
else {
|
|
1316
|
-
if (item.blendMode) {
|
|
1317
|
-
canvas.saveBlendMode(item.blendMode);
|
|
1318
|
-
__font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
|
|
1319
|
-
canvas.restoreBlendMode();
|
|
1320
|
-
}
|
|
1321
|
-
else {
|
|
1322
|
-
__font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
|
|
1323
|
-
}
|
|
1324
|
-
}
|
|
1325
|
-
}
|
|
1326
|
-
}
|
|
1327
|
-
}
|
|
1328
|
-
|
|
1329
|
-
function strokeText(stroke, ui, canvas, renderOptions) {
|
|
1330
|
-
const { strokeAlign } = ui.__;
|
|
1331
|
-
const isStrokes = typeof stroke !== 'string';
|
|
1332
|
-
switch (strokeAlign) {
|
|
1333
|
-
case 'center':
|
|
1334
|
-
canvas.setStroke(isStrokes ? undefined : stroke, ui.__.strokeWidth, ui.__);
|
|
1335
|
-
isStrokes ? drawStrokesStyle(stroke, true, ui, canvas) : drawTextStroke(ui, canvas);
|
|
1336
|
-
break;
|
|
1337
|
-
case 'inside':
|
|
1338
|
-
drawAlignStroke('inside', stroke, isStrokes, ui, canvas, renderOptions);
|
|
1339
|
-
break;
|
|
1340
|
-
case 'outside':
|
|
1341
|
-
drawAlignStroke('outside', stroke, isStrokes, ui, canvas, renderOptions);
|
|
1342
|
-
break;
|
|
1343
|
-
}
|
|
1344
|
-
}
|
|
1345
|
-
function drawAlignStroke(align, stroke, isStrokes, ui, canvas, renderOptions) {
|
|
1346
|
-
const { strokeWidth, __font } = ui.__;
|
|
1347
|
-
const out = canvas.getSameCanvas(true);
|
|
1348
|
-
out.setStroke(isStrokes ? undefined : stroke, strokeWidth * 2, ui.__);
|
|
1349
|
-
out.font = __font;
|
|
1350
|
-
isStrokes ? drawStrokesStyle(stroke, true, ui, out) : drawTextStroke(ui, out);
|
|
1351
|
-
out.blendMode = align === 'outside' ? 'destination-out' : 'destination-in';
|
|
1352
|
-
fillText(ui, out);
|
|
1353
|
-
out.blendMode = 'normal';
|
|
1354
|
-
if (ui.__worldFlipped || renderOptions.matrix) {
|
|
1355
|
-
canvas.copyWorldByReset(out);
|
|
1356
|
-
}
|
|
1357
|
-
else {
|
|
1358
|
-
canvas.copyWorldToInner(out, ui.__world, ui.__layout.renderBounds);
|
|
1359
|
-
}
|
|
1360
|
-
out.recycle();
|
|
1361
|
-
}
|
|
1362
|
-
function drawTextStroke(ui, canvas) {
|
|
1363
|
-
let row;
|
|
1364
|
-
const { rows, decorationY, decorationHeight } = ui.__.__textDrawData;
|
|
1365
|
-
for (let i = 0, len = rows.length; i < len; i++) {
|
|
1366
|
-
row = rows[i];
|
|
1367
|
-
if (row.text) {
|
|
1368
|
-
canvas.strokeText(row.text, row.x, row.y);
|
|
1369
|
-
}
|
|
1370
|
-
else if (row.data) {
|
|
1371
|
-
row.data.forEach(charData => {
|
|
1372
|
-
canvas.strokeText(charData.char, charData.x, row.y);
|
|
1373
|
-
});
|
|
1374
|
-
}
|
|
1375
|
-
if (decorationY)
|
|
1376
|
-
canvas.strokeRect(row.x, row.y + decorationY, row.width, decorationHeight);
|
|
1377
|
-
}
|
|
1378
|
-
}
|
|
1379
|
-
function drawStrokesStyle(strokes, isText, ui, canvas) {
|
|
1380
|
-
let item;
|
|
1381
|
-
for (let i = 0, len = strokes.length; i < len; i++) {
|
|
1382
|
-
item = strokes[i];
|
|
1383
|
-
if (item.image && checkImage(ui, canvas, item, false))
|
|
1384
|
-
continue;
|
|
1385
|
-
if (item.style) {
|
|
1386
|
-
canvas.strokeStyle = item.style;
|
|
1387
|
-
if (item.blendMode) {
|
|
1388
|
-
canvas.saveBlendMode(item.blendMode);
|
|
1389
|
-
isText ? drawTextStroke(ui, canvas) : canvas.stroke();
|
|
1390
|
-
canvas.restoreBlendMode();
|
|
1583
|
+
if (allowPaint) {
|
|
1584
|
+
canvas.save();
|
|
1585
|
+
canvas.clip();
|
|
1586
|
+
if (paint.blendMode)
|
|
1587
|
+
canvas.blendMode = paint.blendMode;
|
|
1588
|
+
if (data.opacity)
|
|
1589
|
+
canvas.opacity *= data.opacity;
|
|
1590
|
+
if (data.transform)
|
|
1591
|
+
canvas.transform(data.transform);
|
|
1592
|
+
canvas.drawImage(paint.image.view, 0, 0, data.width, data.height);
|
|
1593
|
+
canvas.restore();
|
|
1594
|
+
return true;
|
|
1595
|
+
}
|
|
1596
|
+
else {
|
|
1597
|
+
if (!paint.style || Export.running) {
|
|
1598
|
+
createPattern(ui, paint, canvas.pixelRatio);
|
|
1391
1599
|
}
|
|
1392
1600
|
else {
|
|
1393
|
-
|
|
1601
|
+
if (!paint.patternTask) {
|
|
1602
|
+
paint.patternTask = ImageManager.patternTasker.add(() => __awaiter(this, void 0, void 0, function* () {
|
|
1603
|
+
paint.patternTask = null;
|
|
1604
|
+
if (canvas.bounds.hit(ui.__nowWorld))
|
|
1605
|
+
createPattern(ui, paint, canvas.pixelRatio);
|
|
1606
|
+
ui.forceUpdate('surface');
|
|
1607
|
+
}), 300);
|
|
1608
|
+
}
|
|
1394
1609
|
}
|
|
1610
|
+
return false;
|
|
1395
1611
|
}
|
|
1396
1612
|
}
|
|
1397
1613
|
}
|
|
1398
1614
|
|
|
1399
|
-
function
|
|
1400
|
-
const
|
|
1401
|
-
|
|
1402
|
-
|
|
1403
|
-
|
|
1404
|
-
|
|
1405
|
-
|
|
1406
|
-
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1410
|
-
|
|
1411
|
-
|
|
1412
|
-
|
|
1413
|
-
|
|
1414
|
-
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
|
|
1418
|
-
canvas.restore();
|
|
1419
|
-
break;
|
|
1420
|
-
case 'outside':
|
|
1421
|
-
const out = canvas.getSameCanvas(true);
|
|
1422
|
-
out.setStroke(stroke, strokeWidth * 2, ui.__);
|
|
1423
|
-
ui.__drawRenderPath(out);
|
|
1424
|
-
out.stroke();
|
|
1425
|
-
options.windingRule ? out.clip(options.windingRule) : out.clip();
|
|
1426
|
-
out.clearWorld(ui.__layout.renderBounds);
|
|
1427
|
-
if (ui.__worldFlipped || renderOptions.matrix) {
|
|
1428
|
-
canvas.copyWorldByReset(out);
|
|
1429
|
-
}
|
|
1430
|
-
else {
|
|
1431
|
-
canvas.copyWorldToInner(out, ui.__world, ui.__layout.renderBounds);
|
|
1432
|
-
}
|
|
1433
|
-
out.recycle();
|
|
1434
|
-
break;
|
|
1435
|
-
}
|
|
1436
|
-
}
|
|
1437
|
-
}
|
|
1438
|
-
function strokes(strokes, ui, canvas, renderOptions) {
|
|
1439
|
-
const options = ui.__;
|
|
1440
|
-
const { strokeWidth, strokeAlign, __font } = options;
|
|
1441
|
-
if (!strokeWidth)
|
|
1442
|
-
return;
|
|
1443
|
-
if (__font) {
|
|
1444
|
-
strokeText(strokes, ui, canvas, renderOptions);
|
|
1445
|
-
}
|
|
1446
|
-
else {
|
|
1447
|
-
switch (strokeAlign) {
|
|
1448
|
-
case 'center':
|
|
1449
|
-
canvas.setStroke(undefined, strokeWidth, options);
|
|
1450
|
-
drawStrokesStyle(strokes, false, ui, canvas);
|
|
1451
|
-
break;
|
|
1452
|
-
case 'inside':
|
|
1453
|
-
canvas.save();
|
|
1454
|
-
canvas.setStroke(undefined, strokeWidth * 2, options);
|
|
1455
|
-
options.windingRule ? canvas.clip(options.windingRule) : canvas.clip();
|
|
1456
|
-
drawStrokesStyle(strokes, false, ui, canvas);
|
|
1457
|
-
canvas.restore();
|
|
1458
|
-
break;
|
|
1459
|
-
case 'outside':
|
|
1460
|
-
const { renderBounds } = ui.__layout;
|
|
1461
|
-
const out = canvas.getSameCanvas(true);
|
|
1462
|
-
ui.__drawRenderPath(out);
|
|
1463
|
-
out.setStroke(undefined, strokeWidth * 2, ui.__);
|
|
1464
|
-
drawStrokesStyle(strokes, false, ui, out);
|
|
1465
|
-
options.windingRule ? out.clip(options.windingRule) : out.clip();
|
|
1466
|
-
out.clearWorld(renderBounds);
|
|
1467
|
-
if (ui.__worldFlipped || renderOptions.matrix) {
|
|
1468
|
-
canvas.copyWorldByReset(out);
|
|
1469
|
-
}
|
|
1470
|
-
else {
|
|
1471
|
-
canvas.copyWorldToInner(out, ui.__world, renderBounds);
|
|
1615
|
+
function recycleImage(attrName, data) {
|
|
1616
|
+
const paints = data['_' + attrName];
|
|
1617
|
+
if (paints instanceof Array) {
|
|
1618
|
+
let image, recycleMap, input, url;
|
|
1619
|
+
for (let i = 0, len = paints.length; i < len; i++) {
|
|
1620
|
+
image = paints[i].image;
|
|
1621
|
+
url = image && image.url;
|
|
1622
|
+
if (url) {
|
|
1623
|
+
if (!recycleMap)
|
|
1624
|
+
recycleMap = {};
|
|
1625
|
+
recycleMap[url] = true;
|
|
1626
|
+
ImageManager.recycle(image);
|
|
1627
|
+
if (image.loading) {
|
|
1628
|
+
if (!input) {
|
|
1629
|
+
input = (data.__input && data.__input[attrName]) || [];
|
|
1630
|
+
if (!(input instanceof Array))
|
|
1631
|
+
input = [input];
|
|
1632
|
+
}
|
|
1633
|
+
image.unload(paints[i].loadId, !input.some((item) => item.url === url));
|
|
1472
1634
|
}
|
|
1473
|
-
|
|
1474
|
-
break;
|
|
1635
|
+
}
|
|
1475
1636
|
}
|
|
1637
|
+
return recycleMap;
|
|
1476
1638
|
}
|
|
1639
|
+
return null;
|
|
1477
1640
|
}
|
|
1478
1641
|
|
|
1479
|
-
const
|
|
1480
|
-
|
|
1481
|
-
|
|
1482
|
-
|
|
1483
|
-
|
|
1484
|
-
|
|
1485
|
-
|
|
1486
|
-
|
|
1487
|
-
|
|
1488
|
-
|
|
1489
|
-
|
|
1490
|
-
if (!current.bounds.includes(__world, options.matrix)) {
|
|
1491
|
-
const { renderShapeSpread: spread } = ui.__layout;
|
|
1492
|
-
const worldClipBounds = getIntersectData(spread ? getSpread(current.bounds, spread * scaleX, spread * scaleY) : current.bounds, __world, options.matrix);
|
|
1493
|
-
matrix = current.bounds.getFitMatrix(worldClipBounds);
|
|
1494
|
-
if (matrix.a < 1) {
|
|
1495
|
-
worldCanvas = current.getSameCanvas();
|
|
1496
|
-
ui.__renderShape(worldCanvas, options);
|
|
1497
|
-
scaleX *= matrix.a;
|
|
1498
|
-
scaleY *= matrix.d;
|
|
1499
|
-
}
|
|
1500
|
-
shapeBounds = getOuterOf(__world, matrix);
|
|
1501
|
-
bounds = getByMove(shapeBounds, -matrix.e, -matrix.f);
|
|
1502
|
-
if (options.matrix)
|
|
1503
|
-
matrix.multiply(options.matrix);
|
|
1504
|
-
options = Object.assign(Object.assign({}, options), { matrix });
|
|
1505
|
-
}
|
|
1506
|
-
else {
|
|
1507
|
-
if (options.matrix) {
|
|
1508
|
-
scaleX *= options.matrix.a;
|
|
1509
|
-
scaleY *= options.matrix.d;
|
|
1510
|
-
bounds = shapeBounds = getOuterOf(__world, options.matrix);
|
|
1511
|
-
}
|
|
1512
|
-
else {
|
|
1513
|
-
bounds = shapeBounds = __world;
|
|
1514
|
-
}
|
|
1515
|
-
worldCanvas = canvas;
|
|
1516
|
-
}
|
|
1517
|
-
ui.__renderShape(canvas, options);
|
|
1518
|
-
return {
|
|
1519
|
-
canvas, matrix, bounds,
|
|
1520
|
-
worldCanvas, shapeBounds, scaleX, scaleY
|
|
1521
|
-
};
|
|
1522
|
-
}
|
|
1642
|
+
const PaintImageModule = {
|
|
1643
|
+
image,
|
|
1644
|
+
checkImage,
|
|
1645
|
+
createPattern,
|
|
1646
|
+
recycleImage,
|
|
1647
|
+
createData,
|
|
1648
|
+
getPatternData,
|
|
1649
|
+
fillOrFitMode,
|
|
1650
|
+
clipMode,
|
|
1651
|
+
repeatMode
|
|
1652
|
+
};
|
|
1523
1653
|
|
|
1524
|
-
const
|
|
1525
|
-
const
|
|
1654
|
+
const { toPoint: toPoint$2 } = AroundHelper;
|
|
1655
|
+
const realFrom$2 = {};
|
|
1656
|
+
const realTo$2 = {};
|
|
1526
1657
|
function linearGradient(paint, box) {
|
|
1527
1658
|
let { from, to, type, blendMode, opacity } = paint;
|
|
1528
|
-
from ||
|
|
1529
|
-
to ||
|
|
1530
|
-
const style = Platform.canvas.createLinearGradient(
|
|
1659
|
+
toPoint$2(from || 'top', box, realFrom$2);
|
|
1660
|
+
toPoint$2(to || 'bottom', box, realTo$2);
|
|
1661
|
+
const style = Platform.canvas.createLinearGradient(realFrom$2.x, realFrom$2.y, realTo$2.x, realTo$2.y);
|
|
1531
1662
|
applyStops(style, paint.stops, opacity);
|
|
1532
1663
|
const data = { type, style };
|
|
1533
1664
|
if (blendMode)
|
|
@@ -1538,137 +1669,84 @@ function applyStops(gradient, stops, opacity) {
|
|
|
1538
1669
|
let stop;
|
|
1539
1670
|
for (let i = 0, len = stops.length; i < len; i++) {
|
|
1540
1671
|
stop = stops[i];
|
|
1541
|
-
|
|
1672
|
+
if (typeof stop === 'string') {
|
|
1673
|
+
gradient.addColorStop(i / (len - 1), ColorConvert.string(stop, opacity));
|
|
1674
|
+
}
|
|
1675
|
+
else {
|
|
1676
|
+
gradient.addColorStop(stop.offset, ColorConvert.string(stop.color, opacity));
|
|
1677
|
+
}
|
|
1542
1678
|
}
|
|
1543
1679
|
}
|
|
1544
1680
|
|
|
1545
|
-
const {
|
|
1546
|
-
const { get
|
|
1547
|
-
const
|
|
1548
|
-
const defaultTo$1 = { x: 0.5, y: 1 };
|
|
1681
|
+
const { getAngle, getDistance: getDistance$1 } = PointHelper;
|
|
1682
|
+
const { get, rotateOfOuter, scaleOfOuter } = MatrixHelper;
|
|
1683
|
+
const { toPoint: toPoint$1 } = AroundHelper;
|
|
1549
1684
|
const realFrom$1 = {};
|
|
1550
1685
|
const realTo$1 = {};
|
|
1551
1686
|
function radialGradient(paint, box) {
|
|
1552
1687
|
let { from, to, type, opacity, blendMode, stretch } = paint;
|
|
1553
|
-
from ||
|
|
1554
|
-
to ||
|
|
1555
|
-
const { x, y, width, height } = box;
|
|
1556
|
-
set$1(realFrom$1, x + from.x * width, y + from.y * height);
|
|
1557
|
-
set$1(realTo$1, x + to.x * width, y + to.y * height);
|
|
1558
|
-
let transform;
|
|
1559
|
-
if (width !== height || stretch) {
|
|
1560
|
-
transform = get$1();
|
|
1561
|
-
scaleOfOuter$1(transform, realFrom$1, width / height * (stretch || 1), 1);
|
|
1562
|
-
rotateOfOuter$1(transform, realFrom$1, getAngle$1(realFrom$1, realTo$1) + 90);
|
|
1563
|
-
}
|
|
1688
|
+
toPoint$1(from || 'center', box, realFrom$1);
|
|
1689
|
+
toPoint$1(to || 'bottom', box, realTo$1);
|
|
1564
1690
|
const style = Platform.canvas.createRadialGradient(realFrom$1.x, realFrom$1.y, 0, realFrom$1.x, realFrom$1.y, getDistance$1(realFrom$1, realTo$1));
|
|
1565
1691
|
applyStops(style, paint.stops, opacity);
|
|
1566
|
-
const data = { type, style
|
|
1692
|
+
const data = { type, style };
|
|
1693
|
+
const transform = getTransform(box, realFrom$1, realTo$1, stretch, true);
|
|
1694
|
+
if (transform)
|
|
1695
|
+
data.transform = transform;
|
|
1567
1696
|
if (blendMode)
|
|
1568
1697
|
data.blendMode = blendMode;
|
|
1569
1698
|
return data;
|
|
1570
1699
|
}
|
|
1700
|
+
function getTransform(box, from, to, stretch, rotate90) {
|
|
1701
|
+
let transform;
|
|
1702
|
+
const { width, height } = box;
|
|
1703
|
+
if (width !== height || stretch) {
|
|
1704
|
+
const angle = getAngle(from, to);
|
|
1705
|
+
transform = get();
|
|
1706
|
+
if (rotate90) {
|
|
1707
|
+
scaleOfOuter(transform, from, width / height * (stretch || 1), 1);
|
|
1708
|
+
rotateOfOuter(transform, from, angle + 90);
|
|
1709
|
+
}
|
|
1710
|
+
else {
|
|
1711
|
+
scaleOfOuter(transform, from, 1, width / height * (stretch || 1));
|
|
1712
|
+
rotateOfOuter(transform, from, angle);
|
|
1713
|
+
}
|
|
1714
|
+
}
|
|
1715
|
+
return transform;
|
|
1716
|
+
}
|
|
1571
1717
|
|
|
1572
|
-
const {
|
|
1573
|
-
const {
|
|
1574
|
-
const defaultFrom = { x: 0.5, y: 0.5 };
|
|
1575
|
-
const defaultTo = { x: 0.5, y: 1 };
|
|
1718
|
+
const { getDistance } = PointHelper;
|
|
1719
|
+
const { toPoint } = AroundHelper;
|
|
1576
1720
|
const realFrom = {};
|
|
1577
1721
|
const realTo = {};
|
|
1578
1722
|
function conicGradient(paint, box) {
|
|
1579
1723
|
let { from, to, type, opacity, blendMode, stretch } = paint;
|
|
1580
|
-
from ||
|
|
1581
|
-
to ||
|
|
1582
|
-
const { x, y, width, height } = box;
|
|
1583
|
-
set(realFrom, x + from.x * width, y + from.y * height);
|
|
1584
|
-
set(realTo, x + to.x * width, y + to.y * height);
|
|
1585
|
-
const transform = get();
|
|
1586
|
-
const angle = getAngle(realFrom, realTo);
|
|
1587
|
-
if (Platform.conicGradientRotate90) {
|
|
1588
|
-
scaleOfOuter(transform, realFrom, width / height * (stretch || 1), 1);
|
|
1589
|
-
rotateOfOuter(transform, realFrom, angle + 90);
|
|
1590
|
-
}
|
|
1591
|
-
else {
|
|
1592
|
-
scaleOfOuter(transform, realFrom, 1, width / height * (stretch || 1));
|
|
1593
|
-
rotateOfOuter(transform, realFrom, angle);
|
|
1594
|
-
}
|
|
1724
|
+
toPoint(from || 'center', box, realFrom);
|
|
1725
|
+
toPoint(to || 'bottom', box, realTo);
|
|
1595
1726
|
const style = Platform.conicGradientSupport ? Platform.canvas.createConicGradient(0, realFrom.x, realFrom.y) : Platform.canvas.createRadialGradient(realFrom.x, realFrom.y, 0, realFrom.x, realFrom.y, getDistance(realFrom, realTo));
|
|
1596
1727
|
applyStops(style, paint.stops, opacity);
|
|
1597
|
-
const data = { type, style
|
|
1728
|
+
const data = { type, style };
|
|
1729
|
+
const transform = getTransform(box, realFrom, realTo, stretch || 1, Platform.conicGradientRotate90);
|
|
1730
|
+
if (transform)
|
|
1731
|
+
data.transform = transform;
|
|
1598
1732
|
if (blendMode)
|
|
1599
1733
|
data.blendMode = blendMode;
|
|
1600
1734
|
return data;
|
|
1601
1735
|
}
|
|
1602
1736
|
|
|
1603
|
-
|
|
1604
|
-
|
|
1605
|
-
|
|
1606
|
-
|
|
1607
|
-
|
|
1608
|
-
|
|
1609
|
-
if (!(paints instanceof Array))
|
|
1610
|
-
paints = [paints];
|
|
1611
|
-
recycleMap = recycleImage(attrName, data);
|
|
1612
|
-
for (let i = 0, len = paints.length; i < len; i++) {
|
|
1613
|
-
item = getLeafPaint(attrName, paints[i], ui);
|
|
1614
|
-
if (item)
|
|
1615
|
-
value.push(item);
|
|
1616
|
-
}
|
|
1617
|
-
data['_' + attrName] = value.length ? value : undefined;
|
|
1618
|
-
let isPixel;
|
|
1619
|
-
if (paints.length === 1) {
|
|
1620
|
-
const paint = paints[0];
|
|
1621
|
-
if (paint.type === 'image')
|
|
1622
|
-
isPixel = ImageManager$1.isPixel(paint);
|
|
1623
|
-
}
|
|
1624
|
-
if (attrName === 'fill') {
|
|
1625
|
-
data.__pixelFill = isPixel;
|
|
1626
|
-
}
|
|
1627
|
-
else {
|
|
1628
|
-
data.__pixelStroke = isPixel;
|
|
1629
|
-
}
|
|
1630
|
-
}
|
|
1631
|
-
function getLeafPaint(attrName, paint, ui) {
|
|
1632
|
-
if (typeof paint !== 'object' || paint.visible === false || paint.opacity === 0)
|
|
1633
|
-
return undefined;
|
|
1634
|
-
const { boxBounds } = ui.__layout;
|
|
1635
|
-
switch (paint.type) {
|
|
1636
|
-
case 'solid':
|
|
1637
|
-
let { type, blendMode, color, opacity } = paint;
|
|
1638
|
-
return { type, blendMode, style: ColorConvert$1.string(color, opacity) };
|
|
1639
|
-
case 'image':
|
|
1640
|
-
return image(ui, attrName, paint, boxBounds, !recycleMap || !recycleMap[paint.url]);
|
|
1641
|
-
case 'linear':
|
|
1642
|
-
return linearGradient(paint, boxBounds);
|
|
1643
|
-
case 'radial':
|
|
1644
|
-
return radialGradient(paint, boxBounds);
|
|
1645
|
-
case 'angular':
|
|
1646
|
-
return conicGradient(paint, boxBounds);
|
|
1647
|
-
default:
|
|
1648
|
-
return paint.r ? { type: 'solid', style: ColorConvert$1.string(paint) } : undefined;
|
|
1649
|
-
}
|
|
1650
|
-
}
|
|
1651
|
-
|
|
1652
|
-
var UIPaint = /*#__PURE__*/Object.freeze({
|
|
1653
|
-
__proto__: null,
|
|
1654
|
-
compute: compute,
|
|
1655
|
-
drawTextStroke: drawTextStroke,
|
|
1656
|
-
fill: fill,
|
|
1657
|
-
fillText: fillText,
|
|
1658
|
-
fills: fills,
|
|
1659
|
-
recycleImage: recycleImage,
|
|
1660
|
-
shape: shape,
|
|
1661
|
-
stroke: stroke,
|
|
1662
|
-
strokeText: strokeText,
|
|
1663
|
-
strokes: strokes
|
|
1664
|
-
});
|
|
1737
|
+
const PaintGradientModule = {
|
|
1738
|
+
linearGradient,
|
|
1739
|
+
radialGradient,
|
|
1740
|
+
conicGradient,
|
|
1741
|
+
getTransform
|
|
1742
|
+
};
|
|
1665
1743
|
|
|
1666
1744
|
const { copy, toOffsetOutBounds: toOffsetOutBounds$1 } = BoundsHelper;
|
|
1667
1745
|
const tempBounds = {};
|
|
1668
1746
|
const offsetOutBounds$1 = {};
|
|
1669
|
-
function shadow(ui, current, shape
|
|
1747
|
+
function shadow(ui, current, shape) {
|
|
1670
1748
|
let copyBounds, spreadScale;
|
|
1671
|
-
const {
|
|
1749
|
+
const { __nowWorld: nowWorld, __layout } = ui;
|
|
1672
1750
|
const { shadow } = ui.__;
|
|
1673
1751
|
const { worldCanvas, bounds, shapeBounds, scaleX, scaleY } = shape;
|
|
1674
1752
|
const other = current.getSameCanvas();
|
|
@@ -1683,21 +1761,21 @@ function shadow(ui, current, shape, renderOptions) {
|
|
|
1683
1761
|
other.restore();
|
|
1684
1762
|
other.save();
|
|
1685
1763
|
if (worldCanvas) {
|
|
1686
|
-
other.copyWorld(other, bounds,
|
|
1687
|
-
copyBounds =
|
|
1764
|
+
other.copyWorld(other, bounds, nowWorld, 'copy');
|
|
1765
|
+
copyBounds = nowWorld;
|
|
1688
1766
|
}
|
|
1689
|
-
worldCanvas ? other.copyWorld(worldCanvas,
|
|
1767
|
+
worldCanvas ? other.copyWorld(worldCanvas, nowWorld, nowWorld, 'destination-out') : other.copyWorld(shape.canvas, shapeBounds, bounds, 'destination-out');
|
|
1690
1768
|
}
|
|
1691
|
-
if (ui.__worldFlipped
|
|
1692
|
-
current.copyWorldByReset(other, copyBounds,
|
|
1769
|
+
if (ui.__worldFlipped) {
|
|
1770
|
+
current.copyWorldByReset(other, copyBounds, nowWorld, item.blendMode);
|
|
1693
1771
|
}
|
|
1694
1772
|
else {
|
|
1695
1773
|
current.copyWorldToInner(other, copyBounds, __layout.renderBounds, item.blendMode);
|
|
1696
1774
|
}
|
|
1697
1775
|
if (end && index < end)
|
|
1698
|
-
other.
|
|
1776
|
+
other.clearWorld(copyBounds, true);
|
|
1699
1777
|
});
|
|
1700
|
-
other.recycle();
|
|
1778
|
+
other.recycle(copyBounds);
|
|
1701
1779
|
}
|
|
1702
1780
|
function drawWorldShadow(canvas, outBounds, spreadScale, shape) {
|
|
1703
1781
|
const { bounds, shapeBounds } = shape;
|
|
@@ -1728,9 +1806,9 @@ function drawWorldShadow(canvas, outBounds, spreadScale, shape) {
|
|
|
1728
1806
|
|
|
1729
1807
|
const { toOffsetOutBounds } = BoundsHelper;
|
|
1730
1808
|
const offsetOutBounds = {};
|
|
1731
|
-
function innerShadow(ui, current, shape
|
|
1809
|
+
function innerShadow(ui, current, shape) {
|
|
1732
1810
|
let copyBounds, spreadScale;
|
|
1733
|
-
const {
|
|
1811
|
+
const { __nowWorld: nowWorld, __layout: __layout } = ui;
|
|
1734
1812
|
const { innerShadow } = ui.__;
|
|
1735
1813
|
const { worldCanvas, bounds, shapeBounds, scaleX, scaleY } = shape;
|
|
1736
1814
|
const other = current.getSameCanvas();
|
|
@@ -1743,40 +1821,115 @@ function innerShadow(ui, current, shape, renderOptions) {
|
|
|
1743
1821
|
drawWorldShadow(other, offsetOutBounds, spreadScale, shape);
|
|
1744
1822
|
other.restore();
|
|
1745
1823
|
if (worldCanvas) {
|
|
1746
|
-
other.copyWorld(other, bounds,
|
|
1747
|
-
other.copyWorld(worldCanvas,
|
|
1748
|
-
copyBounds =
|
|
1824
|
+
other.copyWorld(other, bounds, nowWorld, 'copy');
|
|
1825
|
+
other.copyWorld(worldCanvas, nowWorld, nowWorld, 'source-out');
|
|
1826
|
+
copyBounds = nowWorld;
|
|
1749
1827
|
}
|
|
1750
1828
|
else {
|
|
1751
1829
|
other.copyWorld(shape.canvas, shapeBounds, bounds, 'source-out');
|
|
1752
1830
|
copyBounds = bounds;
|
|
1753
1831
|
}
|
|
1754
1832
|
other.fillWorld(copyBounds, item.color, 'source-in');
|
|
1755
|
-
if (ui.__worldFlipped
|
|
1756
|
-
current.copyWorldByReset(other, copyBounds,
|
|
1833
|
+
if (ui.__worldFlipped) {
|
|
1834
|
+
current.copyWorldByReset(other, copyBounds, nowWorld, item.blendMode);
|
|
1757
1835
|
}
|
|
1758
1836
|
else {
|
|
1759
1837
|
current.copyWorldToInner(other, copyBounds, __layout.renderBounds, item.blendMode);
|
|
1760
1838
|
}
|
|
1761
1839
|
if (end && index < end)
|
|
1762
|
-
other.
|
|
1840
|
+
other.clearWorld(copyBounds, true);
|
|
1763
1841
|
});
|
|
1764
|
-
other.recycle();
|
|
1842
|
+
other.recycle(copyBounds);
|
|
1765
1843
|
}
|
|
1766
1844
|
|
|
1767
1845
|
function blur(ui, current, origin) {
|
|
1768
1846
|
const { blur } = ui.__;
|
|
1769
|
-
origin.setWorldBlur(blur * ui.
|
|
1770
|
-
origin.copyWorldToInner(current, ui.
|
|
1847
|
+
origin.setWorldBlur(blur * ui.__nowWorld.a);
|
|
1848
|
+
origin.copyWorldToInner(current, ui.__nowWorld, ui.__layout.renderBounds);
|
|
1771
1849
|
origin.filter = 'none';
|
|
1772
1850
|
}
|
|
1773
1851
|
|
|
1774
|
-
|
|
1775
|
-
|
|
1776
|
-
|
|
1777
|
-
|
|
1778
|
-
shadow
|
|
1779
|
-
|
|
1852
|
+
function backgroundBlur(_ui, _current, _shape) {
|
|
1853
|
+
}
|
|
1854
|
+
|
|
1855
|
+
const EffectModule = {
|
|
1856
|
+
shadow,
|
|
1857
|
+
innerShadow,
|
|
1858
|
+
blur,
|
|
1859
|
+
backgroundBlur
|
|
1860
|
+
};
|
|
1861
|
+
|
|
1862
|
+
const { excludeRenderBounds } = LeafBoundsHelper;
|
|
1863
|
+
Group.prototype.__renderMask = function (canvas, options) {
|
|
1864
|
+
let child, maskCanvas, contentCanvas, maskOpacity, currentMask;
|
|
1865
|
+
const { children } = this;
|
|
1866
|
+
for (let i = 0, len = children.length; i < len; i++) {
|
|
1867
|
+
child = children[i];
|
|
1868
|
+
if (child.__.mask) {
|
|
1869
|
+
if (currentMask) {
|
|
1870
|
+
maskEnd(this, currentMask, canvas, contentCanvas, maskCanvas, maskOpacity);
|
|
1871
|
+
maskCanvas = contentCanvas = null;
|
|
1872
|
+
}
|
|
1873
|
+
if (child.__.mask === 'path') {
|
|
1874
|
+
if (child.opacity < 1) {
|
|
1875
|
+
currentMask = 'opacity-path';
|
|
1876
|
+
maskOpacity = child.opacity;
|
|
1877
|
+
if (!contentCanvas)
|
|
1878
|
+
contentCanvas = getCanvas(canvas);
|
|
1879
|
+
}
|
|
1880
|
+
else {
|
|
1881
|
+
currentMask = 'path';
|
|
1882
|
+
canvas.save();
|
|
1883
|
+
}
|
|
1884
|
+
child.__clip(contentCanvas || canvas, options);
|
|
1885
|
+
}
|
|
1886
|
+
else {
|
|
1887
|
+
currentMask = 'alpha';
|
|
1888
|
+
if (!maskCanvas)
|
|
1889
|
+
maskCanvas = getCanvas(canvas);
|
|
1890
|
+
if (!contentCanvas)
|
|
1891
|
+
contentCanvas = getCanvas(canvas);
|
|
1892
|
+
child.__render(maskCanvas, options);
|
|
1893
|
+
}
|
|
1894
|
+
if (child.__.mask !== 'clipping')
|
|
1895
|
+
continue;
|
|
1896
|
+
}
|
|
1897
|
+
if (excludeRenderBounds(child, options))
|
|
1898
|
+
continue;
|
|
1899
|
+
child.__render(contentCanvas || canvas, options);
|
|
1900
|
+
}
|
|
1901
|
+
maskEnd(this, currentMask, canvas, contentCanvas, maskCanvas, maskOpacity);
|
|
1902
|
+
};
|
|
1903
|
+
function maskEnd(leaf, maskMode, canvas, contentCanvas, maskCanvas, maskOpacity) {
|
|
1904
|
+
switch (maskMode) {
|
|
1905
|
+
case 'alpha':
|
|
1906
|
+
usePixelMask(leaf, canvas, contentCanvas, maskCanvas);
|
|
1907
|
+
break;
|
|
1908
|
+
case 'opacity-path':
|
|
1909
|
+
copyContent(leaf, canvas, contentCanvas, maskOpacity);
|
|
1910
|
+
break;
|
|
1911
|
+
case 'path':
|
|
1912
|
+
canvas.restore();
|
|
1913
|
+
}
|
|
1914
|
+
}
|
|
1915
|
+
function getCanvas(canvas) {
|
|
1916
|
+
return canvas.getSameCanvas(false, true);
|
|
1917
|
+
}
|
|
1918
|
+
function usePixelMask(leaf, canvas, content, mask) {
|
|
1919
|
+
const realBounds = leaf.__nowWorld;
|
|
1920
|
+
content.resetTransform();
|
|
1921
|
+
content.opacity = 1;
|
|
1922
|
+
content.useMask(mask, realBounds);
|
|
1923
|
+
mask.recycle(realBounds);
|
|
1924
|
+
copyContent(leaf, canvas, content, 1);
|
|
1925
|
+
}
|
|
1926
|
+
function copyContent(leaf, canvas, content, maskOpacity) {
|
|
1927
|
+
const realBounds = leaf.__nowWorld;
|
|
1928
|
+
canvas.resetTransform();
|
|
1929
|
+
canvas.opacity = maskOpacity;
|
|
1930
|
+
canvas.copyWorld(content, realBounds);
|
|
1931
|
+
content.recycle(realBounds);
|
|
1932
|
+
}
|
|
1780
1933
|
|
|
1781
1934
|
const money = '¥¥$€££¢¢';
|
|
1782
1935
|
const letter = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz';
|
|
@@ -1933,7 +2086,8 @@ function createRows(drawData, content, style) {
|
|
|
1933
2086
|
if (breakAll) {
|
|
1934
2087
|
if (wordWidth)
|
|
1935
2088
|
addWord();
|
|
1936
|
-
|
|
2089
|
+
if (rowWidth)
|
|
2090
|
+
addRow();
|
|
1937
2091
|
}
|
|
1938
2092
|
else {
|
|
1939
2093
|
if (!afterBreak)
|
|
@@ -1941,10 +2095,12 @@ function createRows(drawData, content, style) {
|
|
|
1941
2095
|
if (langBreak || afterBreak || charType === Break || charType === Before || charType === Single || (wordWidth + charWidth > realWidth)) {
|
|
1942
2096
|
if (wordWidth)
|
|
1943
2097
|
addWord();
|
|
1944
|
-
|
|
2098
|
+
if (rowWidth)
|
|
2099
|
+
addRow();
|
|
1945
2100
|
}
|
|
1946
2101
|
else {
|
|
1947
|
-
|
|
2102
|
+
if (rowWidth)
|
|
2103
|
+
addRow();
|
|
1948
2104
|
}
|
|
1949
2105
|
}
|
|
1950
2106
|
}
|
|
@@ -2039,11 +2195,11 @@ function layoutChar(drawData, style, width, _height) {
|
|
|
2039
2195
|
if (mode === WordMode) {
|
|
2040
2196
|
wordChar = { char: '', x: charX };
|
|
2041
2197
|
charX = toWordChar(word.data, charX, wordChar);
|
|
2042
|
-
if (wordChar.char !== ' ')
|
|
2198
|
+
if (row.isOverflow || wordChar.char !== ' ')
|
|
2043
2199
|
row.data.push(wordChar);
|
|
2044
2200
|
}
|
|
2045
2201
|
else {
|
|
2046
|
-
charX = toChar(word.data, charX, row.data);
|
|
2202
|
+
charX = toChar(word.data, charX, row.data, row.isOverflow);
|
|
2047
2203
|
}
|
|
2048
2204
|
if (!row.paraEnd && addWordWidth) {
|
|
2049
2205
|
charX += addWordWidth;
|
|
@@ -2070,9 +2226,9 @@ function toWordChar(data, charX, wordChar) {
|
|
|
2070
2226
|
});
|
|
2071
2227
|
return charX;
|
|
2072
2228
|
}
|
|
2073
|
-
function toChar(data, charX, rowData) {
|
|
2229
|
+
function toChar(data, charX, rowData, isOverflow) {
|
|
2074
2230
|
data.forEach(char => {
|
|
2075
|
-
if (char.char !== ' ') {
|
|
2231
|
+
if (isOverflow || char.char !== ' ') {
|
|
2076
2232
|
char.x = charX;
|
|
2077
2233
|
rowData.push(char);
|
|
2078
2234
|
}
|
|
@@ -2104,12 +2260,14 @@ function layoutText(drawData, style) {
|
|
|
2104
2260
|
for (let i = 0, len = rows.length; i < len; i++) {
|
|
2105
2261
|
row = rows[i];
|
|
2106
2262
|
row.x = x;
|
|
2107
|
-
|
|
2108
|
-
|
|
2109
|
-
|
|
2110
|
-
|
|
2111
|
-
|
|
2112
|
-
|
|
2263
|
+
if (row.width < width || (row.width > width && !__clipText)) {
|
|
2264
|
+
switch (textAlign) {
|
|
2265
|
+
case 'center':
|
|
2266
|
+
row.x += (width - row.width) / 2;
|
|
2267
|
+
break;
|
|
2268
|
+
case 'right':
|
|
2269
|
+
row.x += width - row.width;
|
|
2270
|
+
}
|
|
2113
2271
|
}
|
|
2114
2272
|
if (row.paraStart && paraSpacing && i > 0)
|
|
2115
2273
|
starY += paraSpacing;
|
|
@@ -2145,16 +2303,20 @@ function layoutText(drawData, style) {
|
|
|
2145
2303
|
bounds.height = realHeight;
|
|
2146
2304
|
}
|
|
2147
2305
|
|
|
2148
|
-
function clipText(drawData, style) {
|
|
2306
|
+
function clipText(drawData, style, x, width) {
|
|
2307
|
+
if (!width)
|
|
2308
|
+
return;
|
|
2149
2309
|
const { rows, overflow } = drawData;
|
|
2150
2310
|
let { textOverflow } = style;
|
|
2151
2311
|
rows.splice(overflow);
|
|
2152
|
-
if (textOverflow !== '
|
|
2153
|
-
if (textOverflow === '
|
|
2312
|
+
if (textOverflow && textOverflow !== 'show') {
|
|
2313
|
+
if (textOverflow === 'hide')
|
|
2314
|
+
textOverflow = '';
|
|
2315
|
+
else if (textOverflow === 'ellipsis')
|
|
2154
2316
|
textOverflow = '...';
|
|
2155
2317
|
let char, charRight;
|
|
2156
|
-
const ellipsisWidth = Platform.canvas.measureText(textOverflow).width;
|
|
2157
|
-
const right =
|
|
2318
|
+
const ellipsisWidth = textOverflow ? Platform.canvas.measureText(textOverflow).width : 0;
|
|
2319
|
+
const right = x + width - ellipsisWidth;
|
|
2158
2320
|
const list = style.textWrap === 'none' ? rows : [rows[overflow - 1]];
|
|
2159
2321
|
list.forEach(row => {
|
|
2160
2322
|
if (row.isOverflow && row.data) {
|
|
@@ -2201,42 +2363,40 @@ function decorationText(drawData, style) {
|
|
|
2201
2363
|
}
|
|
2202
2364
|
|
|
2203
2365
|
const { top, right, bottom, left } = Direction4;
|
|
2204
|
-
|
|
2205
|
-
|
|
2206
|
-
|
|
2207
|
-
|
|
2208
|
-
|
|
2209
|
-
|
|
2210
|
-
|
|
2211
|
-
|
|
2212
|
-
if (
|
|
2213
|
-
|
|
2214
|
-
|
|
2215
|
-
|
|
2216
|
-
|
|
2217
|
-
|
|
2218
|
-
|
|
2219
|
-
|
|
2220
|
-
|
|
2221
|
-
|
|
2222
|
-
|
|
2223
|
-
|
|
2224
|
-
|
|
2225
|
-
|
|
2226
|
-
|
|
2227
|
-
|
|
2228
|
-
|
|
2229
|
-
|
|
2230
|
-
|
|
2231
|
-
|
|
2232
|
-
|
|
2233
|
-
|
|
2234
|
-
|
|
2235
|
-
|
|
2236
|
-
|
|
2237
|
-
|
|
2238
|
-
}
|
|
2239
|
-
};
|
|
2366
|
+
function getDrawData(content, style) {
|
|
2367
|
+
if (typeof content !== 'string')
|
|
2368
|
+
content = String(content);
|
|
2369
|
+
let x = 0, y = 0;
|
|
2370
|
+
let width = style.__getInput('width') || 0;
|
|
2371
|
+
let height = style.__getInput('height') || 0;
|
|
2372
|
+
const { textDecoration, __font, __padding: padding } = style;
|
|
2373
|
+
if (padding) {
|
|
2374
|
+
if (width) {
|
|
2375
|
+
x = padding[left];
|
|
2376
|
+
width -= (padding[right] + padding[left]);
|
|
2377
|
+
}
|
|
2378
|
+
if (height) {
|
|
2379
|
+
y = padding[top];
|
|
2380
|
+
height -= (padding[top] + padding[bottom]);
|
|
2381
|
+
}
|
|
2382
|
+
}
|
|
2383
|
+
const drawData = {
|
|
2384
|
+
bounds: { x, y, width, height },
|
|
2385
|
+
rows: [],
|
|
2386
|
+
paraNumber: 0,
|
|
2387
|
+
font: Platform.canvas.font = __font
|
|
2388
|
+
};
|
|
2389
|
+
createRows(drawData, content, style);
|
|
2390
|
+
if (padding)
|
|
2391
|
+
padAutoText(padding, drawData, style, width, height);
|
|
2392
|
+
layoutText(drawData, style);
|
|
2393
|
+
layoutChar(drawData, style, width);
|
|
2394
|
+
if (drawData.overflow)
|
|
2395
|
+
clipText(drawData, style, x, width);
|
|
2396
|
+
if (textDecoration !== 'none')
|
|
2397
|
+
decorationText(drawData, style);
|
|
2398
|
+
return drawData;
|
|
2399
|
+
}
|
|
2240
2400
|
function padAutoText(padding, drawData, style, width, height) {
|
|
2241
2401
|
if (!width) {
|
|
2242
2402
|
switch (style.textAlign) {
|
|
@@ -2264,67 +2424,152 @@ function offsetText(drawData, attrName, value) {
|
|
|
2264
2424
|
rows[i][attrName] += value;
|
|
2265
2425
|
}
|
|
2266
2426
|
|
|
2267
|
-
const
|
|
2268
|
-
|
|
2269
|
-
if (typeof color === 'string')
|
|
2270
|
-
return color;
|
|
2271
|
-
let a = color.a === undefined ? 1 : color.a;
|
|
2272
|
-
if (opacity)
|
|
2273
|
-
a *= opacity;
|
|
2274
|
-
const rgb = color.r + ',' + color.g + ',' + color.b;
|
|
2275
|
-
return a === 1 ? 'rgb(' + rgb + ')' : 'rgba(' + rgb + ',' + a + ')';
|
|
2276
|
-
}
|
|
2427
|
+
const TextConvertModule = {
|
|
2428
|
+
getDrawData
|
|
2277
2429
|
};
|
|
2278
2430
|
|
|
2279
|
-
|
|
2431
|
+
function string(color, opacity) {
|
|
2432
|
+
if (typeof color === 'string')
|
|
2433
|
+
return color;
|
|
2434
|
+
let a = color.a === undefined ? 1 : color.a;
|
|
2435
|
+
if (opacity)
|
|
2436
|
+
a *= opacity;
|
|
2437
|
+
const rgb = color.r + ',' + color.g + ',' + color.b;
|
|
2438
|
+
return a === 1 ? 'rgb(' + rgb + ')' : 'rgba(' + rgb + ',' + a + ')';
|
|
2439
|
+
}
|
|
2440
|
+
|
|
2441
|
+
const ColorConvertModule = {
|
|
2442
|
+
string
|
|
2443
|
+
};
|
|
2444
|
+
|
|
2445
|
+
const { setPoint, addPoint, toBounds } = TwoPointBoundsHelper;
|
|
2446
|
+
function getTrimBounds(canvas) {
|
|
2447
|
+
const { width, height } = canvas.view;
|
|
2448
|
+
const { data } = canvas.context.getImageData(0, 0, width, height);
|
|
2449
|
+
let x, y, pointBounds, index = 0;
|
|
2450
|
+
for (let i = 0; i < data.length; i += 4) {
|
|
2451
|
+
if (data[i + 3] !== 0) {
|
|
2452
|
+
x = index % width;
|
|
2453
|
+
y = (index - x) / width;
|
|
2454
|
+
pointBounds ? addPoint(pointBounds, x, y) : setPoint(pointBounds = {}, x, y);
|
|
2455
|
+
}
|
|
2456
|
+
index++;
|
|
2457
|
+
}
|
|
2458
|
+
const bounds = new Bounds();
|
|
2459
|
+
toBounds(pointBounds, bounds);
|
|
2460
|
+
return bounds.scale(1 / canvas.pixelRatio).ceil();
|
|
2461
|
+
}
|
|
2462
|
+
|
|
2463
|
+
const ExportModule = {
|
|
2280
2464
|
export(leaf, filename, options) {
|
|
2281
|
-
|
|
2465
|
+
this.running = true;
|
|
2466
|
+
const fileType = FileHelper.fileType(filename);
|
|
2467
|
+
options = FileHelper.getExportOptions(options);
|
|
2282
2468
|
return addTask((success) => new Promise((resolve) => {
|
|
2469
|
+
const over = (result) => {
|
|
2470
|
+
success(result);
|
|
2471
|
+
resolve();
|
|
2472
|
+
this.running = false;
|
|
2473
|
+
};
|
|
2474
|
+
const { toURL } = Platform;
|
|
2475
|
+
const { download } = Platform.origin;
|
|
2476
|
+
if (filename === 'json') {
|
|
2477
|
+
return over({ data: leaf.toJSON(options.json) });
|
|
2478
|
+
}
|
|
2479
|
+
else if (fileType === 'json') {
|
|
2480
|
+
download(toURL(JSON.stringify(leaf.toJSON(options.json)), 'text'), filename);
|
|
2481
|
+
return over({ data: true });
|
|
2482
|
+
}
|
|
2483
|
+
if (filename === 'svg') {
|
|
2484
|
+
return over({ data: leaf.toSVG() });
|
|
2485
|
+
}
|
|
2486
|
+
else if (fileType === 'svg') {
|
|
2487
|
+
download(toURL(leaf.toSVG(), 'svg'), filename);
|
|
2488
|
+
return over({ data: true });
|
|
2489
|
+
}
|
|
2283
2490
|
const { leafer } = leaf;
|
|
2284
2491
|
if (leafer) {
|
|
2492
|
+
checkLazy(leaf);
|
|
2285
2493
|
leafer.waitViewCompleted(() => __awaiter(this, void 0, void 0, function* () {
|
|
2286
|
-
let
|
|
2287
|
-
|
|
2288
|
-
|
|
2289
|
-
|
|
2290
|
-
|
|
2291
|
-
|
|
2292
|
-
|
|
2494
|
+
let renderBounds, trimBounds, scaleX = 1, scaleY = 1;
|
|
2495
|
+
const { worldTransform, isLeafer, isFrame } = leaf;
|
|
2496
|
+
const { slice, trim, onCanvas } = options;
|
|
2497
|
+
let scale = options.scale || 1;
|
|
2498
|
+
let pixelRatio = options.pixelRatio || 1;
|
|
2499
|
+
const smooth = options.smooth === undefined ? leafer.config.smooth : options.smooth;
|
|
2500
|
+
const contextSettings = options.contextSettings || leafer.config.contextSettings;
|
|
2501
|
+
if (leaf.isApp) {
|
|
2502
|
+
scale *= pixelRatio;
|
|
2503
|
+
pixelRatio = leaf.app.pixelRatio;
|
|
2504
|
+
}
|
|
2505
|
+
const screenshot = options.screenshot || leaf.isApp;
|
|
2506
|
+
const fill = (isLeafer && screenshot) ? (options.fill === undefined ? leaf.fill : options.fill) : options.fill;
|
|
2507
|
+
const needFill = FileHelper.isOpaqueImage(filename) || fill, matrix = new Matrix();
|
|
2508
|
+
if (screenshot) {
|
|
2509
|
+
renderBounds = screenshot === true ? (isLeafer ? leafer.canvas.bounds : leaf.worldRenderBounds) : screenshot;
|
|
2293
2510
|
}
|
|
2294
|
-
|
|
2295
|
-
|
|
2296
|
-
|
|
2297
|
-
|
|
2298
|
-
|
|
2299
|
-
|
|
2300
|
-
|
|
2301
|
-
|
|
2302
|
-
|
|
2303
|
-
|
|
2304
|
-
|
|
2305
|
-
|
|
2511
|
+
else {
|
|
2512
|
+
let relative = options.relative || (isLeafer ? 'inner' : 'local');
|
|
2513
|
+
scaleX = worldTransform.scaleX;
|
|
2514
|
+
scaleY = worldTransform.scaleY;
|
|
2515
|
+
switch (relative) {
|
|
2516
|
+
case 'inner':
|
|
2517
|
+
matrix.set(worldTransform);
|
|
2518
|
+
break;
|
|
2519
|
+
case 'local':
|
|
2520
|
+
matrix.set(worldTransform).divide(leaf.localTransform);
|
|
2521
|
+
scaleX /= leaf.scaleX;
|
|
2522
|
+
scaleY /= leaf.scaleY;
|
|
2523
|
+
break;
|
|
2524
|
+
case 'world':
|
|
2525
|
+
scaleX = 1;
|
|
2526
|
+
scaleY = 1;
|
|
2527
|
+
break;
|
|
2528
|
+
case 'page':
|
|
2529
|
+
relative = leaf.leafer;
|
|
2530
|
+
default:
|
|
2531
|
+
matrix.set(worldTransform).divide(leaf.getTransform(relative));
|
|
2532
|
+
const l = relative.worldTransform;
|
|
2533
|
+
scaleX /= scaleX / l.scaleX;
|
|
2534
|
+
scaleY /= scaleY / l.scaleY;
|
|
2535
|
+
}
|
|
2536
|
+
renderBounds = leaf.getBounds('render', relative);
|
|
2306
2537
|
}
|
|
2307
|
-
|
|
2308
|
-
|
|
2309
|
-
|
|
2538
|
+
const { x, y, width, height } = new Bounds(renderBounds).scale(scale);
|
|
2539
|
+
let canvas = Creator.canvas({ width: Math.round(width), height: Math.round(height), pixelRatio, smooth, contextSettings });
|
|
2540
|
+
const renderOptions = { matrix: matrix.scale(1 / scale).invert().translate(-x, -y).withScale(1 / scaleX * scale, 1 / scaleY * scale) };
|
|
2541
|
+
if (slice) {
|
|
2542
|
+
leaf = leafer;
|
|
2543
|
+
renderOptions.bounds = canvas.bounds;
|
|
2310
2544
|
}
|
|
2311
|
-
|
|
2312
|
-
|
|
2545
|
+
canvas.save();
|
|
2546
|
+
if (isFrame && fill !== undefined) {
|
|
2547
|
+
const oldFill = leaf.get('fill');
|
|
2548
|
+
leaf.fill = '';
|
|
2549
|
+
leaf.__render(canvas, renderOptions);
|
|
2550
|
+
leaf.fill = oldFill;
|
|
2313
2551
|
}
|
|
2314
2552
|
else {
|
|
2315
|
-
|
|
2553
|
+
leaf.__render(canvas, renderOptions);
|
|
2316
2554
|
}
|
|
2317
|
-
|
|
2318
|
-
|
|
2319
|
-
|
|
2320
|
-
|
|
2321
|
-
|
|
2555
|
+
canvas.restore();
|
|
2556
|
+
if (trim) {
|
|
2557
|
+
trimBounds = getTrimBounds(canvas);
|
|
2558
|
+
const old = canvas, { width, height } = trimBounds;
|
|
2559
|
+
const config = { x: 0, y: 0, width, height, pixelRatio };
|
|
2560
|
+
canvas = Creator.canvas(config);
|
|
2561
|
+
canvas.copyWorld(old, trimBounds, config);
|
|
2562
|
+
}
|
|
2563
|
+
if (needFill)
|
|
2564
|
+
canvas.fillWorld(canvas.bounds, fill || '#FFFFFF', 'destination-over');
|
|
2565
|
+
if (onCanvas)
|
|
2566
|
+
onCanvas(canvas);
|
|
2567
|
+
const data = filename === 'canvas' ? canvas : yield canvas.export(filename, options);
|
|
2568
|
+
over({ data, width: canvas.pixelWidth, height: canvas.pixelHeight, renderBounds, trimBounds });
|
|
2322
2569
|
}));
|
|
2323
2570
|
}
|
|
2324
2571
|
else {
|
|
2325
|
-
|
|
2326
|
-
resolve();
|
|
2327
|
-
Export.running = false;
|
|
2572
|
+
over({ data: false });
|
|
2328
2573
|
}
|
|
2329
2574
|
}));
|
|
2330
2575
|
}
|
|
@@ -2337,13 +2582,64 @@ function addTask(task) {
|
|
|
2337
2582
|
tasker.add(() => __awaiter(this, void 0, void 0, function* () { return yield task(resolve); }), { parallel: false });
|
|
2338
2583
|
});
|
|
2339
2584
|
}
|
|
2585
|
+
function checkLazy(leaf) {
|
|
2586
|
+
if (leaf.__.__needComputePaint)
|
|
2587
|
+
leaf.__.__computePaint();
|
|
2588
|
+
if (leaf.isBranch)
|
|
2589
|
+
leaf.children.forEach(child => checkLazy(child));
|
|
2590
|
+
}
|
|
2591
|
+
|
|
2592
|
+
const canvas = LeaferCanvasBase.prototype;
|
|
2593
|
+
const debug = Debug.get('@leafer-ui/export');
|
|
2594
|
+
canvas.export = function (filename, options) {
|
|
2595
|
+
const { quality, blob } = FileHelper.getExportOptions(options);
|
|
2596
|
+
if (filename.includes('.')) {
|
|
2597
|
+
return this.saveAs(filename, quality);
|
|
2598
|
+
}
|
|
2599
|
+
else if (blob) {
|
|
2600
|
+
return this.toBlob(filename, quality);
|
|
2601
|
+
}
|
|
2602
|
+
else {
|
|
2603
|
+
return this.toDataURL(filename, quality);
|
|
2604
|
+
}
|
|
2605
|
+
};
|
|
2606
|
+
canvas.toBlob = function (type, quality) {
|
|
2607
|
+
return new Promise((resolve) => {
|
|
2608
|
+
Platform.origin.canvasToBolb(this.view, type, quality).then((blob) => {
|
|
2609
|
+
resolve(blob);
|
|
2610
|
+
}).catch((e) => {
|
|
2611
|
+
debug.error(e);
|
|
2612
|
+
resolve(null);
|
|
2613
|
+
});
|
|
2614
|
+
});
|
|
2615
|
+
};
|
|
2616
|
+
canvas.toDataURL = function (type, quality) {
|
|
2617
|
+
return Platform.origin.canvasToDataURL(this.view, type, quality);
|
|
2618
|
+
};
|
|
2619
|
+
canvas.saveAs = function (filename, quality) {
|
|
2620
|
+
return new Promise((resolve) => {
|
|
2621
|
+
Platform.origin.canvasSaveAs(this.view, filename, quality).then(() => {
|
|
2622
|
+
resolve(true);
|
|
2623
|
+
}).catch((e) => {
|
|
2624
|
+
debug.error(e);
|
|
2625
|
+
resolve(false);
|
|
2626
|
+
});
|
|
2627
|
+
});
|
|
2628
|
+
};
|
|
2340
2629
|
|
|
2341
|
-
Object.assign(
|
|
2342
|
-
Object.assign(
|
|
2343
|
-
Object.assign(
|
|
2344
|
-
Object.assign(
|
|
2345
|
-
Object.assign(
|
|
2630
|
+
Object.assign(TextConvert, TextConvertModule);
|
|
2631
|
+
Object.assign(ColorConvert, ColorConvertModule);
|
|
2632
|
+
Object.assign(Paint, PaintModule);
|
|
2633
|
+
Object.assign(PaintImage, PaintImageModule);
|
|
2634
|
+
Object.assign(PaintGradient, PaintGradientModule);
|
|
2635
|
+
Object.assign(Effect, EffectModule);
|
|
2636
|
+
Object.assign(Export, ExportModule);
|
|
2346
2637
|
|
|
2638
|
+
Object.assign(Creator, {
|
|
2639
|
+
interaction: (target, canvas, selector, options) => new InteractionBase(target, canvas, selector, options),
|
|
2640
|
+
hitCanvas: (options, manager) => new LeaferCanvas(options, manager),
|
|
2641
|
+
hitCanvasManager: () => new HitCanvasManager()
|
|
2642
|
+
});
|
|
2347
2643
|
useCanvas();
|
|
2348
2644
|
|
|
2349
2645
|
export { Layouter, LeaferCanvas, Renderer, Selector, Watcher, useCanvas };
|