Подтвердить что ты не робот

ObservableCollection теряет привязку, когда я "новый" это

У меня есть ListBox на моем пользовательском интерфейсе, который связан с свойством ObservableCollection. Я установил новый экземпляр ObservableCollection в свойство в конструкторе модели представления, и я могу добавить элементы к нему с помощью кнопки в форме. Они видны в списке.

Все хорошо.

Однако, если я повторно инициализую свойство с новым в обратном вызове кнопки, он разбивает привязку, и пользовательский интерфейс больше не показывает то, что находится в коллекции.

Я предположил, что привязка будет продолжать искать значения свойства, но, по-видимому, связана с ссылкой, которая уничтожается новым.

Есть ли у меня это право? Может ли кто-нибудь расширить, как это связано? Есть ли способ переподтвердить его, когда моя модель представления не знает представления?

4b9b3361

Ответ 1

Убедитесь, что вы поднимаете PropertyChangedEvent после повторной инициализации своей коллекции. Повышение этого события позволит виду обрабатывать изменения в свойстве с моделью, не имеющей представления о представлении.

class Model : INotifyPropertyChanged
{
    public event PropertyChangedEventHandler PropertyChanged;

    private void NotifyPropertyChanged(string name)
    {
        if (PropertyChanged != null)
            PropertyChanged(this, new PropertyChangedEventArgs(name));
    }

    private ObservableCollection<string> _list = new ObservableCollection<string>();
    public ObservableCollection<string> List
    {
        get { return _list; }
        set 
        { 
            _list = value;
            NotifyPropertyChanged("List");
        }
    }

    public Model()
    {
        List.Add("why");
        List.Add("not");
        List.Add("these?");
    }
}

Ответ 2

Я думаю, что на основе вашего описания, что вам нужно сделать, это реорганизовать свойство, которое предоставляет ваш ObservableCollection, чтобы оно вызывало событие PropertyChanged и когда ему присваивается новое значение. Пример:

public ObservableCollection<int> Integers
{
    get { return this.integers; }
    set {
        if (this.integers != value)
        {
            this.integers = value;
            RaisePropertyChanged("Integers");
        }
    }
}

Ответ 3

Предположим, что вы внедрили INotifyPropertyChanged в ViewModel, вы можете поднять событие изменения свойства на свой ObservableCollection всякий раз, когда вы назначаете ему новое значение.

public ObservableCollection<string> MyList { get; set; }

public void SomeMethod()
{
    MyList = new ObservableCollection<string>();
    RaisePropertyChanged("MyList");
}

Ответ 4

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

Два простых предложения заключались бы в том, чтобы реализовать INotifyPropertyChanged в классе, который содержит ObservableCollection, и вызывать событие PropertyChanged в настройщике свойства коллекции (не забудьте отцепить от старого сначала ваш наблюдатель, если это ваш собственный код).

private ObservableCollection<string> _myCollection = new ObservableCollection<string>();
public ObservableCollection<string> MyCollection
{
    get { return _myCollection; }
    set
    {
        if(_myCollection == value)
            return;

        _myCollection = value;
        RaisePropertyChanged("MyCollection");
    }
}

Вторым, и вариант, который я обычно предпочитаю, - это просто очистить и повторно заполнить коллекцию новыми данными, когда они появятся.

public void HandleCollectionData(IEnumerable<string> incomingData)
{
    MyCollection.Clear();
    foreach(var item in incomingData)
    {
        MyCollection.Add(item);
    }
}