WPF SimpleCommand possible with generics?
I am using this code to make a Simple Command:
public class SimpleCommand : ICommand
{
public Predicate<object> CanExecuteDelegate { get; set; }
public Action<object> ExecuteDelegate { get; set; }
#region ICommand Members
public bool CanExecute(object parameter)
{
if (CanExecuteDelegate != null)
return CanExecuteDelegate(parameter);
return true;// if there is no can execute default to true
}
public event EventHandler CanExecuteChanged
{
add { CommandManager.RequerySuggested += value; }
remove { CommandManager.RequerySuggested -= value; }
}
public void Execute(object parameter)
{
if (ExecuteDelegate != null)
ExecuteDelegate(parameter);
}
#endregion
}
I did not write this. But I enjoy using it. When I use it it ends up being like this:
// This is the value that gets set to the command in the UI
public SimpleCommand DoSomethingCommand { get; set; }
public DoSomethingCommandConstructor()
{
DoSomethingCommand = new SimpleCommand
{
ExecuteDelegate = x => RunCommand(x)
};
}
private void RunCommand(object o)
{
// Run the command.
}
The only problem with this is that the parameter 开发者_如何学编程of RunCommand is an object. I think I have been spoiled by generics. I always want the IDE/compiler to just know what the type I am working with is with out casting.
Is it possible to change this SimpleCommand class to be implemented using generics?
Sure. Was gonna point you to Prism's implementation, but CodePlex source tab seems to not be working. It would look something like:
public class SimpleCommand<T> : ICommand
{
public Predicate<T> CanExecuteDelegate { get; set; }
public Action<T> ExecuteDelegate { get; set; }
#region ICommand Members
public bool CanExecute(object parameter)
{
if (CanExecuteDelegate != null)
return CanExecuteDelegate((T)parameter);
return true;// if there is no can execute default to true
}
public event EventHandler CanExecuteChanged
{
add { CommandManager.RequerySuggested += value; }
remove { CommandManager.RequerySuggested -= value; }
}
public void Execute(object parameter)
{
if (ExecuteDelegate != null)
ExecuteDelegate((T)parameter);
}
#endregion
}
Incidentally, your usage of SimpleCommand in your question is a little roundabout. Instead of this:
DoSomethingCommand = new SimpleCommand
{
ExecuteDelegate = x => RunCommand(x)
};
You could just have:
DoSomethingCommand = new SimpleCommand
{
ExecuteDelegate = this.RunCommand
};
Specifying a lambda is really only useful if you're doing the work inline like this:
DoSomethingCommand = new SimpleCommand
{
ExecuteDelegate = o => this.SelectedItem = o,
CanExecuteDelegate = o => o != null
};
精彩评论