简体   繁体   中英

Stop the row selection change of datagridview in C#

I'm making a program in which we can edit or insert record through data grid view by just pressing the enter key. The problem is that whenever I write a value in any cell and press enter, the row selection changes to the next row.

When I press enter key, i want it to not change the selected row. It should just get out of cell editing or move to the next cell.

I had the same problem on enter press when the row was just selected. I solved it by subtracting one from row index, but how do I solve this with the cell issue?

You would think that there would be a property in the grid to change how the selection moves when the enter key is pressed. Unfortunately, the DataGridView does not have this property. I am guessing a third-party library may have a grid with this feature.

Below is a possible solution taken from an answer by @Cody Gray. DataGridView keydown event not working in C# ... His answer touches on the problem when trying to wire-up the grids KeyDown or other “Key” events that are for the “GRID.” Meaning that when the user is “editing” in a cell, those events will not fire. In most cases, you should use the grids EditingControlShowing event to capture the individual cell key events. This appears simple enough; however, it is unclear “when” this should be done.

Example, using either solution below will work as described by moving the selection horizontally and not vertically when the user presses the enter key… HOWEVER…. this ONLY works IF the user is “editing” a cell when the “Enter” key is pressed. If the user simply “clicks” on a different cell then presses the “Enter” key the selection will move down.

I am confident that you could get this to work for the cases when the cell is NOT being edited. The question I would ask… Is it worth the effort to turn the “Enter” key into a “Tab” key? If you were to implement this beyond the cell being edited, I am confident that you will realize after you implement this that the functionality you just implemented is already available in the “Tab” key. Just a thought on reinventing the wheel.

As Cody's answer alludes to, it is not straight forward to do what you are describing using the “DataGridView” base events. This solution basically creates a Class that inherits from the DataGridView and overrides the grids ProcessCmdKey event. Here you can implement the behavior described, however, as stated above, the horizontal movement will only happen if the cell is being edited.

class MyDataGridView : DataGridView {

  protected override bool ProcessCmdKey(ref System.Windows.Forms.Message msg, System.Windows.Forms.Keys keyData) {
    if ((keyData == (Keys.Enter))) {
      if (this.CurrentCell.IsInEditMode) {
        Point lastPosition = new Point(this.CurrentCell.ColumnIndex, this.CurrentCell.RowIndex);
        if (lastPosition.X == this.ColumnCount - 1) {
          lastPosition.X = 0;
          lastPosition.Y++;
        }
        else {
          lastPosition.X++;
        }
        this.CurrentCell = this.Rows[lastPosition.Y].Cells[lastPosition.X];
      }
    }
    return base.ProcessCmdKey(ref msg, keyData);
  }
}

@Asaf 's answer in the same link above, supplied an example using the grids base events. A full example is below using both approaches. Drop a DataGridView and a myDataGridView onto a form for the code to work properly. Hope this helps.

DataTable GridTable;
DataTable GridTable2;

public Form1() {
  InitializeComponent();
}

private void Form1_Load(object sender, EventArgs e) {
  GridTable = GetTable();
  FillTable(GridTable);
  dataGridView1.DataSource = GridTable;
  GridTable2 = GetTable();
  FillTable(GridTable2);
  myDataGridView1.DataSource = GridTable2;
}

private DataTable GetTable() {
  DataTable dt = new DataTable();
  dt.Columns.Add("Col1", typeof(string));
  dt.Columns.Add("Col2", typeof(string));
  dt.Columns.Add("Col3", typeof(string));
  dt.Columns.Add("Col4", typeof(string));
  return dt;
}

private void FillTable(DataTable dt) {
  for (int i = 0; i < 15; i++) {
    dt.Rows.Add("C1R" + i, "C2R" + i, "C3R" + i, "C4R" + i);
  }
}

private void dataGridView1_EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e) {
  if (e.Control is DataGridViewTextBoxEditingControl) {
    DataGridViewTextBoxEditingControl tb = e.Control as DataGridViewTextBoxEditingControl;
    tb.PreviewKeyDown -= dataGridView1_PreviewKeyDown;
    tb.PreviewKeyDown += dataGridView1_PreviewKeyDown;
  }
}

private void dataGridView1_PreviewKeyDown(object sender, PreviewKeyDownEventArgs e) {
  if (e.KeyData == Keys.Enter) {
    //if (dataGridView1.CurrentCell.IsInEditMode) {
      Point lastPosition = new Point(dataGridView1.CurrentCell.ColumnIndex, dataGridView1.CurrentCell.RowIndex);
      if (lastPosition.X == dataGridView1.ColumnCount - 1) {
        lastPosition.X = 0;
        lastPosition.Y++;
      }
      else {
        lastPosition.X++;
      }
      dataGridView1.CurrentCell = dataGridView1.Rows[lastPosition.Y].Cells[lastPosition.X];
    //}
    //else {
      // good luck here
    //}
  }
}

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