2011-09-05 99 views
2

我有一個很好的WPF DataGrid綁定到對象集合。一切工作正常,當任何對象的屬性更改網格更新。問題是當更新發生時行不會重新排序,然後排序不再有效。Datagrid在項目更新時不保持排序

關於如何解決這個問題的任何想法?

在此先感謝。

編輯:這是我如何綁定的DataGrid:

<Controls:DataGrid MinHeight="300" MinWidth="300" ItemsSource="{Binding Data}" AutoGenerateColumns="True"> 

public class MainWindowViewModel 
{ 
    public ObservableCollectionMultiThread<StockViewModel> Data { get; private set; } 
} 

public class ObservableCollectionMultiThread<T> : ObservableCollection<T> 
{ 
    // Override the event so this class can access it 
    public override event System.Collections.Specialized.NotifyCollectionChangedEventHandler CollectionChanged; 

    protected override void OnCollectionChanged(System.Collections.Specialized.NotifyCollectionChangedEventArgs e) 
    { 
     // Be nice - use BlockReentrancy like MSDN said 
     using (base.BlockReentrancy()) 
     { 
      System.Collections.Specialized.NotifyCollectionChangedEventHandler eventHandler = this.CollectionChanged; 
      if (eventHandler == null) 
       return; 

      Delegate[] delegates = eventHandler.GetInvocationList(); 
      // Walk thru invocation list 
      foreach (System.Collections.Specialized.NotifyCollectionChangedEventHandler handler in delegates) 
      { 
       DispatcherObject dispatcherObject = handler.Target as DispatcherObject; 
       // If the subscriber is a DispatcherObject and different thread 
       if (dispatcherObject != null && dispatcherObject.CheckAccess() == false) 
       { 
        // Invoke handler in the target dispatcher's thread 
        dispatcherObject.Dispatcher.Invoke(DispatcherPriority.DataBind, handler, this, e); 
       } 
       else // Execute handler as is 
        handler(this, e); 
      } 
     } 
    } 
} 

PD:我使用DataGrid從CTP 2008年10月,我與.NET 3.5

+0

你能告訴我們如何加載和綁定數據嗎?你知道取決於你做的方式,你應該重新應用排序標準嗎? –

+0

啊,這是我第一次使用WPF DataGRid,我不知道。我正在使用一個特殊的ObservableCollection進行綁定,它允許來自其他線程的更新。我會嘗試使用正常的收集並更新問題,謝謝。 –

回答

1

我平時對WPF控件對物品版本沒有反應。我已經使用這個類作爲網格的源代碼:

using System; 
using System.Collections; 
using System.Collections.Specialized; 
using System.ComponentModel; 
using System.Windows.Data; 
using System.Windows.Threading; 

namespace StockCrawler 
{ 
public class AutoRefreshListCollectionView : ListCollectionView 
{ 

    public AutoRefreshListCollectionView(IList list) 
     : base(list) 
    { 
     this.SubscribeSourceEvents(list, false); 
    } 

    private void Item_PropertyChanged(object sender, PropertyChangedEventArgs e) 
    { 

     bool refresh = false; 

     foreach (SortDescription sort in this.SortDescriptions) 
     { 
      if (sort.PropertyName == e.PropertyName) 
      { 
       refresh = true; 
       break; 
      } 
     } 

     if (!refresh) 
     { 
      foreach (GroupDescription group in this.GroupDescriptions) 
      { 
       PropertyGroupDescription propertyGroup = group as PropertyGroupDescription; 

       if (propertyGroup != null && propertyGroup.PropertyName == e.PropertyName) 
       { 
        refresh = true; 
        break; 
       } 
      } 
     } 

     if (refresh) 
     { 
      if (!this.Dispatcher.CheckAccess()) 
      { 
       // Invoke handler in the target dispatcher's thread 
       this.Dispatcher.Invoke((Action)this.Refresh); 
      } 
      else // Execute handler as is 
      { 
       this.Refresh();     
      } 
     } 
    } 

    private void Source_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
    { 
     if (e.Action == NotifyCollectionChangedAction.Add) 
     { 
      this.SubscribeItemsEvents(e.NewItems, false); 
     } 
     else if (e.Action == NotifyCollectionChangedAction.Remove) 
     { 
      this.SubscribeItemsEvents(e.OldItems, true); 
     } 
     else 
     { 
      // TODO: Support this 

     } 
    } 

    private void SubscribeItemEvents(object item, bool remove) 
    { 
     INotifyPropertyChanged notify = item as INotifyPropertyChanged; 

     if (notify != null) 
     { 
      if (remove) 
      { 
       notify.PropertyChanged -= this.Item_PropertyChanged; 
      } 
      else 
      { 
       notify.PropertyChanged += this.Item_PropertyChanged; 
      } 
     } 
    } 

    private void SubscribeItemsEvents(IEnumerable items, bool remove) 
    { 
     foreach (object item in items) 
     { 
      this.SubscribeItemEvents(item, remove); 
     } 
    } 

    private void SubscribeSourceEvents(object source, bool remove) 
    { 
     INotifyCollectionChanged notify = source as INotifyCollectionChanged; 

     if (notify != null) 
     { 
      if (remove) 
      { 
       notify.CollectionChanged -= this.Source_CollectionChanged; 
      } 
      else 
      { 
       notify.CollectionChanged += this.Source_CollectionChanged; 
      } 
     } 

     this.SubscribeItemsEvents((IEnumerable)source, remove); 
    } 
} 
} 
相關問題