Show a warning for incorrect value for component setters. Fix some TODOs

This commit is contained in:
Anton Lavrenov 2019-01-27 15:43:50 -05:00
parent a0b2f027ba
commit 31785f6323
13 changed files with 141 additions and 1352 deletions

View File

@ -9,6 +9,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
* Show a warning when a stage has too many layers * Show a warning when a stage has too many layers
* Show a warning on duplicate ids * Show a warning on duplicate ids
* Show a warning on weird class in `Node.create` parsing from JSON * Show a warning on weird class in `Node.create` parsing from JSON
* Show a warning for incorrect value for component setters.
### Changed ### Changed
* Fixes inconsistent `layer.setSize()` method. Now it has same arguments as any container. * Fixes inconsistent `layer.setSize()` method. Now it has same arguments as any container.

1409
konva.js

File diff suppressed because it is too large Load Diff

4
konva.min.js vendored

File diff suppressed because one or more lines are too long

View File

@ -59,7 +59,8 @@ export abstract class BaseLayer extends Container {
return this.getCanvas().getContext(); return this.getCanvas().getContext();
} }
/** /**
* clear scene and hit canvas contexts tied to the layer * clear scene and hit canvas contexts tied to the layer.
* This function doesn't remove any nodes. It just clear canvas element.
* @method * @method
* @name Konva.BaseLayer#clear * @name Konva.BaseLayer#clear
* @param {Object} [bounds] * @param {Object} [bounds]

View File

@ -1,5 +1,6 @@
import { isUnminified } from './Global'; import { isUnminified } from './Global';
import { Util } from './Util'; import { Util } from './Util';
import Konva from './index';
var GET = 'get', var GET = 'get',
SET = 'set'; SET = 'set';
@ -62,6 +63,8 @@ export const Factory = {
return ret; return ret;
}; };
var basicValidator = Validators.getComponentValidator(components);
// setter // setter
constructor.prototype[setter] = function(val) { constructor.prototype[setter] = function(val) {
var oldVal = this.attrs[attr], var oldVal = this.attrs[attr],
@ -71,6 +74,10 @@ export const Factory = {
val = validator.call(this, val); val = validator.call(this, val);
} }
if (basicValidator) {
basicValidator.call(this, val, attr);
}
for (key in val) { for (key in val) {
if (!val.hasOwnProperty(key)) { if (!val.hasOwnProperty(key)) {
continue; continue;
@ -288,5 +295,21 @@ export const Validators = {
return val; return val;
}; };
} }
},
getComponentValidator(components) {
if (isUnminified) {
return function(val, attr) {
if (!Util.isObject(val)) {
Util.warn(
Validators._formatValue(val) +
' is a not valid value for "' +
attr +
'" attribute. The value should be an object with properties ' +
components
);
}
return val;
};
}
} }
}; };

View File

@ -2157,6 +2157,7 @@ export abstract class Node {
} else { } else {
this.on('mousedown.konva touchstart.konva', function(evt) { this.on('mousedown.konva touchstart.konva', function(evt) {
// ignore right and middle buttons // ignore right and middle buttons
// TODO: should we add a global config for buttons?
if (evt.evt.button === 1 || evt.evt.button === 2) { if (evt.evt.button === 1 || evt.evt.button === 2) {
return; return;
} }
@ -2225,7 +2226,7 @@ export abstract class Node {
enhance: GetSet<number, this>; enhance: GetSet<number, this>;
filters: GetSet<Filter[], this>; filters: GetSet<Filter[], this>;
position: GetSet<Vector2d, this>; position: GetSet<Vector2d, this>;
size: GetSet<Vector2d, this>; size: GetSet<{ width: number; height: number }, this>;
id: GetSet<string, this>; id: GetSet<string, this>;
@ -2441,7 +2442,6 @@ Factory.addGetterSetter(Node, 'opacity', 1, Validators.getNumberValidator());
* node.opacity(0.5); * node.opacity(0.5);
*/ */
// TODO: should default name be empty string?
Factory.addGetterSetter(Node, 'name', '', Validators.getStringValidator()); Factory.addGetterSetter(Node, 'name', '', Validators.getStringValidator());
/** /**
@ -2881,7 +2881,7 @@ Factory.addGetterSetter(Node, 'size');
* // important pos - is absolute position of the node * // important pos - is absolute position of the node
* // you should return absolute position too * // you should return absolute position too
* return { * return {
* x: this.getAbsolutePosition().x, * x: this.absolutePosition().x,
* y: pos.y * y: pos.y
* }; * };
* }); * });

View File

@ -179,7 +179,6 @@ export class Shape extends Node {
return ( return (
this.strokeEnabled() && this.strokeEnabled() &&
!!(this.stroke() || this.strokeLinearGradientColorStops()) !!(this.stroke() || this.strokeLinearGradientColorStops())
// TODO: do we need radial gradient
// this.getStrokeRadialGradientColorStops() // this.getStrokeRadialGradientColorStops()
); );
} }
@ -216,8 +215,10 @@ export class Shape extends Node {
delete shapes[this.colorKey]; delete shapes[this.colorKey];
return this; return this;
} }
// TODO: write why do we need it, // why do we need buffer canvas?
// try to use it without stage (use global buffer canvas) // it give better result when a shape has
// stroke with fill and with some opacity
// TODO: try to use it without stage (use global buffer canvas)
_useBufferCanvas(caching) { _useBufferCanvas(caching) {
return ( return (
(!caching || this.hasShadow()) && (!caching || this.hasShadow()) &&
@ -241,7 +242,7 @@ export class Shape extends Node {
* *
*/ */
getSelfRect() { getSelfRect() {
var size = this.getSize(); var size = this.size();
return { return {
x: this._centroid ? Math.round(-size.width / 2) : 0, x: this._centroid ? Math.round(-size.width / 2) : 0,
y: this._centroid ? Math.round(-size.height / 2) : 0, y: this._centroid ? Math.round(-size.height / 2) : 0,

View File

@ -7,7 +7,6 @@ import { GetSet, Vector2d } from './types';
import { Shape } from './Shape'; import { Shape } from './Shape';
import { BaseLayer } from './BaseLayer'; import { BaseLayer } from './BaseLayer';
// TODO: add a warning if stage has too many layers
// TODO: remove "content" events from docs // TODO: remove "content" events from docs
// CONSTANTS // CONSTANTS
@ -110,7 +109,6 @@ export class Stage extends Container {
constructor(config) { constructor(config) {
super(config); super(config);
this.nodeType = STAGE;
this._buildDOM(); this._buildDOM();
this._bindContentEvents(); this._bindContentEvents();
stages.push(this); stages.push(this);
@ -745,7 +743,6 @@ export class Stage extends Container {
} }
} }
// currently cache function is now working for stage, because stage has no its own canvas element // currently cache function is now working for stage, because stage has no its own canvas element
// TODO: may be it is better to cache all children layers?
cache() { cache() {
Util.warn( Util.warn(
'Cache function is not allowed for stage. You may use cache only for layers, groups and shapes.' 'Cache function is not allowed for stage. You may use cache only for layers, groups and shapes.'
@ -771,6 +768,8 @@ export class Stage extends Container {
container: GetSet<HTMLDivElement, this>; container: GetSet<HTMLDivElement, this>;
} }
Stage.prototype.nodeType = STAGE;
// TODO: test for replacing container // TODO: test for replacing container
Factory.addGetterSetter(Stage, 'container'); Factory.addGetterSetter(Stage, 'container');

View File

@ -305,8 +305,7 @@ export class Tag extends Shape {
}; };
} }
// TODO: not a string, but a strict set pointerDirection: GetSet<'left' | 'top' | 'right' | 'bottom', this>;
pointerDirection: GetSet<string, this>;
pointerWidth: GetSet<number, this>; pointerWidth: GetSet<number, this>;
pointerHeight: GetSet<number, this>; pointerHeight: GetSet<number, this>;
cornerRadius: GetSet<number, this>; cornerRadius: GetSet<number, this>;

View File

@ -188,7 +188,8 @@ export class Text extends Shape {
? totalWidth - padding * 2 ? totalWidth - padding * 2
: width; : width;
context.lineTo(Math.round(lineWidth), Math.round(lineHeightPx / 2)); context.lineTo(Math.round(lineWidth), Math.round(lineHeightPx / 2));
// TODO: I have no idea what is real ratio
// I have no idea what is real ratio
// just /15 looks good enough // just /15 looks good enough
context.lineWidth = fontSize / 15; context.lineWidth = fontSize / 15;
context.strokeStyle = fill; context.strokeStyle = fill;
@ -286,7 +287,7 @@ export class Text extends Shape {
return this.textHeight; return this.textHeight;
} }
// TODO: make it public? // TODO: make it public, rename to "measure text"?
_getTextSize(text) { _getTextSize(text) {
var _context = getDummyContext(), var _context = getDummyContext(),
fontSize = this.fontSize(), fontSize = this.fontSize(),

View File

@ -433,7 +433,7 @@ export class TextPath extends Shape {
}; };
// fake search for offset, this is very bad approach // fake search for offset, this is very bad approach
// TODO: find other way to add offset from start (for align) // find other way to add offset from start (for align)
var testChar = 'C'; var testChar = 'C';
var glyphWidth = that._getTextSize(testChar).width + letterSpacing; var glyphWidth = that._getTextSize(testChar).width + letterSpacing;
for (var k = 0; k < offset / glyphWidth; k++) { for (var k = 0; k < offset / glyphWidth; k++) {

View File

@ -6,7 +6,7 @@ import { Rect } from './Rect';
import { Group } from '../Group'; import { Group } from '../Group';
import { getAngle, getGlobalKonva } from '../Global'; import { getAngle, getGlobalKonva } from '../Global';
import { GetSet } from '../types'; import { GetSet, IRect } from '../types';
var ATTR_CHANGE_LIST = [ var ATTR_CHANGE_LIST = [
'resizeEnabledChange', 'resizeEnabledChange',
@ -107,7 +107,6 @@ function getCursor(anchorName, rad, isMirrored) {
return 'nwse-resize'; return 'nwse-resize';
} else { } else {
// how can we can there? // how can we can there?
// TODO: throw error
Util.error('Transformer has unknown angle for cursor detection: ' + angle); Util.error('Transformer has unknown angle for cursor detection: ' + angle);
return 'pointer'; return 'pointer';
} }
@ -216,7 +215,8 @@ export class Transformer extends Group {
}.bind(this) }.bind(this)
); );
// TODO: why do we need this? // we may need it if we set not in initial props
// so elements are not defined yet
var elementsCreated = !!this.findOne('.top-left'); var elementsCreated = !!this.findOne('.top-left');
if (elementsCreated) { if (elementsCreated) {
this.update(); this.update();
@ -834,8 +834,7 @@ export class Transformer extends Group {
keepRatio: GetSet<boolean, this>; keepRatio: GetSet<boolean, this>;
centeredScaling: GetSet<boolean, this>; centeredScaling: GetSet<boolean, this>;
ignoreStroke: GetSet<boolean, this>; ignoreStroke: GetSet<boolean, this>;
// TODO: add better types boundBoxFunc: GetSet<(oldBox: IRect, newBox: IRect) => IRect, this>;
boundBoxFunc: GetSet<Function, this>;
} }
function validateAnchors(val) { function validateAnchors(val) {

View File

@ -3789,4 +3789,18 @@ suite('Node', function() {
assert.equal(layer.getChildren().length, 1); assert.equal(layer.getChildren().length, 1);
assert.equal(rect3.getZIndex(), 0); assert.equal(rect3.getZIndex(), 0);
}); });
test('show warning when we are trying to use non-objects for component setters', function() {
var stage = addStage();
var callCount = 0;
var oldWarn = Konva.Util.warn;
Konva.Util.warn = function() {
callCount += 1;
};
stage.scale(0.5);
assert.equal(callCount, 1);
Konva.Util.warn = oldWarn;
});
}); });