WPF TreeView привязан к ObservableCollection без обновления корневых узлов - PullRequest
9 голосов
/ 26 января 2010

Извините, мой вопрос почти идентичен этому , но поскольку он не получил жизнеспособного ответа, я надеюсь, что у кого-то еще есть свежие идеи.

У меня есть WPF TreeView, который связан с иерархией одного типа:

public class Entity
{
    public string Title { get; set; }
    public ObservableCollection<Entity> Children { get; set; }
}

Класс Entity реализует INotifyPropertyChanged, но для ясности я пропустил этот код.

TreeView привязан к ObservableCollection , и каждый экземпляр Entity предоставляет набор содержащихся экземпляров Entity через свое свойство Children:

<TreeView ItemsSource="{Binding Path=Entities}">
    <TreeView.Resources>
        <HierarchicalDataTemplate DataType="{x:Type local:Entity}" ItemsSource="{Binding Path=Children}">
           <TextBlock Text="{Binding Path=Title}" />
        </HierarchicalDataTemplate>
   </TreeView.Resources>
</TreeView>

Первоначально TreeView связывается должным образом и правильно отображает многоуровневую иерархию. Кроме того, когда членство в одной из коллекций Children изменяется программным способом, изменения корректно отражаются в TreeView.

Однако изменения членства уровня корневого члена ObservableCollection не отражаются в TreeView.

Любые предложения будут оценены.

Спасибо, Тим

Ответы [ 2 ]

21 голосов
/ 26 января 2010

Мое первоначальное предположение, что у вас есть что-то вроде следующего для корневого узла:

public ObservableCollection<Entity> Entities
{
    get;
    set;
}

Затем, вместо того, чтобы сделать что-то [хорошее], подобное следующему:

Entities.Clear();
foreach (var item in someSetOfItems)
    Entities.Add(item);

Вы делаете что-то [плохое] как это:

Entities = new ObservableCollection<Entity>(someSetOfItems);

Вы должны быть в состоянии отследить проблему, сделав поле поддержки свойства Entities readonly:

private readonly ObservableCollection<Entity> _entities
    = new ObservableCollection<Entity>();

public ObservableCollection<Entity> Entities
{
    get
    {
        return _entities;
    }
}
2 голосов
/ 07 марта 2012

Дальнейшее объяснение, долгое время для ответа, но я полагаю, что если вы делаете привязку в XAML, а затем в коде назначаете новый объект свойству, вы нарушаете привязку, поэтому вам придется повторить привязку в код для его работы. Отсюда и решение с полем только для чтения. В таком случае вы не сможете назначить новую коллекцию ObservableCollection и не нарушите привязку, назначив новый объект вспомогательному полю.

...