代码之家  ›  专栏  ›  技术社区  ›  CJ.

具有核心数据的nsundomanager-重做不工作

  •  1
  • CJ.  · 技术社区  · 15 年前

    我有一个基于核心数据文档的应用程序,它通过与nsmanagedobjectcontext关联的内置nsundomanager支持撤消/重做。我设置了一些操作,这些操作在核心数据中执行许多任务,通过 beginUndoGrouping / endUndoGrouping ,并由nsundomanager处理。

    撤销操作很好。我可以执行几个连续的操作,然后依次撤消每个操作,并且我的应用程序的状态得到正确维护。但是,“重做”菜单项从未启用。这意味着nsundomanager告诉菜单没有要重做的项。

    我想知道为什么nsundomanager似乎忘记了项目一旦被撤销,而不允许重做发生?

    我要提到的一件事是,在打开/创建文档后,我将禁用撤消注册。当我执行一个动作时 enableUndoRegistration , 开始分组 ,执行操作,然后调用 processPendingChanges , setActionName: , 结束撤消分组 ,最后 disableUndoRegistration . 这样可以确保只有特定的操作是可撤消的,并且我在这些操作之外所做的任何其他数据更改都不会被nsundomanager注意到。这可能是问题的一部分,但如果是这样,我想知道为什么它会影响redo?

    提前谢谢。

    3 回复  |  直到 11 年前
        1
  •  3
  •   Rob    15 年前

    实际上,只要在-undo和-redo之前调用enableUndoRegistration(在它们之后调用disableUndoRegistration),您就可以实现您所追求的目标。

    我相信您只是在对托管对象进行更改之前和之后调用了enable(/disable)undorregistration。这意味着您的“undo”没有在undo管理器中注册,因此您不能“重做”。

        2
  •  1
  •   CJ.    15 年前

    我已通过以下方式解决此问题:

    始终启用撤消注册,但明确不希望记录撤消的情况除外。

    我了解到:

    如果在执行要记录的更改之前启用撤消注册,并在提交这些更改之后立即禁用,则不会填充nsundomanager的重做堆栈。

    所以,不要打电话 disableUndoRegistration .

        3
  •  1
  •   Community CDub    8 年前

    我在启用“重做”的同时调用了disableundomanager。为此,我对nsundomanager进行了子类化,并包含了以下方法:

    -(void) undo
    {
      [[appDelegate managedObjectContext] processPendingChanges];
      [self enableUndoRegistration];
      [[NSRunLoop currentRunLoop] runMode: NSDefaultRunLoopMode beforeDate:[NSDate date]];
      [super undo];
      [[appDelegate managedObjectContext] processPendingChanges];
      [self disableUndoRegistration];
    }
    

    如Stefanf在 NSUndoManager, Core Data and selective undo/redo :“nsundomanager等待下一个运行循环,直到它注册您的更改”