2009-01-08 22 views
8

Estoy usando DataGridView en mi aplicación WinForms. Mi objetivo principal es hacer que la tecla Enter no se mueva a la siguiente fila en la grilla. Todavía quiero la tecla Intro para validar y finalizar el modo de edición.¿Puedo hacer que DataGridView.EndEdit active el evento CellValidating?

Encontré this FAQ entry y subgrupo DataGridView para reemplazar a ProcessDialogKey(). Si la tecla presionada es Enter, invoco EndEdit(), de lo contrario, llamo a base.ProcessDialogKey().

Funciona de maravilla, excepto que el evento CellValidating no se activa.

Actualmente, estoy llamando manualmente a mi lógica de validación antes de llamar a EndEdit, pero parece que me falta algo.

Creo que podría llamar a OnCellValidating, pero me preocuparía que me pierda algún otro evento. Lo que realmente quiero es algo de EndEdit() que se comporte como presionar enter en la última fila de una grilla con la adición deshabilitada.

Respuesta

11

CellValidating no recibe una llamada hasta que no cambie la CurrentCell. Así que la forma en que me arriesgué fue cambiar CurrentCell, luego volver al actual.

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

Sí, he visto estrategias similares, pero definitivamente se siente como un obstáculo. Aunque me gusta la idea de establecer CurrentCell en nulo. Creo que los otros ejemplos pasaron a la siguiente fila y luego regresaron. –

+0

dice: 'operación no tuvo éxito, porque el programa no puede confirmar o salir de un cambio de valor de celda' cuando la validación falla no es una solución real – PUG

+0

Ver [respuesta de jaminator] (http: // stackoverflow.com/a/9788083/4794) para una forma de manejar los errores de validación, aunque probablemente quiera establecer el 'ErrorText' de la fila o algo así si la validación falla. –

0

No, pero puede desencadenar manualmente el evento CellValidating. Solo crea los parámetros adecuados. Todos los eventos son una clase que usa el Patrón de Observador, no son diferentes de cualquier otro método. Si eso no funciona, puede crear un evento KeyPress en la celda y emular presionando Enter en la celda, pero eso puede interferir con la interfaz de usuario de los usuarios, simplemente coloque el quilate nuevamente donde estaba.

+0

Por desgracia, la clase EventArgs para el evento CellValidating no tiene un constructor público. –

+0

Por supuesto, puede usar el reflejo para acceder al constructor de todos modos, pero fuera de las pruebas unitarias parece bastante burdo. –

1

gracias por la solución. mi versión es ligeramente diferente a la suya, porque cuando me muevo a la otra celda, y mi código devuelve e.cancel = false en el evento de validación de la celda, se generará un error que dice: "la operación no tuvo éxito, porque el programa no puede confirmar o salir de un cambio de valor de celda ". entonces pongo try catch para superar este problema.

este es mi código:

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 
2

si DataSource de su DataGridView es BindingSouce, hacer esto (poner esto en su Key processing events):

bds.EndEdit(); 

si DataSource de su DataGridView es DataTable:

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

El código de JJO se bloqueará si la celda está en modo de edición. A continuación evita excepción de validación:

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

Fuente: Kennet Harris's answer here

Cuestiones relacionadas