DataGrid - 更改编辑行为

Gob*_*lin 1 c# wpf datagrid mvvm

我有一个带有一些复杂行为的ChildViewModels的ObservableCollection.

当我去编辑一行时 - DataGrid进入'编辑模式' - 这有效地禁用了当前单元格之外的UI通知,直到提交了行 - 这是预期的行为,更重要的是它可以被更改吗?

例:

public class ViewModel
{
    public ViewModel()
    {
        Childs = new ObservableCollection<ChildViewModel> {new ChildViewModel()};
    }
    public ObservableCollection<ChildViewModel> Childs { get; private set; }
}
public class ChildViewModel : INotifyPropertyChanged
{
    private string _firstProperty;
    public string FirstProperty
    {
        get { return _firstProperty; }
        set
        {
            _firstProperty = value;
            _secondProperty = value;
            OnPropetyChanged("FirstProperty");
            OnPropetyChanged("SecondProperty");
        }
    }

    private string _secondProperty;
    public string SecondProperty
    {
        get { return _secondProperty; }
        set
        {
            _secondProperty = value;
            OnPropetyChanged("SecondProperty");
        }
    }

    private void OnPropetyChanged(string property)
    {
        if (PropertyChanged != null)
            PropertyChanged(this, new PropertyChangedEventArgs(property));
    }
    public event PropertyChangedEventHandler PropertyChanged;
}
Run Code Online (Sandbox Code Playgroud)

在视图中:

<Window.Resources>
    <local:ViewModel x:Key="Data"/>
</Window.Resources>
<DataGrid DataContext="{Binding Source={StaticResource Data}}" ItemsSource="{Binding Childs}"/>
Run Code Online (Sandbox Code Playgroud)

请注意在离开行之前,如何隐藏编辑第一列时的第二个通知.

编辑:实现IEditableObject什么都不做:

public class ChildViewModel : INotifyPropertyChanged,IEditableObject
{
    ...
    private ChildViewModel _localCopy;

    public void BeginEdit()
    {
        _localCopy = new ChildViewModel {FirstProperty = FirstProperty, SecondProperty = SecondProperty};
    }

    public void EndEdit()
    {
        _localCopy = null;
    }

    public void CancelEdit()
    {
        SecondProperty = _localCopy.SecondProperty;
        FirstProperty = _localCopy.FirstProperty;
    }
}
Run Code Online (Sandbox Code Playgroud)

Qua*_*ter 7

此行为是在DataGrid中实现的BindingGroup.DataGrid设置ItemsControl.ItemBindingGroup为将BindingGroup行应用于每一行.它将其初始化MeasureOverride,因此您可以覆盖MeasureOverride并清除它们:

public class NoBindingGroupGrid
    : DataGrid
{
    protected override Size MeasureOverride(Size availableSize)
    {
        var desiredSize = base.MeasureOverride(availableSize);
        ClearBindingGroup();
        return desiredSize;
    }

    private void ClearBindingGroup()
    {
        // Clear ItemBindingGroup so it isn't applied to new rows
        ItemBindingGroup = null;
        // Clear BindingGroup on already created rows
        foreach (var item in Items)
        {
            var row = ItemContainerGenerator.ContainerFromItem(item) as FrameworkElement;
            row.BindingGroup = null;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)


use*_*202 5

这是一个非常老的问题,但是存在一个不需要子类化DataGrid的更好的解决方案。只需在CellEditEnding事件中调用CommitEdit()即可:

bool manualCommit = false;

private void MyDataGrid_CellEditEnding(object sender, DataGridCellEditEndingEventArgs e)
{
    if (!manualCommit)
    {
        manualCommit = true;
        MyDataGrid.CommitEdit(DataGridEditingUnit.Row, true);
        manualCommit = false;
    }
}
Run Code Online (Sandbox Code Playgroud)

  • @ user2190035-它符合MVVM。没有代码中的viewmodel操作。该代码与视图纯粹相关,这是适当的。 (3认同)