2011-01-27 51 views
4

好的,所以我想了解WPF命令的概念。它们看起来非常直截了当,直到你尝试将命令转发给不是XAML后面的代码。我已经看到了几种使用自定义命令执行此操作的方法,但没有直接解释如何使用内置的WPF命令执行此操作。诸如“打开”,“保存”,“剪切”等等。使用内置的WPF命令与ViewModel

是否有一种简单的方法,使用RelayCommand类或其他方法将Open命令转发给ViewModel?

回答

6

WPF的内置ApplicationCommands等最初并不是在设计时考虑到了MVVM,所以当你试图将它们放入ViewModel时,它们并不真正匹配。

在WPF 4,现在可以绑定InputCommands到您的视图模型:

https://www.thomaslevesque.com/2009/10/26/vs2010-binding-support-in-inputbindings/

另一种方法是使用一个DelegateCommands,你可以自己实现或从像Prism库得到。您可以将DelegateCommand定义为视图模型中的对象,并从视图中将其绑定到该对象。

一旦你有绑定工作,你定义了什么命令在你的视图模型代码。

+0

我猜测使用这两种方法中的任何一种都不会给我免费的keybindings。 – s73v3r 2011-01-27 23:37:19

1

一种方法是使用附加属性来允许您的ViewModel在视图上定义CommandBindings。检查我的博客文章详细内容:

CommandBindings with MVVM

2

如果你使用WPF做MVVM,我强烈建议寻找一个框架,来帮助你,比如:

  1. Prism(提供自己的DelegateCommand)
  2. MVVM Light Toolkit(提供了自己的RelayCommand)
  3. Caliburn.Micro(我的最爱,提供操作)
0

假设您的ViewModel公开新命令。你可以用这样的代码重新路由Application.New命令绑定到VM。在XAML中:

<Window.CommandBindings> 
    <CommandBinding Command="New" /> 
    ... 
</Window.CommandBindings> 

然后在代码中,您可以这样做。 (我喜欢保持码出后面的代码,所以我这个房子在一个实用程序类。)

foreach (CommandBinding cb in CommandBindings) 
{ 
    switch (((RoutedUICommand)cb.Command).Name) 
    { 
     case "New": 
      cb.Executed += (sender, e) => ViewModel.New.Execute(e); 
      cb.CanExecute += (sender, e) => e.CanExecute = ViewModel.New.CanExecute(e); 
      break; 
    } 
} 

匿名方法提供RoutedUICommand和之间的ICommand一个thunk。

编辑:或者,最好的做法是设置命令与CommandManager显式绑定,而不是添加处理程序。

CommandManager.RegisterClassCommandBinding(typeof(MainWindow), 
    new CommandBinding(ApplicationCommands.New, 
     (sender, e) => ViewModel.NewScore.Execute(e), 
     (sender, e) => e.CanExecute = ViewModel.NewScore.CanExecute(e)));