Como: Sort a GridView Column When a Header Is Clicked

Este exemplo mostra como criar um controle ListView que implementa um modo de exibição GridView e ordena o conteúdo dos dados quando um usuário clica em um cabeçalho de coluna.

Exemplo

O exemplo a seguir define um GridView com três colunas que se associam a Year, Month e Day, propriedades da estrutura DateTime.

<GridView>
  <GridViewColumn DisplayMemberBinding="{Binding Path=Year}" 
                  Header="Year"
                  Width="100"/>
  <GridViewColumn DisplayMemberBinding="{Binding Path=Month}" 
                  Header="Month"
                  Width="100"/>
  <GridViewColumn DisplayMemberBinding="{Binding Path=Day}" 
                  Header="Day"
                  Width="100"/>
</GridView>

O exemplo a seguir mostra os itens de dados que são definidos como um ArrayList de objetos DateTime. O ArrayList é definido com a ItemsSource do controle ListView.

<ListView.ItemsSource>
  <s:ArrayList>
    <p:DateTime>1993/1/1 12:22:02</p:DateTime>
    <p:DateTime>1993/1/2 13:2:01</p:DateTime>
    <p:DateTime>1997/1/3 2:1:6</p:DateTime>
    <p:DateTime>1997/1/4 13:6:55</p:DateTime>
    <p:DateTime>1999/2/1 12:22:02</p:DateTime>
    <p:DateTime>1998/2/2 13:2:01</p:DateTime>
    <p:DateTime>2000/2/3 2:1:6</p:DateTime>
    <p:DateTime>2002/2/4 13:6:55</p:DateTime>
    <p:DateTime>2001/3/1 12:22:02</p:DateTime>
    <p:DateTime>2006/3/2 13:2:01</p:DateTime>
    <p:DateTime>2004/3/3 2:1:6</p:DateTime>
    <p:DateTime>2004/3/4 13:6:55</p:DateTime>
  </s:ArrayList>
</ListView.ItemsSource>

Os identificadores s e p nas marcas XAML se referem a mapeamentos de espaço de nomes que são definidos nos metadados da página XAML. O exemplo a seguir mostra a definição dos metadados.

<Window      
    xmlns="https://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="https://schemas.microsoft.com/winfx/2006/xaml"
    x:Class="ListViewSort.Window1"    
    xmlns:s="clr-namespace:System.Collections;assembly=mscorlib"
    xmlns:p="clr-namespace:System;assembly=mscorlib">

Para ordenar os dados de acordo com o conteúdo de uma coluna, o exemplo define um manipulador de eventos para tratar o evento Click que ocorre quando você pressiona o botão de cabeçalho de coluna. O exemplo a seguir mostra como especificar um manipulador de eventos para o controle GridViewColumnHeader.

<ListView x:Name='lv' Height="150" HorizontalAlignment="Center" 
  VerticalAlignment="Center" 
  GridViewColumnHeader.Click="GridViewColumnHeaderClickedHandler"
 >

O exemplo define o manipulador de eventos para que a direção de ordenação alterne entre ordem crescente e decrescente sempre que se pressionar o botão de cabeçalho da coluna. O exemplo a seguir mostra o manipulador de eventos.

public partial class Window1 : Window
{
    public Window1()
    {
        InitializeComponent();
    }

    GridViewColumnHeader _lastHeaderClicked = null;
    ListSortDirection _lastDirection = ListSortDirection.Ascending;

    void GridViewColumnHeaderClickedHandler(object sender,
                                            RoutedEventArgs e)
    {
        GridViewColumnHeader headerClicked =
              e.OriginalSource as GridViewColumnHeader;
        ListSortDirection direction;

        if (headerClicked != null)
        {
            if (headerClicked.Role != GridViewColumnHeaderRole.Padding)
            {
                if (headerClicked != _lastHeaderClicked)
                {
                    direction = ListSortDirection.Ascending;
                }
                else
                {
                    if (_lastDirection == ListSortDirection.Ascending)
                    {
                        direction = ListSortDirection.Descending;
                    }
                    else
                    {
                        direction = ListSortDirection.Ascending;
                    }
                }

                string header = headerClicked.Column.Header as string;
                Sort(header, direction);

                if (direction == ListSortDirection.Ascending)
                {
                    headerClicked.Column.HeaderTemplate =
                      Resources["HeaderTemplateArrowUp"] as DataTemplate;
                }
                else
                {
                    headerClicked.Column.HeaderTemplate =
                      Resources["HeaderTemplateArrowDown"] as DataTemplate;
                }

                // Remove arrow from previously sorted header
                if (_lastHeaderClicked != null && _lastHeaderClicked != headerClicked)
                {
                    _lastHeaderClicked.Column.HeaderTemplate = null;
                }


                _lastHeaderClicked = headerClicked;
                _lastDirection = direction;
            }
        }
    }

O exemplo a seguir mostra o algoritmo de ordenação que é chamado pelo manipulador de eventos para ordenar os dados. A ordenação é executada ao criar um nova estrutura SortDescription.

private void Sort(string sortBy, ListSortDirection direction)
{
    ICollectionView dataView =
      CollectionViewSource.GetDefaultView(lv.ItemsSource);

    dataView.SortDescriptions.Clear();
    SortDescription sd = new SortDescription(sortBy, direction);
    dataView.SortDescriptions.Add(sd);
    dataView.Refresh();
}

For the complete sample, see Exemplo de dados que classifica Exibição em Lista.

Consulte também

Tarefas

Exemplo de dados que classifica Exibição em Lista

Conceitos

Visão geral de ListView

GridView Overview

Referência

ListView

GridView

Outros recursos

ListView How-to Topics

Exemplos de Exibição em Lista