我可以使DataGridView.EndEdit触发CellValidating事件吗?

时间:2009-01-08 01:16:13

标签: c# winforms datagridview

我在WinForms应用程序中使用DataGridView。我的主要目标是使Enter键不移动到网格中的下一行。我仍然希望输入键验证并结束编辑模式。

我找到了this FAQ entry并将子类化的DataGridView重写为ProcessDialogKey()。如果按下的键是Enter,我调用EndEdit(),否则我调用base.ProcessDialogKey()。

它很好用,除了没有触发CellValidating事件。

目前,我只是在调用EndEdit之前手动调用我的验证逻辑,但似乎我错过了一些东西。

我想我可以打电话给OnCellValidating,但后来我担心我错过了其他一些事件。我真正想要的是一些EndEdit()的行为,就像在网格的最后一行按Enter键并添加禁用一样。

5 个答案:

答案 0 :(得分:11)

在更改CurrentCell之前,不会调用CellValidating。所以我解决这个问题的方法就是改变CurrentCell,然后切换回当前的.C。

    protected override bool ProcessDialogKey(Keys keyData)
    {
        if (keyData == Keys.Enter)
        {
            DataGridViewCell currentCell = CurrentCell;
            EndEdit();
            CurrentCell = null;
            CurrentCell = currentCell;
            return true;
        }
        return base.ProcessDialogKey(keyData);
    }

答案 1 :(得分:6)

如果单元格处于编辑模式,JJO的代码将崩溃。以下避免了验证异常:

DataGridViewCell currentCell = AttachedGrid.CurrentCell;
        try
        {             
            AttachedGrid.EndEdit();
            AttachedGrid.CurrentCell = null;
            AttachedGrid.CurrentCell = currentCell;
        }
        catch 
        {
            AttachedGrid.CurrentCell = currentCell;
            AttachedGrid.CurrentCell.Selected = true; 
        }

来源:Kennet Harris's answer here

答案 2 :(得分:2)

如果您的DataGridView的DataSource是BindingSouce,请执行此操作(将其放在Key processing events中):

bds.EndEdit();

如果您的DataGridView的DataSource是DataTable:

this.BindingContext[dgv.DataSource].EndCurrentEdit();

答案 3 :(得分:1)

感谢您的解决方案。 我的版本与你的版本略有不同,因为当我移动到另一个单元格,并且我的代码在单元格验证事件中返回e.cancel = false时,会产生错误,说:“操作没有成功,因为程序无法提交或退出单元格值更改“。所以我把try catch克服了这个问题。

这是我的代码:

Protected Overrides Function ProcessDialogKey(ByVal keyData As System.Windows.Forms.Keys) As Boolean

    Dim key As Keys = (keyData And Keys.KeyCode)

    If key = Keys.Enter Then
        If MyBase.CurrentCell.ColumnIndex = 1 Then
            Dim iRow As Integer = MyBase.CurrentCell.RowIndex

            MyBase.EndEdit()
            Try
                MyBase.CurrentCell = Nothing
                MyBase.CurrentCell = MyBase.Rows(iRow).Cells(1)
                frmFilter.cmdOk_Click(Me, New EventArgs)
            Catch ex As Exception
            End Try

            Return True
        End If
    End If

    Return MyBase.ProcessDialogKey(keyData)
End Function

答案 4 :(得分:0)

不,但您可以手动触发CellValidating事件。只需创建适当的参数。所有事件都是使用观察者模式的类,它们与任何其他方法没有什么不同。如果这不起作用,您可以在单元格上创建一个KeyPress事件并模拟单元格上的Enter键,但这可能会弄乱用户UI,只需将克拉放回原位。

相关问题