【6月日新计划27】WPF入门-Validation

106 阅读2分钟

1. Introduction

方法如下:

Equals(Object)

确定指定对象是否等于当前对象。

GetHashCode()

作为默认哈希函数。

GetType()

获取当前实例的 Type

MemberwiseClone()

创建当前 Object 的浅表副本。

ToString()

返回表示当前对象的字符串。

Validate(Object, CultureInfo)

在派生类中重写时,对值执行验证检查。

Validate(Object, CultureInfo, BindingExpressionBase)

对值执行验证检查。

Validate(Object, CultureInfo, BindingGroup)

对值执行验证检查。

適用與

产品 版本
.NET Framework 3.0, 3.5, 4.0, 4.5, 4.5.1, 4.5.2, 4.6, 4.6.1, 4.6.2, 4.7, 4.7.1, 4.7.2, 4.8
Windows Desktop 3.0, 3.1, 5, 6, 7

2. Demo

Path=“Age”,表示綁定後端的Age的值,用來前後端交互

可以傳值,也可以不傳Max和Min

//名稱空間要導入進來
<TextBox Name="textBox1" 
         Width="50" 
         FontSize="15"
         Grid.Row="1" 
         Grid.Column="1" 
         Margin="2">
  <TextBox.Text>
    <Binding Path="Age"
             UpdateSourceTrigger="PropertyChanged" >
      <Binding.ValidationRules>
        <c:AgeRangeRule Min="21" Max="130"/>
      </Binding.ValidationRules>
    </Binding>
  </TextBox.Text>
</TextBox>

自定義Rule

public class AgeRangeRule : ValidationRule
{
    public int Min { get; set; }
    public int Max { get; set; }

    public AgeRangeRule()
    {
    }

    public override ValidationResult Validate(object value, CultureInfo cultureInfo)
    {
        int age = 0;

        try
        {
            if (((string)value).Length > 0)
                age = Int32.Parse((String)value);
        }
        catch (Exception e)
        {
            return new ValidationResult(false, $"Illegal characters or {e.Message}");
        }

        if ((age < Min) || (age > Max))
        {
            return new ValidationResult(false,
              $"Please enter an age in the range: {Min}-{Max}.");
        }
        return ValidationResult.ValidResult;
    }
}

3. Dynamic Validation Rule

3.1 UpdateSourceTrigger

Default 0

使用绑定的依赖属性的默认行为。 在 Windows 运行时 中,此计算结果与 PropertyChanged 的值相同。

Explicit 2

仅当调用 BindingExpression.UpdateSource 方法时,才会更新绑定源。

LostFocus 3

每当绑定目标元素失去焦点时,都会更新绑定源。

PropertyChanged 1

每当绑定目标值更改时,都会更新绑定源。 绑定系统会自动检测到这一点。

3.2 Code

動態傳參,使用校驗規則

 public class BindingProxy : Freezable
    {
        protected override Freezable CreateInstanceCore()
        {
            return new BindingProxy();
        }
 
        public static readonly DependencyProperty DataProperty = DependencyProperty.Register("Data", typeof(object), typeof(BindingProxy), new UIPropertyMetadata(null));
 
        public object Data
        {
            get { return (object)GetValue(DataProperty); }
            set { SetValue(DataProperty, value); }
        }      
    }

自定義校驗規則

 public class MyValidationRule1 : ValidationRule
    {
        public ValidationParams Params
        {
            get;set;
        }
 
        public override ValidationResult Validate(object value, System.Globalization.CultureInfo cultureInfo)
        {
        
            //記錄結果
            bool result = false;
            string msg = "校驗規則是" + (string)Params.Data;

            //要校驗的值
            var content = value.ToString().Trim();

            var rule = (string)Params.Data;
            if (rule == null || "".Equals(rule))
            {
                //验证成功
                result = true;
            }
            else
            {
                xxxxxx
            }

            if (result)
                //验证成功
                return new ValidationResult(true, null);
            else
                //验证失败
                return new ValidationResult(false, msg);
        }
    }
 
    public class ValidationParams : DependencyObject
    {
        public static readonly DependencyProperty DataProperty = DependencyProperty.Register(
           "Data", typeof(object), typeof(ValidationParams), new FrameworkPropertyMetadata(null));
 
        public object Data
        {
            get { return GetValue(DataProperty); }
            set
            {
                SetValue(DataProperty, value);
            }
        }
    }

xaml頁面部分

  • AAA:就是TextBox和後端交互的值,類似{Binding xxxx}
  • BBB:就是後端用來保存Validation Rule的值,可能是從其他Api返回的。
<UserControl x:Class="xxxxx"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:local="clr-namespace:WindowDemo"
             xmlns:hs="http://controls.hs.net/xaml"
             Title="MainWindow"
             Background="White"
             Name="MainWnd">
    <UserControl.Resources>
        <local:BindingProxy x:Key="BindingProxy"
                            Data="{Binding}" />
    </UserControl.Resources>
    <Grid Margin="20">
        <StackPanel>
            <TextBox Grid.Column="1"
                     Margin="5"
                     Style="{StaticResource MaterialDesignOutlinedTextBox}">
                <TextBox.InputBindings>
                    <KeyBinding Key="Enter"
                                Command="{Binding ExecuteCommand}"
                                CommandParameter="Check" />
                </TextBox.InputBindings>
                <TextBox.Text>
                    <Binding Mode="TwoWay"
                             Path="{AAA}"
                             UpdateSourceTrigger="LostFocus">
                        <Binding.ValidationRules>
                            <rule:InformationCollectionValidationRule>
                                <rule:InformationCollectionValidationRule.Params>
                                    <rule:ValidationParams Data="{Binding  Source={StaticResource BindingProxy},Path=Data.BBB}" />
                                </rule:InformationCollectionValidationRule.Params>
                            </rule:InformationCollectionValidationRule>
                        </Binding.ValidationRules>
                    </Binding>
                </TextBox.Text>
            </TextBox>
        </StackPanel>
    </Grid>
</UserControl>