合并的要点:

1.datagid的单元格合并原理是table中tr,td的布局实现;

2.合并的时机实在其datagridcreate事件中实现;

3.认识一个对象TableCellCollection,它是由TableCell组成的集合,TableCell可以看成一个标题.

实现下面的效果;

 

 

前台只有一个空DataGrid,后台源码如下:

 1 private DataTable dt = null;
 2         protected void Page_Load(object sender, EventArgs e)
 3         {
 4             //数据源
 5             dt = new DataTable();
 6             dt.Columns.Add("姓名");
 7             dt.Columns.Add("年龄");
 8             dt.Columns.Add("住址");
 9             dt.Columns.Add("公司");
10             dt.Columns.Add("邮件");
11             dt.Columns.Add("电话");
12 
13             //绑定数据源
14             mydg.DataSource = dt;
15             mydg.DataBind();
16 
17         }
18 
19         protected void mydg_ItemCreated(object sender, DataGridItemEventArgs e)
20         {
21             if (e.Item.ItemType == ListItemType.Header)
22             {
23                 List<CellRule> ils = new List<CellRule>();
24 
25 
26                 TableCellCollection tcc = e.Item.Cells;
27                 tcc.Add(new TableCell());
28                 tcc[0].Text = dt.Columns[0].ColumnName;
29                 tcc[0].Attributes.Add("rowspan", "2");
30                 tcc.Add(new TableCell());
31                 tcc[1].Text = dt.Columns[1].ColumnName;
32                 tcc[1].Attributes.Add("rowspan", "2");
33                 tcc.Add(new TableCell());
34                 tcc[2].Attributes.Add("colspan", "4");
35                 tcc[2].Text = "详细信息</th></tr><tr>";
36                 tcc[2].HorizontalAlign = HorizontalAlign.Center;
37 
38 
39                 tcc.Add(new TableCell());
40                 tcc[3].Text = dt.Columns[2].ColumnName;
41                 tcc.Add(new TableCell());
42                 tcc[4].Text = dt.Columns[3].ColumnName;
43                 tcc.Add(new TableCell());
44                 tcc[5].Text = dt.Columns[4].ColumnName;
45                 tcc.Add(new TableCell());
46                 tcc[6].Text = dt.Columns[5].ColumnName;
47 
48 
49 
50                 //ils.Add(new CellRule(2, 4, "详细信息"));
51                 //OganizeTcc(e.Item.Cells, ils, dt);
52             }
53         }
View Code

 

再将合并表头单元格封装成通用的方法:

优化后的代码如下:

 1 private DataTable dt = null;
 2         protected void Page_Load(object sender, EventArgs e)
 3         {
 4             //数据源
 5             dt = new DataTable();
 6             dt.Columns.Add("姓名");
 7             dt.Columns.Add("年龄");
 8             dt.Columns.Add("住址");
 9             dt.Columns.Add("公司");
10             dt.Columns.Add("邮件");
11             dt.Columns.Add("电话");
12 
13             //绑定数据源
14             mydg.DataSource = dt;
15             mydg.DataBind();
16 
17         }
18 
19         protected void mydg_ItemCreated(object sender, DataGridItemEventArgs e)
20         {
21             if (e.Item.ItemType == ListItemType.Header)
22             {
23                 List<CellRule> ils = new List<CellRule>();
24 
25 
26                 //TableCellCollection tcc = e.Item.Cells;
27                 //tcc.Add(new TableCell());
28                 //tcc[0].Text = dt.Columns[0].ColumnName;
29                 //tcc[0].Attributes.Add("rowspan", "2");
30                 //tcc.Add(new TableCell());
31                 //tcc[1].Text = dt.Columns[1].ColumnName;
32                 //tcc[1].Attributes.Add("rowspan", "2");
33                 //tcc.Add(new TableCell());
34                 //tcc[2].Attributes.Add("colspan", "4");
35                 //tcc[2].Text = "详细信息</th></tr><tr>";
36                 //tcc[2].HorizontalAlign = HorizontalAlign.Center;
37 
38 
39                 //tcc.Add(new TableCell());
40                 //tcc[3].Text = dt.Columns[2].ColumnName;
41                 //tcc.Add(new TableCell());
42                 //tcc[4].Text = dt.Columns[3].ColumnName;
43                 //tcc.Add(new TableCell());
44                 //tcc[5].Text = dt.Columns[4].ColumnName;
45                 //tcc.Add(new TableCell());
46                 //tcc[6].Text = dt.Columns[5].ColumnName;
47 
48 
49 
50                 ils.Add(new CellRule(2, 4, "详细信息"));
51                 OganizeTcc(e.Item.Cells, ils, dt);
52             }
53         }
54 
55         private void OganizeTcc(TableCellCollection tcc, List<CellRule> ils, DataTable dt)
56         {
57             tcc.Clear();
58             ils = ils.OrderBy(p => p.iStart).ToList();
59             List<string> secHeaders = new List<string>();
60             //第一行
61             for (int i = 0, j = 0; j < dt.Columns.Count;)
62             {
63                 if (i >= ils.Count || ils[i].iStart != j)
64                 {
65                     tcc.Add(new TableCell());
66                     tcc[tcc.Count - 1].Text = dt.Columns[j].ColumnName;
67                     tcc[tcc.Count - 1].Attributes.Add("rowspan", "2");
68                     j++;
69                     if (j == dt.Columns.Count)
70                         tcc[tcc.Count - 1].Text = tcc[tcc.Count - 1].Text + "</th></tr><tr>";
71                 }
72                 else 
73                 {
74                     for (int iSec = 0; iSec < ils[i].iCount; iSec++)
75                     {
76                         secHeaders.Add(dt.Columns[j + iSec].ColumnName);
77                     }
78                     tcc.Add(new TableCell());      
79                     tcc[tcc.Count-1].Text = ils[i].strHeaderText;
80                     tcc[tcc.Count - 1].Attributes.Add("colspan", ils[i].iCount.ToString());
81                     tcc[tcc.Count - 1].HorizontalAlign = HorizontalAlign.Center;
82                     j = j + ils[i].iCount;
83                     i++;
84                     if(j == dt.Columns.Count)
85                         tcc[tcc.Count-1].Text = tcc[tcc.Count-1].Text+"</th></tr><tr>";
86                 }
87                 
88             }
89             //第二行
90             foreach (string str in secHeaders)
91             {
92                 tcc.Add(new TableCell());
93                 tcc[tcc.Count - 1].Text = str;
94             }
95         }
View Code

设定合并规则的实体类:

 1 public class CellRule
 2     {
 3         public int iStart { get; set; }
 4         public int iCount { get; set; }
 5         public string strHeaderText { get; set; }
 6         public CellRule(int iStart, int iCount, string strHeaderText)
 7         {
 8             this.iStart = iStart;
 9             this.iCount = iCount;
10             this.strHeaderText = strHeaderText;
11         }
12     }
View Code

 

现在只有一阶转二阶的方法,如果在搞成N阶通用的方法,我是暂时想不到了.就这样.