无法在阵列中正确保存对象

时间:2011-04-04 01:50:21

标签: javascript jquery

var currentState = 1;
var mainImage);
$.fn.mapImage.saveImage = function(image) {
    if (imageState[currentState] != undefined) {
        imageState.splice(currentState - 1);
        imageState.push($.extend(true, {}, image));
    } else {
        imageState.push($.extend(true, {}, image));
    }
    currentState++;
    mainImage = image;
}
$.fn.mapImage.undoImage = function() {
    if (currentState != 1) {
        currentState--;
        mainImage = imageState[currentState - 1];
        $.fn.mapImage.loadState(imageState[currentState - 1]);
    }
}
$.fn.mapImage.loadState = function(image) {
    mainImage = image;
}

如果我多次调用saveImage并增加currentState,则调用undoImage几次,然后再次调用saveImage,它将遍历saveImage中的if语句。出于某种原因,在if语句中(在saveImage内部)中推入的imageState会反映在此之后被推送到数组的任何图像,它将仅镜像最近推送的一个图像。我觉得某处存在参考问题,但我似乎无法找到它。

2 个答案:

答案 0 :(得分:0)

我没有广泛使用JavaScript或jQuery,但我会尽力帮助你。

首先,一个简单的编码错误。第2行应该是: var mainImage; 删除额外的括号。

在saveImage中,检查currentState是否正在使用中。然后你从(currentState-1)拼接。这可能会删除太多图片?或者你可能会检查一个太少的图像?我不确定,但其中一个似乎就是这种情况。请看以下内容:

$.fn.mapImage.saveImage = function(image) {
if (imageState[currentState-1] != undefined) {
    imageState.splice(currentState - 1);
    imageState.push($.extend(true, {}, image));
} else {
    imageState.push($.extend(true, {}, image));
}
currentState++;
mainImage = image;
}

最后,在设置mainImage然后调用loadState(执行相同的操作)时,undoImage似乎是多余的。您应该坚持使用一种更改mainImage的方法。

答案 1 :(得分:0)

我读了以下问题:

目标:

  • 程序应包含单个图像的撤消/重做历史记录
  • 保存图像时,会在撤消/重做历史记录
  • 之上推送新项目
  • 调用撤消时,将使用上一个图像而不是最新的
  • 再次保存图像时,会删除撤消/重做历史记录,以便最新保存的图像替换上次撤消步骤后保存的所有图像。

问题:

  • 您想知道为什么保存图像会截断重做历史以及如何处理

答案:

  • 保存新图像会截断历史记录,因此仅镜像最新图像
  • 您必须使用重做来选择下一步而不是保存图像,或者如果您希望将图像保存到历史记录的顶部,那么就可以摆脱拼接。

一些修改:

$.fn.mapImage = function() {
  // changed the currentState to start at 0 as you repeated currentState - 1 three times
  // while used the currentState as is only once. 
  var currentState = 0;
  var mainImage;
  var imageState = [];

  this.saveImage = function(image) {
    // Truncates the redo history as redos are no longer
    // valid. Start a new history using the latest saved
    // image.
    if (imageState[currentState + 1] != undefined) {
        // XXX: splice(index) is not standard, you should use 
        // splice(index, howMany) instead 
        imageState.splice(currentState + 1, imageState.length);
    }
    // The rest of the if branch and the else branch were identical
    // No need for the else branch
    imageState.push($.extend(true, {}, image));
     // It's more consistent to set the main image the same way
    // each time by using the loadState function as you already did
    // in undo image. 
    this.loadState(imageState[currentState]);
    currentState++; 
  };
  this.undoImage = function() { 
    // replaced != 1 with > 0 to prevent defects
    if (currentState > 0) {
        currentState--;
        // You set the main image in loadState 
        // so you don't have to set it here
        // mainImage = imageState[currentState];
        this.loadState(imageState[currentState]);
    }
  };
  this.redoImage = function() { 
    if (currentState + 1 < imageState.length) {
        currentState++;
        this.loadState(imageState[currentState]);
    }
  };
  this.loadState = function(image) {
    mainImage = image;
  };
}

You can play with with this fiddle.