DataGridView CheckBox 이벤트 변경을 감지하는 방법은 무엇입니까?
winforms 앱이 있고 DataGridView
컨트롤에 포함 된 확인란 이 선택 / 선택 취소 될 때 일부 코드를 트리거하고 싶습니다 . 내가 시도한 모든 이벤트
- 를
CheckBox
클릭 하자마자 선택된 상태가 변경되기 전에 트리거됩니다. CheckBox
초점을 잃은 경우에만 트리거됩니다.
확인 된 상태가 변경된 직후에 트리거되는 이벤트를 찾을 수없는 것 같습니다.
편집하다:
내가 달성하려는 CheckBox
것은 하나 의 체크 상태가 DataGridView
변경되면 다른 두 개의 데이터가 변경 된다는 것 DataGridView
입니다. 그러나 내가 사용한 모든 이벤트, 다른 그리드의 데이터 CheckBox
는 첫 번째 DataGridView
초점을 잃은 후에 만 변경 됩니다.
DatGridView
s CheckedChanged
이벤트 를 처리하려면 먼저 CellContentClick
to fire ( CheckBox
es 현재 상태 가 없습니다 !)를 가져온 다음을 호출해야 CommitEdit
합니다. 그러면 CellValueChanged
작업을 수행하는 데 사용할 수 있는 이벤트가 시작됩니다. 이것은 Microsoft의 감독 입니다. 다음과 같은 일을하십시오 ...
private void dataGridViewSites_CellContentClick(object sender,
DataGridViewCellEventArgs e)
{
dataGridViewSites.CommitEdit(DataGridViewDataErrorContexts.Commit);
}
/// <summary>
/// Works with the above.
/// </summary>
private void dataGridViewSites_CellValueChanged(object sender,
DataGridViewCellEventArgs e)
{
UpdateDataGridViewSite();
}
이게 도움이 되길 바란다.
@Killercam의 솔루션이 작동하는 것을 찾았지만 사용자가 너무 빨리 두 번 클릭하면 약간 이상했습니다. 다른 사람도 그 사건을 발견했는지 확실하지 않습니다. 여기서 다른 해결책을 찾았 습니다 .
데이터 그리드의 CellValueChanged
및 CellMouseUp
. Changhong은 다음과 같이 설명합니다.
"그 이유는 DataGridView가 편집을 완료했다고 생각할 때까지 OnCellvalueChanged 이벤트가 실행되지 않기 때문입니다. OnCellvalueChanged가 각 키 입력에 대해 실행되지는 않기 때문에 TextBox 열에 대해 의미가 있지만 [ 이해하기] CheckBox. "
다음은 그의 예에서 나온 것입니다.
private void myDataGrid_OnCellValueChanged(object sender, DataGridViewCellEventArgs e)
{
if (e.ColumnIndex == myCheckBoxColumn.Index && e.RowIndex != -1)
{
// Handle checkbox state change here
}
}
그리고 체크 박스에 사용자가 필드를 떠날 때까지 기다리지 않고 클릭하면 편집이 완료되었음을 알리는 코드 :
private void myDataGrid_OnCellMouseUp(object sender,DataGridViewCellMouseEventArgs e)
{
// End of edition on each click on column of checkbox
if (e.ColumnIndex == myCheckBoxColumn.Index && e.RowIndex != -1)
{
myDataGrid.EndEdit();
}
}
jsturtevants의 솔루션은 훌륭하게 작동했습니다. 그러나 EndEdit 이벤트에서 처리를 선택했습니다. CellValueChanged 이벤트와 달리 그리드를 채우는 동안 EndEdit 이벤트가 발생하지 않기 때문에이 방법 (내 응용 프로그램에서)을 선호합니다.
내 코드는 다음과 같습니다. 일부는 jsturtevant에서 도난당했습니다.
private void gridCategories_CellEndEdit(object sender, DataGridViewCellEventArgs e)
{
if (e.ColumnIndex == gridCategories.Columns["AddCategory"].Index)
{
//do some stuff
}
}
private void gridCategories_CellMouseUp(object sender, DataGridViewCellMouseEventArgs e)
{
if (e.ColumnIndex == gridCategories.Columns["AddCategory"].Index)
{
gridCategories.EndEdit();
}
}
이것은 또한 키보드 활성화를 처리합니다.
private void dgvApps_CellContentClick(object sender, DataGridViewCellEventArgs e)
{
if(dgvApps.CurrentCell.GetType() == typeof(DataGridViewCheckBoxCell))
{
if (dgvApps.CurrentCell.IsInEditMode)
{
if (dgvApps.IsCurrentCellDirty)
{
dgvApps.EndEdit();
}
}
}
}
private void dgvApps_CellValueChanged(object sender, DataGridViewCellEventArgs e)
{
// handle value changed.....
}
다음 Killercam'answer, 내 코드
private void dgvProducts_CellContentClick(object sender, DataGridViewCellEventArgs e)
{
dgvProducts.CommitEdit(DataGridViewDataErrorContexts.Commit);
}
및 :
private void dgvProducts_CellValueChanged(object sender, DataGridViewCellEventArgs e)
{
if (dgvProducts.DataSource != null)
{
if (dgvProducts.Rows[e.RowIndex].Cells[e.ColumnIndex].Value.ToString() == "True")
{
//do something
}
else
{
//do something
}
}
}
다음은 몇 가지 코드입니다.
private void dgvStandingOrder_CellContentClick(object sender, DataGridViewCellEventArgs e)
{
if (dgvStandingOrder.Columns[e.ColumnIndex].Name == "IsSelected" && dgvStandingOrder.CurrentCell is DataGridViewCheckBoxCell)
{
bool isChecked = (bool)dgvStandingOrder[e.ColumnIndex, e.RowIndex].EditedFormattedValue;
if (isChecked == false)
{
dgvStandingOrder.Rows[e.RowIndex].Cells["Status"].Value = "";
}
dgvStandingOrder.EndEdit();
}
}
private void dgvStandingOrder_CellEndEdit(object sender, DataGridViewCellEventArgs e)
{
dgvStandingOrder.CommitEdit(DataGridViewDataErrorContexts.Commit);
}
private void dgvStandingOrder_CurrentCellDirtyStateChanged(object sender, EventArgs e)
{
if (dgvStandingOrder.CurrentCell is DataGridViewCheckBoxCell)
{
dgvStandingOrder.CommitEdit(DataGridViewDataErrorContexts.Commit);
}
}
셀 편집에 관한 것입니다. 실제로 셀이 편집되지 않은 문제이므로 확인란을 클릭하면 이벤트를 가져 오기 위해 셀 또는 행의 변경 사항을 저장해야이 기능을 사용할 수 있습니다.
datagridview.CommitEdit(DataGridViewDataErrorContexts.CurrentCellChange)
이것으로 다른 이벤트에도 사용할 수 있습니다.
이 문제에 대한 더 간단한 답을 찾았습니다. 나는 단순히 역 논리를 사용합니다. 코드는 VB에 있지만 C #과 크게 다르지 않습니다.
Private Sub DataGridView1_CellContentClick(sender As Object, e As
DataGridViewCellEventArgs) Handles DataGridView1.CellContentClick
Dim _ColumnIndex As Integer = e.ColumnIndex
Dim _RowIndex As Integer = e.RowIndex
'Uses reverse logic for current cell because checkbox checked occures
'after click
'If you know current state is False then logic dictates that a click
'event will set it true
'With these 2 check boxes only one can be true while both can be off
If DataGridView1.Rows(_RowIndex).Cells("Column2").Value = False And
DataGridView1.Rows(_RowIndex).Cells("Column3").Value = True Then
DataGridView1.Rows(_RowIndex).Cells("Column3").Value = False
End If
If DataGridView1.Rows(_RowIndex).Cells("Column3").Value = False And
DataGridView1.Rows(_RowIndex).Cells("Column2").Value = True Then
DataGridView1.Rows(_RowIndex).Cells("Column2").Value = False
End If
End Sub
이것에 대한 가장 좋은 점 중 하나는 여러 이벤트가 필요 없다는 것입니다.
무엇 나를 위해 일한 것은이었다 CurrentCellDirtyStateChanged
과 함께datagridView1.EndEdit()
private void dataGridView1_CurrentCellDirtyStateChanged( object sender, EventArgs e ) {
if ( dataGridView1.CurrentCell is DataGridViewCheckBoxCell ) {
DataGridViewCheckBoxCell cb = (DataGridViewCheckBoxCell)dataGridView1.CurrentCell;
if ( (byte)cb.Value == 1 ) {
dataGridView1.CurrentRow.Cells["time_loadedCol"].Value = DateTime.Now.ToString();
}
}
dataGridView1.EndEdit();
}
코드는 DataGridView에서 반복되며 CheckBox 열이 선택되었는지 확인합니다.
private void dgv1_CellMouseUp(object sender, DataGridViewCellMouseEventArgs e)
{
if (e.ColumnIndex == 0 && e.RowIndex > -1)
{
dgv1.CommitEdit(DataGridViewDataErrorContexts.Commit);
var i = 0;
foreach (DataGridViewRow row in dgv1.Rows)
{
if (Convert.ToBoolean(row.Cells[0].Value))
{
i++;
}
}
//Enable Button1 if Checkbox is Checked
if (i > 0)
{
Button1.Enabled = true;
}
else
{
Button1.Enabled = false;
}
}
}
CellContentClick 이벤트에서 다음 전략을 사용할 수 있습니다.
private void myDataGrid_CellContentClick(object sender, DataGridViewCellEventArgs e)
{
if (e.ColumnIndex == 2)//set your checkbox column index instead of 2
{ //When you check
if (Convert.ToBoolean(myDataGrid.Rows[e.RowIndex].Cells[2].EditedFormattedValue) == true)
{
//EXAMPLE OF OTHER CODE
myDataGrid.Rows[e.RowIndex].Cells[5].Value = DateTime.Now.ToShortDateString();
//SET BY CODE THE CHECK BOX
myDataGrid.Rows[e.RowIndex].Cells[2].Value = 1;
}
else //When you decheck
{
myDataGrid.Rows[e.RowIndex].Cells[5].Value = String.Empty;
//SET BY CODE THE CHECK BOX
myDataGrid.Rows[e.RowIndex].Cells[2].Value = 0;
}
}
}
To do this when using the devexpress xtragrid, it is necessary to handle the EditValueChanged event of a corresponding repository item as described here. It is also important to call the gridView1.PostEditor() method to ensure the changed value has been posted. Here is an implementation:
private void RepositoryItemCheckEdit1_EditValueChanged(object sender, System.EventArgs e)
{
gridView3.PostEditor();
var isNoneOfTheAboveChecked = false;
for (int i = 0; i < gridView3.DataRowCount; i++)
{
if ((bool) (gridView3.GetRowCellValue(i, "NoneOfTheAbove")) && (bool) (gridView3.GetRowCellValue(i, "Answer")))
{
isNoneOfTheAboveChecked = true;
break;
}
}
if (isNoneOfTheAboveChecked)
{
for (int i = 0; i < gridView3.DataRowCount; i++)
{
if (!((bool)(gridView3.GetRowCellValue(i, "NoneOfTheAbove"))))
{
gridView3.SetRowCellValue(i, "Answer", false);
}
}
}
}
Note that because the xtragrid doesnt provide an enumerator it is necessary to use a for loop to iterate over rows.
Removing the focus after the cell value changes allow the values to update in the DataGridView. Remove the focus by setting the CurrentCell to null.
private void DataGridView1OnCellValueChanged(object sender, DataGridViewCellEventArgs dataGridViewCellEventArgs)
{
// Remove focus
dataGridView1.CurrentCell = null;
// Put in updates
Update();
}
private void DataGridView1OnCurrentCellDirtyStateChanged(object sender, EventArgs eventArgs)
{
if (dataGridView1.IsCurrentCellDirty)
{
dataGridView1.CommitEdit(DataGridViewDataErrorContexts.Commit);
}
}
You can force the cell to commit the value as soon as you click the checkbox and then catch the CellValueChanged event. The CurrentCellDirtyStateChanged fires as soon as you click the checkbox.
The following code works for me:
private void grid_CurrentCellDirtyStateChanged(object sender, EventArgs e)
{
SendKeys.Send("{tab}");
}
You can then insert your code in the CellValueChanged event.
I've tried some answers from here, but I've always had some kind of problem (like double clicking or using the keyboard). So, I combined some of them and got a consistent behavior (it's not perfect, but works properly).
void gridView_CellContentClick(object sender, DataGridViewCellEventArgs e) {
if(gridView.CurrentCell.GetType() != typeof(DataGridViewCheckBoxCell))
return;
if(!gridView.CurrentCell.IsInEditMode)
return;
if(!gridView.IsCurrentCellDirty)
return;
gridView.EndEdit();
}
void gridView_CellMouseUp(object sender, DataGridViewCellMouseEventArgs e) {
if(e.ColumnIndex == gridView.Columns["cFlag"].Index && e.RowIndex >= 0)
gridView.EndEdit();
}
void gridView_CellValueChanged(object sender, DataGridViewCellEventArgs e) {
if(e.ColumnIndex != gridView.Columns["cFlag"].Index || e.RowIndex < 0)
return;
// Do your stuff here.
}
참고URL : https://stackoverflow.com/questions/11843488/how-to-detect-datagridview-checkbox-event-change
'Development Tip' 카테고리의 다른 글
SQL Server 2005에서 데이터 손실없이 테이블의 "스키마"를 변경하려면 어떻게해야합니까? (0) | 2020.10.25 |
---|---|
NSString의 일부를 굵게 표시하는 방법은 무엇입니까? (0) | 2020.10.25 |
빈 셀의 테두리를 표시하는 CSS? (0) | 2020.10.25 |
iPhone에서 쓰기 가능한 경로를 얻으려면 어떻게해야합니까? (0) | 2020.10.25 |
트위터 부트 스트랩에서 행 줄 제거 (0) | 2020.10.25 |