2014-01-16 179 views
2

我在這裏有一點點(沒有雙關語意圖);我有大量視圖模型(500+),它們使用ItemsControlWrapPanel作爲ItemsPanelTemplate顯示。這些視圖模型中的每一個都顯示Boolean?,其值在用戶界面上綁定到CheckBoxIsChecked屬性。複選框綁定慢

問題是這樣的...每當我嘗試立即更新所有複選框時,它的速度非常慢。幾乎10秒鐘來更新500個項目的列表。如果我在一個單獨的線程中運行更新代碼,我幾乎可以看到複選框被逐一更新。

任何人都可以啓發我爲什麼這個過程如此緩慢,我如何能夠改善它?

我曾考慮過WrapPanel的非虛擬化性質可能是罪惡派對。但是,當我綁定到IsEnabled屬性而不是IsChecked時,我看到一個有趣的結果;即將IsEnabled的值更改爲true的速度與預期的一樣緩慢,但瞬時發生更改爲false的情況。這讓我懷疑複選框動畫是有問題的,因爲據我可以直觀地看到,在禁用複選框時沒有動畫,但是啓用時有。分析顯示絕大多數時間都花在PropertyChangedEventManager.OnPropertyChanged()方法中。

下面

示例代碼,我很遺憾不得不使用.NET 3.5:

XAML:

<ItemsControl ItemsSource="{Binding ChildItems}"> 
    <ItemsControl.ItemsPanel> 
     <ItemsPanelTemplate> 
      <WrapPanel Orientation="Horizontal" /> 
     </ItemsPanelTemplate> 
    </ItemsControl.ItemsPanel> 
    <ItemsControl.Resources> 
     <DataTemplate DataType="{x:Type SampleViewModel}"> 
      <CheckBox IsThreeState="True" IsChecked="{Binding Path=IncludeInPrinting, Mode=OneWay}" /> 
     </DataTemplate> 
    </ItemsControl.Resources> 
</ItemsControl> 

視圖模型:

public class SampleViewModel : INotifyPropertyChanged 
{ 
    private Boolean? _includeInPrinting; 
    public Boolean? IncludeInPrinting 
    { 
     get 
     { 
      return _includeInPrinting; 
     } 
     set 
     { 
      if (_includeInPrinting != value) 
      { 
       _includeInPrinting = value; 
       RaisePropertyChanged(() => IncludeInPrinting); 
      } 
     } 
    } 
} 

慢代碼:

foreach (SampleViewModel model in ChildItems) 
{ 
    model.IncludeInPrinting = false; 
} 

編輯:對於我t的價值每當我全選或取消選中所有複選框時,我也會看到內存使用率激增。 〜10MB

編輯:下面的性能分析似乎證實動畫確實是問題。 Performance Analysis Hot Path

+0

您可以嘗試的是禁用所有項目上的屬性通知,更改所有屬性,然後在持有所有項目的集合上引發NotifyCollectionChangedAction.Reset。 – dowhilefor

+0

http://virtualwrappanel.codeplex.com/ – Bas

+0

@dowhilefor原諒我的無知,但我如何提高'ObservableCollection'上的'NotifyCollectionChangedAction.Reset'? –

回答

0

我想看看下面的控制是在CodePlex開源..

http://virtualwrappanel.codeplex.com/(注:我有虛擬環繞面板沒有affilication)

由於大量視圖模型你正在使用這將大大提高你的表現。

+0

正如我在評論中提到上述,我一直沒能得到這個習俗控制工作。我在這裏提到了同樣的異常[WPF - 虛擬化WrapPanel](http://stackoverflow.com/questions/3736989/wpf-virtualising-wrappanel),但接受的答案沒有解決它。 –