今天遇到一个需求,winform 表格(DataGridView)中需要让某些行不能被选中。如下图,默认所有行都能被选中。
表格中的行,可以通过多种方法选中,例如:单击一行可以选中,用ctrl、shift等快捷键也可以选中,单击左上角的一块也能全部选中.
解决的思路是通过控件的事件来做,根据常识,一行的选中或取消选中,肯定会触发一个选中或取消选中的事件,理论上可以在这个事件中将其selected属性置为false即可,
但是对于这些动态加载的行,怎样定义选中事件呢?
答案是无法直接对一行进行操作,而应该通过整个表格来做,也就是定义DataGridView的事件。
思路:
为表格的RowStateChanged事件添加处理方法,实测只要有一行发生变化(显示、隐藏、选中、取消选中等多种情况),就会触发一次该事件。如下图,表格加载的时候,有多少行,就触发多少次该事件。
有了RowStateChange事件,还要配合DataGridViewRowStateChangedEventHandler这个事件处理器,其中自带了DataGridViewRowStateChangedEventArgs这个参数,里面包含了对某一行的引用。
废话不多说,上代码:
dgv.RowStateChanged += new DataGridViewRowStateChangedEventHandler(handleRowState);
//...
/// <summary>
/// 行选中时的处理
/// </summary>
private void handleRowState(Object sender, DataGridViewRowStateChangedEventArgs e)
{
Console.WriteLine("RowStateChanged:" + e.Row.Cells[1].Value);
if (e.Row.Cells[10].Value.Equals("未上传"))
{
e.Row.Selected = false;
}
}
问题解决!
关于RowStateChange事件的补充:
假设目前A行被选中,此时又单击了B行,我们看到的是A行取消选中,B行被选中。实际触发了两次RowStateChange事件,也就是A行的失去选中和B行的被选中这两件事。