我正在尝试学习如何使用WPF命令,以及它们如何适应MVVM模式。我知道一些控件,如按钮或菜单,有一个Command属性,当设置为ICommand类的实例时,该按钮将按钮连接到该命令。设置完成后,该按钮将禁用并启用该命令的CanExecuteChanged事件,单击该控件将调用该命令的Execute方法。
但是,每个ICommand的实例应该在哪里生活?我在教程中看到了各种不同的选项,我不确定哪个是正确的。在一些示例中,创建静态“ApplicationCommands”类,并且将每个命令的实例分配给该类的静态属性。在其他示例中,我看到命令设置为ViewModel的属性,而在其他视图/窗口本身中。命令实例的首选位置是什么?
此外,命令如何与视图,视图模型或模型相关联?命令应该注意和操纵哪些组件?执行命令时应该怎么办?它应该调用模型的某个方法,然后将更改传递回View Model / View吗?或者命令是否应该通过View Model的方法与模型进行通信?
答案 0 :(得分:1)
使用静态命令的方法通常使用RoutedCommands
或具有广泛应用程序的命令,该应用程序未与任何特定对象的状态耦合。如果使用ICommand
的动态实现来获取在构造函数中传递给它们的方法,那么它们通常是与该命令相关的ViewModel
的实例。
这些命令可以作用于ViewModel和Model,你如何做到这一点取决于你,我经常只是从命令Execute
调用VM上的相应方法来保存命令初始化代码简洁。
我无法真正告诉你最好的方法是什么,也许其他人对什么时候和为什么效果最好有更深入的了解。
答案 1 :(得分:1)
在某些示例中,创建了静态“ApplicationCommands”类,并将每个命令的实例分配给该类的静态属性
您可以为希望能够从任何地方访问的命令执行此操作。例如,如果您希望 F1 的键绑定始终显示帮助屏幕,那么您可以在一个全局可访问的位置实现此命令,然后从各个屏幕绑定它。
可以看到命令设置为ViewModel的属性,而其他视图/窗口本身也是如此。
如果命令正在对数据执行某些操作,那么ViewModel是一个很好的选择。如果命令不需要对数据做任何事情,那么将它放在View后面的代码中(因为它与ViewModel无关,你不需要用它来污染ViewModel)。一个有趣的案例是,当您执行诸如弹出对话框以响应击键之类的操作时,您需要将当前选定的网格项目传递到对话框 - 命令应该放在哪里?在这种情况下,我会将它放在视图后面的代码中,因为没有令人信服的理由将它放在ViewModel中 - 如果需要,可以通过View从ViewModel中检索所选项目。
很多时候我看到命令被不必要地放入ViewModel只是因为人们认为这是唯一的方法。我使用的经验法则是:如果它正在进行与UI相关的工作,那么它就属于视图背后的代码。如果它正在进行与数据相关的工作,那么它可以进入ViewModel。如果它正在混合,那么考虑在View和ViewModel上分解功能。
命令应该注意和/或操作哪些组件?
只有它需要知道的。从ViewModel访问模型等组件应该通过正确定义的属性或函数来完成,该属性或函数返回一个接口,这是为了避免紧耦合。
它应该调用Model的某个方法,然后将更改传回View Model / View吗?
从ViewModel访问Model的命令没有问题。该命令可以更新ViewModel或Model上的属性,通过数据绑定和属性通知的魔力,这些更新可以反映在UI中。