【问题标题】:Keeping track of parameters using a Command Pattern and ICommand for Undo/Redo. Storing multiple commands?使用命令模式和用于撤消/重做的 ICommand 跟踪参数。存储多个命令?
【发布时间】:2013-01-17 03:26:08
【问题描述】:

我一直在开发一个涉及移动许多形状的 WPF 应用程序。它主要是 MVVM 并且严重依赖命令。直到最近我才担心撤消/重做。我认为这不会太难,因为我的大部分更改都涉及继承实现 ICommand 的基类 CommandBase 的命令。

到目前为止,我已经添加了另一个名为 IUndoCommand 的接口,它使用 ICommand。我添加了一个 Undo 方法,该方法将在调用 undo 时执行所需的操作。

我将为 Undo 和 Redo 使用堆栈,但我遇到了 Execute/Undo 方法的参数问题。有没有合适的方法来存储这些对象类型的参数?是否建议向 IUndoCommand 添加字段/方法?如果是这样,我应该在 Execute 方法或构造函数中设置它(如果我可以的话。)

如果不是,我应该将它作为堆栈中的自己的对象传递吗?

其次,(尽管这可能是它自己的问题)是否有更好的数据结构来跟踪多个命令?我目前有一个循环,它运行多个命令来移动多个选定的形状,并希望允许一次撤消全部撤消。我想我可以将它自己转换为命令并将命令传递给它,但我还是新手,宁愿做对。

感谢您的阅读,我们将不胜感激。

来源:

Code Project VisualStudioMagazine StackOverFlow

【问题讨论】:

  • 您看过 Momento 设计模式吗?它专门用于撤消。重做将与您对队列所做的模式相反。 en.wikipedia.org/wiki/Memento_pattern
  • 我看到了,这就是我最初开始的工作。我觉得这给了我更多的控制权,并且与我已经完成的工作更有效。我有一个 DrawingEditViewModel 设置为我的数据上下文。这具有与模型交互的可观察的视图模型集合。它还跟踪我的内容宽度/高度和偏移量(因为有缩放。)我有可能将宽度/高度/缩放移动到另一个类,但它仍然需要访问它。跨度>
  • 这是一个问题,因为 momento 设计模式中最简单的解决方案是对整个视图模型进行深度复制正确吗?这会导致放大/缩小更改被保存为一个非常烦人的步骤。用户必须控制+z 8 次才能回到他们的最后一个视图位置。我希望这是有道理的..

标签: wpf command undo command-pattern redo


【解决方案1】:

由于接口不需要访问数据(它应该只需要一个Undo()/Redo() 方法对,并且可能需要一个是否可以撤消的标志),它不需要知道参数。

一种选择可能是使您的IUndoCommand 实现通用。然后,您可以使用它以类型安全的方式存储参数。

您的CommandBase 类可以是通用的,即:

class CommandBase<T> : ICommand, IUndoCommand
{
    // You could then store the parameter directly...
    public T Parameter { get; private set; }
}

【讨论】:

  • 我明白了,我喜欢那个解决方案,但是我可以在 Execute 方法中设置它吗?我会这么认为,因为除非调用 Execute,否则不会将 Command 添加到任一堆栈中。我只是不确定有没有更好的方法..
猜你喜欢
  • 1970-01-01
  • 2015-06-22
  • 2016-11-18
  • 1970-01-01
  • 2011-03-16
  • 2011-06-14
  • 2013-09-30
  • 1970-01-01
  • 2023-03-10
相关资源
最近更新 更多