2013-05-05 89 views
9

我在Visual Studios 2012中制作了我的第一个Windows应用商店应用程序。我有一个gridview控件,可以重新排序。当列表重新排序时,我需要运行代码。我已经尝试了Drop事件。它不会着火。我尝试了其他几个拖动事件,这些事件也没有启动。看起来这应该是如此简单......感谢您的时间!XAML/C#:重新排序gridview后会发生什么事件?

+1

可以使用的ObservableCollection 的''CollectionChanged'事件',如果您提供'和'的ObservableCollection GridView'的'ItemsSource' ' – Xyroid 2013-05-06 05:10:56

回答

21

除非ItemsSource绑定到ObservableCollectionCanReorderItemsCanDragItems,并AllowDrop设置为true不能重新排序GridView。它是而不是必需使用CollectionViewSource来启用您的gridview重新排序。实际上,collectionviewsource通常用于分组gridview,并且在数据分组时不可能进行重新排序。

无论如何,你的XAML应该是这样的:

<Grid Background="Black"> 
    <Grid.DataContext> 
     <local:MyModel/> 
    </Grid.DataContext> 
    <GridView CanReorderItems="True" CanDragItems="True" AllowDrop="True" 
       ItemsSource="{Binding Items}"> 
    </GridView> 
</Grid> 

虽然任何enumerable可以绑定到一个GridView它只是一个ObservableCollection,使订货的ItemsSource。是的,你可以使用自定义类型来实现重新排序,但为什么ObservableCollection会为你做什么?

您的视图模型可能是这样的:

public class MyModel 
{ 
    public MyModel() 
    { 
     foreach (var item in Enumerable.Range(1, 50)) 
      Items.Add(item); 
     Items.CollectionChanged += Items_CollectionChanged; 
    } 

    ObservableCollection<int> m_Items = new ObservableCollection<int>(); 
    public ObservableCollection<int> Items { get { return m_Items; } } 

    object m_ReorderItem; 
    int m_ReorderIndexFrom; 
    void Items_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
    { 
     switch (e.Action) 
     { 
      case NotifyCollectionChangedAction.Remove: 
       m_ReorderItem = e.OldItems[0]; 
       m_ReorderIndexFrom = e.OldStartingIndex; 
       break; 
      case NotifyCollectionChangedAction.Add: 
       if (m_ReorderItem == null) 
        return; 
       var _ReorderIndexTo = e.NewStartingIndex; 
       HandleReorder(m_ReorderItem, m_ReorderIndexFrom, _ReorderIndexTo); 
       m_ReorderItem = null; 
       break; 
     } 
    } 

    void HandleReorder(object item, int indexFrom, int indexTo) 
    { 
     Debug.WriteLine("Reorder: {0}, From: {1}, To: {2}", item, indexFrom, indexTo); 
    } 
} 

在上面的代码,重新排序event是不是真实的。它来源于CollectionChanged事件中“删除”操作和“添加”操作的组合。这就是为什么这是真棒。如果重新订购仅适用于GridView,则ViewModel将无法​​处理。由于底层列表是您检测重新排序的方式,因此启用ViewModel

每种情况都有所不同。你可能不关心索引,所以你可以简化代码。您可能不允许添加或从集合中删除,因此您只需要监视添加操作。再次,这取决于你的情况。我上面的示例代码应该会处理99%的案例。

请记住,GridView不是唯一允许重新排序的控件。任何基于ListViewBase(如ListView)的控件都支持重新排序 - 仍然使用ObservableCollection。但GridView是使用此功能的最常用控件。当然。

参考:http://msdn.microsoft.com/en-us/library/windows/apps/windows.ui.xaml.controls.listviewbase.canreorderitems

哦,要回答你的问题!

没有事件表示重新排序。重新排序是基于底层ObservableCollectionCollectionChanged事件中的操作组合导出的操作。合理?

顺便说一句,这里的样本语法来绑定到CollectionViewSource,如果你选择:

<Grid Background="Black"> 
    <Grid.DataContext> 
     <local:MyModel/> 
    </Grid.DataContext> 
    <Grid.Resources> 
     <CollectionViewSource x:Name="CVS" Source="{Binding Items}" /> 
    </Grid.Resources> 
    <GridView CanReorderItems="True" CanDragItems="True" AllowDrop="True" 
       ItemsSource="{Binding Source={StaticResource CVS}}" > 
    </GridView> 
</Grid> 

好运。

+0

非常感谢你的解释!很有帮助!! – 2013-05-14 12:51:20

+0

一直在寻找这一整天的答案 - 这是完美的,正是我所需要的。 – 2013-10-03 02:23:00

+0

@ JerryNixon-MSFT Inside Items_CollectionChanged改变了事件,我将如何处理__adding__到集合?由于目前__removing__跟着__adding__会导致'HandleReorder()' – lbrahim 2014-12-04 15:19:21