我正在编写一个使用DataGridView的C#应用程序,我想在每次用户更改那里的数据时验证输入。
我开始使用CellValidating事件,该事件具有非常好的CancelEdit()方法,该方法将单元格返回到其先前的值。但是,每次用户离开单元格时都会触发此事件,无论它是否已更改。
CellValueChanged是否支持对前一个值的取消或回滚方法?这样我仍然可以验证数据,但不会浪费时间与不需要它的单元格,但如果数据无效,则不希望牺牲恢复单元格的能力。
以下是一些代码:
private void dataGrid1_CellValidating(object sender, DataGridViewCellValidatingEventArgs e)
{
if(dataGrid1.Columns[e.ColumnIndex].Name == "dateColumn")
{
String input = e.FormattedValue.ToString();
// Split the date from MM/DD/YYYY format
String[] temps = input.Split('/');
try
{
if(temps[2].Length != 4)
MessageBox.Show("The year entered is not the correct length.", "Invalid Year", MessageBoxButtons.OK);
DateTime date = new DateTime(Convert.ToInt32(temps[2]), Convert.ToInt32(temps[0]), Convert.ToInt32(temps[1]));
}
catch (Exception ex) // If exception is thrown, date was invalid
{
MessageBox.Show("The date entered was invalid.", "Invalid date", MessageBoxButtons.OK);
dataGrid1.CancelEdit(); // Set cell value back to what it was prior to user's change
e.Cancel = true; // Have focus stays with this cell rather than move down a row.
}
}
}
答案 0 :(得分:8)
你可以尝试这样的另一种方法:
private void dataGridView1_CellEndEdit(object sender, DataGridViewCellEventArgs e)
{
newvalue = (int)dataGridView1[e.ColumnIndex, e.RowIndex].Value;
}
private void dataGridView1_CellBeginEdit(object sender, DataGridViewCellCancelEventArgs e)
{
oldvalue = (int)dataGridView1[e.ColumnIndex, e.RowIndex].Value;
}
假设它是一个int,如果它的另一个数据类型也可以工作(除了offcourse变量oldvalue和newvalue也必须是那个类型)。
或者通过你的问题,它只是旧值,那么你只需要CellBeginEdit事件,然后在验证事件中使用oldvalue变量。
答案 1 :(得分:5)
恕我直言更好的解决方案,如果拒绝该值,则导致基础DataTable不会被标记为已更改。旧值将自动显示
private void dataGridView_CellEndEdit(object sender, DataGridViewCellEventArgs e)
{
var underlyingDataRow = ((DataRowView)dataGridView.Rows[e.RowIndex].DataBoundItem).Row;
if (DoesNotMeetYourCondition)
{
row.RejectChanges();
}