2009-10-26 5 views
24

Ho un DataGrid nell'app WPF con diverse colonne, inclusa una colonna Nome. Se gli utenti passano ad una vista particolare, voglio che i dati siano preordinati per nome (e vorrei che una freccia di ordinamento appaia nell'intestazione Nome proprio come se l'utente avesse fatto clic su quell'intestazione). Tuttavia, non riesco a trovare le proprietà previste per farlo accadere. Ero alla ricerca di qualcosa di simile SortColumn, SortColumnIndex, SortDirection, eccPreordinamento di un DataGrid in WPF

E 'possibile specificare l'ordinamento di default e la direzione nel markup (XAML) o è che non supportata dal WPF Toolkit DataGrid?

+0

Dal WPF non viene fornito con un DataGrid integrato, si può supporre ti riferisci al DataGrid che viene fornito con WPF Toolkit (http://www.codeplex.com/wpf) ??? –

+0

Sì, ho inserito il tag wpftoolkit, ma suppongo di non averlo menzionato nella mia domanda. Lo aggiungerò. – devuxer

risposta

38

Supponendo che si sta parlando del controllo WPF Toolkit DataGrid, è necessario impostare solo the CanUserSortColumns property su true e quindi impostare the SortMemberPath property di ogni DataGridColumn in DataGrid.

Per quanto riguarda l'ordinamento iniziale della raccolta, è necessario utilizzare CollectionViewSource e impostare l'ordinamento su quello e quindi assegnarlo come ItemsSource del proprio DataGrid. Se stai facendo questo in XAML allora sarebbe facile come:

<Window.Resources> 
    <CollectionViewSource x:Key="MyItemsViewSource" Source="{Binding MyItems}"> 
     <CollectionViewSource.SortDescriptions> 
      <scm:SortDescription PropertyName="MyPropertyName"/> 
     </CollectionViewSource.SortDescriptions> 
    </CollectionViewSource> 
</Window.Resources> 

<DataGrid ItemsSource="{StaticResource MyItemsViewSource}"> 

</DataGrid> 

NOTA: mappe la "SCM" prefisso namespace per System.ComponentModel dove vive classe SortDescription.

xmlns:scm="clr-namespace:System.ComponentModel;assembly=WindowsBase" 

EDIT: Penso numero sufficiente di persone hanno ottenuto l'aiuto di questo post, che questo commento upvoted dovrebbe essere incluso in questa risposta:

ho dovuto usare questo per farlo funzionare:

<DataGrid ItemsSource="{Binding Source={StaticResource MyItemsViewSource}}"> 
+0

@Drew, grazie, ma 'SortMemberPath' specifica solo quale campo nell'origine dati va con quale colonna nel DataGrid. Devo impostare la colonna * current * sort (e direction). Ad esempio, questo DataGrid è attualmente ordinato in ordine crescente per Nome. – devuxer

+1

Bene come risolvi il tuo "clic sulla colonna dell'intestazione e il problema di classificazione". Ho accidentalmente dimenticato come ordinare inizialmente la griglia, aggiungerò alla mia risposta ora. –

+5

Sì :) Questo è molto più vicino a quello che stavo cercando, grazie. L'unico problema è che la freccia di ordinamento non appare nell'intestazione della colonna per cui la tabella è ordinata. Posso conviverci, ma una freccia renderebbe un po 'più chiaro all'utente quale sia la colonna di ordinamento. Solo una nota per chiunque cerchi di farlo, è necessario un riferimento a 'WindowsBase' per usare' System.ComponentModel'. Una volta aggiunto il riferimento, è necessario: 'xmlns: scm =" clr-namespace: System.ComponentModel; assembly = WindowsBase "'. – devuxer

2

Quando vedi ItemsSource doesn't support CollectionViewSource eccezione, è possibile ordinare la raccolta da LINQ, prima si fa riferimento ad un DataGrid:

ObservableCollection<MyDataClass> myCollection = new ObservableCollection<MyDataClass>(); 
dataGrid.ItemsSource = from item in myCollection orderby item select item; 

è necessario implementare IComparable interfaccia per MyDataClass:

public class MyDataClass : IComparable<MyDataClass> { 
    public int CompareTo(Classified other) { 
     return other.Value.CompareTo(this.Value); // DESC 
     return this.Value.CompareTo(other.Value); // ASC 
    } 
} 
+0

Questo in realtà ha funzionato per me mentre stavo cercando di ordinare una BindlingList usando Lambda. Questo ha funzionato, Lambda no! – DerpyNerd

4

Quando si vede ItemsSource non supporta eccezione CollectionViewSource quindi è possibile impostare il DataContext di DataGrid come 'MyItemsViewSource' e ItemsSource come {} Binding come questo :

<DataGrid DataContext="{StaticResource MyItemsViewSource}" ItemsSource="{Binding}"> 
</DataGrid> 
+1

Continuo a tornare su questo post (3a volta quest'anno) perché mi dimentico di fare questa parte/pezzo molto importante del puzzle! Grazie per averlo pubblicato. –

19

so che questo è un vecchio post, ma in aggiunta alla risposta di Drew Marsh e in risposta al problema del daNm con le frecce del intestazione colonna non compare ... è necessario aggiungere la proprietà SortDirection th e DataGridColumn:

<DataGridTextColumn Header="Name" Binding="{Binding Name}" SortDirection="Ascending" /> 

ho postato una domanda su questo e ha trovato la risposta pochi giorni dopo:

ColumnHeader arrows not reflected when sorting a DataGrid in XAML

+0

Significa che la proprietà 'SortDirection' deve corrispondere manualmente alle colonne in' SortDescription' - esiste un modo per DataGrid di rilevare l'ordinamento di CollectionViewSource e visualizzare gli indicatori automaticamente? – Dai

0

Questo funziona per me.

ListSortDirection sortDirection; 
int selectedColumnIndex; 
private void customerDataGrid_Sorting(object sender, DataGridSortingEventArgs e) 
{ 
    selectedColumnIndex = e.Column.DisplayIndex; 
    sortDirection = (e.Column.SortDirection == ListSortDirection.Ascending ? ListSortDirection.Descending: ListSortDirection.Ascending); 
} 

private void applySortDescriptions(ListSortDirection listSortDirection) 
{ 
    //Clear current sort descriptions 
    customerDataGrid.Items.SortDescriptions.Clear(); 

    //Get property name to apply sort based on desired column 
    string propertyName = customerDataGrid.Columns[selectedColumnIndex].SortMemberPath; 

    //Add the new sort description 
    customerDataGrid.Items.SortDescriptions.Add(new SortDescription(propertyName, listSortDirection)); 

    //apply sort 
    applySortDirection(listSortDirection); 

    //refresh items to display sort 
    customerDataGrid.Items.Refresh(); 
} 

private void applySortDirection(ListSortDirection listSortDirection) 
{ 
    customerDataGrid.Columns[selectedColumnIndex].SortDirection = listSortDirection; 
}