我想在整个浏览器会话中保留Ace EditorUndoManager实例,就像Cloud9 IDE那样。

我试图对UndoManager对象进行字符串化,以便可以将其存储在某个地方,以便以后像这样检索它:

 let undoManager    = editorHTML.getSession().getUndoManager();
 let undoManagerStr = JSON.stringify(undoManager);


但是stringify调用抛出异常Uncaught TypeError: Converting circular structure to JSON

我也尝试过提取对象的一部分进行存储:

 let redoStackStr       = JSON.stringify(undoManager.$redoStack, null, 2);
 let undoStackStr       = JSON.stringify(undoManager.$undoStack, null, 2);
 let dirtyCounter       = undoManager.dirtyCounter;




 let manager = new ace.UndoManager();
 if(redoStackStr && undoStackStr && dirtyCounter) {
      manager.$redoStack = JSON.parse(redoStackStr);
      manager.$undoStack = JSON.parse(undoStackStr);
      manager.dirtyCounter = dirtyCounter;
 }
 editorHTML.getSession().setUndoManager(manager)


但是Ace一点都不喜欢这样,并在CTRL-Z上炸了炸弹

我希望在已经存在的情况下不必编写自己的文件历史记录管理器。

编辑

我只能使用下面选择的答案解决此问题,但只能在升级到Ace编辑器1.4.2版后进行。上面的代码是我在分析版本1.2.8中的UndoManager之后尝试的,这就是为什么它如此不同的原因。

最佳答案

使用ace 1.4,您提到的第二种方法有效,示例中的唯一问题是未定义dirtyCounter

UndoManager = require("ace/undomanager").UndoManager
undoManager = editor.session.$undoManager
var str  = JSON.stringify({
    $redoStack: undoManager.$redoStack,
    $undoStack: undoManager.$undoStack,
    mark: undoManager.mark,
    $rev: undoManager.$rev,
 })
 var manager = new UndoManager();
 if (str) {
     var json = JSON.parse(str)
      manager.$redoStack = json.$redoStack;
      manager.$undoStack = json.$undoStack
      manager.mark = json.mark
      manager.$rev = json.$rev
 }
 editor.getSession().setUndoManager(manager)


但是请注意,如果对具有不同值的会话执行此操作将失败。

关于javascript - 跨 session 坚持使用ACE编辑器UndoManager,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/53672383/

10-16 20:55