将画布数据保存到数组的问题 [英] Issue with saving canvas data to an array
问题描述
我使用HTML5 canvas来创建一个web应用程序来绘制图像(如画web),我尝试实现撤消(ctrl + Z)和重做功能,这里我面临一个奇怪的问题与数组的画布元素。
有时,当我按ctrl + Z撤消时,会出现一个空白图像,但是数据在数组中,并且指向正确的元素(因为当我使用undo / redo播放时,我得到了正确的图像在正确的顺序)。
I am creating a web application using HTML5 canvas to draw images ( like paint web ), I try to implement the "undo" (ctrl+Z) and "redo" features and here I am facing a strange problem with an array of canvas elements. Sometimes, when I hit ctrl+Z to undo, a blank image appears, however the data is in the array and I point to the correct element (because when I play with undo/redo I manage to have the corrects images in the right order).
如果你可以看看下面的代码我会很感激,我已经花了很多时间,我不是能够找到问题...: - (
If you can have a look at the following code I would be grateful, I've spent a lot of time already and I'm not able to locate the problem... :-(
function Stack(firstImg , size) {
var drawStack = new Array();
var stackIndex = 0;
var stackTop = 0;
var stackFloor = 0;
var stackSize = size;
drawStack[0] = firstImg;
this.add = function() {
drawStack[++stackIndex%stackSize] = cvs.toDataURL("image/png");
if (stackIndex >= stackSize) stackFloor = (stackIndex +1) % stackSize ;
stackTop = stackIndex % stackSize;
}
this.undo = function () {
if (stackIndex%stackSize == stackFloor ) return;
clearCanvas();
var tmpImg = new Image();
tmpImg.src = drawStack[--stackIndex%stackSize];
cvsCtx.drawImage(tmpImg, 0, 0);
}
this.redo = function () {
if (stackIndex%stackSize == stackTop) return;
clearCanvas();
var tmpImg = new Image();
tmpImg.src = drawStack[++stackIndex%stackSize];
cvsCtx.drawImage(tmpImg, 0, 0);
}
}
任何解决方案或解决方法,我会采取,谢谢非常多!
Any solution or workaround, I will take, thank you very much !!
推荐答案
我已经实现了撤消/重做功能几次,虽然我不能发布代码的许可原因,我可以给你一些伪代码,应该展示如何简单的撤销/重做实际上是:
I have implemented undo/redo functionality a few times and, while I cannot post the code for licensing reasons, I can give you some psuedocode that should demonstrate how simple undo/redo actually is:
首先,你需要两个数组。请调用这些撤消和重做。
first, you need two arrays. call these "undo" and "redo".
每次状态更改时,将该状态推送到撤销堆栈。
Every time the state changes, push that state to the undo stack.
当用户按ctrl-z(撤消)时,从撤消堆栈弹出最后保存的状态。
When the user presses ctrl-z (undo), pop the last saved state from the undo stack. push this state to the redo queue, and also make it the current state.
当用户按下ctrl-y(redo)时,弹出重做的最后保存的状态
When the user presses ctrl-y (redo), pop the last saved state from the redo queue.
如果任何一个数组开始填满超过您要保存的状态数,请使用shift来舍弃最旧的状态。
If either of the arrays begins to fill up past the # of states you want to save, use shift to discard the oldest state.
有关push,pop和shift的参考,请参阅 MDN文档。
For references on push, pop, and shift, see the MDN documentation.
此外,您可能会发现自己希望数组偷看,所以这里是:
Also, you will probably find yourself wishing arrays had peek, so here it is:
Array.prototype.peek = function () {
var theArray = this;
var temp = theArray.pop();
if (temp !== undefined) {
theArray.push(temp);
}
return temp;
};
编辑:我的代码段中有一个错误,在空数组上调用.peek未定义。
edit: there was a bug in my snippet, calling .peek() on an empty array would push undefined.
这篇关于将画布数据保存到数组的问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!