【问题标题】:How to get the new column order after reordering the columns of a datagrid?重新排序数据网格的列后如何获得新的列顺序?
【发布时间】:2011-10-03 16:16:15
【问题描述】:

在数据网格中拖放一些列后,如何以 MVVM 方式将新顺序传递给 Viewmodel?

EventArgs 非常奇怪。

DataGrid_Reordered 传递一个仅包含一个列的 DataGridColumnEventArgs。我该怎么办?我如何知道新的列顺序?

显然列的顺序是由 DisplayIndex 决定的,但是我怎么知道旧值是什么,新值是什么,以及这与整个列集有什么关系?

非常感谢,

【问题讨论】:

标签: c# .net wpf silverlight datagrid


【解决方案1】:

在我的页面中,我使用LoadedColumnDisplayedIndexChanged 的事件设置了DataGrid。两者兼备很重要,我将在底部进行解释。

<DataGrid x:Name="dataGrid"
              Loaded="dataGrid_Loaded" 
              ColumnDisplayIndexChanged="dataGrid_ColumnDisplayIndexChanged" 
              ItemsSource="{Binding modulecollection, 
                            Source={StaticResource viewmodel}}"/>

一旦任一事件触发,我将发送者发送到DataGrid。然后访问所有列对象的DataGrid.Columns

我将它发送到另一个函数,该函数从DataGridColumn 类中创建列名的快速数组。数组的索引与别处引用的列的顺序保持同步。你可以创建你想要的任何东西,keyvaluepair,另一个类,并使用你想要的DataGridColumn类中的任何对象。只是取决于它是如何设置的。

        string [] displayedColumnOrder;

    private void dataGrid_ColumnDisplayIndexChanged( object sender , DataGridColumnEventArgs e )
    {
        DataGrid _dataGrid = ( DataGrid ) sender;
        _getColumnOrder( _dataGrid.Columns );        
    }

    private void dataGrid_Loaded( object sender , RoutedEventArgs e )
    {
        DataGrid _datagrid = ( DataGrid ) sender;  
        _getColumnOrder( _datagrid.Columns );
    }
    void _getColumnOrder( IEnumerable<DataGridColumn> columnCollection )
    {
        DataGridColumn [] columnArray;
        int columnIndexWorking;
        displayedColumnOrder = new string [columnCollection.Count() ];
        columnArray = columnCollection.ToArray();

        foreach( var item_Column in columnCollection )
        {
            columnIndexWorking = item_Column.DisplayIndex;
            displayedColumnOrder [ columnIndexWorking ] = item_Column.Header.ToString();         
        }                                                                                        
    }

好的,您需要来自Loaded 的事件来获取基线。这里我的DataGrid 从绑定源加载,所以除非我在加载网格时捕获它,否则我不会有我的列顺序的基线。

您需要ColumnDisplayedIndexChanged,因为您想跟踪列顺序的变化。

我发现了一件重要的事情,当用户将列移动几行时,ColumnDisplayedIndexChanged 会为它移动的每个索引触发。正如您在下面看到的,因为一列被移动,事件将针对它移动的每个空间触发。 DataGridColumn 的 Header 对象也变为空。因此,如果您使用这种方法要小心,您可能需要添加一些额外的处理。或者利用它来跟踪对更改的响应。示例:除非 headervalue 不为 null,否则不要在后台线程中重新计算某些内容。

原文:

A|B|C   <- Column Name
0|1|2   <- Column Index

用户更改为:

B|C|A
0|1|2

用户移动一列,ColumnDisplayedIndexChanged 事件如下触发:

第一个事件:

  null | B | C
  0    | 1 | 2

第二次活动:

  B  | null | C
  0  |  1   | 2

第三次活动:

  B | C | A
  0 | 1 | 2

【讨论】:

    【解决方案2】:

    好问题 :-) 我猜你是在重新启动应用程序后保持列顺序之后。

    我不太喜欢网格,所以我没有任何具体的建议,但在我看来,您最终会在视图模型(或新的视图模型)中拥有一堆属性) 对列及其顺序进行建模。

    我猜你必须关闭 AutoGenerateColumns,在 Xaml 中定义你需要的列,并在每列的 Header 和 DisplayIndex 属性上使用两种方式绑定来绑定到 VM 中的适当值。

    这样,您可以使用 MVVM Light 中的 EventToCommand 行为,将其绑定到网格的 ColumnReordering 事件和视图模型中的 RelayCommand。由于 VM 负责保持列的顺序,因此在事件触发时您将拥有它。

    HTH

    【讨论】:

      猜你喜欢
      • 2019-02-22
      • 2023-03-29
      • 1970-01-01
      • 1970-01-01
      • 2015-03-25
      • 2020-03-30
      • 2012-08-11
      • 2011-03-21
      • 1970-01-01
      相关资源
      最近更新 更多