如何在WPF MVVM DataGrid中跟踪当前列名和排序方向

时间:2014-08-27 04:22:53

标签: wpfdatagrid

我需要在WPF MVVM DataGrid中跟踪当前列名和排序方向。我知道如何在代码背后做到这一点。请看如下代码:

private void columnHeader_Click(object sender, RoutedEventArgs e)
   {


            var columnHeader = sender as DataGridColumnHeader;

            if (columnHeader != null)
            {

                columnName = ((DataGridColumnHeader)sender).Content.ToString();

                ListSortDirection sortDirection = (((DataGridColumnHeader)sender).SortDirection != ListSortDirection.Ascending) ?
                                ListSortDirection.Ascending : ListSortDirection.Descending;
                txb1.Text = columnName;                
                txb2.Text = sortDirection.ToString();
             }
      }

但是,我在MVVM中被阻止了。在View Model中,我在SortCommand中的方法sort()中编写了代码,但它们不起作用。如果有人能提供帮助,我将不胜感激。以下是三个文件。

1)Xaml

<Window x:Class="SortSampleMVVM1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
        xmlns:se="clr-namespace:Microsoft.Expression.Interactivity.Core;assembly=Microsoft.Expression.Interactions"
        Title="MainWindow" Height="350" Width="525">


    <Grid>
    <DataGrid x:Name="Test" 
                ItemsSource="{Binding}" 
                AutoGenerateColumns="False" > 
                <DataGrid.ColumnHeaderStyle>    
                    <Style TargetType="{x:Type DataGridColumnHeader}">   
                        <Setter Property="Command" 
                                Value="{Binding SortCommand}"/>
                        <Setter Property="CommandParameter" 
                               Value="{Binding Path=Content, RelativeSource={RelativeSource Self}}"/>   
                        <Style.Triggers>

                            <Trigger Property="IsPressed" Value="True">
                                <Setter Property="Background" Value="Red" />
                            </Trigger>   
                        </Style.Triggers>  
                    </Style>    
            </DataGrid.ColumnHeaderStyle>

        <DataGrid Name="dataGrid1" AutoGenerateColumns="False" ItemsSource="{Binding ViewSource.View}" >

            <DataGrid.Columns>
                <DataGridTextColumn Header="ID" Binding="{Binding ID }"
             SortDirection="Descending" />
                <DataGridTextColumn Header="firstName" Binding="{Binding firstName}"/>
                <DataGridTextColumn Header="lastName" Binding="{Binding lastName}"/>
            </DataGrid.Columns>
        </DataGrid>
        <Label Content="Column Name" HorizontalAlignment="Left" Margin="100,166,0,0" VerticalAlignment="Top"/>
        <TextBox HorizontalAlignment="Left" Height="23" Margin="250,169,0,0" TextWrapping="Wrap" Name="txb1" Text="{Binding ColumnName}" VerticalAlignment="Top" Width="150"  />
        <Label Content="Sorting direction" HorizontalAlignment="Left" Margin="100,229,0,0" VerticalAlignment="Top"/>
        <TextBox HorizontalAlignment="Left" Height="23" Margin="250,232,0,0" TextWrapping="Wrap"  Name="txb2" Text="{Binding SortDirection}" VerticalAlignment="Top" Width="150" />
        <Button Content="Refresh" Name="btnRefresh1" HorizontalAlignment="Left" Margin="140,273,0,0" VerticalAlignment="Top" Width="75" Command="{Binding Refresh1Command}" />
        <Button Content="Refresh Keep Sort" Name="btnRefresh2" HorizontalAlignment="Left" Margin="282,273,0,0" VerticalAlignment="Top" Width="125" Command="{Binding Refresh2Command}" />
    </Grid>
</Window>

2)背后的代码

    using System.Windows;**strong text**
    using System.Collections.ObjectModel;
    using System.Collections.Generic;

namespace SortSampleMVVM1
{

    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            DataContext = new SortViewModel();
        }       

    }
}

3)查看模型

using System;
using System.ComponentModel;
using System.Windows.Input;
using System.Windows.Controls.Primitives;
using System.Windows;
using System.Windows.Data;
using System.Collections.ObjectModel;

namespace SortSampleMVVM1
{
class SortViewModel: INotifyPropertyChanged
{
    public CollectionViewSource ViewSource { get; set; }     
    public ObservableCollection<MyData> Collection {get; set;}

    private string _columnName;
    private ListSortDirection _sortDirection;
    private ICommand _sortCommand;
    private ICommand _refresh1Command;
    private ICommand _refresh2Command;

    public SortViewModel () 
    {
        this.Collection = new ObservableCollection<MyData>();
        Collection.Add(new MyData(1, "David", "Lee"));
        Collection.Add(new MyData(2, "John", "kim"));
        Collection.Add(new MyData(3, "Michael", "Wadsworth"));
        Collection.Add(new MyData(4, "Chris", "Smith"));
        Collection.Add(new MyData(5, "Peter", "Chen"));
        Collection.Add(new MyData(6, "Jonas", "Zhang"));

        this.ViewSource = new CollectionViewSource();
        ViewSource.Source = this.Collection;
    }

    public event PropertyChangedEventHandler PropertyChanged;

    public string ColumnName
    {
        get { return _columnName; }
        set
        {
            _columnName = value;
            OnPropertyChanged("ColumnName");
        }
    }

    public ListSortDirection SortDirection
     {
        get { return _sortDirection; }
        set
        {
            _sortDirection = value;
             OnPropertyChanged("SortDirection");
        }
    }       

    protected void OnPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this,
                 new PropertyChangedEventArgs(propertyName));
        }
    }


    #region SortCommand
     public ICommand SortCommand
     {
        get
        {
            if (_sortCommand == null)
            {
                _sortCommand = new RelayCommand(param => this.sort(),
                    null);
            }
            return _sortCommand;
        }
    }

    private void sort()
    {
        //var columnHeader = (object)sender as DataGridColumnHeader;

        //if (columnHeader != null)
         //{

        //    _columnName = ViewSource.GetValuecolumnName   ((DataGridColumnHeader)sender).Content.ToString();
        //    ListSortDirection sortDirection = (((DataGridColumnHeader)sender).SortDirection != ListSortDirection.Ascending) ?
        //                    ListSortDirection.Ascending : ListSortDirection.Descending;

        //}
}
    #endregion

    #region Refresh1Command
        public ICommand Refresh1Command
        {
            get
            {
                if (_refresh1Command == null)
                {
                    _refresh1Command = new RelayCommand(param => this.Refresh1(),
                    null);
                 }
                return _refresh1Command;
             }
        }

        private void Refresh1()
        {
             ViewSource.SortDescriptions.Clear();
            _columnName = "firstName";
             _sortDirection = ListSortDirection.Descending;
            ViewSource.SortDescriptions.Add(new SortDescription(_columnName, _sortDirection));
            ViewSource.View.Refresh();
        }
        #endregion

        #region Refresh2Command
        public ICommand Refresh2Command
        {
            get
             {
                if (_refresh2Command == null)
                {
                    _refresh2Command = new RelayCommand(param => this.Refresh2(),
                    null);
                }
                return _refresh2Command;
            }
        }

        private void Refresh2()
        {
            ViewSource.SortDescriptions.Clear();
            ViewSource.SortDescriptions.Add(new SortDescription(_columnName, _sortDirection));
            ViewSource.View.Refresh();
        }
         #endregion

    }  
}

1 个答案:

答案 0 :(得分:0)

您可以使用以下样式来获取列标题。

            <Style TargetType="{x:Type DataGridColumnHeader}">

                <Setter Property="Command" 
                        Value="{Binding DataContext.MyCommand}"/>
                <Setter Property="CommandParameter" 
                        Value="{Binding Path=Content, RelativeSource={RelativeSource Self}}"/>

                <Style.Triggers>

                    <Trigger Property="IsPressed" Value="True">

                    </Trigger>

                </Style.Triggers>

            </Style>

        </DataGrid.ColumnHeaderStyle>

您必须在视图模型中创建命令“MyCommand”。然后作为执行方法的参数,您将获得列标题名称。