【问题标题】:WPF : Binding a collection to an itemscontrolWPF:将集合绑定到项目控件
【发布时间】:2012-02-16 03:21:40
【问题描述】:

iv'e 有一个包含 3 个代表棋盘游戏的类的 dll:

   Board , Pipe , Checker 

棋盘是管子的集合,管子是棋子的集合

对手的移动将包括从一个管道中取出一个检查器并将其放置在另一个管道中。

我的板由一个带有 23 个项目控制的网格面板表示, 我需要将每个项目控件绑定到管道,以便在 UI 上显示动作

玩家的移动将通过项目控件之间的拖放来完成 (还没有接触到那部分)

Checker 类:

  public Checker 
  {
      public bool IsMine{get; set;} 
  }

需要使用 IsMine 属性来确定 Checkers Color 。

管道类:拥有一个 ObservableCollection 检查器

  public class Pipe : INotifyPropertyChanged
  {
    public Pipe()
    {
        checkers = new ObservableCollection<Checker>();
    }

    private  ObservableCollection<Checker> checkers {get;set;}
    public ObservableCollection<Checker> Checkers
    {
        get { return checkers; }
        set
        {                               
            checkers = value;
            if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs("Checkers"));
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;            
 }

我需要做的是在每个 itemscontrol 及其对应的 Pipe 项之间创建一个 2 路绑定,当集合更改时添加和删除项

我还需要一个自定义转换器来检查 IsMine 属性并设置对象 相应的颜色(itemsControl DataItemTemplate 由一个椭圆组成,它将 代表每个检查器)。

到目前为止,我只是填充集合并将它们设置为每个项目控件的项目源

例如:

   Pipe23.ItemsSource = board.Pipes[23].Checkers;

我面临两个挑战: (1) ether 在后面的代码中创建与 OwnerToColor 转换器的 2 路绑定 我找不到如何做到这一点的示例。

(2) 在标记中创建此绑定,但是我如何初始化起始项 在适当的管道中

例如:

pipe23 starts with 2 checkers 

board.Pipes[23].Checkers.Add(new Checker(true));
board.Pipes[23].Checkers.Add(new Checker(true));   

任何关于 collection 和 itemsControl 之间双向绑定的好例子都将不胜感激。

itemsControl:

    <ItemsControl Grid.Row="0" Grid.Column="0" Name="Pipe23"  ItemTemplate="{StaticResource PipeDataItem}"/>

数据模板:

     <DataTemplate x:Key="PipeDataItem" >
          <Ellipse Width="45" Height="45" Fill="{Binding IsMine,Converter={StaticResource MyOwnerToColorConverter}}"></Ellipse> 
     </DataTemplate>

【问题讨论】:

  • 我开始想,也许不可能在 itemscontrol 和集合之间进行双向绑定我尝试向项目控件添加一个椭圆,这引发了一个异常,指出没有项目可以在使用 itemscontrol 时添加。

标签: c# wpf data-binding collections


【解决方案1】:

您应该创建一个绑定,而不是直接设置 ItemsSource。

Binding b = new Binding();
b.Source = board.Pipes[23];
b.UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged;
b.Path = new PropertyPath("Checkers");
Pipe23.SetBinding(ListBox.ItemsSourceProperty, b);

【讨论】:

  • 谢谢这似乎从源到控制工作,你将如何从控制到源测试它。查看我上面问题中的数据模板。如果我在哪里添加椭圆应该更新源集合还是有一些更一致的方式来添加所需模板的对象?
  • 我看不出这与 Pipe23.ItemsSource = board.Pipe[23] 有何不同,它也会更新它们。我想按照您的描述指定绑定的唯一原因是使其成为双向的,因此当向 Pipe23(ItemsControl) 添加新椭圆时,将向管道(Checker 集合)添加 Checker 对象。但是它怎么知道在源头上进入 Checker 呢?这可以做到吗?
  • 您应该正在修改模型,UI 会自动更新。因此,当用户将标记从 pipeA 拖到 pipeB 时,您将处理该事件。在这种情况下,您将从boards.Pipes[A] 中删除检查器并将其添加到boards.Pipes[B]。由于您已经绑定了集合,因此您无需手动更新 UI。
  • 正是它的一种方式源 -> 目标控制
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-12-16
  • 1970-01-01
  • 2010-09-17
  • 1970-01-01
  • 2011-03-01
  • 2014-08-25
  • 1970-01-01
相关资源
最近更新 更多