Preface
The Commanding Overview says “Commanding is an input mechanism in Windows Presentation Foundation (WPF) which provides input handling at a more semantic level than device input. Examples of commands are the Copy, Cut, and Paste operations found on many applications.”
Well, one should extent the definition and mention Windows Store apps too. Commanding is not limited to WPF.
When looking for a sample implementation that could be used in Windows Store apps too, I found this forum post: ICommand and MVVM.
The implementation looked quite easy to me, but lacks of type safeness from my point of view.
So I extended the DelegateCommand
class from this post to be more typesafe.
Generic ICommand Implementation
/// <summary> /// Generic implementation of <see cref="ICommand"/>. /// </summary> /// <typeparam name="T"> /// Type of the parameter the command expects. /// </typeparam> /// <remarks> /// Copied from http://social.msdn.microsoft.com/Forums/en-US/f457c906-56d3-49c7-91c4-cc35a6ec5d35/icommand-and-mvvm /// </remarks> public class DelegateCommand<T> : ICommand { #region Private Properties /// <summary> /// Gets / sets the action to be executed. /// </summary> private Action<T> ExecuteAction { get; set; } #endregion Private Properties #region Public Events /// <summary> /// Occurs when changes occur that affect whether /// the command should execute. /// </summary> public event EventHandler CanExecuteChanged; #endregion Public Events #region Public Constructors /// <summary> /// Initializes a new instance of <see cref="DelegateCommand"/> /// with the action to be executed. /// </summary> /// <param name="executeAction"> /// Action to be executed. /// </param> public DelegateCommand ( Action<T> executeAction ) { ExecuteAction = executeAction; } #endregion Public Constructors #region Public Methods /// <summary> /// Determines whether the command can execute in its current state. /// </summary> /// <param name="parameter">Data used by the command.</param> /// <returns> /// <c>true</c> if this command can be executed; /// otherwise, <c>false</c>. /// </returns> public bool CanExecute ( object parameter ) { return true; } /// <summary> /// Invokes the method to be called. /// </summary> /// <param name="parameter">Data used by the command.</param> public void Execute ( object parameter ) { ExecuteAction((T) Convert.ChangeType(parameter, typeof(T))); } #endregion Public Methods }
Usage
This class is used something like this:
public class MyViewModel { … public ICommand SomeMethodCommand { get; private set; } … public MyViewModel () { // Set the command. SomeMethodCommand = new DelegateCommand(SomeMethod); } … public void SomeMethod ( bool value ) { // Do something } }
The usage in XAML is like this:
<Button Content="Invoke SomeMethod" Command="{Binding SomeMethodCommand}" CommandParameter="true"/>
where the DataContext
of the page is set to an instance of MyViewModel
.
Limitations of the Implementation
As said, this is a simple implementation of ICommand
.
It does not evaluate the value passed to CanExecute
. And it does not fire an event in case the CanExecute
state changes (which is not implemented here too).
Links
Forum Post ICommand and MVVM