データアクセスにMVVMモデルとEntityFramework5を使用するWPFアプリケーションがあります。従業員のマスター/詳細ビューを含むユーザーコントロールがあります。従業員のリストのリストビューと、データコンテキストがリストビューの選択された従業員に設定された「詳細」グリッド。そのグリッド内に、選択した従業員のナビゲーションプロパティ(employee_certificationという名前のプロパティ)にバインドされたデータグリッドがあります。すべてのバインディングは正しく機能し、出力ウィンドウでもエラーは発生しません。
問題:私の問題は、ユーザーがナビゲーションプロパティのレコードに変更を加えたかどうかを検出できないことです。現在、変更トラッカーを使用してエンティティの変更をテストし、保存、元に戻すなどの特定のコマンドボタンを有効にしています。ただし、変更トラッカーはナビゲーションプロパティ(employee_certificationと呼ばれる)内の変更を検出しません。
モデルから従業員エンティティを取得する方法は次のとおりです。
Public Function GetEmployee_All(Context As FTC_Context) As ObservableCollection(Of employee) Implements IEmployeeDataService.GetEmployee_All
Dim employees = Context.employees.Include("employee_certification").ToList
Return New ObservableCollection(Of employee)(employees)
End Function
これは、ナビゲーションプロパティのデータグリッドへのバインドです。(これは機能します。つまり、適切なレコードが表示されます)
<DataGrid Grid.Column="1" Grid.Row="2" MinWidth="350"
ItemsSource="{Binding ElementName=DetailControl, Mode=TwoWay, Path=DataContext.employee_certification}"
CanUserAddRows="False" CanUserDeleteRows="False" >
<DataGrid.Columns>
</DataGrid.Columns>
</DataGrid>
バインディングは機能し、正しいレコードが表示されますが、ユーザーがナビゲーションプロパティのレコードに変更を加えたかどうかを判断できません。
目標:可能であれば、コンテキスト自体を通じて変更を検出できるようにしたいと思います。現在のレコードをデータベースの元のレコードと比較するためにヘルパークラスを作成する必要はありません。誰かが私がこれをするのを手伝ってくれますか?
編集#1: それはデータグリッドと特別に関係があるかもしれないと思います。アプリの別のユーザーコントロールに次のリストビューがあり、リストビューレコードのレコードフィールドに加えられた変更は、EFコンテキストで追跡できます。
バインディングvendor_accountがエンティティvandorのナビゲーションプロパティであるlistview:
<ListView Grid.Column="1" Grid.Row="2"
Style="{DynamicResource FTC_SubListView}"
ItemContainerStyle="{DynamicResource FTC_SubListViewItem}"
ItemsSource="{Binding vendor_account, Mode=TwoWay}"
ItemTemplate="{DynamicResource FTC_VendorAccountsTemplate}" />
ビューで保存ボタンを有効にするための変更があるかどうかを判断する方法は次のとおりです。
Private Function CanSaveExecute() As Boolean
If _Selection.HasErrors = False Then
If (From entry In Context.ChangeTracker.Entries(Of vendor)() Where entry.Entity.idVendor = _Selection.idVendor And entry.State = EntityState.Modified Select entry).Count > 0 Then
Return True
ElseIf (From entry In Context.ChangeTracker.Entries(Of vendor_account)() Where entry.Entity.idVendor = _Selection.idVendor And (entry.State = EntityState.Modified Or entry.State = EntityState.Added) Select entry).Count > 0 Then
Return True
Else
Return False
End If
Else
Return False
End If
End Function
ただし、データグリッドに以下を使用すると、emplopyee_certificationナビゲーションプロパティの変更カウントがありません。
Private Function CanSaveExecute() As Boolean
If _Selection.HasErrors = False Then
If (From entry In Context.ChangeTracker.Entries(Of employee)() Where entry.Entity.idEmployee = _Selection.idEmployee And entry.State = EntityState.Modified Select entry).Count > 0 Then
Return True
ElseIf (From entry In Context.ChangeTracker.Entries(Of employee_certification)() Where entry.Entity.idEmployee = _Selection.idEmployee And entry.State = EntityState.Modified Select entry).Count > 0 Then
Return True
Else
Return False
End If
Else
Return False
End If
End Function
私のリストビューで、変更トラッカーが変更トラッカーから変更されたエンティティのx個を表示できるが、データグリッドでは表示できない理由を誰かが知っていますか?
編集#2
さて、これを絞り込みます。リストビューとデータグリッドを同じユーザーコントロールに配置し、上記のようにオブジェクトのデータコンテキストのナビゲーションプロパティに同じ方法でバインドします。従業員は、従業員オブジェクトのナビゲーションプロパティ(employee_certification)であるリンクされたレコードとして証明書を持っています。
employee_certificationレコードにリストビューを使用する場合、それらのレコードに変更を加えると、変更トラッカーにクエリを実行して変更をカウントし、カウントがゼロより大きい場合は保存ボタンと元に戻すボタンを有効にできます。
From entry In Context.ChangeTracker.Entries(Of employee_certification)() Where entry.Entity.idEmployee = _Selection.idEmployee And entry.State = EntityState.Modified Select entry).Count
データグリッドを使用してemployee_certificationレコードのフィールドを変更すると、変更トラッカーはそれらのいずれも変更済みとしてマークしません。
datagrid/listviewの定義方法は次のとおりです
<DataGrid Grid.Column="1" Grid.Row="2" MinWidth="350"
ItemsSource="{Binding employee_certification, Mode=TwoWay}"
CanUserAddRows="False" CanUserDeleteRows="False" >
<DataGrid.Columns>
<!-- Custom Defined Columns Go Here -->
</DataGrid.Columns>
</DataGrid>
<ListView Grid.Column="1" Grid.Row="3"
Style="{DynamicResource FTC_SubListView}"
ItemContainerStyle="{DynamicResource FTC_SubListViewItem}"
ItemsSource="{Binding employee_certification, Mode=TwoWay}"
ItemTemplate="{DynamicResource MyTemplate}">
</ListView>
ソートなどが組み込まれているので、データグリッドを使いたいです。
編集の質問#2:変更トラッカーがリストビュー編集の変更を追跡するのにデータグリッド編集は追跡しないのはなぜですか?