@leafer-draw/worker 1.6.1 → 1.6.3

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.cjs CHANGED
@@ -2,6 +2,7 @@
2
2
 
3
3
  var core = require('@leafer/core');
4
4
  var draw = require('@leafer-ui/draw');
5
+ var core$1 = require('@leafer-ui/core');
5
6
 
6
7
  class LeaferCanvas extends core.LeaferCanvasBase {
7
8
  get allowBackgroundColor() { return true; }
@@ -160,17 +161,15 @@ class Watcher {
160
161
  this.target.emitEvent(new core.WatchEvent(core.WatchEvent.DATA, { updatedList: this.updatedList }));
161
162
  this.__updatedList = new core.LeafList();
162
163
  this.totalTimes++;
163
- this.changed = false;
164
- this.hasVisible = false;
165
- this.hasRemove = false;
166
- this.hasAdd = false;
164
+ this.changed = this.hasVisible = this.hasRemove = this.hasAdd = false;
167
165
  }
168
166
  __listenEvents() {
169
- const { target } = this;
170
167
  this.__eventIds = [
171
- target.on_(core.PropertyEvent.CHANGE, this.__onAttrChange, this),
172
- target.on_([core.ChildEvent.ADD, core.ChildEvent.REMOVE], this.__onChildEvent, this),
173
- target.on_(core.WatchEvent.REQUEST, this.__onRquestData, this)
168
+ this.target.on_([
169
+ [core.PropertyEvent.CHANGE, this.__onAttrChange, this],
170
+ [[core.ChildEvent.ADD, core.ChildEvent.REMOVE], this.__onChildEvent, this],
171
+ [core.WatchEvent.REQUEST, this.__onRquestData, this]
172
+ ])
174
173
  ];
175
174
  }
176
175
  __removeListenEvents() {
@@ -180,13 +179,12 @@ class Watcher {
180
179
  if (this.target) {
181
180
  this.stop();
182
181
  this.__removeListenEvents();
183
- this.target = null;
184
- this.__updatedList = null;
182
+ this.target = this.__updatedList = null;
185
183
  }
186
184
  }
187
185
  }
188
186
 
189
- const { updateAllMatrix: updateAllMatrix$1, updateBounds: updateOneBounds, updateAllWorldOpacity } = core.LeafHelper;
187
+ const { updateAllMatrix: updateAllMatrix$1, updateBounds: updateOneBounds, updateChange: updateOneChange } = core.LeafHelper;
190
188
  const { pushAllChildBranch, pushAllParent } = core.BranchHelper;
191
189
  function updateMatrix(updateList, levelList) {
192
190
  let layout;
@@ -229,15 +227,7 @@ function updateBounds(boundsList) {
229
227
  });
230
228
  }
231
229
  function updateChange(updateList) {
232
- let layout;
233
- updateList.list.forEach(leaf => {
234
- layout = leaf.__layout;
235
- if (layout.opacityChanged)
236
- updateAllWorldOpacity(leaf);
237
- if (layout.stateStyleChanged)
238
- setTimeout(() => layout.stateStyleChanged && leaf.updateState());
239
- leaf.__updateChange();
240
- });
230
+ updateList.list.forEach(updateOneChange);
241
231
  }
242
232
 
243
233
  const { worldBounds } = core.LeafBoundsHelper;
@@ -294,7 +284,7 @@ class Layouter {
294
284
  this.disabled = true;
295
285
  }
296
286
  layout() {
297
- if (!this.running)
287
+ if (this.layouting || !this.running)
298
288
  return;
299
289
  const { target } = this;
300
290
  this.times = 0;
@@ -377,12 +367,10 @@ class Layouter {
377
367
  }
378
368
  static fullLayout(target) {
379
369
  updateAllMatrix(target, true);
380
- if (target.isBranch) {
370
+ if (target.isBranch)
381
371
  core.BranchHelper.updateBounds(target);
382
- }
383
- else {
372
+ else
384
373
  core.LeafHelper.updateBounds(target);
385
- }
386
374
  updateAllChange(target);
387
375
  }
388
376
  addExtra(leaf) {
@@ -405,11 +393,12 @@ class Layouter {
405
393
  this.__updatedList = event.data.updatedList;
406
394
  }
407
395
  __listenEvents() {
408
- const { target } = this;
409
396
  this.__eventIds = [
410
- target.on_(core.LayoutEvent.REQUEST, this.layout, this),
411
- target.on_(core.LayoutEvent.AGAIN, this.layoutAgain, this),
412
- target.on_(core.WatchEvent.DATA, this.__onReceiveWatchData, this)
397
+ this.target.on_([
398
+ [core.LayoutEvent.REQUEST, this.layout, this],
399
+ [core.LayoutEvent.AGAIN, this.layoutAgain, this],
400
+ [core.WatchEvent.DATA, this.__onReceiveWatchData, this]
401
+ ])
413
402
  ];
414
403
  }
415
404
  __removeListenEvents() {
@@ -640,12 +629,13 @@ class Renderer {
640
629
  this.target.emitEvent(new core.RenderEvent(type, this.times, bounds, options));
641
630
  }
642
631
  __listenEvents() {
643
- const { target } = this;
644
632
  this.__eventIds = [
645
- target.on_(core.RenderEvent.REQUEST, this.update, this),
646
- target.on_(core.LayoutEvent.END, this.__onLayoutEnd, this),
647
- target.on_(core.RenderEvent.AGAIN, this.renderAgain, this),
648
- target.on_(core.ResizeEvent.RESIZE, this.__onResize, this)
633
+ this.target.on_([
634
+ [core.RenderEvent.REQUEST, this.update, this],
635
+ [core.LayoutEvent.END, this.__onLayoutEnd, this],
636
+ [core.RenderEvent.AGAIN, this.renderAgain, this],
637
+ [core.ResizeEvent.RESIZE, this.__onResize, this]
638
+ ])
649
639
  ];
650
640
  }
651
641
  __removeListenEvents() {
@@ -671,8 +661,10 @@ Object.assign(core.Creator, {
671
661
  core.Platform.layout = Layouter.fullLayout;
672
662
 
673
663
  function fillText(ui, canvas) {
674
- let row, data = ui.__.__textDrawData;
675
- const { rows, decorationY } = data;
664
+ const data = ui.__, { rows, decorationY } = data.__textDrawData;
665
+ if (data.__isPlacehold && data.placeholderColor)
666
+ canvas.fillStyle = data.placeholderColor;
667
+ let row;
676
668
  for (let i = 0, len = rows.length; i < len; i++) {
677
669
  row = rows[i];
678
670
  if (row.text)
@@ -681,7 +673,7 @@ function fillText(ui, canvas) {
681
673
  row.data.forEach(charData => { canvas.fillText(charData.char, charData.x, row.y); });
682
674
  }
683
675
  if (decorationY) {
684
- const { decorationColor, decorationHeight } = data;
676
+ const { decorationColor, decorationHeight } = data.__textDrawData;
685
677
  if (decorationColor)
686
678
  canvas.fillStyle = decorationColor;
687
679
  rows.forEach(row => decorationY.forEach(value => canvas.fillRect(row.x, row.y + value, row.width, decorationHeight)));
@@ -690,65 +682,73 @@ function fillText(ui, canvas) {
690
682
 
691
683
  function fill(fill, ui, canvas) {
692
684
  canvas.fillStyle = fill;
693
- ui.__.__font ? fillText(ui, canvas) : (ui.__.windingRule ? canvas.fill(ui.__.windingRule) : canvas.fill());
685
+ fillPathOrText(ui, canvas);
694
686
  }
695
687
  function fills(fills, ui, canvas) {
696
688
  let item;
697
- const { windingRule, __font } = ui.__;
698
689
  for (let i = 0, len = fills.length; i < len; i++) {
699
690
  item = fills[i];
700
- if (item.image && draw.PaintImage.checkImage(ui, canvas, item, !__font))
701
- continue;
702
- if (item.style) {
703
- canvas.fillStyle = item.style;
704
- if (item.transform) {
705
- canvas.save();
706
- canvas.transform(item.transform);
707
- if (item.blendMode)
708
- canvas.blendMode = item.blendMode;
709
- __font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
710
- canvas.restore();
691
+ if (item.image) {
692
+ if (draw.PaintImage.checkImage(ui, canvas, item, !ui.__.__font))
693
+ continue;
694
+ if (!item.style) {
695
+ if (!i && item.image.isPlacehold)
696
+ ui.drawImagePlaceholder(canvas, item.image);
697
+ continue;
711
698
  }
712
- else {
713
- if (item.blendMode) {
714
- canvas.saveBlendMode(item.blendMode);
715
- __font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
716
- canvas.restoreBlendMode();
717
- }
718
- else {
719
- __font ? fillText(ui, canvas) : (windingRule ? canvas.fill(windingRule) : canvas.fill());
720
- }
699
+ }
700
+ canvas.fillStyle = item.style;
701
+ if (item.transform) {
702
+ canvas.save();
703
+ canvas.transform(item.transform);
704
+ if (item.blendMode)
705
+ canvas.blendMode = item.blendMode;
706
+ fillPathOrText(ui, canvas);
707
+ canvas.restore();
708
+ }
709
+ else {
710
+ if (item.blendMode) {
711
+ canvas.saveBlendMode(item.blendMode);
712
+ fillPathOrText(ui, canvas);
713
+ canvas.restoreBlendMode();
721
714
  }
715
+ else
716
+ fillPathOrText(ui, canvas);
722
717
  }
723
718
  }
724
719
  }
720
+ function fillPathOrText(ui, canvas) {
721
+ ui.__.__font ? fillText(ui, canvas) : (ui.__.windingRule ? canvas.fill(ui.__.windingRule) : canvas.fill());
722
+ }
723
+
724
+ const Paint = {};
725
725
 
726
726
  function strokeText(stroke, ui, canvas) {
727
- const { strokeAlign } = ui.__;
728
- const isStrokes = typeof stroke !== 'string';
729
- switch (strokeAlign) {
727
+ switch (ui.__.strokeAlign) {
730
728
  case 'center':
731
- canvas.setStroke(isStrokes ? undefined : stroke, ui.__.strokeWidth, ui.__);
732
- isStrokes ? drawStrokesStyle(stroke, true, ui, canvas) : drawTextStroke(ui, canvas);
729
+ drawCenter$1(stroke, 1, ui, canvas);
733
730
  break;
734
731
  case 'inside':
735
- drawAlignStroke('inside', stroke, isStrokes, ui, canvas);
732
+ drawAlign(stroke, 'inside', ui, canvas);
736
733
  break;
737
734
  case 'outside':
738
- drawAlignStroke('outside', stroke, isStrokes, ui, canvas);
735
+ ui.__.__fillAfterStroke ? drawCenter$1(stroke, 2, ui, canvas) : drawAlign(stroke, 'outside', ui, canvas);
739
736
  break;
740
737
  }
741
738
  }
742
- function drawAlignStroke(align, stroke, isStrokes, ui, canvas) {
743
- const { __strokeWidth, __font } = ui.__;
739
+ function drawCenter$1(stroke, strokeWidthScale, ui, canvas) {
740
+ const data = ui.__;
741
+ canvas.setStroke(!data.__isStrokes && stroke, data.strokeWidth * strokeWidthScale, data);
742
+ data.__isStrokes ? drawStrokesStyle(stroke, true, ui, canvas) : drawTextStroke(ui, canvas);
743
+ }
744
+ function drawAlign(stroke, align, ui, canvas) {
744
745
  const out = canvas.getSameCanvas(true, true);
745
- out.setStroke(isStrokes ? undefined : stroke, __strokeWidth * 2, ui.__);
746
- out.font = __font;
747
- isStrokes ? drawStrokesStyle(stroke, true, ui, out) : drawTextStroke(ui, out);
746
+ out.font = ui.__.__font;
747
+ drawCenter$1(stroke, 2, ui, out);
748
748
  out.blendMode = align === 'outside' ? 'destination-out' : 'destination-in';
749
749
  fillText(ui, out);
750
750
  out.blendMode = 'normal';
751
- if (ui.__worldFlipped)
751
+ if (ui.__worldFlipped || core$1.Platform.fullImageShadow)
752
752
  canvas.copyWorldByReset(out, ui.__nowWorld);
753
753
  else
754
754
  canvas.copyWorldToInner(out, ui.__nowWorld, ui.__layout.renderBounds);
@@ -790,90 +790,60 @@ function drawStrokesStyle(strokes, isText, ui, canvas) {
790
790
  }
791
791
 
792
792
  function stroke(stroke, ui, canvas) {
793
- const options = ui.__;
794
- const { __strokeWidth, strokeAlign, __font } = options;
795
- if (!__strokeWidth)
793
+ const data = ui.__;
794
+ if (!data.__strokeWidth)
796
795
  return;
797
- if (__font) {
796
+ if (data.__font) {
798
797
  strokeText(stroke, ui, canvas);
799
798
  }
800
799
  else {
801
- switch (strokeAlign) {
800
+ switch (data.strokeAlign) {
802
801
  case 'center':
803
- canvas.setStroke(stroke, __strokeWidth, options);
804
- canvas.stroke();
805
- if (options.__useArrow)
806
- strokeArrow(ui, canvas);
802
+ drawCenter(stroke, 1, ui, canvas);
807
803
  break;
808
804
  case 'inside':
809
- canvas.save();
810
- canvas.setStroke(stroke, __strokeWidth * 2, options);
811
- options.windingRule ? canvas.clip(options.windingRule) : canvas.clip();
812
- canvas.stroke();
813
- canvas.restore();
805
+ drawInside(stroke, ui, canvas);
814
806
  break;
815
807
  case 'outside':
816
- const out = canvas.getSameCanvas(true, true);
817
- out.setStroke(stroke, __strokeWidth * 2, options);
818
- ui.__drawRenderPath(out);
819
- out.stroke();
820
- options.windingRule ? out.clip(options.windingRule) : out.clip();
821
- out.clearWorld(ui.__layout.renderBounds);
822
- if (ui.__worldFlipped)
823
- canvas.copyWorldByReset(out, ui.__nowWorld);
824
- else
825
- canvas.copyWorldToInner(out, ui.__nowWorld, ui.__layout.renderBounds);
826
- out.recycle(ui.__nowWorld);
808
+ drawOutside(stroke, ui, canvas);
827
809
  break;
828
810
  }
829
811
  }
830
812
  }
831
813
  function strokes(strokes, ui, canvas) {
832
- const options = ui.__;
833
- const { __strokeWidth, strokeAlign, __font } = options;
834
- if (!__strokeWidth)
835
- return;
836
- if (__font) {
837
- strokeText(strokes, ui, canvas);
814
+ stroke(strokes, ui, canvas);
815
+ }
816
+ function drawCenter(stroke, strokeWidthScale, ui, canvas) {
817
+ const data = ui.__;
818
+ canvas.setStroke(!data.__isStrokes && stroke, data.__strokeWidth * strokeWidthScale, data);
819
+ data.__isStrokes ? drawStrokesStyle(stroke, false, ui, canvas) : canvas.stroke();
820
+ if (data.__useArrow)
821
+ Paint.strokeArrow(stroke, ui, canvas);
822
+ }
823
+ function drawInside(stroke, ui, canvas) {
824
+ const data = ui.__;
825
+ canvas.save();
826
+ data.windingRule ? canvas.clip(data.windingRule) : canvas.clip();
827
+ drawCenter(stroke, 2, ui, canvas);
828
+ canvas.restore();
829
+ }
830
+ function drawOutside(stroke, ui, canvas) {
831
+ const data = ui.__;
832
+ if (data.__fillAfterStroke) {
833
+ drawCenter(stroke, 2, ui, canvas);
838
834
  }
839
835
  else {
840
- switch (strokeAlign) {
841
- case 'center':
842
- canvas.setStroke(undefined, __strokeWidth, options);
843
- drawStrokesStyle(strokes, false, ui, canvas);
844
- if (options.__useArrow)
845
- strokeArrow(ui, canvas);
846
- break;
847
- case 'inside':
848
- canvas.save();
849
- canvas.setStroke(undefined, __strokeWidth * 2, options);
850
- options.windingRule ? canvas.clip(options.windingRule) : canvas.clip();
851
- drawStrokesStyle(strokes, false, ui, canvas);
852
- canvas.restore();
853
- break;
854
- case 'outside':
855
- const { renderBounds } = ui.__layout;
856
- const out = canvas.getSameCanvas(true, true);
857
- ui.__drawRenderPath(out);
858
- out.setStroke(undefined, __strokeWidth * 2, options);
859
- drawStrokesStyle(strokes, false, ui, out);
860
- options.windingRule ? out.clip(options.windingRule) : out.clip();
861
- out.clearWorld(renderBounds);
862
- if (ui.__worldFlipped)
863
- canvas.copyWorldByReset(out, ui.__nowWorld);
864
- else
865
- canvas.copyWorldToInner(out, ui.__nowWorld, renderBounds);
866
- out.recycle(ui.__nowWorld);
867
- break;
868
- }
869
- }
870
- }
871
- function strokeArrow(ui, canvas) {
872
- if (ui.__.dashPattern) {
873
- canvas.beginPath();
874
- ui.__drawPathByData(canvas, ui.__.__pathForArrow);
875
- canvas.dashPattern = null;
876
- canvas.stroke();
836
+ const { renderBounds } = ui.__layout;
837
+ const out = canvas.getSameCanvas(true, true);
838
+ ui.__drawRenderPath(out);
839
+ drawCenter(stroke, 2, ui, out);
840
+ data.windingRule ? out.clip(data.windingRule) : out.clip();
841
+ out.clearWorld(renderBounds);
842
+ if (ui.__worldFlipped || core$1.Platform.fullImageShadow)
843
+ canvas.copyWorldByReset(out, ui.__nowWorld);
844
+ else
845
+ canvas.copyWorldToInner(out, ui.__nowWorld, renderBounds);
846
+ out.recycle(ui.__nowWorld);
877
847
  }
878
848
  }
879
849
 
@@ -920,9 +890,10 @@ function shape(ui, current, options) {
920
890
  }
921
891
 
922
892
  let recycleMap;
893
+ const { stintSet } = core.DataHelper, { hasTransparent: hasTransparent$1 } = draw.ColorConvert;
923
894
  function compute(attrName, ui) {
924
895
  const data = ui.__, leafPaints = [];
925
- let paints = data.__input[attrName], hasOpacityPixel;
896
+ let paints = data.__input[attrName], isAlphaPixel, isTransparent;
926
897
  if (!(paints instanceof Array))
927
898
  paints = [paints];
928
899
  recycleMap = draw.PaintImage.recycleImage(attrName, data);
@@ -932,35 +903,62 @@ function compute(attrName, ui) {
932
903
  leafPaints.push(item);
933
904
  }
934
905
  data['_' + attrName] = leafPaints.length ? leafPaints : undefined;
935
- if (leafPaints.length && leafPaints[0].image)
936
- hasOpacityPixel = leafPaints[0].image.hasOpacityPixel;
937
- attrName === 'fill' ? data.__pixelFill = hasOpacityPixel : data.__pixelStroke = hasOpacityPixel;
906
+ if (leafPaints.length) {
907
+ if (leafPaints.every(item => item.isTransparent)) {
908
+ if (leafPaints.some(item => item.image))
909
+ isAlphaPixel = true;
910
+ isTransparent = true;
911
+ }
912
+ }
913
+ if (attrName === 'fill') {
914
+ stintSet(data, '__isAlphaPixelFill', isAlphaPixel);
915
+ stintSet(data, '__isTransparentFill', isTransparent);
916
+ }
917
+ else {
918
+ stintSet(data, '__isAlphaPixelStroke', isAlphaPixel);
919
+ stintSet(data, '__isTransparentStroke', isTransparent);
920
+ }
938
921
  }
939
922
  function getLeafPaint(attrName, paint, ui) {
940
923
  if (typeof paint !== 'object' || paint.visible === false || paint.opacity === 0)
941
924
  return undefined;
925
+ let data;
942
926
  const { boxBounds } = ui.__layout;
943
927
  switch (paint.type) {
944
- case 'solid':
945
- let { type, blendMode, color, opacity } = paint;
946
- return { type, blendMode, style: draw.ColorConvert.string(color, opacity) };
947
928
  case 'image':
948
- return draw.PaintImage.image(ui, attrName, paint, boxBounds, !recycleMap || !recycleMap[paint.url]);
929
+ data = draw.PaintImage.image(ui, attrName, paint, boxBounds, !recycleMap || !recycleMap[paint.url]);
930
+ break;
949
931
  case 'linear':
950
- return draw.PaintGradient.linearGradient(paint, boxBounds);
932
+ data = draw.PaintGradient.linearGradient(paint, boxBounds);
933
+ break;
951
934
  case 'radial':
952
- return draw.PaintGradient.radialGradient(paint, boxBounds);
935
+ data = draw.PaintGradient.radialGradient(paint, boxBounds);
936
+ break;
953
937
  case 'angular':
954
- return draw.PaintGradient.conicGradient(paint, boxBounds);
938
+ data = draw.PaintGradient.conicGradient(paint, boxBounds);
939
+ break;
940
+ case 'solid':
941
+ const { type, blendMode, color, opacity } = paint;
942
+ data = { type, blendMode, style: draw.ColorConvert.string(color, opacity) };
943
+ break;
955
944
  default:
956
- return paint.r !== undefined ? { type: 'solid', style: draw.ColorConvert.string(paint) } : undefined;
945
+ if (paint.r !== undefined)
946
+ data = { type: 'solid', style: draw.ColorConvert.string(paint) };
947
+ }
948
+ if (data) {
949
+ if (typeof data.style === 'string' && hasTransparent$1(data.style))
950
+ data.isTransparent = true;
951
+ if (paint.blendMode)
952
+ data.blendMode = paint.blendMode;
957
953
  }
954
+ return data;
958
955
  }
959
956
 
960
957
  const PaintModule = {
961
958
  compute,
962
959
  fill,
963
960
  fills,
961
+ fillPathOrText,
964
962
  fillText,
965
963
  stroke,
966
964
  strokes,
@@ -1019,12 +1017,10 @@ function repeatMode(data, box, width, height, x, y, scaleX, scaleY, rotation, al
1019
1017
 
1020
1018
  const { get: get$2, translate } = core.MatrixHelper;
1021
1019
  const tempBox = new core.Bounds();
1022
- const tempPoint = {};
1023
1020
  const tempScaleData = {};
1021
+ const tempImage = {};
1024
1022
  function createData(leafPaint, image, paint, box) {
1025
- const { blendMode, changeful, sync } = paint;
1026
- if (blendMode)
1027
- leafPaint.blendMode = blendMode;
1023
+ const { changeful, sync } = paint;
1028
1024
  if (changeful)
1029
1025
  leafPaint.changeful = changeful;
1030
1026
  if (sync)
@@ -1032,38 +1028,38 @@ function createData(leafPaint, image, paint, box) {
1032
1028
  leafPaint.data = getPatternData(paint, box, image);
1033
1029
  }
1034
1030
  function getPatternData(paint, box, image) {
1035
- let { width, height } = image;
1036
1031
  if (paint.padding)
1037
1032
  box = tempBox.set(box).shrink(paint.padding);
1038
1033
  if (paint.mode === 'strench')
1039
1034
  paint.mode = 'stretch';
1035
+ let { width, height } = image;
1040
1036
  const { opacity, mode, align, offset, scale, size, rotation, repeat, filters } = paint;
1041
1037
  const sameBox = box.width === width && box.height === height;
1042
1038
  const data = { mode };
1043
1039
  const swapSize = align !== 'center' && (rotation || 0) % 180 === 90;
1044
- const swapWidth = swapSize ? height : width, swapHeight = swapSize ? width : height;
1045
- let x = 0, y = 0, scaleX, scaleY;
1040
+ core.BoundsHelper.set(tempImage, 0, 0, swapSize ? height : width, swapSize ? width : height);
1041
+ let scaleX, scaleY;
1046
1042
  if (!mode || mode === 'cover' || mode === 'fit') {
1047
1043
  if (!sameBox || rotation) {
1048
- const sw = box.width / swapWidth, sh = box.height / swapHeight;
1049
- scaleX = scaleY = mode === 'fit' ? Math.min(sw, sh) : Math.max(sw, sh);
1050
- x += (box.width - width * scaleX) / 2, y += (box.height - height * scaleY) / 2;
1044
+ scaleX = scaleY = core.BoundsHelper.getFitScale(box, tempImage, mode !== 'fit');
1045
+ core.BoundsHelper.put(box, image, align, scaleX, false, tempImage);
1046
+ core.BoundsHelper.scale(tempImage, scaleX, scaleY, true);
1051
1047
  }
1052
1048
  }
1053
- else if (scale || size) {
1054
- core.MathHelper.getScaleData(scale, size, image, tempScaleData);
1055
- scaleX = tempScaleData.scaleX;
1056
- scaleY = tempScaleData.scaleY;
1057
- }
1058
- if (align) {
1059
- const imageBounds = { x, y, width: swapWidth, height: swapHeight };
1060
- if (scaleX)
1061
- imageBounds.width *= scaleX, imageBounds.height *= scaleY;
1062
- core.AlignHelper.toPoint(align, imageBounds, box, tempPoint, true);
1063
- x += tempPoint.x, y += tempPoint.y;
1049
+ else {
1050
+ if (scale || size) {
1051
+ core.MathHelper.getScaleData(scale, size, image, tempScaleData);
1052
+ scaleX = tempScaleData.scaleX;
1053
+ scaleY = tempScaleData.scaleY;
1054
+ }
1055
+ if (align) {
1056
+ if (scaleX)
1057
+ core.BoundsHelper.scale(tempImage, scaleX, scaleY, true);
1058
+ core.AlignHelper.toPoint(align, tempImage, box, tempImage, true, true);
1059
+ }
1064
1060
  }
1065
1061
  if (offset)
1066
- x += offset.x, y += offset.y;
1062
+ core.PointHelper.move(tempImage, offset);
1067
1063
  switch (mode) {
1068
1064
  case 'stretch':
1069
1065
  if (!sameBox)
@@ -1071,12 +1067,12 @@ function getPatternData(paint, box, image) {
1071
1067
  break;
1072
1068
  case 'normal':
1073
1069
  case 'clip':
1074
- if (x || y || scaleX || rotation)
1075
- clipMode(data, box, x, y, scaleX, scaleY, rotation);
1070
+ if (tempImage.x || tempImage.y || scaleX || rotation)
1071
+ clipMode(data, box, tempImage.x, tempImage.y, scaleX, scaleY, rotation);
1076
1072
  break;
1077
1073
  case 'repeat':
1078
1074
  if (!sameBox || scaleX || rotation)
1079
- repeatMode(data, box, width, height, x, y, scaleX, scaleY, rotation, align);
1075
+ repeatMode(data, box, width, height, tempImage.x, tempImage.y, scaleX, scaleY, rotation, align);
1080
1076
  if (!repeat)
1081
1077
  data.repeat = 'repeat';
1082
1078
  break;
@@ -1084,7 +1080,7 @@ function getPatternData(paint, box, image) {
1084
1080
  case 'cover':
1085
1081
  default:
1086
1082
  if (scaleX)
1087
- fillOrFitMode(data, box, x, y, scaleX, scaleY, rotation);
1083
+ fillOrFitMode(data, box, tempImage.x, tempImage.y, scaleX, scaleY, rotation);
1088
1084
  }
1089
1085
  if (!data.transform) {
1090
1086
  if (box.x || box.y) {
@@ -1117,6 +1113,8 @@ function image(ui, attrName, paint, boxBounds, firstUse) {
1117
1113
  }
1118
1114
  else {
1119
1115
  leafPaint = { type: paint.type, image };
1116
+ if (image.hasAlphaPixel)
1117
+ leafPaint.isTransparent = true;
1120
1118
  cache = image.use > 1 ? { leafPaint, paint, boxBounds: box.set(boxBounds) } : null;
1121
1119
  }
1122
1120
  if (firstUse || image.loading)
@@ -1141,7 +1139,7 @@ function image(ui, attrName, paint, boxBounds, firstUse) {
1141
1139
  ignoreRender(ui, false);
1142
1140
  if (!ui.destroyed) {
1143
1141
  if (checkSizeAndCreateData(ui, attrName, paint, image, leafPaint, boxBounds)) {
1144
- if (image.hasOpacityPixel)
1142
+ if (image.hasAlphaPixel)
1145
1143
  ui.__layout.hitCanvasChanged = true;
1146
1144
  ui.forceUpdate('surface');
1147
1145
  }
@@ -1153,6 +1151,17 @@ function image(ui, attrName, paint, boxBounds, firstUse) {
1153
1151
  onLoadError(ui, event, error);
1154
1152
  leafPaint.loadId = null;
1155
1153
  });
1154
+ if (ui.placeholderColor) {
1155
+ if (!ui.placeholderDelay)
1156
+ image.isPlacehold = true;
1157
+ else
1158
+ setTimeout(() => {
1159
+ if (!image.ready) {
1160
+ image.isPlacehold = true;
1161
+ ui.forceUpdate('surface');
1162
+ }
1163
+ }, ui.placeholderDelay);
1164
+ }
1156
1165
  }
1157
1166
  return leafPaint;
1158
1167
  }
@@ -1390,32 +1399,33 @@ const PaintImageModule = {
1390
1399
  repeatMode
1391
1400
  };
1392
1401
 
1393
- const { toPoint: toPoint$2 } = core.AroundHelper;
1402
+ const { toPoint: toPoint$2 } = core.AroundHelper, { hasTransparent } = draw.ColorConvert;
1394
1403
  const realFrom$2 = {};
1395
1404
  const realTo$2 = {};
1396
1405
  function linearGradient(paint, box) {
1397
- let { from, to, type, blendMode, opacity } = paint;
1406
+ let { from, to, type, opacity } = paint;
1398
1407
  toPoint$2(from || 'top', box, realFrom$2);
1399
1408
  toPoint$2(to || 'bottom', box, realTo$2);
1400
1409
  const style = core.Platform.canvas.createLinearGradient(realFrom$2.x, realFrom$2.y, realTo$2.x, realTo$2.y);
1401
- applyStops(style, paint.stops, opacity);
1402
1410
  const data = { type, style };
1403
- if (blendMode)
1404
- data.blendMode = blendMode;
1411
+ applyStops(data, style, paint.stops, opacity);
1405
1412
  return data;
1406
1413
  }
1407
- function applyStops(gradient, stops, opacity) {
1414
+ function applyStops(data, gradient, stops, opacity) {
1408
1415
  if (stops) {
1409
- let stop;
1416
+ let stop, color, offset, isTransparent;
1410
1417
  for (let i = 0, len = stops.length; i < len; i++) {
1411
1418
  stop = stops[i];
1412
- if (typeof stop === 'string') {
1413
- gradient.addColorStop(i / (len - 1), draw.ColorConvert.string(stop, opacity));
1414
- }
1415
- else {
1416
- gradient.addColorStop(stop.offset, draw.ColorConvert.string(stop.color, opacity));
1417
- }
1419
+ if (typeof stop === 'string')
1420
+ offset = i / (len - 1), color = draw.ColorConvert.string(stop, opacity);
1421
+ else
1422
+ offset = stop.offset, color = draw.ColorConvert.string(stop.color, opacity);
1423
+ gradient.addColorStop(offset, color);
1424
+ if (!isTransparent && hasTransparent(color))
1425
+ isTransparent = true;
1418
1426
  }
1427
+ if (isTransparent)
1428
+ data.isTransparent = true;
1419
1429
  }
1420
1430
  }
1421
1431
 
@@ -1425,17 +1435,15 @@ const { toPoint: toPoint$1 } = core.AroundHelper;
1425
1435
  const realFrom$1 = {};
1426
1436
  const realTo$1 = {};
1427
1437
  function radialGradient(paint, box) {
1428
- let { from, to, type, opacity, blendMode, stretch } = paint;
1438
+ let { from, to, type, opacity, stretch } = paint;
1429
1439
  toPoint$1(from || 'center', box, realFrom$1);
1430
1440
  toPoint$1(to || 'bottom', box, realTo$1);
1431
1441
  const style = core.Platform.canvas.createRadialGradient(realFrom$1.x, realFrom$1.y, 0, realFrom$1.x, realFrom$1.y, getDistance$1(realFrom$1, realTo$1));
1432
- applyStops(style, paint.stops, opacity);
1433
1442
  const data = { type, style };
1443
+ applyStops(data, style, paint.stops, opacity);
1434
1444
  const transform = getTransform(box, realFrom$1, realTo$1, stretch, true);
1435
1445
  if (transform)
1436
1446
  data.transform = transform;
1437
- if (blendMode)
1438
- data.blendMode = blendMode;
1439
1447
  return data;
1440
1448
  }
1441
1449
  function getTransform(box, from, to, stretch, rotate90) {
@@ -1461,17 +1469,15 @@ const { toPoint } = core.AroundHelper;
1461
1469
  const realFrom = {};
1462
1470
  const realTo = {};
1463
1471
  function conicGradient(paint, box) {
1464
- let { from, to, type, opacity, blendMode, stretch } = paint;
1472
+ let { from, to, type, opacity, stretch } = paint;
1465
1473
  toPoint(from || 'center', box, realFrom);
1466
1474
  toPoint(to || 'bottom', box, realTo);
1467
1475
  const style = core.Platform.conicGradientSupport ? core.Platform.canvas.createConicGradient(0, realFrom.x, realFrom.y) : core.Platform.canvas.createRadialGradient(realFrom.x, realFrom.y, 0, realFrom.x, realFrom.y, getDistance(realFrom, realTo));
1468
- applyStops(style, paint.stops, opacity);
1469
1476
  const data = { type, style };
1477
+ applyStops(data, style, paint.stops, opacity);
1470
1478
  const transform = getTransform(box, realFrom, realTo, stretch || 1, core.Platform.conicGradientRotate90);
1471
1479
  if (transform)
1472
1480
  data.transform = transform;
1473
- if (blendMode)
1474
- data.blendMode = blendMode;
1475
1481
  return data;
1476
1482
  }
1477
1483
 
@@ -1804,6 +1810,8 @@ function createRows(drawData, content, style) {
1804
1810
  lastCharType = null;
1805
1811
  startCharSize = charWidth = charSize = wordWidth = rowWidth = 0;
1806
1812
  word = { data: [] }, row = { words: [] };
1813
+ if (__letterSpacing)
1814
+ content = [...content];
1807
1815
  for (let i = 0, len = content.length; i < len; i++) {
1808
1816
  char = content[i];
1809
1817
  if (char === '\n') {
@@ -2238,4 +2246,3 @@ Object.keys(draw).forEach(function (k) {
2238
2246
  get: function () { return draw[k]; }
2239
2247
  });
2240
2248
  });
2241
- //# sourceMappingURL=worker.cjs.map