WPF学习:6.绑定

  上一章介绍了依赖属性,本章开始介绍WPF中最重要的部分-绑定。

  数据绑定实际上关联数据源和目标的一种方式,其目标一般是应用程序的用户界面。数据源则可能是一个集合对象,一个XML文件,一个Web服务,一个数据表,一个自定义对象,甚至一个WPF元素,如Button。当数据发送改变时,用户界面会自动反映该变化。

WFP中的绑定

  在WPF中,有两种属性,属性和依赖属性。WPF也支持命令行绑定,让我们讨论下他们具体是怎么执行的。绑定分为数据绑定和类型绑定。

数据绑定

  数据绑定是最重要也是最主要的绑定类型,WPF引入了像ObjectDataProviderXMLDataprovider

等对象加强XAML中的对象绑定能力,WPF中数据绑定是非常灵活的。

1 <TextBox x:Name="txtName" />
2 <TextBlock Text="{Binding ElementName=txtName, Path=Text.Length}" />

  以上是绑定的基本用法,将TextBlockTextTextBox txtName进行绑定,在程序运行时无论你什么时候改变了TextBoxTextBlock都会反映string的长度。标记扩展实际上是一个属性类,这里我们指定了ElementNamePathElementName决定可对象属性的归属,Path决定了对象显示的内容。

  在XAML中,使用ObjectDataProvider装载数据是非常简单的。ObjectDataProvider能够作为静态资源调用,看下面的代码。

1 <StackPanel Orientation="Vertical">
2     <StackPanel.Resources>
3       <ObjectDataProvider ObjectType="{x:Type m:StringData}"
4          x:Key="objStrings" MethodName="GetStrings"/>
5     </StackPanel.Resources>
6     <ListBox Name="lstStrings" Width="200" Height="300"
7            ItemsSource="{Binding Source={StaticResource objStrings}}" />

  ObjectType是一个内置类结构,使用StaticResource调用对象,声明一个类。

 1 public class StringData
 2  {
 3   ObservableCollection<String> lst= new ObservableCollection<String>();
 4 
 5         public StringData()
 6         {
 7             lst.Add("Abhishek");
 8             lst.Add("Abhijit");
 9             lst.Add("Kunal");
10             lst.Add("Sheo");
11         }
12         public ObservableCollection<String> GetStrings()
13         {
14              return lst;
15         }
16     }

  在上面的代码中,我使用ObvervableCollection,ObvervableCollection能够在新对象插入时发出自动通知,使得ListBox进行更新,不需要手动进行。

  WPF绑定在数据改变时需要进行通知,INotifyPropertyChangedINotifyCollectionChanged需要在随着绑定的数据发送改变时更新UI控件,所以如果你想要在绑定数据发生改变的时候同时改变UI,实现INotifycollectionChanged是基本要求,对于像ItemsSource一样的集合,执行INotifyCollectionChanged。ObservableCollection本身包含了INotifyCollectionChanged,因此不管什么时候,当新元素插入或者旧元素删除的时候都会自动更新ListBox。

XML绑定

  XAML支持XML绑定,能够通过Binding类中定义的XPathXMLDataProvider绑定数据。

<TextBlock Text="{Binding XPath=@description}"/>
<TextBlock Text="{Binding XPath=text()}"/>

  假如你有XYZ节点,内部的文本可以使用text()属性取出,@标志用于属性,使用XPath,可以轻松的转载XML

数据文本的重要性

  你可能很奇怪为什么我在讲WPF绑定的时候来讲数据文本(DataContext),DataContext是一种依赖属性当你为网格定义了一个DataContext属性,然后网格所有元素都将得到相同的DataContext

<Grid DataContext="{StaticResource dtItem}">
<TextBox Text="{Binding MyProperty}" />
</Grid>

  为网格定义一个DataContext,网格内的TextBox能够引用属性MyProperty作为dtItem对象。

绑定成员

  绑定实际上是一种标记扩展,让我们讨论下绑定的成员:

  1. Source:DataSource的源属性。默认引用了控件的DataContext属性。

  2.ElementNameElementName是在XAML中定义的需要引用的对象名字。假如path没有指定,使用ToString从源对象中获取数据。

  3.Path:定义了实际属性的路径,目的是得到String Data。假如对象不是一个String,它将调用ToString得到数据。

  4.Mode:定义了数据传送的模式。从图的角度来说存在3中状态。

    OneWay

          正如图A所说,Source影响着Target,但是Target却影响不到Source。

    OneWayToSource

         也正如图B中所表述的一样,Target影响Source,而Source却影响不到Target。

    TwoWay

         这个也就相当于无向图的边,Source与Target相互影响。

    OneTime

         在OneWay的基础上延伸了一个OneTime,仅绑定一次。如果大家属性Jquery中的one函数我想就可以不用表述了。

  5.UpdateSourceTrigger:当源对象发生改变时触发,可以是:

    PropertyChanged:默认选项,不管控件中发生什么改变,都会反映到绑定的对象中。

    LostFocus:属性失去焦点是触发。

    Explicit:源更新时,你需要显式的设置,使用UpdateSourceBindingExpression更新控件。

  6.Converter:当源更新时,提供一个可以设置调用对象的接口。

  7:ConverterParameter:Converter参数设置。

  8:FallbackValue:当绑定没有返回值的时候定义的返回值,默认为空

  9:StringFormat:一个格式化的字符串表明数据传输遵循的格式。

  10:ValidatesOnDataErrors: DataErrors得到验证。

后台代码绑定

 Binding myBinding = new Binding("DataObject");
  myBinding.Source = myDataObject;
  myTextBlock.SetBinding(TextBlock.TextProperty, myBinding);

多重绑定

  

<TextBlock DockPanel.Dock="Top" >
   <TextBlock.Text>
      <MultiBinding Converter="{StaticResource mbindingconv}">
        <Binding ElementName="lst" Path="Items.Count" />
        <Binding ElementName="txtName" Path="Text" />
        <Binding ElementName="txtAge" Path="Text" />
      </MultiBinding>
   </TextBlock.Text>
 </TextBlock>

  TextBox的值依赖与3个元素:ListBox counttxtNametxtAge,我使用Converter来确保我们能有在IMultiValueConverter块中找到所有的元素,然后一个个加载它们。IMultiValueConverterIValueConverter是类似的,能够设置和返回与Text绑定的对象。

  

public class MyMultiBindingConverter : IMultiValueConverter
    {
        #region IMultiValueConverter Members

        public object Convert(object[] values, Type targetType,
                object parameter, System.Globalization.CultureInfo culture)
        {
            string returnval = "Total no of Data {0}, NewData : ";

            if (values.Count() <= 0) return string.Empty;

            returnval = string.Format(returnval, values[0]);

            for (int i = 1; i < values.Count(); i++)
                returnval += "- " + values[i];

            return returnval;
        }

        public object[] ConvertBack(object value, Type[]
            targetTypes, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }

        #endregion
    }

  简便起见,我合并可多个数组。

似水无痕:http://www.cnblogs.com/keylei203/

 

posted @ 2013-03-14 13:20  似水无痕keylei  阅读(1309)  评论(0编辑  收藏  举报