Skip to content

DevExpress-Examples/winforms-grid-reorder-tileview-cards-sql

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

19 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

WinForms Data Grid - How to avoid data conflicts when users drag cards of a TileView connected to a SQL source

When you drag-and-drop cards of a TileView connected to a SQL data source, a record index collision may occur. Moving a card marks the data source record as "to be removed", and a new record (with an updated data source index) is created instead. The previous record is not removed. As a result, the data row is duplicated.

This example shows how to avoid this issue. Create a column in the data source to store the position of cards within their groups. Update the position of a card every time the user drags the card.

// Sort by the "IndexInGroup" column
colIndexInGroup.SortOrder = DevExpress.Data.ColumnSortOrder.Ascending;
tileView1.BeforeItemDrop += TileView1_BeforeItemDrop;

void TileView1_BeforeItemDrop(object sender, BeforeItemDropEventArgs e) {
    e.Handled = true;
    // Leave data source indexes as is
    e.NewListSourceRowIndex = e.ListSourceRowIndex;

    var view = sender as TileView;
    var column = view.Columns["IndexInGroup"];

    /* Assign new IndexInGroup column values for all cards
    that are already in the target group */
    if(e.NewGroupRowHandle != GridControl.InvalidRowHandle) {
        int childRowCount = view.GetChildRowCount(e.NewGroupRowHandle);
        for(int n = 0; n < childRowCount; n++) {
            int rowHandle = view.GetChildRowHandle(e.NewGroupRowHandle, n);
            // Skip the TargetIndexInGroup - this index must belong to the dragged card
            int index = n >= e.TargetIndexInGroup ? n + 1 : n;
            view.SetRowCellValue(rowHandle, column, index);
        }
    }

    // Assign the TargetIndexInGroup value to the "IndexInGroup" cell of the dragged card
    view.SetRowCellValue(e.RowHandle, column, e.TargetIndexInGroup);
    // Assign the new "colGroupId" column value to the dragged card
    view.SetRowCellValue(e.RowHandle, view.ColumnSet.GroupColumn, e.NewGroupColumnValue);
}
' Sort by the "IndexInGroup" column
colIndexInGroup.SortOrder = DevExpress.Data.ColumnSortOrder.Ascending

AddHandler tileView1.BeforeItemDrop, AddressOf TileView1_BeforeItemDrop

Private Sub TileView1_BeforeItemDrop(ByVal sender As Object, ByVal e As BeforeItemDropEventArgs)
    e.Handled = True
    ' Leave data source indexes as is
    e.NewListSourceRowIndex = e.ListSourceRowIndex

    Dim view = TryCast(sender, TileView)
    Dim column = view.Columns("IndexInGroup")

      Assign new IndexInGroup column values for all cards
     that are already in the target group 
    If e.NewGroupRowHandle <> GridControl.InvalidRowHandle Then
        Dim childRowCount As Integer = view.GetChildRowCount(e.NewGroupRowHandle)
        For n As Integer = 0 To childRowCount - 1
            Dim rowHandle As Integer = view.GetChildRowHandle(e.NewGroupRowHandle, n)
            ' Skip the TargetIndexInGroup - this index must belong to the dragged card
            Dim index As Integer = If(n >= e.TargetIndexInGroup, n + 1, n)
            view.SetRowCellValue(rowHandle, column, index)
        Next n
    End If

    ' Assign the TargetIndexInGroup value to the "IndexInGroup" cell of the dragged card
    view.SetRowCellValue(e.RowHandle, column, e.TargetIndexInGroup)
    ' Assign the new "colGroupId" column value to the dragged card
    view.SetRowCellValue(e.RowHandle, view.ColumnSet.GroupColumn, e.NewGroupColumnValue)
End Sub

Files to Review

Documentation