none
Move up/down - selected rows in bound DataGridView vb.net

    Question

  • I use databound datagridview. I'm looking to move a row up and down on button click. RemoveAt  & Insert options doesn't work as the grid is databound to DatasSet - DataTable .

    Please advice how to perform this.

    Thanks


    • Edited by PeterWalls Wednesday, January 30, 2013 12:26 PM
    Wednesday, January 30, 2013 12:18 PM

Answers

  • Hello,

    As a DataSet is a container for a collection of DataTable you would reference the table in the DataSet i.e. DataSet1.Tables.Rows

    If you are using VS2010 this project shows how to work via a DataTable, you would adapt by referencing the Table in the DataSet as DataSet1.Tables("SomeTable").Rows. Please note the link points to a project where the only binary is a MS-Access 2007 database file, you need to compile and run it as full source code is provided. Also note after closing the app and restart rows that were moved in the DataGridView or ListBox retain their position which is optional and uses a field specifically for this which if you wanted to do this it would be simple to add a field.

    The image below is one example of three in the project.

    As demo'd I use a BindingSource component which could be taken out of this but I find in windows forms apps a BindingSource provides some additional functionality not easily done w/o a BindingSource

    Below are language extensions used to move rows up/down

    ''' <summary>
    ''' Contains two methods for moving DataRows up/down for a DataGridView,
    ''' two methods for a ListBox
    ''' </summary>
    ''' <remarks></remarks>
    Module LanguageExtensions
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowUp(ByVal sender As DataGridView, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim CurrentColumnIndex As Integer = sender.CurrentCell.ColumnIndex
            Dim NewIndex As Int32 = CInt(IIf(bs.Position = 0, 0, bs.Position - 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(bs.Position)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = NewIndex
            sender.CurrentCell = sender(CurrentColumnIndex, NewIndex)
        End Sub
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowDown(ByVal sender As DataGridView, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim CurrentColumnIndex As Integer = sender.CurrentCell.ColumnIndex
            Dim UpperLimit As Int32 = bs.Count - 1
            Dim NewIndex As Int32 = CInt(IIf(bs.Position + 1 >= UpperLimit, UpperLimit, bs.Position + 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(bs.Position)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = NewIndex
            sender.CurrentCell = sender(CurrentColumnIndex, NewIndex)
        End Sub
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowUp(ByVal Sender As ListBox, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim DisplayText As String = Sender.Text
            Dim SelectedIndex As Int32 = bs.Position
            Dim SelectedItem As String = Sender.SelectedItem.ToString()
            Dim NewIndex As Int32 = CInt(IIf(bs.Position = 0, 0, bs.Position - 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(SelectedIndex)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = bs.Find(Sender.DisplayMember, DisplayText)
            For x As Integer = 0 To dt.Rows.Count - 1
                dt.Rows(x).Item(2) = x
            Next
        End Sub
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowDown(ByVal Sender As ListBox, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim DisplayText As String = Sender.Text
            Dim SelectIndex As Int32 = bs.Position
            Dim SelectedItem As String = Sender.SelectedItem.ToString()
            Dim UpperLimit As Int32 = bs.Count - 1
            Dim NewIndex As Int32 = CInt(IIf(bs.Position + 1 >= UpperLimit, UpperLimit, bs.Position + 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(SelectIndex)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = bs.Find(Sender.DisplayMember, DisplayText)
            For x As Integer = 0 To dt.Rows.Count - 1
                dt.Rows(x).Item(2) = x
            Next
        End Sub
    End Module


    kevininstructor


    Wednesday, January 30, 2013 12:42 PM

All replies

  • Hello,

    As a DataSet is a container for a collection of DataTable you would reference the table in the DataSet i.e. DataSet1.Tables.Rows

    If you are using VS2010 this project shows how to work via a DataTable, you would adapt by referencing the Table in the DataSet as DataSet1.Tables("SomeTable").Rows. Please note the link points to a project where the only binary is a MS-Access 2007 database file, you need to compile and run it as full source code is provided. Also note after closing the app and restart rows that were moved in the DataGridView or ListBox retain their position which is optional and uses a field specifically for this which if you wanted to do this it would be simple to add a field.

    The image below is one example of three in the project.

    As demo'd I use a BindingSource component which could be taken out of this but I find in windows forms apps a BindingSource provides some additional functionality not easily done w/o a BindingSource

    Below are language extensions used to move rows up/down

    ''' <summary>
    ''' Contains two methods for moving DataRows up/down for a DataGridView,
    ''' two methods for a ListBox
    ''' </summary>
    ''' <remarks></remarks>
    Module LanguageExtensions
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowUp(ByVal sender As DataGridView, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim CurrentColumnIndex As Integer = sender.CurrentCell.ColumnIndex
            Dim NewIndex As Int32 = CInt(IIf(bs.Position = 0, 0, bs.Position - 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(bs.Position)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = NewIndex
            sender.CurrentCell = sender(CurrentColumnIndex, NewIndex)
        End Sub
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowDown(ByVal sender As DataGridView, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim CurrentColumnIndex As Integer = sender.CurrentCell.ColumnIndex
            Dim UpperLimit As Int32 = bs.Count - 1
            Dim NewIndex As Int32 = CInt(IIf(bs.Position + 1 >= UpperLimit, UpperLimit, bs.Position + 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(bs.Position)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = NewIndex
            sender.CurrentCell = sender(CurrentColumnIndex, NewIndex)
        End Sub
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowUp(ByVal Sender As ListBox, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim DisplayText As String = Sender.Text
            Dim SelectedIndex As Int32 = bs.Position
            Dim SelectedItem As String = Sender.SelectedItem.ToString()
            Dim NewIndex As Int32 = CInt(IIf(bs.Position = 0, 0, bs.Position - 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(SelectedIndex)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = bs.Find(Sender.DisplayMember, DisplayText)
            For x As Integer = 0 To dt.Rows.Count - 1
                dt.Rows(x).Item(2) = x
            Next
        End Sub
        <System.Diagnostics.DebuggerStepThrough()> _
        <Runtime.CompilerServices.Extension()> _
        Public Sub MoveRowDown(ByVal Sender As ListBox, ByVal bs As BindingSource)
            If Not String.IsNullOrWhiteSpace(bs.Sort) Then
                bs.Sort = ""
            End If
            Dim DisplayText As String = Sender.Text
            Dim SelectIndex As Int32 = bs.Position
            Dim SelectedItem As String = Sender.SelectedItem.ToString()
            Dim UpperLimit As Int32 = bs.Count - 1
            Dim NewIndex As Int32 = CInt(IIf(bs.Position + 1 >= UpperLimit, UpperLimit, bs.Position + 1))
            Dim dt = CType(bs.DataSource, DataTable)
            Dim RowToMove As DataRow = DirectCast(bs.Current, DataRowView).Row
            Dim NewRow As DataRow = dt.NewRow
            NewRow.ItemArray = RowToMove.ItemArray
            dt.Rows.RemoveAt(SelectIndex)
            dt.Rows.InsertAt(NewRow, NewIndex)
            bs.Position = bs.Find(Sender.DisplayMember, DisplayText)
            For x As Integer = 0 To dt.Rows.Count - 1
                dt.Rows(x).Item(2) = x
            Next
        End Sub
    End Module


    kevininstructor


    Wednesday, January 30, 2013 12:42 PM
  • One last thing which I forgot to mention, if there is a sort, you need to remove the sort, otherwise if the move worked it would appear it did not so in the language extensions above I check to see if there is a sort active and if so remove it.

    kevininstructor

    Wednesday, January 30, 2013 12:44 PM
  • Thank you Kevin for your help !
    Wednesday, January 30, 2013 1:09 PM