如何反映WPF列表框中的订单更改

时间:2011-07-19 22:25:47

标签: wpf binding caliburn.micro

我有(我的感觉)一个非常简单的场景,我似乎无法弄明白。我已经在这里(即StackOverflow.com)寻找解决方案,但似乎找不到任何有我确切问题的人。我没有根据标准对列表框进行排序;我只是希望我的列表框能够反映我的集合中项目的顺序。

我正在使用Caliburn.Micro将底层集合绑定到WPF ListBox。我只是希望能够允许用户使用我提供的按钮在列表中上下移动项目。功能很棒!但是,ListBox不会反映新集合的顺序。

这是一个简单的ViewModel:

public class MyViewModel : PropertyChangedBase
{
  private readonly IObservableCollection<SimpleItem> _items;
  private SimpleItem _selectedItem;

  public MyViewModel()
  {
    _items = new BindableCollection<SimpleItems>();
    _items.Add(new SimpleItem("Item 1"));
    _items.Add(new SimpleItem("Item 2"));
    _items.Add(new SimpleItem("Item 3"));
  }
  public IObservableCollection<SimpleItem> Items
  {
    get { return _items; }
  }

  public SimpleItem SelectedItem
  {
    get { return _selectedItem; }
    set
    {
      _selectedItem = value;
      NotifyOfPropertyChanged(() => SelectedItem);
    }
  }
}

这是绑定到我的ViewModel的Xaml(再次使用Caliburn.Micro):

<ListBox x:Name="Items">
  <ListBox.ItemTemplate>
    <DataTemplate>
      <TextBlock Text="{Binding Caption}"/>
    </DataTemplate>
  </ListBox.ItemTemplate>
</ListBox>

结果显示我的ListBox中的项目:

Item 1
Item 2
Item 3

现在,假设用户想要将Item 2移到Item 1之上。他们选择Item 2,然后点击名为MoveUp的按钮。我的ViewModel中有一个名为MoveUp()的方法,它执行以下逻辑(为简洁起见而简化):

public void MoveUp()
{
  var item = SelectedItem;
  var index = Items.IndexOf(item);

  Items.Remove(item);
  Items.Insert(index - 1, item);

  SelectedItem = item;
}

不幸的是,ListBox没有反映新的顺序...告诉视图列表框刷新显示而不用诉诸代码隐藏的最佳方法是什么?

更新:2011年7月20日

我发现了问题。问题是我的SimpleItems集合实际上是父'SimpleItem'的子集。因此,当用户点击“MoveUp”时,我会对父SimpleItem进行查找并直接引用它的子项。问题是子节点没有绑定到IObservableCollection实例。我不得不改变我的逻辑来找到可观察的集合,现在它可以工作了!谢谢@devdigital的帮助!

- = Luc

1 个答案:

答案 0 :(得分:0)

如果要从您的收藏中添加和删除项目,并且您的绑定设置正确,则视图中的更新应该是自动的。

您是否在MoveUp方法中设置断点以确保实际发生的任何事情?我会确保SelectedItem正确绑定(您不在代码中显示此绑定),并且在访问时不为null。我还会注释掉插入行,并确保删除调用实际上会导致您的视图正确更新。