zoukankan      html  css  js  c++  java
  • WPF 属性值绑定、转换

    TextBlock绑定属性

    绑定集合中的第一项的属性

    <TextBlock Text="{Binding [1].PropertyName1}" DataContext="{Binding DemoList}"/>
    

    绑定单个属性及转换器

    <UserControl.Resources>
        <cvt:StateConv x:Key="stateConv"/>
    </UserControl.Resources>
    ...
    <TextBlock Text="{Binding Name, StringFormat={}{0:F2}, Converter="{StaticResource stateConv}"}"/>
    
    using System;
    using System.Globalization;
    using System.Windows;
    using System.Windows.Data;
    public class StateConv: IValueConverter
    {
        // 此文本将显示在控件中(比如:TextBox)
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            int type = 0;
            if (int.TryParse(value.ToString(), out type))
            {
                if (type == 1) { return "正常"; }
                else { return "异常"; }   
            } 
            return DependencyProperty.UnsetValue;                          
        }
        // 目标数据格式转换为原数据格式(正常->1)
        // 当您更改控件TextBox的值时,ConvertBack方法将在绑定再次触发时调用(默认OnFocusLost)
        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            if (string.IsNullOrEmpty(value?.ToString()))
                    return -1;
                
            var item = TypeResource.FirstOrDefault(x => x.DisplayText == value.ToString());
            if (item == null)
            {
               return -1;
            }
            return item.Key;
        }
    }
    

    转换器2

    数值转换,显示指定枚举类型的文本描述

    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value != null && int.TryParse(value.ToString(), out int type))
        {
            if (Enum.IsDefined(typeof(PropertyNameEnumType), type))
            {
                var @enum = (PropertyNameEnumType)type;
                return @enum.GetEnumDescription();
            }
        }
        return "未知状态";
    }
    

    多重绑定1

    <Label.Content>
        <TextBlock>
    	<TextBlock.Text>
    		<MultiBinding StringFormat="{}{0}({1})">
    			<Binding Path="Name1" TargetNullValue="用默认值来显示为空的字段" />
    			<Binding Path="Name2" />
    		</MultiBinding>
    	</TextBlock.Text>
        </TextBlock>
    </Label.Content>
    

    StringFormat要求它的目标是string类型。 可在指定控件内嵌套TextBlock进行自定义格式转换。
    若要体现动态数据,属性所属类需要实现INotificationPropertyChanged接口,绑定的属性可以响应属性更改事件。

    多重绑定2

    <UserControl.Resources>
        <cvt:MultiStateConv x:Key="multiStateConverter"/>
        <cvt:MultiVersionTypeConv x:Key="multiVersionTypeConverter"/>
    </UserControl.Resources>
    ...
    <TextBlock>
        <TextBlock.Text>
            <MultiBinding Converter="{StaticResource multiStateConverter}" ConverterParameter="{StaticResource bindingProxy}">
                <Binding Path="Name"/>
                <Binding Path="Name2"/>
                <!--绑定父级属性 PropertyName2-->
                <Binding Path="DataContext.PropertyName2" RelativeSource="{RelativeSource AncestorLevel=2, AncestorType={x:Type ListBoxItem}}"/>
            </MultiBinding>
        </TextBlock.Content>
    </TextBlock>
    
    <DataGridTextColumn Header="版本类型" Width="*">
        <DataGridTextColumn.Binding>
            <MultiBinding Converter="{StaticResource multiVersionTypeConverter}" ConverterParameter="{StaticResource multiStateConverter}">
                <Binding Path="Type1"/>
                <Binding Path="Type2"/>
            </MultiBinding>
        </DataGridTextColumn.Binding>
    </DataGridTextColumn>
    
    using System;
    using System.Globalization;
    using System.Windows.Data;
    
    [ValueConversion(typeof(object[]), typeof(string))]
    class MultiStateConv : IMultiValueConverter
    {
        public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
        {
            var cvt = parameter as MultiStateConv;
            string rslt = string.Empty;
            if (int.TryParse(values[0].ToString(), out int type))
            {
                //...             
            }
            if (int.TryParse(values[1].ToString(), out int type2))
            {
                //...
            }
            return rslt;                           
        }
    
        public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
    

    多重绑定3

    当传递的参数过多时,可以使用绑定代理。
    当显示逻辑比较复杂时,有多个参数规则,可重复设置同样内容,并控制不同的显隐来实现。

    xmlns:cvt="clr-namespace:ProjectName.Converters" 
    
    <Color x:Key="Color1">#FF4E5E</Color>
    <SolidColorBrush x:Key="Brush1" Color="{DynamicResource Color1}"/>
    <cvt:BindingProxy x:Key="bindingProxy" Data="{DynamicResource Brush1}" Reserve="{DynamicResource 3thDllBrush}" Thread="10.0"/>
    
    <cvt:ExceptionValueConv x:Key="exceptionValueConveter"/>
    <cvt:ExceptionForegroundVisibleConv x:Key="exceptionForegroundVisibleConveter"/>
    <cvt:ExceptionForegroundReVisibleConv x:Key="exceptionForegroundReVisibleConveter"/>
    
    <Grid>
        <TextBlock Foreground="{DynamicResource Brush3}"
                   Visibility="{Binding Percent, Converter={StaticResource exceptionForegroundVisibleConveter}, ConverterParameter={StaticResource bindingProxy}}">
            <Run Text="{Binding Percent, StringFormat={}{0:f1}, Converter={StaticResource exceptionValueConveter}}" />
            <Run Text="%"/>
        </TextBlock>
        <!--同样内容-->
        <TextBlock Foreground="{DynamicResource Brush4}"
                   Visibility="{Binding Percent, Converter={StaticResource exceptionForegroundReVisibleConveter}, ConverterParameter={StaticResource bindingProxy}}"> 
            <Run Text="{Binding Percent, StringFormat={}{0:f1}, Converter={StaticResource exceptionValueConveter}}" />
            <Run Text="%"/>
        </TextBlock>
    </Grid>
    
    
    
    using System.Windows;
    
    internal class BindingProxy : Freezable
    {
        protected override Freezable CreateInstanceCore()
        {
            return new BindingProxy();
        }
    
        /// <summary>
        /// 原始数据
        /// </summary>
        public object Data
        {
            get { return (object)GetValue(DataProperty); }
            set { SetValue(DataProperty, value); }
        }
        public static readonly DependencyProperty DataProperty = DependencyProperty.Register("Data", typeof(object), typeof(BindingProxy), new PropertyMetadata(null));
    
        /// <summary>
        /// 替代数据
        /// </summary>
        public object Reserve
        {
            get { return (object)GetValue(ReserveProperty); }
            set { SetValue(ReserveProperty, value); }
        }
        public static readonly DependencyProperty ReserveProperty = DependencyProperty.Register("Reserve", typeof(object), typeof(BindingProxy), new PropertyMetadata(null));
    
        /// <summary>
        /// 阈值
        /// </summary>
        public double Thread
        {
            get { return (double)GetValue(ThreadProperty); }
            set { SetValue(ThreadProperty, value); }
        }
        public static readonly DependencyProperty ThreadProperty = DependencyProperty.Register("Thread", typeof(double), typeof(BindingProxy), new PropertyMetadata(0.0));
    }
    

    可直接调用资源词典

    Converter.xaml

    {Binding Converter={StaticResource Boolean2VisibilityConverter}}

    <ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
                        xmlns:converter="clr-namespace:XXX.Converters">
        <BooleanToVisibilityConverter x:Key="Boolean2VisibilityConverter"/>
        ......
    </ResourceDictionary>
    

    DataGrid中,编辑状态下触发事件

    <DataGridTextColumn  Width="auto" IsReadOnly="False"  MinWidth="110"  Binding="{Binding Name}" Header="名称">
        <DataGridTextColumn.EditingElementStyle>
            <Style TargetType="TextBox">
                <EventSetter Event="TextChanged" Handler="DataGridTextColumn_Name_TextChanged"/>
                <EventSetter Event="LostFocus" Handler="DataGridTextColumn_Name_LostFocus"/>
            </Style>
        </DataGridTextColumn.EditingElementStyle>
    </DataGridTextColumn>
    

    RadioButton绑定属性

    <UserControl.Resources>
        <cvt:RadioCheckConv x:Key="radioCheckConverter"/>
    </UserControl.Resources>
    
    <RadioButton Content="XXX" HorizontalAlignment="Center" GroupName="GroupName1" 
                 IsChecked="{Binding PropertyName1, Converter={StaticResource radioCheckConverter}, ConverterParameter=1}"/>
    

    其中,属性PropertyName1是可通知的;

    using System;
    using System.Windows.Data;
    public class RadioCheckConv : IValueConverter
    {
      public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
      {
          if (value == null || parameter == null)
          {
              return false;
          }
          if (value.ToString().Equals(parameter.ToString()))
          {
              return true;
          }
          return false;
      }
    
      public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
      {
          if (value == null || parameter == null)
          {
              return null;
          }
          if ((bool)value)
          {
              return parameter.ToString();
          }
          return null;
      }
    }
    

    TextBox绑定属性

    <TextBox x:name="txt" Text="{Binding PropertName, Mode=TwoWay, UpdateSourceTrigger=Default}" />

    控件绑定属性时,UpdateSourceTrigger默认为Default。源PropertName不会随着Text属性的改变而立即更新;TextBox中的变化并不是立即传递到源,而是在TextBox失去焦点后,源才更新。

    UpdateSourceTrigger枚举 说明 备注
    Default 默认值 默认为LostFocuse
    Explicit 当应用程序调用 UpdateSource 方法时生效 通过代码手动推送来更新
    LostFocus 失去焦点的时候触发
    PropertyChanged 属性改变的时候触发 源会立即更新
    using System.Windows.Data;
    private void btnUpdateSource_Click(object sender, RoutedEventArgs e)
    {
        // Explicit时,手动更新绑定的属性
        BindingExpression binding = txt.GetBindingExpression(TextBox.TextProperty);
        binding.UpdateSource();
    }
    

    后台绑定

    <cvt:IntToBoolConv x:Key="intToBoolConverter"/>
    <CheckBox Content="启用" x:Name="CheckBox1"
       IsChecked="{Binding IsEnable, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged, Converter={StaticResource intToBoolConverter}}" />
    
    this.DataContext = this;  // Prism可省略此步;此时IsEnable可通知客户端即可,不要求是依赖属性propdp
    

    相当于后台实现

    <CheckBox Content="启用" x:Name="CheckBox1"  />
    using System.Windows.Data;
    BindingOperations.SetBinding(CheckBox1,   // 控件名称
        CheckBox.IsCheckedProperty,           // 控件属性
        new Binding                           // 绑定内容
        {
            Path = new PropertyPath("IsEnable"), // 依赖属性 IsEnable
            Mode = BindingMode.TwoWay,
            UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged,
            Converter = new IntToBoolConv(),
            Source = this,                    // 属性所属对象
        });
    
    
  • 相关阅读:
    VysorPro助手
    Play 2D games on Pixel running Android Nougat (N7.1.2) with Daydream View VR headset
    Play 2D games on Nexus 6P running Android N7.1.1 with Daydream View VR headset
    Native SBS for Android
    ADB和Fastboot最新版的谷歌官方下载链接
    How do I install Daydream on my phone?
    Daydream Controller手柄数据的解析
    蓝牙BLE传输性能及延迟分析
    VR(虚拟现实)开发资源汇总
    Android(Java)控制GPIO的方法及耗时分析
  • 原文地址:https://www.cnblogs.com/wesson2019-blog/p/12619655.html
Copyright © 2011-2022 走看看