C# 是否在ViewModelBase中调用CommandManager.InvalidateRequestSuggest?
初始问题:C# 是否在ViewModelBase中调用CommandManager.InvalidateRequestSuggest?,c#,wpf,mvvm,inotifypropertychanged,relaycommand,C#,Wpf,Mvvm,Inotifypropertychanged,Relaycommand,初始问题: 我正在MVVM应用程序中使用典型的RelayCommand实现。 我意识到,即使我的ViewModel的有意义的属性发生了更改,我的RelayCommand的CanExecute也不会总是被调用 我听说我们可以手动调用CommandManager.invalidateRequestSuggested来引发RequerySuggested事件。这最终将使命令源调用CanExecute方法 当某些UI事件发生时,CommandManager会自动引发RequerySuggested。我觉
我正在MVVM应用程序中使用典型的
RelayCommand
实现。
我意识到,即使我的ViewModel的有意义的属性发生了更改,我的RelayCommand
的CanExecute
也不会总是被调用
我听说我们可以手动调用CommandManager.invalidateRequestSuggested
来引发RequerySuggested
事件。这最终将使命令源调用CanExecute
方法
当某些UI事件发生时,CommandManager
会自动引发RequerySuggested
。我觉得如果它也在PropertyChanged
上提出,它会很有用
我当前的解决方案:我修改了我的
ViewModelBase
类的属性更改方法,如下所示:
受保护的虚拟void OnPropertyChanged(字符串propertyName)
{
PropertyChanged(这是新的PropertyChangedEventArgs(propertyName));
Application.Current.Dispatcher?.Invoke(CommandManager.invalidateRequestSuggested);
}
关注点:我还没有发现任何
ViewModelBase
在线以这种方式实现,我觉得这应该是一个危险信号
RelayCommand
因其简单性而在MVVM中得到强烈推荐,因此我觉得奇怪的是,我最终不得不手动调用CommandManager。那么为什么不选择DelegateCommand
我知道这会导致更频繁地调用CanExecute
,但它已经在每次发生UI事件时被垃圾发送了 “典型”继电器命令
如果您使用的是MVVMLight的relaycommand,则源代码为:
您可以在RelayCommand上调用CanExecutechanged
将using语句添加到任何viewmodel时,请确保使用CommandWPF版本
当存在用户输入事件时,调用InvalidateRequestSuggested。因此,当用户输入任何内容并更改了您所提升的属性propertychanged时,您将提升它两次。意思是你的方法是个坏主意
很少有数据是从一个模型到一个viewmodel逐个属性的。更常见的情况是引发事件,然后viewmodel将viewmodel中的数据组合到属性中。您可能只需在获得新记录或更改事件后引发canexecutechanged一次,或者在数据更改不是由用户输入驱动时发生。“典型”relaycommand
如果您使用的是MVVMLight的relaycommand,则源代码为:
您可以在RelayCommand上调用CanExecutechanged
将using语句添加到任何viewmodel时,请确保使用CommandWPF版本
当存在用户输入事件时,调用InvalidateRequestSuggested。因此,当用户输入任何内容并更改了您所提升的属性propertychanged时,您将提升它两次。意思是你的方法是个坏主意
很少有数据是从一个模型到一个viewmodel逐个属性的。更常见的情况是引发事件,然后viewmodel将viewmodel中的数据组合到属性中。您可能只需在获得新记录或更改事件后引发canexecutechanged一次,或者在非用户输入驱动的情况下发生数据更改。通常ICommand的实现都有一些引发canexecutechanged事件的方法。你试过了吗?IMO比CommandManager更干净、更高效。InvalidateRequestSuggested看看如何实现从基本视图模型的
属性更改事件invocator触发RequerySuggested
,这是个坏主意。当任何属性发生更改时,它将触发RequerySuggested
事件。无论属性是否是命令逻辑的一部分。这会产生巨大的开销,因为ViewModelBase
在整个应用程序中使用,并由许多类扩展。通常在焦点更改或键盘鼠标事件时调用CanExecute
。这在大多数情况下是足够的。对于特殊情况,您可以显式调用CommandManager.invalidateRequestSuggested
@DaveM您的意思是让公共RaiseCanceTechChanged
?乔希·史密斯的那张没有。我同意它可以更干净@我想这就是我困惑的地方。我觉得有时不得不手动调用命令管理器会破坏RelayCommand
的功能。我将尝试考虑一个更好的长期解决方案,以确定何时CanExecute可以在没有任何用户交互的情况下更改。通常ICommand的实现都有一些引发CanExecuteChanged事件的方法。你试过了吗?IMO比CommandManager更干净、更高效。InvalidateRequestSuggested看看如何实现从基本视图模型的属性更改事件invocator触发RequerySuggested
,这是个坏主意。当任何属性发生更改时,它将触发RequerySuggested
事件。无论属性是否是命令逻辑的一部分。这会产生巨大的开销,因为ViewModelBase
在整个应用程序中使用,并由许多类扩展。通常在焦点更改或键盘鼠标事件时调用CanExecute
。这在大多数情况下是足够的。对于特殊情况,您可以显式调用CommandManager.invalidateRequestSuggested
@DaveM您的意思是让公共RaiseCanceTechChanged
?乔希·史密斯的那张没有。我同意它可以更干净@我想这就是我困惑的地方。我觉得有时不得不手动调用命令管理器会破坏
RelayCommand