PunCha

导航

ListBox绑定的研究

本文主要研究ListBox的绑定,一般来说,ListBox常用的绑定属性是ItemsSource和SelectedItem,但是本文讨论的是其他两个属性:SelectedValue, SelectedValuePath。下面这个程序很有意思,改变左侧的选中项,右侧的选中项会跟着变,下面2个TextBox里面的内容也会显示出选中的内容。例如我选中了"Mike",右侧自动选中了"Dog",下面两个TextBox分别显示,Mike 和 Dog:

 

下面是“人类”和“动物”两个类型,各自有2个属性,其中一个属性是共同的——ID:

    class Human
    {
        public int ID { get; set; }
        public string Name { get; set; }
    }

    class Animal
    {
        public int ID { get; set; }
        public string Category { get; set; }
    }

 

下面是XAML的定义,很简单,只是把TextBox绑定到了各自的ListBox中:

<Window x:Class="WpfApplication2.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="252" Width="370">
    <Grid Height="205" Width="341">
    <Grid.RowDefinitions>
      <RowDefinition Height="168*" />
      <RowDefinition Height="37*" />
    </Grid.RowDefinitions>
    <Grid.ColumnDefinitions>
      <ColumnDefinition Width="176*" />
      <ColumnDefinition Width="165*" />
    </Grid.ColumnDefinitions>
    <ListBox Grid.Row="0" Grid.Column="0" Name="lsLeft" />
    <ListBox Grid.Row="0" Grid.Column="1" Name="lsRight" />
    <TextBox Grid.Row="1" Grid.Column="0" Name="txtLeft" Text="{Binding Path=SelectedItem.Name, ElementName=lsLeft}" />
    <TextBox Grid.Row="1" Grid.Column="1" Name="txtRight" Text="{Binding Path=SelectedItem.Category, ElementName=lsRight}"/>
  </Grid>
</Window>

 

以下是代码,People和Animals是两个集合,分别放入了4个Human和6个Animal对象。他们的ID都是连续的,并且都从1开始。下面的代码把2个集合绑定到了2个ListBox,ListBox的DisplayNamePath分别设置成Name和Category属性,但是SelectedValuePath都设置成ID。但是,最关键的一点是,左侧的ListBox右侧的相绑定,而中间的桥梁是SelectedValue属性!

   /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        private List<Human> People;
        private List<Animal> Animals;

        public MainWindow()
        {
            People = new List<Human>();
            People.Add(new Human() { ID = 1, Name = "Tom" });
            People.Add(new Human() { ID = 2, Name = "Jerry" });
            People.Add(new Human() { ID = 3, Name = "Mike" });
            People.Add(new Human() { ID = 4, Name = "Lee" });

            Animals = new List<Animal>();
            Animals.Add(new Animal() { ID = 1, Category = "Cat" });
            Animals.Add(new Animal() { ID = 2, Category = "Tiger" });
            Animals.Add(new Animal() { ID = 3, Category = "Dog" });
            Animals.Add(new Animal() { ID = 4, Category = "Pig" });
            Animals.Add(new Animal() { ID = 5, Category = "Cook" });
            Animals.Add(new Animal() { ID = 6, Category = "Cow" });

            InitializeComponent();

            lsLeft.ItemsSource = People;
            lsLeft.DisplayMemberPath = "Name";
            lsLeft.SelectedValuePath = "ID";

            lsRight.ItemsSource = Animals;
            lsRight.DisplayMemberPath = "Category";
            lsRight.SelectedValuePath = "ID";

            Binding binding = new Binding();
            binding.ElementName = "lsRight";
            binding.Path = new PropertyPath("SelectedValue");
            lsLeft.SetBinding(ListBox.SelectedValueProperty, binding);
        }
    }


上面的代码之所以能work,就是因为ListBox的SelectedValuePath设置为ID属性,所以每个选中的Item其SelectedValue就是ID属性,一旦两个ListBox的SelectedValue都一致的话,绑定就自动生效,当左侧Mike (ID=3)被选中,右侧Dog(ID=3)就自动被选中,同理,选中右侧的Cat,左侧的Tom也同样被选中。但是假如你选中右侧的Cook或者Cow,那么左侧就没有一个被选中,下方的TextBox的内容也是空。可见,左侧的SelectedItem被设置成了null。

 

在实际项目中,有时候可能会使用到这个技术,比如,注册论坛注册,允许用户选择不同的内置头像,一旦用户选定,数据库中会保存头像的ID(肯定不是头像的内容吧),那么头像肯定另有一张数据库表来维护,具有ID,图片路径等。然而,当用户需要修改头像的时候,你需要在ComboBox里面列出所有的内置头像,然后把该用户原先选择的头像默认选中。要实现这个功能的话,就需要用到ID的绑定,就可以使用本文的方法~

 

 

posted on 2012-04-08 00:41  PunCha  阅读(153)  评论(0编辑  收藏  举报