2011-04-07 70 views
5

我有一個ListView(GridView),我想按2列進行排序,因此如果2+項在列1中具有相同的值,則按列2排序。簡單。但排序A-Z時,空字符串顯示在頂部。我想將它們移到底部。我做了一個比較器(IComparer)來處理這個問題,但我不確定如何使用它。WPF - 在按多列進行排序時使用自定義比較器

這是我試過的代碼:

Dim view As ListCollectionView = CollectionViewSource.GetDefaultView(myCollection) 
Using view.DeferRefresh 
    view.SortDescriptions.Clear() 
    view.SortDescriptions.Add(New SortDescription(sortHeader.Header, direction)) 
    view.SortDescriptions.Add(New SortDescription(otherColumn, direction)) 
    view.CustomSort = New MyComparer() 
End Using 

問題是我的比較器被賦予一個類型我的課,而不是財產/列的值由進行排序。所以如果這個類是Foo並且我按Foo.Bar進行排序,那麼我得到了整個Foo類,而不僅僅是Bar的值(它真的應該被關注,因爲這就是它的排序依據)。

我的比較器如何知道要比較哪個屬性?也許我在這裏做錯了什麼,因爲這沒有任何意義。我希望得到一個字符串(屬性類型)的x和y ...

有誰知道如何做到這一點?

回答

6

IComparer執行將得到整個對象,你需要找出被點擊的列,可能是做這樣的事情:

this.AddHandler(GridViewColumnHeader.ClickEvent, 
       new RoutedEventHandler(Column_Sort)); 

再喂到這一點你MyComparer可能通過修改你的構造採取物業道路。

Column_Sort你可以得到屬性路徑是這樣的(我在VB有些生疏,但是C#這樣做:。

void Column_Sort(object sender, RoutedEventArgs e) 
{ 
    var memberBinding= ((GridViewColumnHeader)e.OriginalSource).Column.DisplayMemberBinding; 
    var path = ((Binding)memberBinding).Path.Path; 
} 

再喂那到你的排序邏輯

Dim view As ListCollectionView = CollectionViewSource.GetDefaultView(myCollection) 
Using view.DeferRefresh 
    view.SortDescriptions.Clear() 
    view.SortDescriptions.Add(New SortDescription(sortHeader.Header, direction)) 
    view.SortDescriptions.Add(New SortDescription(otherColumn, direction)) 
    view.CustomSort = New MyComparer(PropertyPath) 
End Using 

編輯: 你只需要定製IComparer支持多列排序,我用Google搜索,發現this comparer implementation,你可以給它Severa的用逗號隔開,並與ASC/DESC後綴像該L屬性路徑:

User.LastName DESC, User.FirstName DESC 

我覺得對於多列至於UI而言排序的慣例是,你需要有Ctrl按鈕舉行。因此,繼承ListView類的子類並綁定到GridViewColumnHeader單擊的事件和KeyDown事件中,以瞭解連續單擊了哪些列,然後使用實現將其饋入。

+0

這對一列進行排序時有效,但由於PropertyPath引用了被單擊的列(也是我的代碼中的sortHeader),因此即使它應該比較第二列(第二個SortDescription )。比較器如何知道它應該看第一列(點擊的那一列)還是第二列(當列2中有2+的值相同時)? – grant 2011-04-07 23:28:10

+0

上面做了一些更改,嘗試回答你確切的問題:) – Jose 2011-04-08 13:17:16

相關問題