Cleaning a bit pixel utils + fix empty paste bug

This commit is contained in:
Vince 2012-09-15 01:01:47 +02:00
parent 697f270d78
commit 28835f96f3
3 changed files with 36 additions and 70 deletions

View File

@ -7,6 +7,7 @@
ns.BaseSelection.prototype.reset = function () { ns.BaseSelection.prototype.reset = function () {
this.pixels = []; this.pixels = [];
this.hasPastedContent = false;
}; };
ns.BaseSelection.prototype.move = function (colDiff, rowDiff) { ns.BaseSelection.prototype.move = function (colDiff, rowDiff) {
@ -28,5 +29,6 @@
pixelWithCopiedColor.copiedColor = pixelWithCopiedColor.copiedColor =
targetFrame.getPixel(pixelWithCopiedColor.col, pixelWithCopiedColor.row); targetFrame.getPixel(pixelWithCopiedColor.col, pixelWithCopiedColor.row);
} }
this.hasPastedContent = true;
}; };
})(); })();

View File

@ -72,7 +72,7 @@
}; };
ns.SelectionManager.prototype.onPaste_ = function(evt) { ns.SelectionManager.prototype.onPaste_ = function(evt) {
if(this.currentSelection) { if(this.currentSelection && this.currentSelection.hasPastedContent) {
var pixels = this.currentSelection.pixels; var pixels = this.currentSelection.pixels;
var currentFrame = this.framesheet.getCurrentFrame(); var currentFrame = this.framesheet.getCurrentFrame();
for(var i=0, l=pixels.length; i<l; i++) { for(var i=0, l=pixels.length; i<l; i++) {
@ -86,9 +86,6 @@
} }
} }
} }
else {
throw "Bad state for PASTE callback in SelectionManager";
}
}; };
/** /**

View File

@ -57,75 +57,39 @@
return pixels; return pixels;
}, },
getSimilarConnectedPixelsFromFrame: function(frame, col, row) {
/** /**
* Queue linear Flood-fill (node, target-color, replacement-color): * Return the list of pixels that would have been filled by a paintbucket tool applied
* 1. Set Q to the empty queue. * on pixel at coordinate (x,y).
* 2. If the color of node is not equal to target-color, return. * This function is not altering the Frame object argument.
* 3. Add node to Q.
* 4. For each element n of Q:
* 5. If the color of n is equal to target-color:
* 6. Set w and e equal to n.
* 7. Move w to the west until the color of the node to the west of w no longer matches target-color.
* 8. Move e to the east until the color of the node to the east of e no longer matches target-color.
* 9. Set the color of nodes between w and e to replacement-color.
* 10. For each node n between w and e:
* 11. If the color of the node to the north of n is target-color, add that node to Q.
* 12. If the color of the node to the south of n is target-color, add that node to Q.
* 13. Continue looping until Q is exhausted.
* 14. Return.
* *
* @private * @param frame pskl.model.Frame The frame target in which we want to paintbucket
* @param col number Column coordinate in the frame
* @param row number Row coordinate in the frame
*
* @return an array of the pixel coordinates paint with the replacement color
*/ */
var pixels = []; getSimilarConnectedPixelsFromFrame: function(frame, col, row) {
frame = frame.clone(); // To get the list of connected (eg the same color) pixels, we will use the paintbucket algorithm
var replacementColor = "sdfsdfsdf" // in a fake cloned frame. The returned pixels by the paintbucket algo are the painted pixels
// and are as well connected.
var fakeFrame = frame.clone(); // We just want to
var fakeFillColor = "sdfsdfsdf"; // A fake color that will never match a real color.
var paintedPixels = this.paintSimilarConnectedPixelsFromFrame(fakeFrame, col, row, fakeFillColor);
var queue = []; return paintedPixels;
var dy = [-1, 0, 1, 0];
var dx = [0, 1, 0, -1];
try {
var targetColor = frame.getPixel(col, row);
} catch(e) {
// Frame out of bound exception.
}
if(targetColor == replacementColor) {
return;
}
queue.push({"col": col, "row": row});
var loopCount = 0;
var cellCount = frame.getWidth() * frame.getHeight();
while(queue.length > 0) {
loopCount ++;
var currentItem = queue.pop();
frame.setPixel(currentItem.col, currentItem.row, replacementColor);
pixels.push({"col": currentItem.col, "row": currentItem.row });
for (var i = 0; i < 4; i++) {
var nextCol = currentItem.col + dx[i]
var nextRow = currentItem.row + dy[i]
try {
if (frame.containsPixel(nextCol, nextRow) && frame.getPixel(nextCol, nextRow) == targetColor) {
queue.push({"col": nextCol, "row": nextRow });
}
} catch(e) {
// Frame out of bound exception.
}
}
// Security loop breaker:
if(loopCount > 10 * cellCount) {
console.log("loop breaker called")
break;
}
}
return pixels;
}, },
/**
* Apply the paintbucket tool in a frame at the (col, row) initial position
* with the replacement color.
*
* @param frame pskl.model.Frame The frame target in which we want to paintbucket
* @param col number Column coordinate in the frame
* @param row number Row coordinate in the frame
* @param replacementColor string Hexadecimal color used to fill the area
*
* @return an array of the pixel coordinates paint with the replacement color
*/
paintSimilarConnectedPixelsFromFrame: function(frame, col, row, replacementColor) { paintSimilarConnectedPixelsFromFrame: function(frame, col, row, replacementColor) {
/** /**
* Queue linear Flood-fill (node, target-color, replacement-color): * Queue linear Flood-fill (node, target-color, replacement-color):
@ -146,6 +110,7 @@
* *
* @private * @private
*/ */
var paintedPixels = [];
var queue = []; var queue = [];
var dy = [-1, 0, 1, 0]; var dy = [-1, 0, 1, 0];
var dx = [0, 1, 0, -1]; var dx = [0, 1, 0, -1];
@ -168,6 +133,7 @@
var currentItem = queue.pop(); var currentItem = queue.pop();
frame.setPixel(currentItem.col, currentItem.row, replacementColor); frame.setPixel(currentItem.col, currentItem.row, replacementColor);
paintedPixels.push({"col": currentItem.col, "row": currentItem.row });
for (var i = 0; i < 4; i++) { for (var i = 0; i < 4; i++) {
var nextCol = currentItem.col + dx[i] var nextCol = currentItem.col + dx[i]
@ -187,6 +153,7 @@
break; break;
} }
} }
return paintedPixels;
} }
}; };
})(); })();