2011-02-25 51 views
4

我有以下XAML:在绑定使用MVVM /的ObservableCollection问题

<Grid x:Name="LayoutRoot"> 
     <sdk:DataGrid AutoGenerateColumns="True" Margin="46,38,0,40" x:Name="FamilyListGrid" HorizontalAlignment="Left" Width="475" 
       ItemsSource="{Binding FamilyList}" 
       SelectedItem="{Binding SelectedFamily, Mode=TwoWay}" /> 
    </Grid> 

我FamilyList属性是在我的视图模型类实体的一个ObservableCollection。我发现我需要在我的FamilyList集合的setter中实现INotifyPropertyChanged,或者绑定不起作用。我的理解是一个ObservableCollection已经实现了这个。如果是这种情况,为什么我需要实现通知属性?

如果有帮助,这是我的FamilyList属性定义:

private ObservableCollection<Services.Family> familyList; 
    public ObservableCollection<Services.Family> FamilyList 
    { 
     get { return familyList; } 
     private set 
     { 
      familyList = value; 
      NotifyPropertyChanged("FamilyList"); 
     } 
    } 

回答

6

ObservableCollection<T>实现INotifyCollectionChanged该通知有关集合中(添加,删除,排序项)的变更登记的事件处理程序。但DataGrid必须知道您的某个业务对象的属性是否已更改以更新网格中的值。为此,需要INotifyPropertyChanged
ObservableCollection<T>也实现INotifyCollectionChanged。但是,只有在集合的属性发生变化时才可以使用此功能。没有任何机制可以让集合检测您的业务对象是否已更改(如果它有,它将注册到您的业务对象的INotifyCollectionChanged :)。

2

的ObservableCollection知道如何通知如果集合改变,即一个项目被添加或删除。

但是,如果你做到以下几点:

FamilyList = new ObservableCollection<FamilyList>(); 
// or 
FamilyList = GetFamilyList(); 

,那么你实际上改变的是握着你的集合,这是不同的属性。我猜这是这里的问题。

0

你正在改变观察的集合,可观察集合的不是内容的实例。所以这个集合没有任何通知。

1

INotifyPropertyChanged的的的ObservableCollection的实现基本上是用来在添加或从集合中移除反应。

您需要在setter中调用Notify ...(),因为集合是ViewModel的一个属性,并且DataGrid不会对ViewModel属性进行任何更改,除非调用Notify ...()当改变时。

编辑: 我太慢了。

0

你不应该需要通知,如果集合本身添加或删除的项目。但是,如果您将整个集合与新/不同实例(即familyList = new ObservableCollection<Services.Family>())互换,则需要通知。如果您确实正在更改实例,请考虑清除/重新填充集合。

1

只要持有集合的属性在列表被绑定/ DataContext设置之前创建,您应该没问题。如果收集被替换,正如@Phil Sandler所说,你需要通知。如果你创建的时候只声明变量,或者在类的构造函数内部执行new时,你不应该需要为更改属性的通知属性。如果您需要清除列表,我会建议使用集合的Clear方法,而不是替换它。