简体   繁体   中英

WPF CanExecute Constantly Requerying

I have a property IEnumerable<MyObject> MyObjects in a ViewModel. I want a certain command in a second view model (that references the first) to be executable when MyObjects is populated with at least one object, but not executable when it's empty.

My CanExecute method looks something like this:

private bool CanExecute()
{
    return this.viewModel.MyObjects.Any();
}

I have a PropertyChanged event that is raised whenever the underlying value of MyObjects is changed.

The logic works correctly, however the CanExecute() method is constantly being called-- so much that it basically freezes the entire application. At the same time, MyObjects is not changing (nor am I raising the PropertyChanged event for it). Any ideas how I can stop the CanExecute from being re-queried constantly?

I'm assuming your command either inherits RoutedCommand , or it implements CanExecuteChanged like this:

public event EventHandler CanExecuteChanged {
    add { CommandManager.RequerySuggested += value; }
    remove { CommandManager.RequerySuggested -= value; }
}

Which means adding a handler to your command's CanExecuteChanged (which WPF does, to decide when to call your CanExecute ) is equivalent to adding it to CommandManager.RequerySuggested , which is raised very often and as far as I know there is no way to force it to be raised less often.

There's 2 ways around the problem:

  1. Don't use RequerySuggested at all, just make CanExecuteChanged a standard event and raise it specifically when you want it checked.

  2. Make sure the CanExecute method is very fast so it doesn't matter how often it runs. You could write it as return this.viewModel.HasAnyObjects; , where HasAnyObjects is a simple field that is set to true or false when MyObjects changes.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM