DataGridView是一个比较常用的控件,下面用一个实例来介绍一下具体的使用过程。
实例中是一个简单的管理学生信息的界面。如下:
下面将从以下几个方面来介绍:
DataGridView的初始化
DataGridView与List实体的绑定;
DataGridView与DataTable的绑定;
DataGridView其他一些需要注意的地方;
DataGridView的初始化
有几种方法可以进行初始化,第一种方法如下:
1: dgv.BorderStyle = BorderStyle.None;
2:
3: DataGridViewImageColumn imgCol = new DataGridViewImageColumn();
4: imgCol.HeaderText = "";
5: imgCol.Image = Properties.Resources._2vgrid;
6: imgCol.Width = 20;
7: dgv.Columns.Add(imgCol);
8:
9: dgv.Columns.Add("StudnetId", "Id");
10: dgv.Columns["StudnetId"].DataPropertyName = "StudnetId";
11: dgv.Columns["StudnetId"].Visible = false;
12:
13: dgv.Columns.Add("StudentName", "学生姓名");
14: dgv.Columns["StudentName"].DataPropertyName = "StudentName";
15: dgv.Columns["StudentName"].Width = 120;
16:
17: dgv.Columns.Add("Age", "年龄");
18: dgv.Columns["Age"].DataPropertyName = "Age";
19: dgv.Columns["Age"].Width = 60;
20:
21: dgv.Columns.Add("Grade", "综合测评分数");
22: dgv.Columns["Grade"].DataPropertyName = "Grade";
23: dgv.Columns["Grade"].Width = 120;
24: DataGridViewCellStyle dataGridViewCellStyle1 = new DataGridViewCellStyle();
25: dataGridViewCellStyle1.Format = "N0";//N0代表不显示小数,因为MetaLength默认是decimal类型的,展示的时候,不需要显示小数位
26: dataGridViewCellStyle1.NullValue = null;
27: dgv.Columns["Grade"].DefaultCellStyle = dataGridViewCellStyle1;
28:
29:
30: dgv.Columns.Add("Major", "专业");
31: dgv.Columns["Major"].DataPropertyName = "Major";
32: dgv.Columns["Major"].Width = 120;
33:
34: dgv.Columns.Add("Remark", "备注");
35: dgv.Columns["Remark"].DataPropertyName = "Remark";
36: dgvStudent.Columns["Remark"].Width = 100;
第二种方法如下:
1: DataGridViewCheckBoxColumn colCheck = new DataGridViewCheckBoxColumn();
2: colCheck.Name = "colCheck";
3: colCheck.Width = 40;
4: colCheck.HeaderText = "查找";
5:
6: DataGridViewTextBoxColumn colField = new DataGridViewTextBoxColumn();
7: colField.Name = "colField";
8: colField.Width = 200;
9: colField.HeaderText = "字段";
10: colField.DataPropertyName = "column_name";
11: colField.ReadOnly = true;
12:
13: DataGridViewComboBoxColumn colOperate = new DataGridViewComboBoxColumn();
14: colOperate.Name = "colOperate";
15: colOperate.Width = 60;
16: colOperate.HeaderText = "表达式";
17: colOperate.DataPropertyName = "Operate";
18: colOperate.Items.AddRange(new string[]{">",">=","=","<=","<"});
19:
20: dgv.Columns.AddRange(new DataGridViewColumn[] {
21: colCheck,
22: colField,
23: colOperate
24: );
用第二种方法初始化的时候,可以加载不同的类型,比如说可以在DataGridView上面加载Combox,CheckBox等等。
DataGridView与List实体的绑定
DataGridView与实体进行绑定时,只需要将每一列的DataPropertyName属性设置为实体的字段属性,然后通过DataSource进行绑定即可。
DataGridView与DataTable的绑定
DataGridView与DataTable可以直接绑定,如果你方法所返回的是一个DataTable,那么不需要初始化DataGridView的列,就可以进行绑定,只不过这时候DataGridView列头上显示的是英文的字段名(也就是select语句里面选出来的字段)。如果你想显示成中文的,那么你就需要初始化这个DataGridView的值,然后把DataPropertyName属性值设置为对应的英文字段即可。
DataGridView与DataTable进行绑定比与实体List进行绑定有一个好处,那就是与DataTable绑定后,你点击列头可以进行排序,而与List绑定后没有这个功能。
如图:
与DataTable绑定:(鼠标放在列头上有一个小三角,点击可以排序)
很多时候,我们都需要进行排序,所以我们一般情况是与DataTable进行绑定,但是有很多时候,我们的方法返回的是一个List实体,这个时候,我们就需要把我们的实体集合转换成DataTable然后再进行绑定。
把List实体转换成DataTable有一个泛型的方法,如下:
1: public static DataSet ConvertToDataSet<T>(IList<T> list)
2: {
3: DataSet ds = new DataSet();
4: DataTable dt = new DataTable(typeof(T).Name);
5: DataColumn column;
6: DataRow row;
7:
8: System.Reflection.PropertyInfo[] myPropertyInfo = typeof(T).GetProperties(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance);
9:
10: // 建立空表
11: if (list == null || list.Count <= 0)
12: {
13: for (int i = 0, j = myPropertyInfo.Length; i < j; i++)
14: {
15: System.Reflection.PropertyInfo pi = myPropertyInfo[i];
16:
17: string name = pi.Name;
18:
19: if (dt.Columns[name] == null)
20: {
21: column = new DataColumn(name, pi.PropertyType);
22: dt.Columns.Add(column);
23: }
24: }
25: }
26: else
27: {
28: foreach (T t in list)
29: {
30: if (t == null)
31: {
32: continue;
33: }
34: row = dt.NewRow();
35: for (int i = 0, j = myPropertyInfo.Length; i < j; i++)
36: {
37: System.Reflection.PropertyInfo pi = myPropertyInfo[i];
38: string name = pi.Name;
39: if (dt.Columns[name] == null)
40: {
41: column = new DataColumn(name, pi.PropertyType);
42: dt.Columns.Add(column);
43: }
44: row[name] = pi.GetValue(t, null);
45: }
46: dt.Rows.Add(row);
47: }
48: }
49:
50: ds.Tables.Add(dt);
51: return ds;
52: }
相反的,有时候,我们需要把一个DataTable转换成一个List实体,下面有一个方法是把一个DataRow转换成一个实体。循环调用这个方法即可。
1: public static T ConvertToEntity<T>(DataRow dr)
2: {
3: // 得到模型的类型
4: Type type = typeof(T);
5: T instance = (T)Activator.CreateInstance(type);
6:
7: PropertyInfo[] pis = type.GetProperties(BindingFlags.Public | BindingFlags.Instance | BindingFlags.SetProperty | BindingFlags.SetField);
8:
9: foreach (PropertyInfo pi in pis)
10: {
11: string strColumnName = pi.Name;
12: if (dr[strColumnName] != DBNull.Value)
13: {
14: pi.SetValue(instance, dr[strColumnName], null);
15: }
16: }
17: return instance;
18: }
DataGridView滚动到选中的行
在使用DataGridView的过程中,如果数据量非常多,当我们增加一条数据的时候,这条数据一般是放在最下面的一行,我们让最下面的一行选中,但是滚动条却不滚动到最后的一行的那个位置。最后发现了原因,那就是滚动条不跟着选中的行滚动,而是跟着选中的单元格滚动,也就是你要设置CurrentCell才能让它滚动到选定的行,用下面的代码即可:(下面代码中的Cells[1],可以把数字1换成具体的列名,换成列名后出错的概率要小一些)
dgvProductType.Rows[selectIndex].Selected = true;
dgvProductType.CurrentCell = dgvProductType.Rows[selectIndex].Cells[1];
DataGridView其他一些需要注意的地方
在使用DataGridView的过程中,还有一些地方需要注意一下,一般在初始化的时候,需要设置以下属性。
1: grid.GridColor = SystemColors.ControlDark;
2: grid.AutoGenerateColumns = false;
3: grid.Columns.Clear();
4: grid.Rows.Clear();
5: grid.MultiSelect = false;
6: grid.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
7: grid.BorderStyle = BorderStyle.Fixed3D;
8: grid.ReadOnly = true;
9: grid.AllowUserToAddRows = false;
特别是最后一个属性,“是否允许用户增加行”,如果允许的话,那么每次你增加一行,它会自动在你下面增加一行,但由于我们每一行第一列都是一个图片,但是它自动帮我们加的一行又没有设置图片,这样就非常难看,如下图:
设置成true后,就没有最后一行,如下图:
另外一个需要注意的地方就是,如果你显示小数的时候,不想显示小数点后面的数字,那么你可以用下面的代码:
1: DataGridViewCellStyle dataGridViewCellStyle1 = new DataGridViewCellStyle();
2: dataGridViewCellStyle1.Format = "N0";//N0代表不显示小数,因为MetaLength默认是decimal类型的,展示的时候,不需要显示小数位
3: dataGridViewCellStyle1.NullValue = null;
4: dgv.Columns["Grade"].DefaultCellStyle = dataGridViewCellStyle1;