none
WPF ComboBox绑定问题 RRS feed

  • 问题

  • 源码如下:

    NationFriamlyServiceClient client = new NationFriamlyServiceClient();
                ObservableCollection<NationFriamly> list = new ObservableCollection<NationFriamly>(client.GetNationFriamlyAll());
                //cbm_NationFriamly.ItemsSource = list;
                //cbm_NationFriamly.SelectedValuePath = "Id";
                //cbm_NationFriamly.DisplayMemberPath = "NF_CN";
                Binding NationFriamlyBing = new Binding("");
                NationFriamlyBing.Source = list;
                NationFriamlyBing.Mode = BindingMode.TwoWay;
                cbm_NationFriamly.SelectedValuePath = "Id";
                cbm_NationFriamly.DisplayMemberPath = "NF_CN";
                cbm_NationFriamly.SetBinding(ComboBox.ItemsSourceProperty, NationFriamlyBing);

    说要些Path,不知道写什么.怎么办 ? 如何解决呢 ?

    2012年4月4日 10:29

答案

  • ???

    2012年4月6日 9:01
  • ???

    2012年4月4日 11:54
  •  按照你的想法,给你写个简单的例子,当然是没有你的Linq to SQL等ORM的,我直接用的硬编码数据.

      <StackPanel>
        <TextBox Margin="10"/>
        <Button Content="+" Click="Button_Click" Margin="10" HorizontalAlignment="Center" Width="100" FontSize="20"/>
        <ComboBox Margin="10" x:Name="combobox" IsEditable="True" IsReadOnly="False"/>
        <TextBlock x:Name="text1" Text="{Binding Path=SelectedItem.Value}"/>
        <TextBlock x:Name="text2" Text="{Binding Path=SelectedItem.DisplayValue}"/>
      </StackPanel>

    C#:
      public partial class MainWindow : Window
      {
    
        public ObservableCollection<Item> Items { get; set; }
        public MainWindow()
        {
          InitializeComponent();
    
          Items = new ObservableCollection<Item>()
          {
            new Item(){DisplayValue="Item 1"},
            new Item(){DisplayValue="Item 2"},
            new Item(){DisplayValue="Item 3"},
            new Item(){DisplayValue="Item 4"},
          };
    
          this.DataContext = new Selected();
    
          Binding binding = new Binding(".");
          binding.Source = Items;
          binding.Mode = BindingMode.TwoWay;
          combobox.SelectedValuePath = "Value";
          combobox.DisplayMemberPath = "DisplayValue";
          combobox.SetBinding(ComboBox.ItemsSourceProperty, binding);
          Binding selectedBinding = new Binding("SelectedItem");
          combobox.SetBinding(ComboBox.SelectedItemProperty, selectedBinding);
    
          combobox.IsSynchronizedWithCurrentItem = true;
          combobox.SelectedIndex = 0;
        }
    
        private void Button_Click(object sender, RoutedEventArgs e)
        {
          Items.Add(new Item() { DisplayValue = "New Added Item " + Item.ID });
        }
      }
    
      public class Selected
      {
        public Item SelectedItem { get; set; }
      }
    
      public class Item : INotifyPropertyChanged
      {
        public static int ID;
    
        private string _DisplayValue;
        public string DisplayValue
        {
          get { return _DisplayValue; }
          set
          {
            _DisplayValue = value;
            if (PropertyChanged != null) PropertyChanged(this, new PropertyChangedEventArgs("DisplayValue"));
          }
        }
    
        private int _Value = ID++;
        public int Value
        {
          get { return _Value; }
        }
    
        public event PropertyChangedEventHandler PropertyChanged;
      }
    

    Sincerely,

    Bob Bao [MSFT]
    MSDN Community Support | Feedback to us

    2012年4月6日 3:53
    版主
  • 斑竹你好,找到问题了..没办法啊.只能删除两次.因为ComboBox在Grid中的DataContext是一个字典字段.然后ComboBox还要填充绑定.所以,当删除DataComtext 的时候,无法删除ComboBox中的集合..因为ComboBox绑定的时ItemsSources.而且Path是" . " 并没有真正的绑定到数据库中的某个字段.呵呵,一开始,我以为微软提供ComboBox够智能的..原来也是没有办法的.不过倒是推荐微软提供一个ItemsSources是绑定数据源用的..还有一个是"Sources" 是绑定非数据源交互的任何集合或者对象.

    现在,我只能重写,或者弄一个附加属性..

    2012年4月10日 11:02

全部回复

  • ???

    2012年4月4日 11:54
  • XAML中如果是Path="." 我们可以省略不写Path, 但是C#代码中,创建了Binding对象,我们就不能省略Path,所以要给他一个值,如果是Source自己本身的话,就是"."。

    Bob Bao [MSFT]
    MSDN Community Support | Feedback to us

    2012年4月5日 5:34
    版主
  • 你好,绑定的问题解决了,如图

    当我单击删除的时候,如下图 所示

    ComboBox集合并没有更新。

    ComboBox集合是ObservableCollection,而且也是TwoWay..

    为什么没有更新呢。。而且我连grid_NationFriamly.DataContext = null;

    实在无法理解,我这还到底如何下一步了。。

    2012年4月5日 10:23
  • 你好,绑定的问题解决了,如图

    当我单击删除的时候,如下图 所示

    ComboBox集合并没有更新。

    ComboBox集合是ObservableCollection,而且也是TwoWay..

    为什么没有更新呢。。而且我连grid_NationFriamly.DataContext = null;

    实在无法理解,我这还到底如何下一步了。。

    2012年4月5日 10:23
  • 忘记和你说了,我是用Linq to sql  ORM 技术访问和会传的数据

    2012年4月5日 10:24
  • 忘记和你说了,我是用Linq to sql  ORM 技术访问和会传的数据

    2012年4月5日 10:25
  • 你好,ComboBox确实没有绑定.一语惊醒梦中人.可我已经帮定了ItemSource,那么,ComboBox我还想帮定SelectedValue 行吗 ?

    SelectedValue={Binding path=Id} ?可以么 ?

    2012年4月5日 11:42
  • 试验了,不好用.而且 SelectedValue="{Binding Path=NationFriamly.Id}" 这么些都不可.
    2012年4月5日 11:48
  •  按照你的想法,给你写个简单的例子,当然是没有你的Linq to SQL等ORM的,我直接用的硬编码数据.

      <StackPanel>
        <TextBox Margin="10"/>
        <Button Content="+" Click="Button_Click" Margin="10" HorizontalAlignment="Center" Width="100" FontSize="20"/>
        <ComboBox Margin="10" x:Name="combobox" IsEditable="True" IsReadOnly="False"/>
        <TextBlock x:Name="text1" Text="{Binding Path=SelectedItem.Value}"/>
        <TextBlock x:Name="text2" Text="{Binding Path=SelectedItem.DisplayValue}"/>
      </StackPanel>

    C#:
      public partial class MainWindow : Window
      {
    
        public ObservableCollection<Item> Items { get; set; }
        public MainWindow()
        {
          InitializeComponent();
    
          Items = new ObservableCollection<Item>()
          {
            new Item(){DisplayValue="Item 1"},
            new Item(){DisplayValue="Item 2"},
            new Item(){DisplayValue="Item 3"},
            new Item(){DisplayValue="Item 4"},
          };
    
          this.DataContext = new Selected();
    
          Binding binding = new Binding(".");
          binding.Source = Items;
          binding.Mode = BindingMode.TwoWay;
          combobox.SelectedValuePath = "Value";
          combobox.DisplayMemberPath = "DisplayValue";
          combobox.SetBinding(ComboBox.ItemsSourceProperty, binding);
          Binding selectedBinding = new Binding("SelectedItem");
          combobox.SetBinding(ComboBox.SelectedItemProperty, selectedBinding);
    
          combobox.IsSynchronizedWithCurrentItem = true;
          combobox.SelectedIndex = 0;
        }
    
        private void Button_Click(object sender, RoutedEventArgs e)
        {
          Items.Add(new Item() { DisplayValue = "New Added Item " + Item.ID });
        }
      }
    
      public class Selected
      {
        public Item SelectedItem { get; set; }
      }
    
      public class Item : INotifyPropertyChanged
      {
        public static int ID;
    
        private string _DisplayValue;
        public string DisplayValue
        {
          get { return _DisplayValue; }
          set
          {
            _DisplayValue = value;
            if (PropertyChanged != null) PropertyChanged(this, new PropertyChangedEventArgs("DisplayValue"));
          }
        }
    
        private int _Value = ID++;
        public int Value
        {
          get { return _Value; }
        }
    
        public event PropertyChangedEventHandler PropertyChanged;
      }
    

    Sincerely,

    Bob Bao [MSFT]
    MSDN Community Support | Feedback to us

    2012年4月6日 3:53
    版主
  • 你好,单独删除ComboBox是很容易的..但ComboBox在Grid容器里面的..而且Grid的DataContext里面的ComboBox是一个表中的字段.也要帮定这个字段.然后还要填充ComboBox结合. ComboBox也是DataContext绑定表中的两个字段.

    你的方法还是不行..所以,我不得不在删除表中的一条数据,还要继续删除ItemSources 虽然ItemSources绑定的表中少了一条数据.但,集合中并没有更新,设置TwoWay也没有反应.可能是微软的Bug吧..

    具体代码如下:

    NationFriamlyServiceClient client = new NationFriamlyServiceClient();
    int result = client.DelNationFriamly(SelectId);//删除表中的数据了..但ComboBox并没有更新集合,还得重新加载才能正确显示集合

    //无奈之下,在继续更新集合

    ((ObservableCollection<NationFriamly>)(cbm_NationFriamly.ItemsSource)) .Remove((NationFriamly)grid_NationFriamly.DataContext);

    //之后再设置当前的DataContext

     grid_NationFriamly.DataContext = null;

    这样就OK..不过,期待有更简洁的方法,来完成我上面两次删除操作..微软提供的ObservableCollection和绑定机制,已经不起作用了..

    2012年4月6日 4:46
  • 你好,其实,我思考了一下,为什么ObservableCollection集合不起作用了..首先我帮定DataContext的时候,返回表中的一条记录显示在ComboBox上,这就是一张临时表了..然后我填充ComboBox集合,实际我又访问了数据库,得到一个集合表.那么我的Grid中的DataContext数据上,实际已把ComboBox上第一张临时表替换成了集合表.那么也就是说两张表了..所以,当我删除DataContext绑定的数据,实际上无法删除集合表中的数据了,因为是另一张表了..

    不知道我的见解对不对..不过确实是这样的.

    2012年4月6日 4:53
  • 你是分离的两个集合,所以一个操作了没有通知另一个,当然不会同步。

    我的建议是你直接可以从数据库中查询到数据绑定到一个CollectionViewSource,然后我们的ComboBox.ItemsSource直接绑定到这个CollectionViewSource。 ItemsSource={Binding Source={StaticResource collectionViewSourceKey}}。   至始至终用一个集合数据源。


    Bob Bao [MSFT]
    MSDN Community Support | Feedback to us


    2012年4月6日 7:04
    版主
  • ???

    2012年4月6日 9:01
  • 可能 是我代码 出现问题了。。我自己调试一下看看
    2012年4月9日 5:03
  • 结果怎么样,如果还有有问题,你也可以把你的项目做个简单的打包,分享给我们,我们帮你仔细看看, 你可以分享在 www.skydrive.com


    Bob Bao [MSFT]
    MSDN Community Support | Feedback to us

    2012年4月10日 8:27
    版主
  • 斑竹你好,找到问题了..没办法啊.只能删除两次.因为ComboBox在Grid中的DataContext是一个字典字段.然后ComboBox还要填充绑定.所以,当删除DataComtext 的时候,无法删除ComboBox中的集合..因为ComboBox绑定的时ItemsSources.而且Path是" . " 并没有真正的绑定到数据库中的某个字段.呵呵,一开始,我以为微软提供ComboBox够智能的..原来也是没有办法的.不过倒是推荐微软提供一个ItemsSources是绑定数据源用的..还有一个是"Sources" 是绑定非数据源交互的任何集合或者对象.

    现在,我只能重写,或者弄一个附加属性..

    2012年4月10日 11:02