WPF Binding : Use DataAnnotations for ValidationRules

前端 未结 5 559
眼角桃花
眼角桃花 2020-12-09 04:59

I have read a lot of Blog post on WPF Validation and on DataAnnotations. I was wondering if there is a clean way to use DataAnnotations as Va

5条回答
  •  执笔经年
    2020-12-09 05:47

    Recently I've had the same idea using the Data Annotation API to validate EF Code First POCO classes in WPF. Like Philippe's post my solution uses reflection, but all necessary code is included in a generic validator.

    internal class ClientValidationRule : GenericValidationRule { }
    
    internal class GenericValidationRule : ValidationRule
    {
      public override ValidationResult Validate(object value, CultureInfo cultureInfo)
      {
        string result = "";
        BindingGroup bindingGroup = (BindingGroup)value;
        foreach (var item in bindingGroup.Items.OfType()) {
          Type type = typeof(T);
          foreach (var pi in type.GetProperties()) {
            foreach (var attrib in pi.GetCustomAttributes(false)) {
              if (attrib is System.ComponentModel.DataAnnotations.ValidationAttribute) {
                var validationAttribute = attrib as System.ComponentModel.DataAnnotations.ValidationAttribute;
                var val = bindingGroup.GetValue(item, pi.Name);
                if (!validationAttribute.IsValid(val)) { 
                  if (result != "")
                    result += Environment.NewLine;
                  if (string.IsNullOrEmpty(validationAttribute.ErrorMessage))
                    result += string.Format("Validation on {0} failed!", pi.Name);
                  else
                    result += validationAttribute.ErrorMessage;
                }
              }
            }
          }
        }
        if (result != "")
          return new ValidationResult(false, result);
        else 
          return ValidationResult.ValidResult;
      }
    }
    

    The code above shows a ClientValidatorRule which is derived from the generic GenericValidationRule class. The Client class is my POCO class which will be validated.

    public class Client {
        public Client() {
          this.ID = Guid.NewGuid();
        }
    
        [Key, ScaffoldColumn(false)]
        public Guid ID { get; set; }
    
        [Display(Name = "Name")]
        [Required(ErrorMessage = "You have to provide a name.")]
        public string Name { get; set; }
    }
    

提交回复
热议问题