2012-01-17 3 views
5

tôi muốn chạy CellEndEdit chỉ khi giá trị của ô được thay đổi, cố gắng đưaLàm thế nào để chạy Run CellEndEdit chỉ khi di ValueChanged trong DataGridView

if (dataGridView.Rows[e.RowIndex].Cells[e.ColumnIndex].Value.ToString() == e.FormattedValue.ToString()) 
      return; 

trong trường hợp CellValidation, sự kiện Validation di động không trở lại nhưng CellEndEdit cũng được được thực hiện và cập nhật, updated date & by trường khi người dùng chỉ chuyển sang chế độ chỉnh sửa và xuất hiện mà không thay đổi ô giá trị.
Vào thời điểm CellEndEdit đạt được CellValue & Formatted Value giống nhau nên không thể đặt điều này trong CellEndEdit.

Một giải pháp tầm thường là đặt cờ trong CellValidation và trả lại CellEndEdit khi cờ được đặt, nhưng điều này dường như là một giải pháp dễ bị lỗi vì có khoảng 10 gird trên biểu mẫu. Vậy 10 lá cờ?

Trả lời

13

Thay vì thực hiện các tác vụ của bạn trong CellEndEdit, hãy đặt chúng trong CellValueChanged. Nó chỉ được kích hoạt khi giá trị của ô được thay đổi. Xin lưu ý rằng nó sẽ kích hoạt khi DataGridViews của bạn ban đầu được điền, nhưng để xử lý điều đó, bạn có thể đặt chỉ một biến nói formInitialized hoặc một cái gì đó, để đảm bảo rằng bạn không thực thi CellEndEdit khi bạn điền dữ liệu vào lưới.

Và để trả lời câu hỏi của bạn, không có cách nào để tìm ra nếu giá trị được thay đổi khi CellEndEdit được kích hoạt, vì nó luôn luôn được kích hoạt khi di chuyển ra khỏi chế độ chỉnh sửa. Giải pháp duy nhất là, như bạn đã đề xuất, để lưu trữ giá trị cũ bên ngoài, nhưng bạn đã nhận thấy lý do tại sao điều đó xấu (mặc dù nó hoạt động thực sự tốt trong hầu hết các trường hợp).

+2

Tốt trả lời, để tránh việc phải duy trì một biến 'formInitialized ', bạn có thể kết nối sự kiện' CellValueChanged 'sau' this.InitializeComponent(); ' gọi trong hàm tạo/điều khiển biểu mẫu. Bằng cách đó bạn sẽ không phải duy trì biến. –

0

Bạn chắc chắn có thể đến đó bằng cách bắt giá trị ô hiện tại trong CellBeginEdit, sau đó so sánh nó với giá trị ô hiện tại trong CellEndEdit. (Hoặc sử dụng thủ thuật CellValidation của bạn.)

Để tránh "nhiều cờ", bạn có thể sử dụng Dictionary<DataGridView,object> để có thể nhập từ điển vào lưới sự kiện hiện tại, sau đó nhận hoặc đặt giá trị phù hợp.

0
MessageBox.Show(dataGridView1.Rows[e.RowIndex].Cells[e.ColumnIndex].Value.ToString()); 
0

Nhưng nếu bạn muốn tính giá trị thay đổi nội dung, bạn có thể sử dụng các vấn đề được đề xuất bởi J.Fisher như:

Private Sub dgvHost_CellBeginEdit(sender As Object, e As System.Windows.Forms.DataGridViewCellCancelEventArgs) Handles dgvHost.CellBeginEdit 
    dgvHost.CurrentCell.Tag = dgvHost.CurrentCell.Value 
End Sub 

Private Sub dgvHost_CellEndEdit(sender As Object, e As System.Windows.Forms.DataGridViewCellEventArgs) Handles dgvHost.CellEndEdit 
    If dgvHost.CurrentCell.Tag = dgvHost.CurrentCell.Value Then Exit Sub 
    dgvHost.CurrentCell.Tag = Nothing 
    'Do something like 
    dgvHost.CurrentCell.Value = MD5(dgvHost.CurrentCell.Value) 
End Sub 
0

tôi đã làm cho nó như vậy:

C#:

private void DynList_RowValidated(object sender, DataGridViewCellEventArgs e) 
{ 
    if (ChangedRow == true) { 
     ChangedRow = false; 
     //Row Changed... 
    } 

} 
bool ChangedRow; 
private void DynList_CellValueChanged(object sender, DataGridViewCellEventArgs e) 
{ 
    ChangedRow = true; 
} 

VB.Net:

Private Sub DynList_RowValidated(ByVal sender As Object, ByVal e As DataGridViewCellEventArgs) 
     If ChangedRow = True Then 
      ChangedRow = False 
      'Row Changed... 
     End If 

End Sub 
Dim ChangedRow As Boolean 
Private Sub DynList_CellValueChanged(ByVal sender As Object, ByVal e As DataGridViewCellEventArgs) 
     ChangedRow = True 
End Sub 

tôi đã cố gắng như 1 giờ để archieve này, bởi vì không ai có một giải pháp cho điều đó, vì vậy tôi nghĩ rằng nó có thể có ích cho người khác