ValidationRule 和 DependencyObject

ValidationRule and DependencyObject

我需要将绑定值发送到 ValidationRule。我使用的是 DependencyObject,但值始终是 null

这是我的 DependencyObject

public class MyDependencyObject  : DependencyObject
{
    public string BindingValue
    {
        get { return (string)GetValue(BindingValueProperty); }
        set { SetValue(BindingValueProperty, value); }
    }
    public static readonly DependencyProperty BindingValueProperty =
        DependencyProperty.Register("BindingValue", typeof(string), typeof(MyDependencyObject), new UIPropertyMetadata(null));    
}

这是我的 ValidationRule:

public class MyTextBoxValidationRule : ValidationRule
{
    private MyDependencyObject _TxtVal;
    public MyDependencyObject TxtVal
    {
        get { return _TxtVal; }
        set { _TxtVal = value; }
    }
    public override ValidationResult Validate(object value, System.Globalization.CultureInfo cultureInfo)
    {
        //Validation Logic
    }   
}

这是 XAML:

<TextBox >
    <TextBox.Text>
        <Binding Path="DataUserTypes" 
            NotifyOnValidationError="True" 
            ValidatesOnDataErrors="True" 
            Mode="TwoWay" 
            UpdateSourceTrigger="PropertyChanged"  
            NotifyOnSourceUpdated="True" 
            NotifyOnTargetUpdated="True"
            Delay="100">
            <Binding.ValidationRules>
                <local:MyTextBoxValidationRule ValidatesOnTargetUpdated="True"  >
                    <local:MyTextBoxValidationRule.TxtVal >
                        <local:MyDependencyObject   
                            TxtVal="{Binding Path=ValidateValue}" />
                    </local:MyTextBoxValidationRule.TxtVal>
                </local:MyTextBoxValidationRule>
            </Binding.ValidationRules>
        </Binding>
    </TextBox.Text>
</TextBox>

当我在 MyTextBoxValidationRule 中单步执行验证时,TxtVal.BindingValue 总是 null。我不知道为什么

编辑:

我将 DisplayValue 更改为 DataUserTypes,因为似乎有些混乱。

<Binding Path="DataUserTypes" 

那是文本框Text值的绑定。我需要根据 属性 ValidateValue 验证 DataUserTypes。我正在尝试使用 DependencyObject TxtVal.

我还修复了复制粘贴类型。有一个名为 TextValID 的字段应该是 TxtVal。抱歉。

<local:MyTextBoxValidationRule ValidatesOnTargetUpdated="True"  >
    <local:MyTextBoxValidationRule.TxtVal >
        <local:MyDependencyObject   
            BindingValue="{Binding ValidateValue, PresentationTraceSources.TraceLevel=High}" 
            />
    </local:MyTextBoxValidationRule.TxtVal>
</local:MyTextBoxValidationRule>

PresentationTraceSources.TraceLevel=High 在 VS 输出窗格中生成以下跟踪输出:

System.Windows.Data Warning: 56 : Created BindingExpression (hash=24230272) for Binding (hash=28316044)
System.Windows.Data Warning: 58 :   Path: 'ValidateValue'
System.Windows.Data Warning: 60 : BindingExpression (hash=24230272): Default mode resolved to OneWay
System.Windows.Data Warning: 61 : BindingExpression (hash=24230272): Default update trigger resolved to PropertyChanged
System.Windows.Data Warning: 62 : BindingExpression (hash=24230272): Attach to Lines.MyDependencyObject.BindingValue (hash=37689768)
System.Windows.Data Warning: 64 : BindingExpression (hash=24230272): Use Framework mentor <null>
System.Windows.Data Warning: 67 : BindingExpression (hash=24230272): Resolving source 
System.Windows.Data Warning: 69 : BindingExpression (hash=24230272): Framework mentor not found
System.Windows.Data Warning: 65 : BindingExpression (hash=24230272): Resolve source deferred
'Lines.exe' (CLR v4.0.30319: Lines.exe): Loaded 'C:\Windows\Microsoft.Net\assembly\GAC_MSIL\PresentationFramework.Aero\v4.0_4.0.0.0__31bf3856ad364e35\PresentationFramework.Aero.dll'. Skipped loading symbols. Module is optimized and the debugger option 'Just My Code' is enabled.
System.Windows.Data Warning: 67 : BindingExpression (hash=24230272): Resolving source 
System.Windows.Data Warning: 69 : BindingExpression (hash=24230272): Framework mentor not found

长话短说,local:MyDependencyObject 的实例没有地方可以继承 DataContext,因为它的父级不在可视化树中。

您可以使用 a BindingProxy 来解决这个问题,但是您要绑定什么? ValidateValue 必须是某物的 属性;但是什么?如果它是父视图模型的 属性,则可以这样做:

<TextBox.Resources>
    <local:BindingProxy
        x:Key="ViewmodelProxy"
        Data="{Binding}"
        />
</TextBox.Resources>
<TextBox.Text>
    <Binding Path="DataUserTypes" 
        NotifyOnValidationError="True" 
        ValidatesOnDataErrors="True" 
        Mode="TwoWay" 
        UpdateSourceTrigger="PropertyChanged"  
        NotifyOnSourceUpdated="True" 
        NotifyOnTargetUpdated="True"
        Delay="100">
        <Binding.ValidationRules>
            <local:MyTextBoxValidationRule ValidatesOnTargetUpdated="True"  >
                <local:MyTextBoxValidationRule.TxtVal>
                    <local:MyDependencyObject   
                        BindingValue="{Binding Data.ValidateValue, Source={StaticResource ViewmodelProxy}}" 
                        />
                </local:MyTextBoxValidationRule.TxtVal>
            </local:MyTextBoxValidationRule>
        </Binding.ValidationRules>
    </Binding>
</TextBox.Text>

绑定代理:

public class BindingProxy : Freezable
{
    #region Overrides of Freezable

    protected override Freezable CreateInstanceCore()
    {
        return new BindingProxy();
    }

    #endregion

    public object Data
    {
        get { return (object)GetValue(DataProperty); }
        set { SetValue(DataProperty, value); }
    }

    // Using a DependencyProperty as the backing store for Data.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty DataProperty =
        DependencyProperty.Register("Data", typeof(object), typeof(BindingProxy), new UIPropertyMetadata(null));
}