ObservableCollection <T>未收到<T>属性更改的通知

use*_*480 3 c# wpf events mvvm

我有一个Component的ObservableCollection,一个带有另一个ObservableCollection的类,一个String和一个ComponentVersion.SelectedComponentVersion正在通过我的视图正确更新,但我无法获得组件的属性来激活它的setter/OnPropertyChanged.

private ObservableCollection<Component> components
public ObservableCollection<Component> Components
{
   get { return foo; }
   set { foo = value; OnPropertyChanged(); }
}
Run Code Online (Sandbox Code Playgroud)

这是Component的类.

public class Component : ViewModelBase
{
  private string componentName;
  private ObservableCollection<ComponentVersion> componentVersions;
  private ComponentVersion selectedComponent;

  public string ComponentName
  {
     get { return componentName; }
     set { componentName = value; OnPropertyChanged(); }
  }
  public ObservableCollection<ComponentVersion> ComponentVersions
  {
     get { return componentVersions; }
     set { componentVersions = value; OnPropertyChanged(); }
  }
  public ComponentVersion SelectedComponent
  {
     get { return selectedComponent; }
     set { selectedComponent = value; OnPropertyChanged(); }
  }

  public Component(string componentName, List<ComponentVersion> componentVersion)
  {
     ComponentName = componentName;
     ComponentVersions = componentVersion.ToObservableCollection();
  }
}
Run Code Online (Sandbox Code Playgroud)

然后我从listview绑定到Component内的SelectedComponent属性.

我已经阅读了关于设置CollectionChanged的无数堆栈溢出,并试图实现它而没有运气.

Components.CollectionChanged += stuff;
private void stuff(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
{
   throw new System.NotImplementedException();
}
Run Code Online (Sandbox Code Playgroud)

但这绝不会受到断点测试.

我完全错过了什么,失去理智或愚蠢!如果有任何意义,请有人向我说明正确的方向.

PS另一个解决方案我将在listview中放置一个不可见的按钮,并发送命令告诉vm所选项目已更新.

Rac*_*hel 5

在这样的情况下,当我想要在集合中的项目上的属性发生变化时做某事时,我通常会在PropertyChanged事件中挂钩CollectionChanged事件

这是一个代码示例:

public MyViewModel()
{
    // Setup Collection, with a CollectionChanged event
    Components = new ObservableCollection<Component>();
    Components.CollectionChanged += Components_CollectionChanged;

}

// In the CollectionChanged event (items getting added or removed from collection),
// hook up the PropertyChanged event
void Components_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
{
    if (e.NewItems != null)
        foreach(MyType item in e.NewItems)
            item.PropertyChanged += Component_PropertyChanged;

    if (e.OldItems != null)
        foreach(MyType item in e.OldItems)
            item.PropertyChanged -= Component_PropertyChanged;
}

// In the PropertyChanged event, run some code if SelectedComponent property changed
void Component_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
    if (e.PropertyName == "SelectedComponent")
        DoWork();
} 
Run Code Online (Sandbox Code Playgroud)

请注意,我们在此处使用两个单独的事件.

  • CollectionChanged事件在集合本身发生变化时运行.这意味着它被设置为新的集合,或者从集合中添加或删除项目.

    这将捕获新添加的项并挂接PropertyChanged处理程序,或者为要从集合中删除的项分离PropertyChanged处理程序.

  • PropertyChanged当属性更改并触发事件时,事件将运行.当SelectedComponent集合中任何项目的属性发生更改时,您将使用此事件来运行代码