vb.netwinformsdatagridviewbindingsourcebindinglist

How to refresh via bindingsource in DatagridView in the main form when updating in other forms without closed or not in VB.NET


I'm Trying to refresh via bindingsource in DatagridView in the main form when updating in other forms without closed or not in VB.NET

Please Guide me

Thanks

Code in autocompledatagridview (Form main)

Imports System.ComponentModel
Imports System.Data.OleDb
Imports Dapper

Public Class autocompledatagridview
    Private dictProducts As Dictionary(Of String, ProductFinaltesting)
    Private BindingSource1 As BindingSource = Nothing
    Protected Overrides Sub OnLoad(e As EventArgs)
        MyBase.OnLoad(e)
        dictProducts = ProductFinaltestingService.GetDistinctProducts().
            ToDictionary(Function(p) p.ToString(), Function(p) p)
        BindingSource1 = New BindingSource With {.DataSource = New BindingList(Of ProductFinaltesting)}
        DataGridView1.AutoGenerateColumns = False
        DataGridView1.AllowUserToAddRows = False
        DataGridView1.DataSource = BindingSource1
        DataGridView1.Columns("Unit").ReadOnly = True
        BindingSource1.AddNew()
    End Sub
    Private Sub DataGridView1_EditingControlShowing(
      sender As Object,
      e As DataGridViewEditingControlShowingEventArgs) Handles _
      DataGridView1.EditingControlShowing
        If TypeOf e.Control Is TextBox Then
            Dim dgv = DirectCast(sender, DataGridView)
            Dim tb = DirectCast(e.Control, TextBox)
            If dgv.CurrentCell.ColumnIndex = dgv.Columns("ProductName").Index Then
                If tb.AutoCompleteCustomSource.Count = 0 Then
                    tb.AutoCompleteSource = AutoCompleteSource.CustomSource
                    tb.AutoCompleteCustomSource.AddRange(dictProducts.Keys.ToArray())
                End If
                tb.AutoCompleteMode = AutoCompleteMode.Suggest
            Else
                tb.AutoCompleteMode = AutoCompleteMode.None
            End If
        End If
    End Sub
    Private Sub DataGridView1_CellValidating(
       sender As Object,
       e As DataGridViewCellValidatingEventArgs) _
       Handles DataGridView1.CellValidating
        Dim dgv = DirectCast(sender, DataGridView)

        If e.ColumnIndex = dgv.Columns("ProductName").Index AndAlso
           e.RowIndex <> dgv.NewRowIndex Then
            Dim key As String

            If dgv.IsCurrentCellInEditMode Then
                Dim p = dictProducts.Values.
                FirstOrDefault(Function(x) x.ProductName.
                Equals(e.FormattedValue.
                ToString(), StringComparison.InvariantCultureIgnoreCase))

                If p IsNot Nothing Then
                    key = p.ToString()
                Else
                    key = e.FormattedValue.ToString()
                End If
            Else
                key = dgv(e.ColumnIndex, e.RowIndex).Value?.ToString().Trim()
            End If
            If String.IsNullOrEmpty(key) OrElse
           Not dictProducts.ContainsKey(key) Then
                Dim boundItem = DirectCast(dgv.Rows(e.RowIndex).DataBoundItem, ProductFinaltesting)
                boundItem.Unit = Nothing
                boundItem.Prp = Nothing
                boundItem.Prs = Nothing
                dgv.Rows(e.RowIndex).ErrorText = "Invalid Product!"
                dgv.UpdateCellValue(dgv.Columns("Unit").Index, e.RowIndex)
                dgv.UpdateCellValue(dgv.Columns("PRP").Index, e.RowIndex)
                dgv.UpdateCellValue(dgv.Columns("PRS").Index, e.RowIndex)
                e.Cancel = True
            End If
        End If
    End Sub
    Private Sub DataGridView1_CellValidated(
       sender As Object,
       e As DataGridViewCellEventArgs) Handles DataGridView1.CellValidated
        Dim dgv = DirectCast(sender, DataGridView)

        If e.ColumnIndex = dgv.Columns("ProductName").Index Then
            Dim p As ProductFinaltesting = Nothing
            Dim key = dgv(e.ColumnIndex, e.RowIndex).Value?.ToString().Trim()

            If key Is Nothing Then Return
            If dictProducts.TryGetValue(key, p) Then
                Dim boundItem = TryCast(dgv.Rows(e.RowIndex).DataBoundItem, ProductFinaltesting)
                If p.Unit <> boundItem.Unit And p.Prp <> boundItem.Prp And p.Prs <> boundItem.Prs Then
                    boundItem.Unit = p.Unit
                    dgv.UpdateCellValue(dgv.Columns("Unit").Index, e.RowIndex)
                    boundItem.Prp = p.Prp
                    dgv.UpdateCellValue(dgv.Columns("Prp").Index, e.RowIndex)
                    boundItem.Prs = p.Prs
                    dgv.UpdateCellValue(dgv.Columns("Prs").Index, e.RowIndex)
                End If

                dgv.Rows(e.RowIndex).ErrorText = Nothing
            End If
        End If
    End Sub
    Private Sub DataGridView1_CellEndEdit(
        sender As Object,
        e As DataGridViewCellEventArgs) Handles DataGridView1.CellEndEdit
        Dim dgv = DirectCast(sender, DataGridView)
        Dim src = DirectCast(dgv.DataSource, BindingSource)
        If src.Count = e.RowIndex Then Return
        If e.ColumnIndex = dgv.Columns("ProductName").Index Then
            Dim p As ProductFinaltesting = Nothing
            Dim key = dgv(e.ColumnIndex, e.RowIndex).Value?.ToString().Trim()

            If key Is Nothing Then Return
            If dictProducts.TryGetValue(key, p) Then
                Dim boundItem = TryCast(dgv.Rows(e.RowIndex).DataBoundItem, ProductFinaltesting)
                If p.Unit <> boundItem.Unit And p.Prp <> boundItem.Prp And p.Prs <> boundItem.Prs Then
                    boundItem.Unit = p.Unit
                    dgv.UpdateCellValue(dgv.Columns("Unit").Index, e.RowIndex)
                    boundItem.Prp = p.Prp
                    dgv.UpdateCellValue(dgv.Columns("Prp").Index, e.RowIndex)
                    boundItem.Prs = p.Prs
                    dgv.UpdateCellValue(dgv.Columns("Prs").Index, e.RowIndex)
                End If
                dgv.Rows(e.RowIndex).ErrorText = Nothing
            End If
            End If

    End Sub
    Protected Overrides Function ProcessCmdKey(ByRef msg As Message, ByVal keyData As Keys) As Boolean
        If keyData = Keys.Tab AndAlso CBool(Keys.Enter) Then
            If Me.DataGridView1.Rows.Count > 0 Then
                If DataGridView1.CurrentRow.Index = (DataGridView1.Rows.Count - 1) Then
                    BindingSource1.AddNew()
                End If
            Else
            End If
            Return True
        End If
        Return MyBase.ProcessCmdKey(msg, keyData)
    End Function

    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
        Dim frm As New formproduct
        frm.Show()
    End Sub
End Class

Public Class ProductFinaltesting
    '<Browsable(False)>
    'Public Property Font As String = "☑️"
    Public Property ProductName As String
    Public Property Unit As String
    Public Property Prp As Integer
    Public Property Prs As Integer
    Public Overrides Function ToString() As String
        Return $"{ProductName}"
    End Function

End Class
Public Class ProductFinaltestingService
    Private Shared Function GetOledbConnectionString() As String
        Return "Provider=Microsoft.ACE.OLEDB.12.0;
                    Data Source=|DataDirectory|\test04102024.accdb;
                    Persist Security Info=False;"
    End Function
    ' ...
    Friend Shared Function GetDistinctProducts() As IEnumerable(Of ProductFinaltesting)
        Dim sql = "SELECT DISTINCT ProductName, Unit,Prp,Prs 
                       FROM Products 
                       ORDER BY ProductName"
        Using _conn = New OleDbConnection(GetOledbConnectionString())
            Return _conn.Query(Of ProductFinaltesting)(sql)
        End Using
    End Function
    Friend Shared Function GetProducts() As IEnumerable(Of ProductFinaltesting)
        Dim sql = "SELECT ProductName, Unit,Prp,Prs 
                       FROM Products 
                       ORDER BY ProductName"
        Using _conn = New OleDbConnection(GetOledbConnectionString())
            Return _conn.Query(Of ProductFinaltesting)(sql)
        End Using
    End Function
    Public Sub UpdateProducts(ByVal Obj As ProductFinaltesting)
        Dim sql = "UPDATE Products Set Unit=@Unit,Prp=@Prp,Prs=@Prs WHERE ProductName=@ProductName;"
        Using _conn = New OleDbConnection(GetOledbConnectionString())
            _conn.Execute(sql, New With {
    Key Obj.Unit,
    Key Obj.Prp,
    Key Obj.Prs,
    Key Obj.ProductName
})
        End Using
    End Sub
End Class

Code in formproduct (another form)

Imports System.ComponentModel

Public Class formproduct
    Dim ProductFinaltestingService As New ProductFinaltestingService()
    Private BindingSource1 As BindingSource = Nothing

    Private Sub formproduct_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        loaddata()
    End Sub
    Private Sub loaddata()
        BindingSource1 = New BindingSource With {.DataSource = New BindingList(Of ProductFinaltesting)(CType(ProductFinaltestingService.GetProducts(), IList(Of ProductFinaltesting)))}
        DataGridView1.AutoGenerateColumns = False
        DataGridView1.AllowUserToAddRows = False
        DataGridView1.DataSource = BindingSource1
        DataGridView1.ReadOnly = True
    End Sub
    Private Function GetSELECT() As ProductFinaltesting
        Return If(DataGridView1.SelectedCells.Count = 0, Nothing, TryCast(DataGridView1.SelectedCells(0).OwningRow.DataBoundItem, ProductFinaltesting))
    End Function
    Private Sub DataGridView1_CellContentClick(sender As Object, e As DataGridViewCellEventArgs) Handles DataGridView1.CellContentClick
        Dim dgv = DirectCast(sender, DataGridView)
        If e.RowIndex >= 0 Then
            Dim SelectDgv = GetSELECT()
            txtProductname.Text = SelectDgv.ProductName
            txtUnit.Text = SelectDgv.Unit
            txtPrp.Text = CType(SelectDgv.Prp, String)
            txtPrs.Text = CType(SelectDgv.Prs, String)
        End If
    End Sub

    Private Sub BtnUpdate_Click(sender As Object, e As EventArgs) Handles BtnUpdate.Click
        Try
            Dim Prp As Integer
        Integer.TryParse(txtPrp.Text, Prp)
        Dim Prs As Integer
        Integer.TryParse(txtPrs.Text, Prs)
            ProductFinaltestingService.UpdateProducts(New ProductFinaltesting() With {
                .Unit = txtUnit.Text,
                .Prp = Prp,
                .Prs = Prs,
                .ProductName = txtProductname.Text
                    })

            MessageBox.Show(Me, "Successfull")
            loaddata()
        Catch err As Exception
            MessageBox.Show(Me, err.Message)
        End Try
    End Sub
End Class

I attached the code result in the gif file in the file, you can see that the main form has no update or refresh when I update in another form

code result in the gif file

RESULT CODE ANSWER FROM @djv RESULT CODE ANSWER FROM @djv

update code full (ProductName is the primary key)

DataGridView in mainform reflect when I do an update in the product form but try to call the same productname in the new row the value that appears in the prp is still the old one

Code In formproduct

Imports System.ComponentModel

Public Class formproduct
    Dim ProductFinaltestingService As New ProductFinaltestingService()
    Private BindingSource1 As BindingSource = Nothing
    Private selectedOrder As String
    Private selectedIndex As Integer
    Public Event Updated(sender As Object, e As UpdatedEventArgs)
    Public Class UpdatedEventArgs
        Inherits EventArgs
        Public ReadOnly Property Unit As String
        Public ReadOnly Property ProductName As String
        Public ReadOnly Property Prp As Integer
        Public ReadOnly Property Prs As Integer
        Public Sub New(unit As String, productName As String, prp As Integer, prs As Integer)
            Me.Unit = unit
            Me.ProductName = productName
            Me.Prp = prp
            Me.Prs = prs
        End Sub
    End Class
    Private Sub OnUpdated(e As UpdatedEventArgs)
        RaiseEvent Updated(Me, e)
    End Sub

    Private Sub formproduct_Load(sender As Object, e As EventArgs) Handles MyBase.Load
            loaddata()
        End Sub
        Private Sub loaddata()
        BindingSource1 = New BindingSource With {.DataSource = New BindingList(Of ProductFinaltesting)(CType(ProductFinaltestingService.GetProducts(), IList(Of ProductFinaltesting)))}
        DataGridView1.AutoGenerateColumns = False
        DataGridView1.AllowUserToAddRows = False
        DataGridView1.DataSource = BindingSource1
        DataGridView1.ReadOnly = True
    End Sub
    Private Function GetSELECT() As ProductFinaltesting
        Return If(DataGridView1.SelectedCells.Count = 0, Nothing, TryCast(DataGridView1.SelectedCells(0).OwningRow.DataBoundItem, ProductFinaltesting))
    End Function
    Private Sub DataGridView1_CellContentClick(sender As Object, e As DataGridViewCellEventArgs) Handles DataGridView1.CellContentClick
        Dim dgv = DirectCast(sender, DataGridView)
        If e.RowIndex >= 0 Then
            Dim SelectDgv = GetSELECT()
            txtProductname.Text = SelectDgv.ProductName
            txtUnit.Text = SelectDgv.Unit
            txtPrp.Text = CType(SelectDgv.Prp, String)
            txtPrs.Text = CType(SelectDgv.Prs, String)
        End If
    End Sub

    Private Sub BtnUpdate_Click(sender As Object, e As EventArgs) Handles BtnUpdate.Click
        Try
            Dim bs = TryCast(BindingSource1.DataSource, BindingList(Of ProductFinaltesting))
            Dim Prp As Integer
            Integer.TryParse(txtPrp.Text, Prp)
            Dim Prs As Integer
            Integer.TryParse(txtPrs.Text, Prs)
            ProductFinaltestingService.UpdateProducts(New ProductFinaltesting() With {
                .Unit = txtUnit.Text,
                .Prp = Prp,
                .Prs = Prs,
                .ProductName = txtProductname.Text
                    })

            MessageBox.Show(Me, "Successfull")
 ProductFinaltestingService.GetProducts.ToList().ForEach(Sub(m)
            For i As Integer = 0 To bs.Count() - 1
            If bs(i).ProductName = m.ProductName Then
            bs(i) = m
            End If
            Next i
            End Sub)

            OnUpdated(New UpdatedEventArgs(txtUnit.Text, txtProductname.Text, Prp, Prs))
   Catch err As Exception
            MessageBox.Show(Me, err.Message)
        End Try
    End Sub
  Private Sub DataGridView1_DataBindingComplete(sender As Object, e As DataGridViewBindingCompleteEventArgs) Handles DataGridView1.DataBindingComplete
        If (Not String.IsNullOrEmpty(selectedOrder) _
            AndAlso (e.ListChangedType = ListChangedType.Reset)) Then
            If (BindingSource1.List.Count > 0) Then
                selectedIndex = BindingSource1.Find("ProductName", selectedOrder)
                If (selectedIndex <= 0) Then
                    selectedIndex = 0
                End If

                DataGridView1.Rows(selectedIndex).Selected = True
            Else
                selectedOrder = String.Empty
            End If

        End If

    End Sub
End Class

Code in autocompledatagridview (MainForm)

Imports System.ComponentModel
Imports System.Data.OleDb
Imports Dapper

Public Class autocompledatagridview
    Inherits Form
    Private dictProducts As Dictionary(Of String, ProductFinaltesting)
    Private BindingSource1 As BindingSource = Nothing
    Protected Overrides Sub OnLoad(e As EventArgs)
        MyBase.OnLoad(e)
        updateDataSource()

    End Sub
    Protected Sub updateDataSource()
        dictProducts = ProductFinaltestingService.GetDistinctProducts().
    ToDictionary(Function(p) p.ToString(), Function(p) p)
        BindingSource1 = New BindingSource With {.DataSource = New BindingList(Of ProductFinaltesting)}
        DataGridView1.AutoGenerateColumns = False
        DataGridView1.AllowUserToAddRows = False
        DataGridView1.DataSource = BindingSource1
        DataGridView1.Columns("Unit").ReadOnly = True
        DataGridView1.Columns("No").ReadOnly = True
        BindingSource1.AddNew()
    End Sub

    Private Sub DataGridView1_EditingControlShowing(
      sender As Object,
      e As DataGridViewEditingControlShowingEventArgs) Handles _
      DataGridView1.EditingControlShowing
        If TypeOf e.Control Is TextBox Then
            Dim dgv = DirectCast(sender, DataGridView)
            Dim tb = DirectCast(e.Control, TextBox)
            If dgv.CurrentCell.ColumnIndex = dgv.Columns("ProductName").Index Then
                If tb.AutoCompleteCustomSource.Count = 0 Then
                    tb.AutoCompleteSource = AutoCompleteSource.CustomSource
                    tb.AutoCompleteCustomSource.AddRange(dictProducts.Keys.ToArray())
                End If
                tb.AutoCompleteMode = AutoCompleteMode.Suggest
            Else
                tb.AutoCompleteMode = AutoCompleteMode.None
            End If
        End If
    End Sub
    Private Sub DataGridView1_CellValidating(
       sender As Object,
       e As DataGridViewCellValidatingEventArgs) _
       Handles DataGridView1.CellValidating
        Dim dgv = DirectCast(sender, DataGridView)

        If e.ColumnIndex = dgv.Columns("ProductName").Index AndAlso
           e.RowIndex <> dgv.NewRowIndex Then
            Dim key As String

            If dgv.IsCurrentCellInEditMode Then
                Dim p = dictProducts.Values.
                FirstOrDefault(Function(x) x.ProductName.
                Equals(e.FormattedValue.
                ToString(), StringComparison.InvariantCultureIgnoreCase))

                If p IsNot Nothing Then
                    key = p.ToString()
                Else
                    key = e.FormattedValue.ToString()
                End If
            Else
                key = dgv(e.ColumnIndex, e.RowIndex).Value?.ToString().Trim()
            End If
            If String.IsNullOrEmpty(key) OrElse
           Not dictProducts.ContainsKey(key) Then
                Dim boundItem = DirectCast(dgv.Rows(e.RowIndex).DataBoundItem, ProductFinaltesting)
                boundItem.Unit = Nothing
                boundItem.Prp = Nothing
                boundItem.Prs = Nothing
                dgv.Rows(e.RowIndex).ErrorText = "Invalid Product!"
                dgv.UpdateCellValue(dgv.Columns("Unit").Index, e.RowIndex)
                dgv.UpdateCellValue(dgv.Columns("PRP").Index, e.RowIndex)
                dgv.UpdateCellValue(dgv.Columns("PRS").Index, e.RowIndex)
                e.Cancel = True
            End If
        End If
    End Sub

 Public Sub REFLECT()
        Dim bs = TryCast(BindingSource1.DataSource, BindingList(Of ProductFinaltesting))
        ProductFinaltestingService.GetDistinctProducts.ToList().ForEach(Sub(m)
                                                                            For i As Integer = 0 To bs.Count() - 1
                                                                                If bs(i).ProductName = m.ProductName Then
                                                                                    bs(i) = m
                                                                                End If
                                                                            Next i
                                                                        End Sub)
    End Sub
    Private Sub setno()
        Dim i = 1
        Dim bs = TryCast(BindingSource1.DataSource, BindingList(Of ProductFinaltesting))
        For Each row As ProductFinaltesting In bs
            row.No = i
            i += 1
        Next
    End Sub
    Private Sub DataGridView1_CellValidated(
       sender As Object,
       e As DataGridViewCellEventArgs) Handles DataGridView1.CellValidated
        Dim dgv = DirectCast(sender, DataGridView)

        If e.ColumnIndex = dgv.Columns("ProductName").Index Then
            Dim p As ProductFinaltesting = Nothing
            Dim key = dgv(e.ColumnIndex, e.RowIndex).Value?.ToString().Trim()

            If key Is Nothing Then Return
            If dictProducts.TryGetValue(key, p) Then
                Dim boundItem = TryCast(dgv.Rows(e.RowIndex).DataBoundItem, ProductFinaltesting)
                                If p.Unit <> boundItem.Unit Or p.Prp <> boundItem.Prp Or p.Prs <> boundItem.Prs Then
                    boundItem.Unit = p.Unit
                    dgv.UpdateCellValue(dgv.Columns("Unit").Index, e.RowIndex)
                    boundItem.Prp = p.Prp
                    dgv.UpdateCellValue(dgv.Columns("Prp").Index, e.RowIndex)
                    boundItem.Prs = p.Prs
                    dgv.UpdateCellValue(dgv.Columns("Prs").Index, e.RowIndex)

                End If

                dgv.Rows(e.RowIndex).ErrorText = Nothing
            End If
        End If
    End Sub
  Private Sub DataGridView1_CellEndEdit(
        sender As Object,
        e As DataGridViewCellEventArgs) Handles DataGridView1.CellEndEdit
        Dim dgv = DirectCast(sender, DataGridView)
        Dim src = DirectCast(dgv.DataSource, BindingSource)
        If src.Count = e.RowIndex Then Return
        If e.ColumnIndex = dgv.Columns("ProductName").Index Then
            Dim p As ProductFinaltesting = Nothing
            Dim key = dgv(e.ColumnIndex, e.RowIndex).Value?.ToString().Trim()

            If key Is Nothing Then Return
            If dictProducts.TryGetValue(key, p) Then
                Dim boundItem = TryCast(dgv.Rows(e.RowIndex).DataBoundItem, ProductFinaltesting)
               If p.Unit <> boundItem.Unit Or p.Prp <> boundItem.Prp Or p.Prs <> boundItem.Prs Then
                        boundItem.Unit = p.Unit
                        dgv.UpdateCellValue(dgv.Columns("Unit").Index, e.RowIndex)
                        boundItem.Prp = p.Prp
                        dgv.UpdateCellValue(dgv.Columns("Prp").Index, e.RowIndex)
                        boundItem.Prs = p.Prs
                        dgv.UpdateCellValue(dgv.Columns("Prs").Index, e.RowIndex)
                    End If
                dgv.Rows(e.RowIndex).ErrorText = Nothing
            End If
            setno()
        End If
    End Sub
 Protected Overrides Function ProcessCmdKey(ByRef msg As Message, ByVal keyData As Keys) As Boolean
        If keyData = Keys.Tab AndAlso CBool(Keys.Enter) Then
            If Me.DataGridView1.Rows.Count > 0 Then
                If DataGridView1.CurrentRow.Index = (DataGridView1.Rows.Count - 1) Then
                    BindingSource1.AddNew()
                End If
            Else
            End If
            Return True
        End If
        Return MyBase.ProcessCmdKey(msg, keyData)
    End Function

    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
        Dim frm As New formproduct
        AddHandler frm.Updated, AddressOf frmproduct_Updated
        AddHandler frm.FormClosed, Sub() RemoveHandler frm.Updated, AddressOf frmproduct_Updated
        frm.Show()
    End Sub
    Private Sub frmproduct_Updated(sender As Object, e As formproduct.UpdatedEventArgs)
        Dim item = DirectCast(BindingSource1.Current, ProductFinaltesting)
        If DataGridView1.Rows.Count > 1 Then
            item.ProductName = e.ProductName
            item.Unit = e.Unit
            item.Prp = e.Prp
            item.Prs = e.Prs
        End If
        BindingSource1.ResetBindings(False)
        dictProducts = ProductFinaltestingService.GetDistinctProducts().
ToDictionary(Function(p) p.ToString(), Function(p) p)
    End Sub
End Class
Public Class ProductFinaltesting
    '<Browsable(False)>
    'Public Property Font As String = "☑️"
     Public Property No As Integer?
    Public Property ProductName As String
    Public Property Unit As String
    Public Property Prp As Integer?
    Public Property Prs As Integer?
    Public Overrides Function ToString() As String
        Return $"{ProductName}"
    End Function

End Class
Public Class ProductFinaltestingService
    Private Shared Function GetOledbConnectionString() As String
        Return "Provider=Microsoft.ACE.OLEDB.12.0;
                    Data Source=|DataDirectory|\test04102024.accdb;
                    Persist Security Info=False;"
    End Function
    ' ...
    Friend Shared Function GetDistinctProducts() As IEnumerable(Of ProductFinaltesting)
        Dim sql = "SELECT DISTINCT ProductName, Unit,Prp,Prs 
                       FROM Products 
                       ORDER BY ProductName"
        Using _conn = New OleDbConnection(GetOledbConnectionString())
            Return _conn.Query(Of ProductFinaltesting)(sql)
        End Using
    End Function
    Friend Shared Function GetProducts() As IEnumerable(Of ProductFinaltesting)
        Dim sql = "SELECT ProductName, Unit,Prp,Prs 
                       FROM Products 
                       ORDER BY ProductName"
        Using _conn = New OleDbConnection(GetOledbConnectionString())
            Return _conn.Query(Of ProductFinaltesting)(sql)
        End Using
    End Function
    Public Sub UpdateProducts(ByVal Obj As ProductFinaltesting)
        Dim sql = "UPDATE Products Set Unit=@Unit,Prp=@Prp,Prs=@Prs WHERE ProductName=@ProductName;"
        Using _conn = New OleDbConnection(GetOledbConnectionString())
            _conn.Execute(sql, New With {
    Key Obj.Unit,
    Key Obj.Prp,
    Key Obj.Prs,
    Key Obj.ProductName
})
        End Using
    End Sub
End Class

result update code

result update code

result update code 14102024 RESULTCODEUPDATE14102024


Solution

  • Raise an event from the edit form which signals to the main form to update.

    In formproduct:

    Public Event Updated(sender As Object, e As UpdatedEventArgs)
    Public Class UpdatedEventArgs
        Inherits EventArgs
        Public ReadOnly Property Unit As String
        Public ReadOnly Property ProductName As String
        Public ReadOnly Property Prp As Integer
        Public ReadOnly Property Prs As Integer
        Public Sub New(unit As String, productName As String, prp As Integer, prs As Integer)
            Me.Unit = unit
            Me.ProductName = productName
            Me.Prp = prp
            Me.Prs = prs
        End Sub
    End Class
    Private Sub OnUpdated(e As UpdatedEventArgs)
        RaiseEvent Updated(Me, e)
    End Sub
    

    Inside formproduct.BtnUpdate_Click:

    MessageBox.Show(Me, "Successfull")
    loaddata() 
    OnUpdated(New UpdatedEventArgs(txtUnit.text, txtProductName.Text, Prp, Prs))
    

    Inside autocompledatagridview:

    Protected Overrides Sub OnLoad(e As EventArgs)
        MyBase.OnLoad(e)
        updateDataSource()
    End Sub
    
    ' just to make a method that can be called from different places
    Protected Sub updateDataSource()
        dictProducts = ProductFinaltestingService.GetDistinctProducts().
            ToDictionary(Function(p) p.ToString(), Function(p) p)
        BindingSource1 = New BindingSource With {.DataSource = New BindingList(Of ProductFinaltesting)}
        DataGridView1.AutoGenerateColumns = False
        DataGridView1.AllowUserToAddRows = False
        DataGridView1.DataSource = BindingSource1
        DataGridView1.Columns("Unit").ReadOnly = True
        BindingSource1.AddNew()
    End Sub
    
    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
        Dim frm As New formproduct
        AddHandler frm.Updated, AddressOf frmproduct_Updated
        AddHandler frm.FormClosed, Sub() RemoveHandler frm.Updated, AddressOf frmproduct_Updated
        frm.Show()
    End Sub
    
    Private Sub frmproduct_Updated(sender As Object, e As formproduct.UpdatedEventArgs)
        updateDataSource()
    End Sub
    

    You can also take the property from the UpdatedEventArgs and put it back in your main dgv to display the edited item. It looks like you know how to do that.