Sto cercando alcuni consigli su come risolvere un problema che ci sta infastidendo al momento.Come aggiornare ViewModels nidificati MVVM quando Model cambia e viceversa?
Diciamo che abbiamo un paio di oggetti di business (pocos) come
public class UserGroup
{
public virtual ICollection<Person> People { get; set; }
}
public class Person
{
public virtual ICollection<Adress> Adresses { get; set; }
}
public class Adress
{
public virtual string StreetName { get; set; }
}
Questo è un po 'semplicistico, ma spero che sia abbastanza in modo che si ottiene l'idea. UserGroup ha una collezione di persona casi e ogni persona esempio ha una collezione di Indirizzo istanze.
Il ViewModel per la UserGroup POCO potrebbe assomigliare a questo:
public class UserGroupViewModel
{
private UserGroup userGroupModel;
public UserGroup UserGroupModel
{
get { return this.userGroupModel; }
set
{
this.userGroupModel = value;
this.PeopleViewModelCollection =
new ObservableCollection<PeopleViewModel>();
foreach (Person p in this.UserGroupModel.People)
{
var personViewModel = new PersonViewModel();
personViewModel.PersonModel = p;
this.PeopleViewModelCollection.Add(personViewModel);
}
}
}
public ObservableCollection<PersonViewModel> PersonViewModelCollection
{
get;
set;
}
}
Dove come il ViewModel per la persona POCO potrebbe assomigliare a questo:
public class PersonViewModel
{
private Person personModel;
public Person PersonModel
{
get { return this.personModel; }
set
{
this.personModel = value;
this.AddressViewModelCollection =
new ObservableCollection<AddressViewModel>();
foreach (Address a in this.PersonModel.Adresses)
{
var addressViewModel = new AddressViewModel();
addressViewModel.AddressModel = a;
this.AdressViewModelCollection.Add(addressViewModel);
}
}
}
public ObservableCollection<AddressViewModel> AddressViewModelCollection
{
get;
set;
}
}
Anche in questo caso è eccessivamente semplicistico ma quello che voglio mostrare è che ViewModels ha ObserableCollections di altri ViewModels annidati al loro interno.
Il setter della rispettiva proprietà del modello, ad es. PersonViewModel.PersonModel
crea ViewModels per tutti gli indirizzi di Person
e li aggiunge alla proprietà ObservableCollection<AdressViewModels> AdressViewModelCollection
di PersonViewModel
.
A questo punto è possibile utilizzare questo codice per visualizzare questi ViewModels in una vista. Possiamo ad es. visualizza lo StreetName
di uno Adress
Person
.
Ora cosa si deve fare quando si elimina uno Adress
di un Person
? La rimozione dello PersonViewModel.AdressViewModelCollection
dal PersonViewModel.AdressViewModelCollection
aggiornerà la GUI ma in realtà non consente di aggiornare i modelli sottostanti.
Simile a che se si aggiunge un altro Adress
ad un modello Person
i ViewModels esistenti non sono in corso per riflettere tale cambiamento dal momento che il PersonViewModel.AdressViewModelCollection
sarebbe stato ricostruito solo una volta la proprietà PersonViewModel.PersonModel
è impostata di nuovo.
C'è un modo (preferibilmente facile) per ottenere questo aggiornamento a due vie tra ViewModel e Model? O forse questo non è consigliabile ed è meglio gestire questo problema in un modo completamente diverso?
Sono ansioso di sentire opinioni diverse su questo problema!
EDIT: Vorrei affermare che le nostre classi del modello sono generati dal Entity Framework 4.0 e sono pocos (vedi esempio di oggetti di business sopra). Non sono sicuro se ciò fosse abbastanza chiaro nella domanda stessa. Vorremmo esporre le proprietà di navigazione (ad esempio Person.Addresses
) come ICollection<T>
.
Grazie per la risposta. Ho modificato la domanda per chiarire l'origine dei nostri modelli. Sono POCO e generati dall'EF. Mentre la VM potrebbe (o forse dovrebbe) avere un 'ObservableCollection' la classe del modello stessa avrà un 'ICollection ' quindi la sincronizzazione funzionerebbe solo dal ViewModel al Modello, è corretta? –