wpf - NotifyOnValidationError如何最终调用CanExecute(以及为什么它不适用于MVVM Light RelayCommand)

标签 wpf mvvm prism mvvm-light

也许是有史以来最长的问题标题!因为这是一个两部分的问题。

(1)我不明白如何设置NotifyOnValidationError =“True”可以触发对CanExecute的更新。我需要了解这里涉及的一些魔术。某人(某物)订阅了ICommand的CanExecuteChanged事件,但调用堆栈指向外部代码,因此我无法弄清楚发生了什么。

(2)也许最重要的后续问题是:为什么它在MVVM Light RelayCommand中不起作用! CanExecute仅在初始化时调用一次,然后再也不会调用。与我自己的实现相比,在MVVM Light中查看RelayCommand的源代码并没有发现任何明显的差异。我应该提到Prism的DelegateCommand似乎也不起作用。

(奖金)Maybee我以错误的方式解决了这个问题?我只是基本上想基于验证失败启用/禁用按钮。

XAML(摘要):

    <TextBox Grid.Column="1" Grid.Row="0">
        <Binding Path="X" UpdateSourceTrigger="PropertyChanged" NotifyOnValidationError="True">
            <Binding.ValidationRules>
                <ExceptionValidationRule></ExceptionValidationRule>
            </Binding.ValidationRules>
        </Binding>
    </TextBox>

    <Button Grid.Column="1" Grid.Row="3" Command="{Binding CalculateCommand}">
        Calculate
    </Button>

RelayCommand:
public class MyRelayCommand : ICommand
{
    readonly Action<object> Execute_;
    readonly Predicate<object> CanExecute_;

    public MyRelayCommand(Action<object> Execute, Predicate<object> CanExecute)
    {
        if (Execute == null)
            throw new ArgumentNullException("No action to execute for this command.");

        Execute_ = Execute;
        CanExecute_ = CanExecute;
    }

    public bool CanExecute(object parameter)
    {
        return (CanExecute_ == null) ? true : CanExecute_(parameter);
    }

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

    public void Execute(object parameter)
    {
        Execute_(parameter);
    }
}

ViewModel:
    private DelegateCommand _calculateCommmand;
    public DelegateCommand CalculateCommand
    {
        get
        {
            return _calculateCommmand ?? (_calculateCommmand = new DelegateCommand(
            () =>
            {
                Sum = X + X;
            },
            () =>
            {
                try
                {
                    Convert.ChangeType(X, TypeCode.Byte);
                    return true;
                }
                catch
                {
                    return false;
                }
            }));
        }
    }

PS:如果您想在购买完成后购买我的X + X程序,请发送电子邮件至sales@xplusx.com

最佳答案

(2)我自己弄清楚了这个。您可以选择从两个不同的命名空间中包含RelayCommand,请确保使用

using GalaSoft.MvvmLight.CommandWpf;

我仍在寻找对(1)的良好答案,它如何根据验证错误提高CanExecutetChanged的质量。

关于wpf - NotifyOnValidationError如何最终调用CanExecute(以及为什么它不适用于MVVM Light RelayCommand),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36768968/

相关文章:

c# - 验证密码和密码确认到XAML

c# - WPF 命令 - View 与模型的关系

WPF 图像与 XAML

c# - 应将包装的 EF 实体保存在哪个类中?

windows-phone-7 - NavigationService 抛出 NullReferenceException

wpf - 使用 FlowDocumentScrollViewer 打印所有页面

android - 通过标准模板与 Prism 模板创建 Xamarin 表单项目时出现资源错误

c# - 使用 WPF 和 SlimDx (DirectX 10/11)

c# - 事件不会跨模块触发(prism、MVVM、silverlight c#)

wpf - 检测应用程序退出以及在未保存更改时如何停止