WPF DataGrid: как мне привязать свойства SelectedItem для запуска INotifyPropertyChangedEvents? - PullRequest
1 голос
/ 07 октября 2010

Я пытаюсь сделать это как MVVM, насколько это возможно:
Моя модель ( InterestTypeEntity ) реализует INotifyPropertyChanged.
Моя ViewModel ( InterestTypeAllViewModel ) имеет коллекцию ObservableCollection, которая привязывается к DataGrid. Когда в него вносятся изменения, он отправляет эти изменения (добавление / удаление) в базу данных.

проблема в том, что я хочу также иметь возможность обновлять базу данных при изменении свойств объектов в коллекции. Я не уверен, как это сделать? Вот мой код пока ...

XAML:

<DataGrid Name="TestGrid" Grid.Row="3" Grid.ColumnSpan="2" AutoGenerateColumns="False"
          ItemsSource="{Binding IntTypes}" SelectedItem="{Binding CurrentIntType}">
    <DataGrid.Columns>
        <DataGridTextColumn Header="Interest ID" Binding="{Binding IntType}" />
        <DataGridTextColumn Header="Interested Parties Description" Binding="{Binding Description}" MaxWidth="500" />
    </DataGrid.Columns>
</DataGrid>

Код модели представления:

public ObservableCollection<InterestTypeEntity> IntTypes 
{
    get { return DataRepository.InterestTypeEntities; }
}

public InterestTypeEntity CurrentIntType { get; set; }

public Int16 IntType
{
    get { return CurrentIntType.IntType; }
    set
    {
        if (value != CurrentIntType.IntType)
        {
            CurrentIntType.IntType = value;
            OnPropertyChanged("IntType");
        }
    }
}

public String Description
{
    get { return CurrentIntType.Description; }
    set
    {
        if (value != CurrentIntType.Description)
        {
            CurrentIntType.Description = value;
            OnPropertyChanged("Description");
        }
    }
}

Ответы [ 3 ]

2 голосов
/ 07 октября 2010

Не создавайте коллекцию объектов модели и не реализуйте свойства IntType и Description в вашей (текущей) модели представления. И если у вас нет какой-либо другой причины для этого, не применяйте уведомление об изменении свойства в вашей модели.

Вместо этого сделайте IntTypes коллекцией InterestTypeEntityViewModel объектов.

Этот класс охватывает InterestTypeEntity. Он предоставляет свойства IntType и Description, которые а) обертывают базовые свойства InterestTypeEntity и б) выполняют уведомление об изменении свойства. Если вы заставите его конструктор принять аргумент InterestTypeEntity, его легко заполнить в вашей модели представления:

IntTypes = new ObservableCollection<InterestTypeEntityViewModel>(
   DataRepository.InterestTypeEntities.Select(x => new InterestTypeEntityViewModel(x));

Свяжите ItemsSource с этой коллекцией. (Также, сделайте CurrentIntType свойством типа InterestTypeEntityViewModel и увеличьте PropertyChanged, когда оно изменится.)

Изменить:

Если модель представления-владельца должна уведомляться при изменении свойств элементов в ее коллекции, довольно просто заставить ее обрабатывать PropertyChanged события, которые они вызывают. В вашем конструкторе добавьте:

foreach (InterestTypeEntityViewModel vm in IntTypes)
{
  vm.PropertyChanged += InterestTypeEntityViewModel_PropertyChanged;
}

и этот метод:

private void InterestTypeEntityViewModel_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
   InterestTypeEntityViewModel vm = (InterestTypeEntityViewModel) sender;
   // check e.PropertyName and do whatever you need to do here.
}

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

Кстати, обратите внимание, что, реализовав таким образом модели представлений, вы можете в значительной степени контролировать свои обновления базовой модели сущностей. Например, вы можете реализовать команду в своей родительской модели представления, которая выполняет все обновления за одну операцию, и еще одну, которая позволяет пользователю отменить все изменения, сделанные в пользовательском интерфейсе, без выполнения обновления. И вся эта логика очень хорошо отделена от фактического уровня представления.

1 голос
/ 07 октября 2010

Пожалуйста, смотрите мой ответ здесь .Он даст вам наблюдаемую коллекцию, которая сообщит вам, когда коллекция изменится или когда изменится элемент в коллекции.

0 голосов
/ 07 октября 2010

Общая стратегия:

Добавьте TwoWay к вашей привязке:

SelectedItem="{Binding CurrentIntType,Mode=TwoWay}"

А затем подпишитесь на измененное событие наблюдаемой коллекции в вашей ViewModel. Когда коллекция изменится, отправьте ее в свою модель / DAL и сохраните ее.

...