mirror of
https://github.com/konvajs/konva.git
synced 2025-06-28 15:23:44 +08:00
cache patterns and gradients
This commit is contained in:
parent
1b6238cbb2
commit
99e66c380f
@ -19,6 +19,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
|
|||||||
* A bit changed behavior of `removeId` (private method), now it doesn't clear node ref, if object is changed.
|
* A bit changed behavior of `removeId` (private method), now it doesn't clear node ref, if object is changed.
|
||||||
* simplified `batchDraw` method (it doesn't use `Konva.Animation`) now.
|
* simplified `batchDraw` method (it doesn't use `Konva.Animation`) now.
|
||||||
* `id` and `name` properties defaults are empty strings, not `undefined`
|
* `id` and `name` properties defaults are empty strings, not `undefined`
|
||||||
|
* Performance improvements for shapes will image patterns, linear and radial fills
|
||||||
|
|
||||||
### Removed
|
### Removed
|
||||||
* `Konva.Util.addMethods`
|
* `Konva.Util.addMethods`
|
||||||
|
108
konva.js
108
konva.js
@ -8,7 +8,7 @@
|
|||||||
* Konva JavaScript Framework v3.0.0-0
|
* Konva JavaScript Framework v3.0.0-0
|
||||||
* http://konvajs.github.io/
|
* http://konvajs.github.io/
|
||||||
* Licensed under the MIT
|
* Licensed under the MIT
|
||||||
* Date: Mon Feb 11 2019
|
* Date: Wed Feb 13 2019
|
||||||
*
|
*
|
||||||
* Original work Copyright (C) 2011 - 2013 by Eric Rowell (KineticJS)
|
* Original work Copyright (C) 2011 - 2013 by Eric Rowell (KineticJS)
|
||||||
* Modified work Copyright (C) 2014 - present by Anton Lavrenov (Konva)
|
* Modified work Copyright (C) 2014 - present by Anton Lavrenov (Konva)
|
||||||
@ -1769,29 +1769,22 @@
|
|||||||
if (fillPatternOffsetX || fillPatternOffsetY) {
|
if (fillPatternOffsetX || fillPatternOffsetY) {
|
||||||
this.translate(-1 * fillPatternOffsetX, -1 * fillPatternOffsetY);
|
this.translate(-1 * fillPatternOffsetX, -1 * fillPatternOffsetY);
|
||||||
}
|
}
|
||||||
// TODO: cache pattern
|
this.setAttr('fillStyle', shape._getFillPattern());
|
||||||
this.setAttr('fillStyle', this.createPattern(shape.getFillPatternImage(), shape.getFillPatternRepeat() || 'repeat'));
|
|
||||||
shape._fillFunc(this);
|
shape._fillFunc(this);
|
||||||
};
|
};
|
||||||
SceneContext.prototype._fillLinearGradient = function (shape) {
|
SceneContext.prototype._fillLinearGradient = function (shape) {
|
||||||
var start = shape.getFillLinearGradientStartPoint(), end = shape.getFillLinearGradientEndPoint(), colorStops = shape.getFillLinearGradientColorStops(), grd = this.createLinearGradient(start.x, start.y, end.x, end.y);
|
var grd = shape._getLinearGradient();
|
||||||
if (colorStops) {
|
if (grd) {
|
||||||
// build color stops
|
|
||||||
for (var n = 0; n < colorStops.length; n += 2) {
|
|
||||||
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
|
||||||
}
|
|
||||||
this.setAttr('fillStyle', grd);
|
this.setAttr('fillStyle', grd);
|
||||||
shape._fillFunc(this);
|
shape._fillFunc(this);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
SceneContext.prototype._fillRadialGradient = function (shape) {
|
SceneContext.prototype._fillRadialGradient = function (shape) {
|
||||||
var start = shape.getFillRadialGradientStartPoint(), end = shape.getFillRadialGradientEndPoint(), startRadius = shape.getFillRadialGradientStartRadius(), endRadius = shape.getFillRadialGradientEndRadius(), colorStops = shape.getFillRadialGradientColorStops(), grd = this.createRadialGradient(start.x, start.y, startRadius, end.x, end.y, endRadius);
|
var grd = shape._getRadialGradient();
|
||||||
// build color stops
|
if (grd) {
|
||||||
for (var n = 0; n < colorStops.length; n += 2) {
|
this.setAttr('fillStyle', grd);
|
||||||
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
shape._fillFunc(this);
|
||||||
}
|
}
|
||||||
this.setAttr('fillStyle', grd);
|
|
||||||
shape._fillFunc(this);
|
|
||||||
};
|
};
|
||||||
SceneContext.prototype._fill = function (shape) {
|
SceneContext.prototype._fill = function (shape) {
|
||||||
var hasColor = shape.fill(), fillPriority = shape.getFillPriority();
|
var hasColor = shape.fill(), fillPriority = shape.getFillPriority();
|
||||||
@ -6808,7 +6801,17 @@
|
|||||||
|
|
||||||
var HAS_SHADOW = 'hasShadow';
|
var HAS_SHADOW = 'hasShadow';
|
||||||
var SHADOW_RGBA = 'shadowRGBA';
|
var SHADOW_RGBA = 'shadowRGBA';
|
||||||
// TODO: cache gradient from context
|
var patternImage = 'patternImage';
|
||||||
|
var linearGradient = 'linearGradient';
|
||||||
|
var radialGradient = 'radialGradient';
|
||||||
|
var dummyContext;
|
||||||
|
function getDummyContext() {
|
||||||
|
if (dummyContext) {
|
||||||
|
return dummyContext;
|
||||||
|
}
|
||||||
|
dummyContext = Util.createCanvasElement().getContext('2d');
|
||||||
|
return dummyContext;
|
||||||
|
}
|
||||||
// TODO: write a test for adding destroyed shape into the layer
|
// TODO: write a test for adding destroyed shape into the layer
|
||||||
// will it draw?
|
// will it draw?
|
||||||
// will it pass hit test?
|
// will it pass hit test?
|
||||||
@ -6836,6 +6839,15 @@
|
|||||||
function _clearGetShadowRGBACache() {
|
function _clearGetShadowRGBACache() {
|
||||||
this._clearCache(SHADOW_RGBA);
|
this._clearCache(SHADOW_RGBA);
|
||||||
}
|
}
|
||||||
|
function _clearFillPatternCache() {
|
||||||
|
this._clearCache(patternImage);
|
||||||
|
}
|
||||||
|
function _clearLinearGradientCache() {
|
||||||
|
this._clearCache(linearGradient);
|
||||||
|
}
|
||||||
|
function _clearRadialGradientCache() {
|
||||||
|
this._clearCache(radialGradient);
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
* Shape constructor. Shapes are primitive objects such as rectangles,
|
* Shape constructor. Shapes are primitive objects such as rectangles,
|
||||||
* circles, text, lines, etc.
|
* circles, text, lines, etc.
|
||||||
@ -6947,6 +6959,9 @@
|
|||||||
shapes[key] = _this;
|
shapes[key] = _this;
|
||||||
_this.on('shadowColorChange.konva shadowBlurChange.konva shadowOffsetChange.konva shadowOpacityChange.konva shadowEnabledChange.konva', _clearHasShadowCache);
|
_this.on('shadowColorChange.konva shadowBlurChange.konva shadowOffsetChange.konva shadowOpacityChange.konva shadowEnabledChange.konva', _clearHasShadowCache);
|
||||||
_this.on('shadowColorChange.konva shadowOpacityChange.konva shadowEnabledChange.konva', _clearGetShadowRGBACache);
|
_this.on('shadowColorChange.konva shadowOpacityChange.konva shadowEnabledChange.konva', _clearGetShadowRGBACache);
|
||||||
|
_this.on('fillPriorityChange.konva fillPatternImageChange.konva fillPatternRepeatChange.konva', _clearFillPatternCache);
|
||||||
|
_this.on('fillPriorityChange.konva fillLinearGradientColorStopsChange.konva fillLinearGradientStartPointXChange.konva fillLinearGradientStartPointYChange.konva fillLinearGradientEndPointXChange.konva fillLinearGradientEndPointYChange.konva', _clearLinearGradientCache);
|
||||||
|
_this.on('fillPriorityChange.konva fillRadialGradientColorStopsChange.konva fillRadialGradientStartPointXChange.konva fillRadialGradientStartPointYChange.konva fillRadialGradientEndPointXChange.konva fillRadialGradientEndPointYChange.konva fillRadialGradientStartRadiusChange.konva fillRadialGradientEndRadiusChange.konva', _clearRadialGradientCache);
|
||||||
return _this;
|
return _this;
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
@ -6987,6 +7002,49 @@
|
|||||||
this.shadowOffsetX() ||
|
this.shadowOffsetX() ||
|
||||||
this.shadowOffsetY())));
|
this.shadowOffsetY())));
|
||||||
};
|
};
|
||||||
|
Shape.prototype._getFillPattern = function () {
|
||||||
|
return this._getCache(patternImage, this.__getFillPattern);
|
||||||
|
};
|
||||||
|
Shape.prototype.__getFillPattern = function () {
|
||||||
|
if (this.fillPatternImage()) {
|
||||||
|
var ctx = getDummyContext();
|
||||||
|
return ctx.createPattern(this.fillPatternImage(), this.fillPatternRepeat() || 'repeat');
|
||||||
|
}
|
||||||
|
};
|
||||||
|
Shape.prototype._getLinearGradient = function () {
|
||||||
|
return this._getCache(linearGradient, this.__getLinearGradient);
|
||||||
|
};
|
||||||
|
Shape.prototype.__getLinearGradient = function () {
|
||||||
|
var colorStops = this.fillLinearGradientColorStops();
|
||||||
|
if (colorStops) {
|
||||||
|
var ctx = getDummyContext();
|
||||||
|
var start = this.fillLinearGradientStartPoint();
|
||||||
|
var end = this.fillLinearGradientEndPoint();
|
||||||
|
var grd = ctx.createLinearGradient(start.x, start.y, end.x, end.y);
|
||||||
|
// build color stops
|
||||||
|
for (var n = 0; n < colorStops.length; n += 2) {
|
||||||
|
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
||||||
|
}
|
||||||
|
return grd;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
Shape.prototype._getRadialGradient = function () {
|
||||||
|
return this._getCache(radialGradient, this.__getRadialGradient);
|
||||||
|
};
|
||||||
|
Shape.prototype.__getRadialGradient = function () {
|
||||||
|
var colorStops = this.fillRadialGradientColorStops();
|
||||||
|
if (colorStops) {
|
||||||
|
var ctx = getDummyContext();
|
||||||
|
var start = this.fillRadialGradientStartPoint();
|
||||||
|
var end = this.fillRadialGradientEndPoint();
|
||||||
|
var grd = ctx.createRadialGradient(start.x, start.y, this.fillRadialGradientStartRadius(), end.x, end.y, this.fillRadialGradientEndRadius());
|
||||||
|
// build color stops
|
||||||
|
for (var n = 0; n < colorStops.length; n += 2) {
|
||||||
|
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
||||||
|
}
|
||||||
|
return grd;
|
||||||
|
}
|
||||||
|
};
|
||||||
Shape.prototype.getShadowRGBA = function () {
|
Shape.prototype.getShadowRGBA = function () {
|
||||||
return this._getCache(SHADOW_RGBA, this._getShadowRGBA);
|
return this._getCache(SHADOW_RGBA, this._getShadowRGBA);
|
||||||
};
|
};
|
||||||
@ -12300,13 +12358,13 @@
|
|||||||
],
|
],
|
||||||
// cached variables
|
// cached variables
|
||||||
attrChangeListLen$1 = ATTR_CHANGE_LIST$1.length;
|
attrChangeListLen$1 = ATTR_CHANGE_LIST$1.length;
|
||||||
var dummyContext;
|
var dummyContext$1;
|
||||||
function getDummyContext() {
|
function getDummyContext$1() {
|
||||||
if (dummyContext) {
|
if (dummyContext$1) {
|
||||||
return dummyContext;
|
return dummyContext$1;
|
||||||
}
|
}
|
||||||
dummyContext = Util.createCanvasElement().getContext(CONTEXT_2D);
|
dummyContext$1 = Util.createCanvasElement().getContext(CONTEXT_2D);
|
||||||
return dummyContext;
|
return dummyContext$1;
|
||||||
}
|
}
|
||||||
function _fillFunc$1(context) {
|
function _fillFunc$1(context) {
|
||||||
context.fillText(this.partialText, 0, 0);
|
context.fillText(this.partialText, 0, 0);
|
||||||
@ -12565,7 +12623,7 @@
|
|||||||
};
|
};
|
||||||
// TODO: make it public, rename to "measure text"?
|
// TODO: make it public, rename to "measure text"?
|
||||||
Text.prototype._getTextSize = function (text) {
|
Text.prototype._getTextSize = function (text) {
|
||||||
var _context = getDummyContext(), fontSize = this.fontSize(), metrics;
|
var _context = getDummyContext$1(), fontSize = this.fontSize(), metrics;
|
||||||
_context.save();
|
_context.save();
|
||||||
_context.font = this._getContextFont();
|
_context.font = this._getContextFont();
|
||||||
metrics = _context.measureText(text);
|
metrics = _context.measureText(text);
|
||||||
@ -12605,7 +12663,7 @@
|
|||||||
Text.prototype._getTextWidth = function (text) {
|
Text.prototype._getTextWidth = function (text) {
|
||||||
var letterSpacing = this.letterSpacing();
|
var letterSpacing = this.letterSpacing();
|
||||||
var length = text.length;
|
var length = text.length;
|
||||||
return (getDummyContext().measureText(text).width +
|
return (getDummyContext$1().measureText(text).width +
|
||||||
(length ? letterSpacing * (length - 1) : 0));
|
(length ? letterSpacing * (length - 1) : 0));
|
||||||
};
|
};
|
||||||
Text.prototype._setTextData = function () {
|
Text.prototype._setTextData = function () {
|
||||||
@ -12613,7 +12671,7 @@
|
|||||||
// align = this.align(),
|
// align = this.align(),
|
||||||
shouldWrap = wrap !== NONE$1, wrapAtWord = wrap !== CHAR && shouldWrap, shouldAddEllipsis = this.ellipsis() && !shouldWrap;
|
shouldWrap = wrap !== NONE$1, wrapAtWord = wrap !== CHAR && shouldWrap, shouldAddEllipsis = this.ellipsis() && !shouldWrap;
|
||||||
this.textArr = [];
|
this.textArr = [];
|
||||||
getDummyContext().font = this._getContextFont();
|
getDummyContext$1().font = this._getContextFont();
|
||||||
var additionalWidth = shouldAddEllipsis ? this._getTextWidth(ELLIPSIS) : 0;
|
var additionalWidth = shouldAddEllipsis ? this._getTextWidth(ELLIPSIS) : 0;
|
||||||
for (var i = 0, max = lines.length; i < max; ++i) {
|
for (var i = 0, max = lines.length; i < max; ++i) {
|
||||||
var line = lines[i];
|
var line = lines[i];
|
||||||
|
4
konva.min.js
vendored
4
konva.min.js
vendored
File diff suppressed because one or more lines are too long
@ -496,52 +496,23 @@ export class SceneContext extends Context {
|
|||||||
this.translate(-1 * fillPatternOffsetX, -1 * fillPatternOffsetY);
|
this.translate(-1 * fillPatternOffsetX, -1 * fillPatternOffsetY);
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: cache pattern
|
this.setAttr('fillStyle', shape._getFillPattern());
|
||||||
this.setAttr(
|
|
||||||
'fillStyle',
|
|
||||||
this.createPattern(
|
|
||||||
shape.getFillPatternImage(),
|
|
||||||
shape.getFillPatternRepeat() || 'repeat'
|
|
||||||
)
|
|
||||||
);
|
|
||||||
shape._fillFunc(this);
|
shape._fillFunc(this);
|
||||||
}
|
}
|
||||||
_fillLinearGradient(shape) {
|
_fillLinearGradient(shape) {
|
||||||
var start = shape.getFillLinearGradientStartPoint(),
|
var grd = shape._getLinearGradient();
|
||||||
end = shape.getFillLinearGradientEndPoint(),
|
|
||||||
colorStops = shape.getFillLinearGradientColorStops(),
|
|
||||||
grd = this.createLinearGradient(start.x, start.y, end.x, end.y);
|
|
||||||
|
|
||||||
if (colorStops) {
|
if (grd) {
|
||||||
// build color stops
|
|
||||||
for (var n = 0; n < colorStops.length; n += 2) {
|
|
||||||
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
|
||||||
}
|
|
||||||
this.setAttr('fillStyle', grd);
|
this.setAttr('fillStyle', grd);
|
||||||
shape._fillFunc(this);
|
shape._fillFunc(this);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
_fillRadialGradient(shape) {
|
_fillRadialGradient(shape) {
|
||||||
var start = shape.getFillRadialGradientStartPoint(),
|
var grd = shape._getRadialGradient();
|
||||||
end = shape.getFillRadialGradientEndPoint(),
|
if (grd) {
|
||||||
startRadius = shape.getFillRadialGradientStartRadius(),
|
this.setAttr('fillStyle', grd);
|
||||||
endRadius = shape.getFillRadialGradientEndRadius(),
|
shape._fillFunc(this);
|
||||||
colorStops = shape.getFillRadialGradientColorStops(),
|
|
||||||
grd = this.createRadialGradient(
|
|
||||||
start.x,
|
|
||||||
start.y,
|
|
||||||
startRadius,
|
|
||||||
end.x,
|
|
||||||
end.y,
|
|
||||||
endRadius
|
|
||||||
);
|
|
||||||
|
|
||||||
// build color stops
|
|
||||||
for (var n = 0; n < colorStops.length; n += 2) {
|
|
||||||
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
|
||||||
}
|
}
|
||||||
this.setAttr('fillStyle', grd);
|
|
||||||
shape._fillFunc(this);
|
|
||||||
}
|
}
|
||||||
_fill(shape) {
|
_fill(shape) {
|
||||||
var hasColor = shape.fill(),
|
var hasColor = shape.fill(),
|
||||||
|
104
src/Shape.ts
104
src/Shape.ts
@ -8,8 +8,19 @@ import { Context } from './Context';
|
|||||||
|
|
||||||
var HAS_SHADOW = 'hasShadow';
|
var HAS_SHADOW = 'hasShadow';
|
||||||
var SHADOW_RGBA = 'shadowRGBA';
|
var SHADOW_RGBA = 'shadowRGBA';
|
||||||
|
var patternImage = 'patternImage';
|
||||||
|
var linearGradient = 'linearGradient';
|
||||||
|
var radialGradient = 'radialGradient';
|
||||||
|
|
||||||
|
var dummyContext;
|
||||||
|
function getDummyContext() {
|
||||||
|
if (dummyContext) {
|
||||||
|
return dummyContext;
|
||||||
|
}
|
||||||
|
dummyContext = Util.createCanvasElement().getContext('2d');
|
||||||
|
return dummyContext;
|
||||||
|
}
|
||||||
|
|
||||||
// TODO: cache gradient from context
|
|
||||||
// TODO: write a test for adding destroyed shape into the layer
|
// TODO: write a test for adding destroyed shape into the layer
|
||||||
// will it draw?
|
// will it draw?
|
||||||
// will it pass hit test?
|
// will it pass hit test?
|
||||||
@ -42,6 +53,18 @@ function _clearGetShadowRGBACache() {
|
|||||||
this._clearCache(SHADOW_RGBA);
|
this._clearCache(SHADOW_RGBA);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function _clearFillPatternCache() {
|
||||||
|
this._clearCache(patternImage);
|
||||||
|
}
|
||||||
|
|
||||||
|
function _clearLinearGradientCache() {
|
||||||
|
this._clearCache(linearGradient);
|
||||||
|
}
|
||||||
|
|
||||||
|
function _clearRadialGradientCache() {
|
||||||
|
this._clearCache(radialGradient);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shape constructor. Shapes are primitive objects such as rectangles,
|
* Shape constructor. Shapes are primitive objects such as rectangles,
|
||||||
* circles, text, lines, etc.
|
* circles, text, lines, etc.
|
||||||
@ -101,6 +124,21 @@ export class Shape extends Node {
|
|||||||
'shadowColorChange.konva shadowOpacityChange.konva shadowEnabledChange.konva',
|
'shadowColorChange.konva shadowOpacityChange.konva shadowEnabledChange.konva',
|
||||||
_clearGetShadowRGBACache
|
_clearGetShadowRGBACache
|
||||||
);
|
);
|
||||||
|
|
||||||
|
this.on(
|
||||||
|
'fillPriorityChange.konva fillPatternImageChange.konva fillPatternRepeatChange.konva',
|
||||||
|
_clearFillPatternCache
|
||||||
|
);
|
||||||
|
|
||||||
|
this.on(
|
||||||
|
'fillPriorityChange.konva fillLinearGradientColorStopsChange.konva fillLinearGradientStartPointXChange.konva fillLinearGradientStartPointYChange.konva fillLinearGradientEndPointXChange.konva fillLinearGradientEndPointYChange.konva',
|
||||||
|
_clearLinearGradientCache
|
||||||
|
);
|
||||||
|
|
||||||
|
this.on(
|
||||||
|
'fillPriorityChange.konva fillRadialGradientColorStopsChange.konva fillRadialGradientStartPointXChange.konva fillRadialGradientStartPointYChange.konva fillRadialGradientEndPointXChange.konva fillRadialGradientEndPointYChange.konva fillRadialGradientStartRadiusChange.konva fillRadialGradientEndRadiusChange.konva',
|
||||||
|
_clearRadialGradientCache
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -146,6 +184,64 @@ export class Shape extends Node {
|
|||||||
))
|
))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
_getFillPattern() {
|
||||||
|
return this._getCache(patternImage, this.__getFillPattern);
|
||||||
|
}
|
||||||
|
__getFillPattern() {
|
||||||
|
if (this.fillPatternImage()) {
|
||||||
|
var ctx = getDummyContext();
|
||||||
|
return ctx.createPattern(
|
||||||
|
this.fillPatternImage(),
|
||||||
|
this.fillPatternRepeat() || 'repeat'
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_getLinearGradient() {
|
||||||
|
return this._getCache(linearGradient, this.__getLinearGradient);
|
||||||
|
}
|
||||||
|
__getLinearGradient() {
|
||||||
|
var colorStops = this.fillLinearGradientColorStops();
|
||||||
|
if (colorStops) {
|
||||||
|
var ctx = getDummyContext();
|
||||||
|
|
||||||
|
var start = this.fillLinearGradientStartPoint();
|
||||||
|
var end = this.fillLinearGradientEndPoint();
|
||||||
|
var grd = ctx.createLinearGradient(start.x, start.y, end.x, end.y);
|
||||||
|
|
||||||
|
// build color stops
|
||||||
|
for (var n = 0; n < colorStops.length; n += 2) {
|
||||||
|
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
||||||
|
}
|
||||||
|
return grd;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
_getRadialGradient() {
|
||||||
|
return this._getCache(radialGradient, this.__getRadialGradient);
|
||||||
|
}
|
||||||
|
__getRadialGradient() {
|
||||||
|
var colorStops = this.fillRadialGradientColorStops();
|
||||||
|
if (colorStops) {
|
||||||
|
var ctx = getDummyContext();
|
||||||
|
|
||||||
|
var start = this.fillRadialGradientStartPoint();
|
||||||
|
var end = this.fillRadialGradientEndPoint();
|
||||||
|
var grd = ctx.createRadialGradient(
|
||||||
|
start.x,
|
||||||
|
start.y,
|
||||||
|
this.fillRadialGradientStartRadius(),
|
||||||
|
end.x,
|
||||||
|
end.y,
|
||||||
|
this.fillRadialGradientEndRadius()
|
||||||
|
);
|
||||||
|
|
||||||
|
// build color stops
|
||||||
|
for (var n = 0; n < colorStops.length; n += 2) {
|
||||||
|
grd.addColorStop(colorStops[n], colorStops[n + 1]);
|
||||||
|
}
|
||||||
|
return grd;
|
||||||
|
}
|
||||||
|
}
|
||||||
getShadowRGBA() {
|
getShadowRGBA() {
|
||||||
return this._getCache(SHADOW_RGBA, this._getShadowRGBA);
|
return this._getCache(SHADOW_RGBA, this._getShadowRGBA);
|
||||||
}
|
}
|
||||||
@ -550,6 +646,12 @@ export class Shape extends Node {
|
|||||||
fillRadialGradientStartRadius: GetSet<number, this>;
|
fillRadialGradientStartRadius: GetSet<number, this>;
|
||||||
fillRadialGradientEndRadius: GetSet<number, this>;
|
fillRadialGradientEndRadius: GetSet<number, this>;
|
||||||
fillRadialGradientColorStops: GetSet<Array<number | string>, this>;
|
fillRadialGradientColorStops: GetSet<Array<number | string>, this>;
|
||||||
|
fillRadialGradientStartPoint: GetSet<Vector2d, this>;
|
||||||
|
fillRadialGradientStartPointX: GetSet<number, this>;
|
||||||
|
fillRadialGradientStartPointY: GetSet<number, this>;
|
||||||
|
fillRadialGradientEndPoint: GetSet<Vector2d, this>;
|
||||||
|
fillRadialGradientEndPointX: GetSet<number, this>;
|
||||||
|
fillRadialGradientEndPointY: GetSet<number, this>;
|
||||||
fillPatternOffset: GetSet<Vector2d, this>;
|
fillPatternOffset: GetSet<Vector2d, this>;
|
||||||
fillPatternOffsetX: GetSet<number, this>;
|
fillPatternOffsetX: GetSet<number, this>;
|
||||||
fillPatternOffsetY: GetSet<number, this>;
|
fillPatternOffsetY: GetSet<number, this>;
|
||||||
|
@ -377,7 +377,7 @@ suite('Shape', function() {
|
|||||||
|
|
||||||
assert.equal(
|
assert.equal(
|
||||||
trace,
|
trace,
|
||||||
'clearRect(0,0,578,200);save();transform(3,0,0,1.5,10,15);beginPath();rect(0,0,100,100);closePath();createLinearGradient(0,0,100,100);fillStyle=[object CanvasGradient];fill();lineWidth=2;createLinearGradient(0,0,100,100);strokeStyle=[object CanvasGradient];stroke();restore();'
|
'clearRect(0,0,578,200);save();transform(3,0,0,1.5,10,15);beginPath();rect(0,0,100,100);closePath();fillStyle=[object CanvasGradient];fill();lineWidth=2;createLinearGradient(0,0,100,100);strokeStyle=[object CanvasGradient];stroke();restore();'
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -1471,4 +1471,307 @@ suite('Shape', function() {
|
|||||||
layer.add(rect);
|
layer.add(rect);
|
||||||
stage.add(layer);
|
stage.add(layer);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// ======================================================
|
||||||
|
test('cache fill pattern', function(done) {
|
||||||
|
var imageObj = new Image();
|
||||||
|
imageObj.onload = function() {
|
||||||
|
var stage = addStage();
|
||||||
|
var layer = new Konva.Layer();
|
||||||
|
|
||||||
|
var star = new Konva.Star({
|
||||||
|
x: 200,
|
||||||
|
y: 100,
|
||||||
|
numPoints: 5,
|
||||||
|
innerRadius: 40,
|
||||||
|
outerRadius: 70,
|
||||||
|
|
||||||
|
fillPatternImage: imageObj,
|
||||||
|
fillPatternX: -20,
|
||||||
|
fillPatternY: -30,
|
||||||
|
fillPatternScale: { x: 0.5, y: 0.5 },
|
||||||
|
fillPatternOffset: { x: 219, y: 150 },
|
||||||
|
fillPatternRotation: 90,
|
||||||
|
fillPatternRepeat: 'no-repeat',
|
||||||
|
|
||||||
|
stroke: 'blue',
|
||||||
|
strokeWidth: 5,
|
||||||
|
draggable: true
|
||||||
|
});
|
||||||
|
|
||||||
|
layer.add(star);
|
||||||
|
stage.add(layer);
|
||||||
|
|
||||||
|
var ctx = layer.getContext();
|
||||||
|
var oldCreate = ctx.createPattern;
|
||||||
|
|
||||||
|
var callCount = 0;
|
||||||
|
ctx.createPattern = function() {
|
||||||
|
callCount += 1;
|
||||||
|
return oldCreate.apply(this, arguments);
|
||||||
|
};
|
||||||
|
|
||||||
|
layer.draw();
|
||||||
|
layer.draw();
|
||||||
|
assert.equal(callCount, 0);
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
imageObj.src = 'assets/darth-vader.jpg';
|
||||||
|
});
|
||||||
|
|
||||||
|
test('recache fill pattern on changes', function(done) {
|
||||||
|
var imageObj = new Image();
|
||||||
|
imageObj.onload = function() {
|
||||||
|
var stage = addStage();
|
||||||
|
var layer = new Konva.Layer();
|
||||||
|
|
||||||
|
var star = new Konva.Star({
|
||||||
|
x: 200,
|
||||||
|
y: 100,
|
||||||
|
numPoints: 5,
|
||||||
|
innerRadius: 40,
|
||||||
|
outerRadius: 70,
|
||||||
|
|
||||||
|
fillPatternImage: imageObj,
|
||||||
|
fillPatternX: -20,
|
||||||
|
fillPatternY: -30,
|
||||||
|
fillPatternScale: { x: 0.5, y: 0.5 },
|
||||||
|
fillPatternOffset: { x: 219, y: 150 },
|
||||||
|
fillPatternRotation: 90,
|
||||||
|
fillPatternRepeat: 'no-repeat',
|
||||||
|
|
||||||
|
stroke: 'blue',
|
||||||
|
strokeWidth: 5,
|
||||||
|
draggable: true
|
||||||
|
});
|
||||||
|
|
||||||
|
layer.add(star);
|
||||||
|
stage.add(layer);
|
||||||
|
|
||||||
|
var pattern1 = star._getFillPattern();
|
||||||
|
|
||||||
|
star.fillPatternImage(document.createElement('canvas'));
|
||||||
|
|
||||||
|
var pattern2 = star._getFillPattern();
|
||||||
|
|
||||||
|
assert.notEqual(pattern1, pattern2);
|
||||||
|
|
||||||
|
star.fillPatternRepeat('repeat');
|
||||||
|
|
||||||
|
var pattern3 = star._getFillPattern();
|
||||||
|
|
||||||
|
assert.notEqual(pattern2, pattern3);
|
||||||
|
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
imageObj.src = 'assets/darth-vader.jpg';
|
||||||
|
});
|
||||||
|
|
||||||
|
// ======================================================
|
||||||
|
test('cache linear gradient', function() {
|
||||||
|
var stage = addStage();
|
||||||
|
var layer = new Konva.Layer();
|
||||||
|
|
||||||
|
var star = new Konva.Star({
|
||||||
|
x: 200,
|
||||||
|
y: 100,
|
||||||
|
numPoints: 5,
|
||||||
|
innerRadius: 40,
|
||||||
|
outerRadius: 70,
|
||||||
|
|
||||||
|
fillLinearGradientStartPoint: { x: -50, y: -50 },
|
||||||
|
fillLinearGradientEndPoint: { x: 50, y: 50 },
|
||||||
|
fillLinearGradientColorStops: [0, 'red', 1, 'yellow'],
|
||||||
|
|
||||||
|
stroke: 'blue',
|
||||||
|
strokeWidth: 5,
|
||||||
|
draggable: true
|
||||||
|
});
|
||||||
|
|
||||||
|
layer.add(star);
|
||||||
|
stage.add(layer);
|
||||||
|
|
||||||
|
var ctx = layer.getContext();
|
||||||
|
var oldCreate = ctx.createLinearGradient;
|
||||||
|
|
||||||
|
var callCount = 0;
|
||||||
|
ctx.createLinearGradient = function() {
|
||||||
|
callCount += 1;
|
||||||
|
return oldCreate.apply(this, arguments);
|
||||||
|
};
|
||||||
|
|
||||||
|
layer.draw();
|
||||||
|
layer.draw();
|
||||||
|
assert.equal(callCount, 0);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('recache linear gradient on changes', function() {
|
||||||
|
var stage = addStage();
|
||||||
|
var layer = new Konva.Layer();
|
||||||
|
|
||||||
|
var star = new Konva.Star({
|
||||||
|
x: 200,
|
||||||
|
y: 100,
|
||||||
|
numPoints: 5,
|
||||||
|
innerRadius: 40,
|
||||||
|
outerRadius: 70,
|
||||||
|
|
||||||
|
fillLinearGradientStartPoint: { x: -50, y: -50 },
|
||||||
|
fillLinearGradientEndPoint: { x: 50, y: 50 },
|
||||||
|
fillLinearGradientColorStops: [0, 'red', 1, 'yellow'],
|
||||||
|
|
||||||
|
stroke: 'blue',
|
||||||
|
strokeWidth: 5,
|
||||||
|
draggable: true
|
||||||
|
});
|
||||||
|
|
||||||
|
layer.add(star);
|
||||||
|
stage.add(layer);
|
||||||
|
|
||||||
|
var gradient1 = star._getLinearGradient();
|
||||||
|
|
||||||
|
star.fillLinearGradientStartPointX(-10);
|
||||||
|
|
||||||
|
var gradient2 = star._getLinearGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient1, gradient2);
|
||||||
|
|
||||||
|
star.fillLinearGradientStartPointY(-10);
|
||||||
|
|
||||||
|
var gradient3 = star._getLinearGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient2, gradient3);
|
||||||
|
|
||||||
|
star.fillLinearGradientEndPointX(100);
|
||||||
|
|
||||||
|
var gradient4 = star._getLinearGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient3, gradient4);
|
||||||
|
|
||||||
|
star.fillLinearGradientEndPointY(100);
|
||||||
|
|
||||||
|
var gradient5 = star._getLinearGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient4, gradient5);
|
||||||
|
|
||||||
|
star.fillLinearGradientColorStops([0, 'red', 1, 'green']);
|
||||||
|
|
||||||
|
var gradient6 = star._getLinearGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient5, gradient6);
|
||||||
|
|
||||||
|
layer.draw();
|
||||||
|
});
|
||||||
|
|
||||||
|
// ======================================================
|
||||||
|
test('cache radial gradient', function() {
|
||||||
|
var stage = addStage();
|
||||||
|
var layer = new Konva.Layer();
|
||||||
|
|
||||||
|
var star = new Konva.Star({
|
||||||
|
x: 200,
|
||||||
|
y: 100,
|
||||||
|
numPoints: 5,
|
||||||
|
innerRadius: 40,
|
||||||
|
outerRadius: 70,
|
||||||
|
|
||||||
|
fillRadialGradientStartPoint: { x: 0, y: 0 },
|
||||||
|
fillRadialGradientStartRadius: 0,
|
||||||
|
fillRadialGradientEndPoint: { x: 0, y: 0 },
|
||||||
|
fillRadialGradientEndRadius: 70,
|
||||||
|
fillRadialGradientColorStops: [0, 'red', 0.5, 'yellow', 1, 'blue'],
|
||||||
|
|
||||||
|
stroke: 'blue',
|
||||||
|
strokeWidth: 5,
|
||||||
|
draggable: true
|
||||||
|
});
|
||||||
|
|
||||||
|
layer.add(star);
|
||||||
|
stage.add(layer);
|
||||||
|
|
||||||
|
var ctx = layer.getContext();
|
||||||
|
var oldCreate = ctx.createRadialGradient;
|
||||||
|
|
||||||
|
var callCount = 0;
|
||||||
|
ctx.createRadialGradient = function() {
|
||||||
|
callCount += 1;
|
||||||
|
return oldCreate.apply(this, arguments);
|
||||||
|
};
|
||||||
|
|
||||||
|
layer.draw();
|
||||||
|
layer.draw();
|
||||||
|
assert.equal(callCount, 0);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('recache linear gradient on changes', function() {
|
||||||
|
var stage = addStage();
|
||||||
|
var layer = new Konva.Layer();
|
||||||
|
|
||||||
|
var star = new Konva.Star({
|
||||||
|
x: 200,
|
||||||
|
y: 100,
|
||||||
|
numPoints: 5,
|
||||||
|
innerRadius: 40,
|
||||||
|
outerRadius: 70,
|
||||||
|
|
||||||
|
fillRadialGradientStartPoint: { x: 0, y: 0 },
|
||||||
|
fillRadialGradientStartRadius: 0,
|
||||||
|
fillRadialGradientEndPoint: { x: 0, y: 0 },
|
||||||
|
fillRadialGradientEndRadius: 70,
|
||||||
|
fillRadialGradientColorStops: [0, 'red', 0.5, 'yellow', 1, 'blue'],
|
||||||
|
|
||||||
|
stroke: 'blue',
|
||||||
|
strokeWidth: 5,
|
||||||
|
draggable: true
|
||||||
|
});
|
||||||
|
|
||||||
|
layer.add(star);
|
||||||
|
stage.add(layer);
|
||||||
|
|
||||||
|
var gradient1 = star._getRadialGradient();
|
||||||
|
|
||||||
|
star.fillRadialGradientStartPointX(-10);
|
||||||
|
|
||||||
|
var gradient2 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient1, gradient2);
|
||||||
|
|
||||||
|
star.fillRadialGradientStartPointY(-10);
|
||||||
|
|
||||||
|
var gradient3 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient2, gradient3);
|
||||||
|
|
||||||
|
star.fillRadialGradientEndPointX(100);
|
||||||
|
|
||||||
|
var gradient4 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient3, gradient4);
|
||||||
|
|
||||||
|
star.fillRadialGradientEndPointY(100);
|
||||||
|
|
||||||
|
var gradient5 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient4, gradient5);
|
||||||
|
|
||||||
|
star.fillRadialGradientColorStops([0, 'red', 1, 'green']);
|
||||||
|
|
||||||
|
var gradient6 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient5, gradient6);
|
||||||
|
|
||||||
|
star.fillRadialGradientStartRadius(10);
|
||||||
|
|
||||||
|
var gradient7 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient6, gradient7);
|
||||||
|
|
||||||
|
star.fillRadialGradientEndRadius(200);
|
||||||
|
|
||||||
|
var gradient8 = star._getRadialGradient();
|
||||||
|
|
||||||
|
assert.notEqual(gradient7, gradient8);
|
||||||
|
|
||||||
|
layer.draw();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
Loading…
Reference in New Issue
Block a user