2016-08-15 6 views
0

私は、ユーザーが子供のマスターデータを編集できるアプリケーションを作成しています。子供のために行った変更を保存することで、ユーザーのシームレスなエクスペリエンスを作成しようとしています。WPF MVVMネストされたプロパティをバインドする

私はChildというモデルを持っています。

class Child 
{ 
    [Key] 
    public int ID { get; set; } 
    public string FirstName { get; set; } 
    public string Surname { get; set; } 
} 

私は、ビュー(ChildMasterDataView)そのディスプレイの姓と姓編集可能なテキストボックス内を持っています。

<!--First name--> 
<Label Content="First name:" /> 
<TextBox Text="{Binding Path=Child.FirstName, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}"/> 

<!--Surname--> 
<Label Content="Surname:" /> 
<TextBox Text="{Binding Path=Child.Surname, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}"/> 

私はINotifyPropertyChangedインターフェイスの実装を扱うクラスを持っています。

public class ObservableObject : INotifyPropertyChanged 
{ 
    public event PropertyChangedEventHandler PropertyChanged; 

    protected void RaisePropertyChangedEvent(string propertyName) 
    { 
     var handler = PropertyChanged; 
     if (handler != null) 
      handler(this, new PropertyChangedEventArgs(propertyName)); 
    } 
} 

私は、それぞれのプロパティが変更されたとき、FirstNameおよび姓に加えられた変更を保存することになっているのViewModelを持っています。問題は... FirstNameおよび姓は子クラスのプロパティをネストされている、とPropertyChangedイベントを発射していないということです

class ChildMasterDataViewModel : ObservableObject 
{ 
    private Database db; // Database context 

    public ChildViewModel() 
    { 
     db = new Database(); 
     Child = db.Children.ToList().Where(e => e.PlbNr == 1).FirstOrDefault(); // Won't be null because child has been chosen earlier 

     PropertyChanged += ChildPropertyChanged; 
    } 

    private Child child; 
    public Child Child 
    { 
     get { return child; } 
     set { child = value; RaisePropertyChangedEvent("Child"); } 
    } 

    private void ChildPropertyChanged(object sender, PropertyChangedEventArgs e) 
    { 
     db.SaveChanges(); 
    } 
} 

私はViewModelにに次の変更を加えることで、私が欲しいものを達成することができます(とビューバインディングを変更する):

class ChildMasterDataViewModel : ObservableObject 
{ 
    private Database db; // Database context 
    private Child child; 

    public ChildViewModel() 
    { 
     db = new Database(); 
     child = db.Children.ToList().Where(e => e.PlbNr == 1).FirstOrDefault(); // Won't be null because child has been chosen earlier 

     PropertyChanged += ChildPropertyChanged; 
    } 

    public string FirstName 
    { 
     get { return child.FirstName; } 
     set { child.FirstName= value; RaisePropertyChangedEvent("FirstName"); } 
    } 

    public string Surname 
    { 
     get { return child.Surname; } 
     set { child.Surname= value; RaisePropertyChangedEvent("Surname"); } 
    } 

    private void ChildPropertyChanged(object sender, PropertyChangedEventArgs e) 
    { 
     db.SaveChanges(); 
    } 
} 

これは正しい方法ではありませんか?

私はChildクラスでObservableObjectを実装してから、ViewModelのChildPropertyChangedメソッドにChildクラスのPropertyChangedイベントをサブスクライブするViewModelで試してみました。これはうまくいかなかった。

+0

3つの方法があります。 1)ラップモデル - あなたはすでにそれを作った、INotifiPropertyChangedがもっと簡単になると思った、imho。 2)INotifyPropertyChangedをモデルに直接追加します。 3)INotifypropertyChangedを実装するStadaloneクラスを作成するか、ObservableObjectから派生します。そして、このクラスはあなたのモデルを** input **として扱い、そのプロパティを初期化するためにそれを独自に処理しなければなりません。また、変換を元に戻す必要があります。 – Shakra

+0

バインドする場合は、おそらくINotifyPropertyChangedを実装する必要があります。そして、IDataErrorInfoも。 – Will

答えて

0

個人的には、単純なINotifyPropertyChanged実装を子モデルに配置しない理由がないことがわかります。変更後のプロパティはすべて変更されています。これで、直接バインドできます。

同じ理由で、なぜViewModelの状態を保存していますか?私はそれをモデルに入れるか、別の永続性マネージャーに移します。 VMは、モデルとは独立したビューの側面をモデル化することになっています。

+0

あなたはそれらにバインドする方法を示すことができますか?私が試したので、私はそれを働かせることができませんでした。モデルを介してデータを保存するにはどうすればよいですか? – Starwop

+0

特別なバインディングはありません.XAMLは完全に問題ありません。 ChildクラスにINotifyPropertyChangedを実装するだけで済みます。 –

+0

注意しておきますが、現在、すべてのキーストロークがデータベースの更新をトリガーしています... –

関連する問題