zoukankan      html  css  js  c++  java
  • 深入浅出WPF-06.Binding(绑定)02

    Binding对数据的校验和转换

    1)数据校验,通过Binding的ValidationRules属性(Collection类型)进行校验。可以设置多个数据校验条件。

    <Slider Margin="5" Maximum="100" Minimum="0" SmallChange="1" x:Name="silder1">
        <Slider.Value>
            <Binding Path="CurrentValue">
                <Binding.ValidationRules>
                    <local:MyValidationRule/>
                </Binding.ValidationRules>
            </Binding>
        </Slider.Value>
    </Slider>
    
    public class MyValidationRule : ValidationRule
    {
        public override ValidationResult Validate(object value, CultureInfo cultureInfo)
        {
            if (value != null && value is double input)
            {
                if (input > 0 && input < 100)
                {
                    return new ValidationResult(true, null);
                }
            }
    
            return new ValidationResult(false, "can not null");
        }
    }
    

    ValidationRule是个抽象类,使用的时候需要创建他的派生类并实现Validate方法。如果通过校验,就把ValidationResult对象的IsValid属性设为true,否则设为false,并设置ErrorContent的消息内容。

    校验的默认行为是认为来自于Source的数据总是正确的,只有来自目标Target的数据才可能出问题(Target多为UI控件,多数是用户输入的数据),为了就是不让输入的数据污染Source数据,所以才进行校验。Binding只有在Target被外部方法更新时才会校验(手动输入)。如果想在Source数据更新时Target也进行校验,需要将校验条件的ValidatesOnTargetUpdated设置为true。

    当校验错误的时候Validate方法返回的ValidationResult对象,携带的错误信息如何显示?需要用到后面的知识---路由事件(EventRouted)。

    如果Binding对象的NotifyOnValidationError="True",这时,当数据校验错误的时候Binding会像报警器一样发出一个信号,这个信号以Target为起点,沿着树进行传播,直到某个节点监听并处理了这个信号。信号处理完之后,可以决定这个信号是继续传播,还是终止(e.Handled = true;)。这就是路由事件,传递这个信号的过程叫做路由。

    private MainWindowViewModel model = new MainWindowViewModel();
    public Window1()
    {
        InitializeComponent();
        this.DataContext = model;
    
        this.silder1.AddHandler(Validation.ErrorEvent, new RoutedEventHandler(ValidationError));
    }
    
    void ValidationError(object sender, RoutedEventArgs e)
    {
        if (Validation.GetErrors(this.silder1).Count > 0)
        {
            //处理错误信息
    
            e.Handled = true;
        }
    }
    

    2)数据转换,当源Source端的Path所关联的数据与Target端目标属性数据展示不一致时,我们就可以通过添加数据转换器来实现。比如最常用的性别,在数据源Source端一般使用枚举值,Target端一般使用字符串或者图片来区分,这是我们就可以使用转换器来实现。

    xaml代码:

    <TextBlock Margin="5" Height="23" Text="{Binding SexType, Converter={StaticResource DtoShowStringConverter}}"/>
    

    性别枚举值:

    /// <summary>
    /// 性别
    /// </summary>
    public enum SexType : byte
    {
        /// <summary>
        /// 女
        /// </summary>
        Female = 0,
        /// <summary>
        /// 男
        /// </summary>
        Male = 1,
        /// <summary>
        /// 未知
        /// </summary>
        Null = 2
    }
    
    

    转换器:

    public class DtoShowStringConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            if (value == null) return null;
    
            string output = null;
    
            if (value is SexType input)
            {
                switch (input)
                {
                    case SexType.Female:
                        output = "女";
                        break;
                    case SexType.Male:
                        output = "男";
                        break;
                    case SexType.Null:
                        output = "未知";
                        break;
                    default:
                        break;
                }
            }
    
            return output;
        }
    
        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
    
    

    当数据从Source流向Target时,Convert方法被调用,反之,ConvertBack被调用。第一个参数是传入的值,第二个参数是返回的值的类型,第三个参数是用来传递额外信息的(对应的Binding中的ConverterParameter)。我们最常用的是Source流向Target(Convert方法),极少使用ConvertBack。

  • 相关阅读:
    event loop笔记
    webpack不同devtools打包对比
    windows 7系统搭建本地SVN服务器的过程
    Eclipse安装SVN插件
    总结eclipse中安装maven插件
    myeclipse building workspace如何禁止及提高myeclipse速度
    基于SAML的单点登录介绍
    使用 CAS 在 Tomcat 中实现单点登录
    SSO之CAS备忘
    Maven环境变量配置
  • 原文地址:https://www.cnblogs.com/vigorous/p/13162300.html
Copyright © 2011-2022 走看看