Thursday, March 05, 2009 3:08 PM
rudi
The power of ICommand
“ICommand contains methods to execute commands. A command can be executed many times, and the parameter values can vary. This interface is mandatory on commands.”
The native support for the command pattern in WPF is great! It allows us to create very decoupled applications and in some instances even remove the need for a code-behind file completely.
WPF implement RoutedCommands & RoutedUICommands… Both of these are great for most scenarios but it still ties you to the visual tree. To completely decouple yourself from the visual tree, we need to explorer some custom implementations of the ICommand interface…
To test these great implementations, I created a application with a VERY basic “ViewModel”
This CustomerViewModel has 2 properties (Name & Surname). It also exposes a ICommand called Clean. If a View calls the Clean command, the name and surname should be set to string.empty! I know this is a overly simplified example but it shows how a View can communicate with the ViewModel in a completely decoupled way
Marlon Grech - SimpleCommand
Marlon created a excellent implementation called SimpleCommand. This truly lives up to its name… here is a example of how I would implement the Clean command using his implementation
Clean = new SimpleCommand()
{
CanExecuteDelegate = x => Name != string.Empty || Surname != string.Empty,
ExecuteDelegate = x => Name = Surname = string.Empty
};
Josh Smith – RelayCommand
“RelayCommand allows you to inject the command's logic via delegates passed into its constructor. This approach allows for terse, concise command implementation in ViewModel classes. RelayCommand is a simplified variation of the DelegateCommand found in the .”
Josh also has a similar implementation
Clean = new RelayCommand(
x => Name = Surname = string.Empty,
x => Name != string.Empty || Surname != string.Empty
);
PRISM team - DelegateCommand<T>
“The DelegateCommand allows delegating the commanding logic instead of requiring a handler in the code behind. It uses a delegate as the method of invoking a target handling method.”
Clean = new DelegateCommand<object>(
x => Name = Surname = string.Empty,
x => Name != string.Empty || Surname != string.Empty
);
What I like about the PRISM team’s implementation is that it supports generics. It did however look like the DelegateCommand<T> did not fire its CanExecuteChanged event. From both Marlon & Josh’s implementations it looks thy are suppose to call CommandManager.RequerySuggested… but I am not sure (It might also be the IActiveAware stuff)
Conclusion
All three these implementations have two thing in common… Thy make it extremely easy to decouple your View and you ViewModel and thy encapsulate the command logic very cleanly!
If you found this article useful, please 
Must read articles about commands
Frameworks
History
Filed under: Prism, SimpleCommand, RelayCommand, DelegateCommand, ICommand, WPF