Quantcast
Viewing all articles
Browse latest Browse all 18858

wpf ef generated code - using INotifyPropertyChanged question

Code used to bind a datagrid on a form was automatically generated when setting up the entity framework.  The issue I'm having is that if the user edits a cell, then immediately closes the form, the edit is not made back to the database.

Using this as a guide, I implemented the INotifyPropertyChanged event to handle this issue.  But it's not capturing the non-committed edit like I expect.  In fact, I'm wondering why INPC is needed at all.

I changed the class generated by the code generator from this:

'------------------------------------------------------------------------------
' <auto-generated>
'     This code was generated from a template.
'
'     Manual changes to this file may cause unexpected behavior in your application.
'     Manual changes to this file will be overwritten if the code is regenerated.
' </auto-generated>
'------------------------------------------------------------------------------

Imports System
Imports System.Collections.ObjectModel

Partial Public Class tlkpProcedures_PartB
        Public Property CPT As String
        Public Property ProcedureName As String
        Public Property BillingAmount As Nullable(Of Decimal)
        Public Overridable Property tblBilling_PartB As ObservableCollection(Of tblBilling_PartB) = New ObservableCollection(Of tblBilling_PartB)

End Class

to this:

'------------------------------------------------------------------------------
' <auto-generated>
'     This code was generated from a template.
'
'     Manual changes to this file may cause unexpected behavior in your application.
'     Manual changes to this file will be overwritten if the code is regenerated.
' </auto-generated>
'------------------------------------------------------------------------------

Imports System
Imports System.Collections.ObjectModel

Partial Public Class tlkpProcedures_PartB
    Inherits PropertyChangedBase
    Public Property CPT As String
        Get
            Return _CPT
        End Get
        Set(value As String)
            _CPT = value
            RaisePropertyChanged("CPT")
        End Set
    End Property
    Private _CPT As String
    Public Property ProcedureName As String
        Get
            Return _ProcedureName
        End Get
        Set(value As String)
            _ProcedureName = value
            RaisePropertyChanged("ProcedureName")
        End Set
    End Property
    Private _ProcedureName As String

    Public Property BillingAmount As Nullable(Of Decimal)
        Get
            Return _BillingAmount
        End Get
        Set(value As Nullable(Of Decimal))
            _BillingAmount = value
            RaisePropertyChanged("BillingAmount")
        End Set
    End Property
    Private _BillingAmount As Nullable(Of Decimal)
    Public Property UniqueID As Integer

    Public Overridable Property tblBilling_PartB As ObservableCollection(Of tblBilling_PartB) = New ObservableCollection(Of tblBilling_PartB)

End Class

Code to bind form: 

Public Class PartBProcedures_Lookup

    Private _ProceduresContext As New DentistAppointmentsContext
    Private _bolSaved As Boolean = False
    Public Sub New()

        ' This call is required by the designer.
        InitializeComponent()

        ' Add any initialization after the InitializeComponent() call.

    End Sub
    
    Private Sub Window_Loaded(sender As Object, e As RoutedEventArgs) Handles MyBase.Loaded

        Dim TlkpProcedures_PartBViewSource As System.Windows.Data.CollectionViewSource = CType(Me.FindResource("TlkpProcedures_PartBViewSource"), System.Windows.Data.CollectionViewSource)
        'Load data by setting the CollectionViewSource.Source property:
        'TlkpProcedures_PartBViewSource.Source = [generic data source]
        _ProceduresContext.tlkpProcedures_PartB.Load()
        TlkpProcedures_PartBViewSource.Source = _ProceduresContext.tlkpProcedures_PartB.Local

    End Sub
    Private Sub Button_Click(sender As Object, e As RoutedEventArgs)

        _ProceduresContext.SaveChanges()
        _bolSaved = True

    End Sub
    
End Class

Xaml:

<DataGrid x:Name="TlkpProcedures_PartBDataGrid" RowDetailsVisibilityMode="VisibleWhenSelected" Margin="11,10,10,49" 
                  ItemsSource="{Binding}" EnableRowVirtualization="True" AutoGenerateColumns="False"><DataGrid.Columns><DataGridTextColumn x:Name="CPTColumn" Width="100" Header="CPT" 
                                    Binding="{Binding CPT, UpdateSourceTrigger=PropertyChanged}"/><DataGridTextColumn x:Name="ProcedureNameColumn" Width="200" Header="Procedure Name" 
                                    Binding="{Binding ProcedureName, UpdateSourceTrigger=PropertyChanged}"/><DataGridTextColumn x:Name="BillingAmountColumn" Width="SizeToHeader" Header="Billing Amount" 
                                    Binding="{Binding BillingAmount, StringFormat={}{0:n2}, UpdateSourceTrigger=PropertyChanged}" /></DataGrid.Columns></DataGrid>

If I strip out all the INPC coding, the datagrid binds and saves as expected, as long as the user clicks off the edited cell and into another, then clicks on Save. If I use INPC, the user still has to click off the edited cell onto another, then click on Save. So I'm not sure what I'm gaining by using INPC.

Ultimately, I'd like for the user to have to avoid the Save button all together.  I tried stripping out the Save code thinking that INPC would automatically save edits back to the datasource, with no luck.

So, my problem is:  I'm not sure if I'm doing the right thing by using INPC, and if it is the right thing, then what am I doing wrong that it doesn't function like I expect?


Thanks.


Viewing all articles
Browse latest Browse all 18858

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>