简体   繁体   中英

Delete a row in WPF DataGrid

I have a datagrid with a delete icon as one column and update icon as another column. On click of update, the first cell is set on focus.

On click on delete I want to delete that selected row, but I get the error "Operation is not valid while ItemsSource is in use. Access and modify elements with ItemsControl.ItemsSource instead." with the following code:

XAML:

<DataGrid Name="grdList" Margin="3,16,0,5" RowHeight="30" ColumnWidth="*"
          ItemsSource="{Binding  List,Mode=TwoWay}" Width="434" 
          AutoGenerateColumns="False" 
          CanUserAddRows="False" AlternatingRowBackground="#FFB9BBFF">
    <DataGrid.Columns>
        <DataGridTextColumn MinWidth="0" Header="Property"
                            Binding="{Binding Path=Property}"/>

        <DataGridTemplateColumn Header="Update"  MinWidth="50" MaxWidth="50">
            <DataGridTemplateColumn.CellStyle>
                <Style TargetType="DataGridCell">
                    <EventSetter Event="PreviewMouseLeftButtonDown"
                                 Handler="EventSetter_OnHandler"/>
                </Style>
            </DataGridTemplateColumn.CellStyle>
            <DataGridTemplateColumn.CellTemplate>
                <DataTemplate>
                    <Image Source="Icons/Update.jpg"/>
                </DataTemplate>
            </DataGridTemplateColumn.CellTemplate>
        </DataGridTemplateColumn>

        <DataGridTemplateColumn Header="Delete"  MinWidth="50" MaxWidth="50">
            <DataGridTemplateColumn.CellStyle>
                <Style TargetType="DataGridCell">
                    <EventSetter Event="PreviewMouseLeftButtonDown"
                                 Handler="EventSetter_OnHandler"/>
                </Style>
            </DataGridTemplateColumn.CellStyle>
            <DataGridTemplateColumn.CellTemplate>
                <DataTemplate>
                    <Image Source="Icons/Delete.jpg"/>
                </DataTemplate>
            </DataGridTemplateColumn.CellTemplate>
        </DataGridTemplateColumn>
    </DataGrid.Columns>
</DataGrid>

C#:

private void EventSetter_OnHandler(object sender, MouseButtonEventArgs e)
{
    object source = e.OriginalSource;
    if (source.GetType() == typeof(Image))
    {
        grdList.IsReadOnly = false;

        selectedRow = FindParent<DataGridRow>(sender as DependencyObject);

        if (((DataGridCell)sender).Column.Header.ToString().ToUpperInvariant() == "DELETE")
        {
            grdList.Items.Remove(selectedRow);
        }
        else
        {
            DataGridCellsPanel panel = FindVisualChild<DataGridCellsPanel>(selectedRow);

            DataGridCell dgc = panel.Children[0] as DataGridCell; 
            dgc.Focus();
            grdList.BeginEdit();

            e.Handled = true;
        }
    }
}

Also How to add the delete function with the "Delete" key together with the click on the delete cell.

I suspect on Delete ie in EventSetter_OnHandler , you must be removing items from the Items collection of dataGrid. Something like this:

grdList.Items.Remove(someItem);

But as the error is self explanatory

"Operation is not valid while ItemsSource is in use. Access and modify elements with ItemsControl.ItemsSource instead."

You have binded ItemsSource to some collection, so you need to remove item from it. You can't modify the Items collection directly when binding ItemsSource with some collection . It should be something like:

List.Remove(someItem);

尝试这个,

grdList.Items.RemoveAt(grdList.SelectedIndex);

You can bind the SelectedItem of your DataGrid to a property. Then you can call

List.Remove(SelectedDataGridItem);

SelectedDataGridItem is the property which the Selected Item is bound to

I had the same Problem, i solved it so:

yourrowbindingobject row = (yourrowbindingobject)yourdatagrid.SelectedItems[0];

ObservableCollection<yourrowbindingobject> data = (ObservableCollection<yourrowbindingobject>)yourdatagrid.ItemsSource;
data.Remove(row);

I had the same problem when trying to remove a datagrid row using button click, I solved it as below:

Datagrid rows populated by data retrieved from SQL database:

/* Assign ItemsSource of DataGrid. */
dataGridSupplier.ItemsSource = Ldtbl.DefaultView;

 DataRowView dr = dataGridSupplier.SelectedItem as DataRowView;
 DataRow dr1 = dr.Row;

/* Remove selected item from the datagrid after successfully updating database. */
Ldtbl.Rows.Remove(dr1);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM