Fix block style insertion (#4192)

* fix style nsertion

* fixed tests from older changes

* fixed tests from older changes
This commit is contained in:
Andrea Bogazzi 2017-08-13 20:49:39 +02:00 committed by GitHub
parent 836bf158b9
commit ffd2d3254c
8 changed files with 42 additions and 39 deletions

View file

@ -722,12 +722,12 @@
qty || (qty = 1);
this.shiftLineStyles(lineIndex, qty);
if (this.styles[lineIndex] && this.styles[lineIndex][charIndex - 1]) {
currentCharStyle = this.styles[lineIndex][charIndex - 1];
if (this.styles[lineIndex]) {
currentCharStyle = this.styles[lineIndex][charIndex === 0 ? charIndex : charIndex - 1];
}
// we clone styles of all chars
// after cursor onto the last line
// after cursor onto the current line
for (var index in this.styles[lineIndex]) {
var numIndex = parseInt(index, 10);
if (numIndex >= charIndex) {
@ -747,7 +747,7 @@
// we clone current char style onto the next (otherwise empty) line
while (qty > 1) {
qty--;
if (copiedStyle[qty]) {
if (copiedStyle && copiedStyle[qty]) {
this.styles[lineIndex + qty] = { 0: clone(copiedStyle[qty]) };
}
else if (currentCharStyle) {
@ -812,32 +812,31 @@
/**
* Inserts style object(s)
* @param {Array} insertedText Characters at the location where style is inserted
* @param {Number} start True if it's end of line
* @param {Number} start cursor index for inserting style
* @param {Array} [copiedStyle] array of style objects to insert.
*/
insertNewStyleBlock: function(insertedText, start, copiedStyle) {
var cursorLoc = this.get2DCursorLocation(start, true),
addingNewLines = 0, addingChars = 0;
addedLines = [0], linesLenght = 0;
for (var i = 0; i < insertedText.length; i++) {
if (insertedText[i] === '\n') {
if (addingChars) {
this.insertCharStyleObject(cursorLoc.lineIndex, cursorLoc.charIndex, addingChars, copiedStyle);
copiedStyle = copiedStyle && copiedStyle.slice(addingChars);
addingChars = 0;
}
addingNewLines++;
linesLenght++;
addedLines[linesLenght] = 0;
}
else {
if (addingNewLines) {
this.insertNewlineStyleObject(cursorLoc.lineIndex, cursorLoc.charIndex, addingNewLines, copiedStyle);
copiedStyle = copiedStyle && copiedStyle.slice(addingNewLines);
addingNewLines = 0;
}
addingChars++;
addedLines[linesLenght]++;
}
}
addingChars && this.insertCharStyleObject(cursorLoc.lineIndex, cursorLoc.charIndex, addingChars, copiedStyle);
addingNewLines && this.insertNewlineStyleObject(
cursorLoc.lineIndex, cursorLoc.charIndex, addingNewLines, copiedStyle);
if (addedLines[0] > 0) {
this.insertCharStyleObject(cursorLoc.lineIndex, cursorLoc.charIndex, addedLines[0], copiedStyle);
copiedStyle = copiedStyle && copiedStyle.slice(addedLines[0] + 1);
}
linesLenght && this.insertNewlineStyleObject(
cursorLoc.lineIndex, cursorLoc.charIndex + addedLines[0], linesLenght);
for (var i = 1; i <= linesLenght; i++) {
this.insertCharStyleObject(cursorLoc.lineIndex + i, 0, addedLines[i], copiedStyle);
copiedStyle = copiedStyle && copiedStyle.slice(addedLines[i] + 1);
}
},
/**

View file

@ -230,7 +230,7 @@ fabric.util.object.extend(fabric.IText.prototype, /** @lends fabric.IText.protot
}
fabric.copiedText = this.getSelectedText();
fabric.copiedTextStyle = this.getSelectionStyles(this.selectionStart, this.selectionEnd, false);
fabric.copiedTextStyle = this.getSelectionStyles(this.selectionStart, this.selectionEnd, true);
this._copyDone = true;
},

View file

@ -826,7 +826,7 @@
renderAll: function () {
var canvasToDrawOn = this.contextContainer;
if (this.isRendering) {
fabric.window.cancelAnimationFrame(this.isRendering);
fabric.util.cancelAnimFrame(this.isRendering);
}
this.renderCanvas(canvasToDrawOn, this._objects);
return this;

View file

@ -64,6 +64,8 @@
return fabric.window.setTimeout(callback, 1000 / 60);
};
var _cancelAnimFrame = fabric.window.cancelAnimationFrame || fabric.window.clearTimeout;
/**
* requestAnimationFrame polyfill based on http://paulirish.com/2011/requestanimationframe-for-smart-animating/
* In order to get a precise start time, `requestAnimFrame` should be called as an entry into the method
@ -77,5 +79,5 @@
fabric.util.animate = animate;
fabric.util.requestAnimFrame = requestAnimFrame;
fabric.util.cancelAnimFrame = _cancelAnimFrame;
})();

View file

@ -714,11 +714,11 @@
equal(canvas.straightenObject(rect), canvas, 'should be chainable');
equal(rect.get('angle'), 0, 'angle should be coerced to 0 (from 10)');
rect.setAngle('60');
rect.rotate('60');
canvas.straightenObject(rect);
equal(rect.get('angle'), 90, 'angle should be coerced to 90 (from 60)');
rect.setAngle('100');
rect.rotate('100');
canvas.straightenObject(rect);
equal(rect.get('angle'), 90, 'angle should be coerced to 90 (from 100)');
});

View file

@ -619,11 +619,11 @@
equal(canvas.straightenObject(rect), canvas, 'should be chainable');
equal(rect.get('angle'), 0, 'angle should be coerced to 0 (from 10)');
rect.setAngle('60');
rect.rotate('60');
canvas.straightenObject(rect);
equal(rect.get('angle'), 90, 'angle should be coerced to 90 (from 60)');
rect.setAngle('100');
rect.rotate('100');
canvas.straightenObject(rect);
equal(rect.get('angle'), 90, 'angle should be coerced to 90 (from 100)');
});

View file

@ -261,12 +261,14 @@
// });
test('copy', function() {
var event = { stopPropagation: function(){}, preventDefault: function(){} };
var iText = new fabric.IText('test', { styles: { 0: { 0: { fill: 'red' }, 1: { fill: 'blue' }}}});
var iText = new fabric.IText('test', { fontSize: 25, styles: { 0: { 0: { fill: 'red' }, 1: { fill: 'blue' }}}});
iText.selectionStart = 0;
iText.selectionEnd = 2;
iText.copy(event);
equal(fabric.copiedText, 'te', 'it copied first 2 characters');
equal(fabric.copiedTextStyle[0], iText.styles[0][0], 'style is referenced');
equal(fabric.copiedTextStyle[1], iText.styles[0][1], 'style is referenced');
equal(fabric.copiedTextStyle[0].fill, iText.styles[0][0].fill, 'style is cloned');
equal(fabric.copiedTextStyle[1].fill, iText.styles[0][1].fill, 'style is referenced');
equal(iText.styles[0][1].fontSize, undefined, 'style had not fontSize');
equal(fabric.copiedTextStyle[1].fontSize, 25, 'style took fontSize from text element');
});
})();

View file

@ -507,7 +507,7 @@
equal(cObj.get('angle'), 45);
});
test('setAngle', function() {
test('rotate', function() {
var cObj = new fabric.Object();
equal(cObj.get('angle'), 0);
equal(cObj.set('angle', 45), cObj, 'chainable');
@ -540,7 +540,7 @@
equal(clone.get('opacity'), 0.66);
// augmenting clone properties should not affect original instance
clone.set('left', 12).set('scaleX', 2.5).setAngle(33);
clone.set('left', 12).set('scaleX', 2.5).rotate(33);
equal(cObj.get('left'), 123);
equal(cObj.get('scaleX'), 1);
@ -685,27 +685,27 @@
var object = new fabric.Object({ left: 100, top: 124, width: 210, height: 66 });
ok(typeof object.straighten == 'function');
object.setAngle(123.456);
object.rotate(123.456);
object.straighten();
equal(object.get('angle'), 90);
object.setAngle(97.111);
object.rotate(97.111);
object.straighten();
equal(object.get('angle'), 90);
object.setAngle(3.45);
object.rotate(3.45);
object.straighten();
equal(object.get('angle'), 0);
object.setAngle(-157);
object.rotate(-157);
object.straighten();
equal(object.get('angle'), -180);
object.setAngle(159);
object.rotate(159);
object.straighten();
equal(object.get('angle'), 180);
object.setAngle(999);
object.rotate(999);
object.straighten();
equal(object.get('angle'), 270);
});