2016-09-21 95 views
2

有人可以幫助我,我怎麼能更新ObservableCollection,綁定到ListView的ItemSource,而不眨眼?當我這樣做時:更新ObservableCollection不閃爍

Contacs = _contacs; 

整個ListView閃爍。我想在ListView中進行搜索,但總是在用新的結果替換舊的結果後,ListView閃爍。

+0

你是什麼意思的更新?你是否替換整個OC,或添加/刪除記錄。 – AnjumSKhan

+0

我替換整個集合。 – JuP

+0

@rbm你說的「雙緩衝」與問題問題完全沒有關係。用戶要求更好的方式來通知UI在後臺發生了什麼。雙緩衝區是一種位圖優化技術,僅對Winforms有效(不在UWP/WPF中) –

回答

2

這裏的問題是,你正在重新分配整個集合。這沒有利用可觀察性,並強制ListView重新加載所有項目。嘗試刪除/添加項目,所以ListView只需要更新實際更改的項目。

在搜索隱藏的情況下,不匹配的結果也可能是一個可行的解決方案。爲此,請在聯繫人類型(例如,稱爲「IsVisible」)上創建一個屬性,並將其綁定到ListViewItems可見性屬性。 (您可能需要在BooleanToVisibility轉換這裏的版本)

更新

如使用CollectionViewSource評論中指出的是實現一個搜索過濾器的正確WPF方式。有關如何使用它的詳細信息,請參閱this答案。

+0

它是有道理的,當我用新數據替換集合時,它閃爍。所以我應該只使用現有的源代碼並添加/刪除項目。您的搜索解決方案很好。 – JuP

+0

這是一個很好的黑客攻擊,但是當你擁有使用CollectionViewSource和ICollectionView的內置功能時,你不需要它。 –

+0

你當然是對的。我鏈接你的答案 – vkluge

1

如果你想在你的集合中啓用過濾,那麼就沒有必要直接在你的集合上執行操作。爲此目的,使用ICollectionViewCollectionViewSource

因爲你有一個ObservableCollection所以你可以做這樣的事情。

ICollectionView contactsView; 

public ICollectionView ContactsView 
{ 
    get { return contactsView; } 
    set 
    { 
     if(contactsView != value) 
     { 
      contactsView = value; 
     } 
    } 
} 

而在ObservableCollection

public ObservableCollection<ContactType> Contacs 
{ 
    get { return _contacs; } 
    set 
    { 
     if(_contacs != value) 
     { 
     _contacs = value; 
     ContactsView = CollectionViewSource.GetDefaultView(value); 
     ContactsView.Filter = ContactsFilter; 
     } 
    } 
} 

其中ContactsFilter的二傳手是如下定義的函數。

bool ContactsFilter(object item) 
{ 
    var contact = item as ContactType; 

    if(condition) 
    return true; //show this item in ListView. 

    return false; //Do not show this item in ListView 
} 

,只要你想僅僅通過

ContactsView.Refresh(); 

,我認爲將是TextChanged事件中,正在輸入搜索查詢的文本框的篩選,你可以做的項目。

更詳細的文章在CollectionViewSource

+0

謝謝。我會嘗試。 :) – JuP

+0

當然。讓我知道事情的後續。我推薦這是因爲它分離了你的過濾邏輯。 –

+0

我有一個問題。屬性過濾器不在UWP中:/ – JuP