I got the following code from Josh Smith's MVVM tutorial.
Can anyone provide a quick explanation of what this code actually does?
public event EventHandler CanExecuteChanged
{
add { CommandManager.RequerySuggested += value; }
remove { CommandManager.RequerySuggested -= value; }
}
I can't understand two things:
- what does the
CanExecuteChanged
event do? - what does the
CommandManager.RequerySuggested
do?
The above code is from the RelayCommand
Class from here.
CanExecuteChanged
notifies any command sources (like aButton
orMenuItem
) that are bound to thatICommand
that the value returned byCanExecute
has changed. Command sources care about this because they generally need to update their status accordingly (eg. aButton
will disable itself ifCanExecute()
returnsfalse
).- The
CommandManager.RequerySuggested
event is raised whenever theCommandManager
thinks that something has changed that will affect the ability of commands to execute. This might be a change of focus, for example. Turns out that this event fires a lot.
So, in essence, what this bit of code does is ensure that whenever the command manager thinks a command's ability to execute has changed, the command will raise CanExecuteChanged
even if it hasn't actually changed.
I actually dislike this approach to implementing ICommand.CanExecuteChanged
- it feels lazy and isn't entirely reliable. I prefer a much more fine-grained approach where the command exposes a method (eg. RaiseCanExecuteChanged()
) you can call to raise CanExecuteChanged
, then you call this at the appropriate times from your view model.
For example, if you have a command that deletes the currently selected customer, it would have a CanExecute()
handler that returns true
only if there is a customer selected. You would therefore call RaiseCanExecuteChanged
whenever the selected customer changes.
RoutedCommands
can automatically notify if theirCanExecute
has changed, since we are implementingICommand
here, which the WPF system doesn't know about, we wire them to CommandManager'sRequerySuggested
event.- Now this event is called quite often by the WPF system when the focus changes, any control is edited etc. Hence in turn
CanExecuteChanged
is raised. As your button is listening to this event it will reinvokeCanExecute
to know the latest status.
Here is an article that might be of interest.
来源:https://stackoverflow.com/questions/6634777/what-is-the-actual-task-of-canexecutechanged-and-commandmanager-requerysuggested