首 页 | 新 闻 | 技术中心 | 第二书店 | 《程序员》 | 《开发高手》 | 社 区 | 黄 页 | 人 才
移 动专 题SUNIBM微 软微 创精 华Donews人 邮
我的技术中心 
我的分类 我的文档
全部文章 发表文章
专栏管理 使用说明



 RSS 订阅 
最新文档列表
Windows/.NET
.NET  (rss)    
Visual C++  (rss)    
Delphi  (rss)    
Visual Basic  (rss)    
ASP  (rss)    
JavaScript  (rss)    
Java/Linux
Java  (rss)    
Perl  (rss)    
综合
其他开发语言  (rss)    
文件格式  (rss)    
企业开发
游戏开发  (rss)    
网站制作技术  (rss)    
数据库
数据库开发  (rss)    
软件工程
其他  (rss)    

积极原创作者 
tellmenow (22)
cutemouse (22)
softj (78)
iiprogram (69)
qdzx2008 (50)
goodboy1881 (14)
wangchinaking (58)
fancyhf (1)
harrymeng (41)
yjz0065 (113)
CSDN - 文档中心 - .NET 阅读:14890   评论: 0    参与评论
标题   DataGrid使用技巧(二)     选择自 dy_2000_abc 的 Blog
关键字   DataGrid,使用技巧
出处  

       DataGrid使用技巧(二)

------------如何实现多行表头

       有时候听有些朋友抱怨.NET的DataGrid不是很好用。就我个人的体会,DataGrid的功能非常强大,可以使我们随心所欲的完成各种各样的工作,可惜就是实现起来不够简单明了。我对平时经常碰到的一些问题积累了一些解决的方法,现在把它们总结一下供大家参考。
       比较经常碰到的一个问题是:我们希望DataGrid的表头是多行的(图1)。我在网上找了很久也找不到解决的方法,后来想到了DataGrid的CaptionText和CaptionFont属性。于是我就想能不能在Caption的显示区域画出多行表头。下面的示例代码实现了这个想法,结果如图1所示。

       首先需要编写一个类来表示自画的表头,这个类将记录表头的显示文本、图标和属于它管辖的列的信息。

                  //表头类
                  public class TopHeaderColumn
                  {
                         public TopHeaderColumn()
                         {
                         this.columnCollection=new ArrayList();
                         }
                          private string caption;
                        //表头的显示文本 
                          public string Caption
                          {
                            get {return caption;}
                            set {caption=value;}
                          }
                         private ArrayList columnCollection;
                        //用来记录属于表头管辖的各列的信息(通过往集合里添加object)
                         public ArrayList ColumnCollection
                         {
                          get {return this.columnCollection;}
                          set {this.columnCollection=value;}
                          }
                         private int width;
                         //表头的宽度
                         public int Width
                         {
                          get {return width;}
                          set {width=value;}
                          }
                         private Image image=null;
                         //表头的图标
                         public Image Image
                         {
                           get {return image;}
                           set {image=value;}
                          }

                    }
       另外,因为以后的代码需要DataGrid水平滚动条的位置,而DataGrid无法取得水平滚动条的位置,所以需要对DataGrid做一点修改。
                   public class myDataGrid:DataGrid
                   {
  
                       public ScrollBar HScrollBar
                       {
                          get {return this.HorizScrollBar;}
                       }
                   }

       好了,可以工作了。新建一个Window应用程序,加入一个myDataGrid、SqlConnection和ImageList,连接SQL数据库NorthWind。当然,还得加入上面的代码
                  
               namespace WindowsApplication1
              {
                       public class Form1 : System.Windows.Forms.Form
                       {
                          private System.Data.SqlClient.SqlConnection sqlConnection1;
                          private myDataGrid dataGrid1;
                          private ArrayList al;
                          private System.Windows.Forms.ImageList imageList1;
                          \\在InitializeComponent()里加入这一句:this.dataGrid1 = new myDataGrid(),并根据你的需要设置其他的DataGrid属性。注意,CaptionVisible必须设为true,CaptionText=""。
                          private void Form1_Load(object sender, System.EventArgs e)
                          {
                             SqlDataAdapter da=new SqlDataAdapter("select lastname, firstname, Address,City from employees",this.sqlConnection1);
                             DataSet ds=new DataSet();
                             da.Fill(ds,"employees");
                             this.dataGrid1.DataSource=ds;
                             this.dataGrid1.DataMember="employees";

                             //设置DataGrid的各列
                             DataGridTextBoxColumn c1=new DataGridTextBoxColumn();
                             DataGridTextBoxColumn c2=new DataGridTextBoxColumn();
                             DataGridTextBoxColumn c3=new DataGridTextBoxColumn();
                             DataGridTextBoxColumn c4=new DataGridTextBoxColumn();
                             c1.MappingName="lastname";
                             c2.MappingName="firstname";
                             c3.MappingName="Address";
                             c4.MappingName="City";
                             c1.HeaderText="lastname";
                             c2.HeaderText="firstname";
                             c3.HeaderText="Address";
                             c4.HeaderText="City";
               c1.WidthChanged+=new EventHandler(this.abc);//列的宽变动时调整表头宽度
                             c2.WidthChanged+=new EventHandler(this.abc);
                             c3.WidthChanged+=new EventHandler(this.abc);
                             c4.WidthChanged+=new EventHandler(this.abc);

                             DataGridTableStyle dts=new DataGridTableStyle();
                             dts.GridColumnStyles.Add(c1);
                             dts.GridColumnStyles.Add(c2);
                             dts.GridColumnStyles.Add(c3);
                             dts.GridColumnStyles.Add(c4);

                             dts.MappingName="employees";   this.dataGrid1.TableStyles.Add(dts);

                              //建立自画的表头类并将它们加入集合al   
                             al=new ArrayList();
                             TopHeaderColumn tc1=new TopHeaderColumn();
                             tc1.Caption="Name";
                             tc1.Image=this.imageList1.Images[0];
                             tc1.ColumnCollection.Add(0);//记录它管辖的列的index
                             tc1.ColumnCollection.Add(1);
                             tc1.Width=c1.Width+c2.Width;

                            TopHeaderColumn tc2=new TopHeaderColumn();
                             tc2.Caption="Address";
                             tc2.ColumnCollection.Add(2);
                             tc2.ColumnCollection.Add(3);
                             tc2.Width=c3.Width+c4.Width;
   
                             al.Add(tc1);
                             al.Add(tc2);
                             this.dataGrid1.Paint += new System.Windows.Forms.PaintEventHandler(this.dataGrid1_Paint);
                          }

                         private void dataGrid1_Paint(object sender, System.Windows.Forms. PaintEventArgs e)
                        {
                           int x=0;
                           //计算出第一个表头的左边距
                           int left=this.dataGrid1.TableStyles[0].RowHeaderWidth-this.dataGrid1.HScrollBar.Value;
                           //遍历表头集合al,画出表头   
                           foreach (object o in this.al)
                           {
                          //计算出表头文字(文字居中)的左边距
                           x=left+(((TopHeaderColumn)o).Width-Convert.ToInt32(e.Graphics. MeasureString (((TopHeaderColumn)o).Caption, this.dataGrid1.CaptionFont). Width))/2;
                          //完成表头绘制  
                          if (((TopHeaderColumn)o).Image!=null)
                          e.Graphics.DrawImage(((TopHeaderColumn)o).Image,x-imageList1.Images[0].Size.Width,0); 

                           e.Graphics.DrawString(((TopHeaderColumn)o).Caption,this.dataGrid1. CaptionFont,new SolidBrush(this.dataGrid1.CaptionForeColor),x,0);
                           if (x>0)
                           e.Graphics.DrawLine(new Pen(Color.Black,2),left-1,0,left-1,this.dataGrid1.Height);
                           //计算出下一个表头的左边距
                           left+=((TopHeaderColumn)o).Width;
                           }
                           if (x<this.dataGrid1.Width)
                           e.Graphics.DrawLine(new Pen(Color.Black,2),left-1,0,left-1,this.dataGrid1.Height);  
                         }

                     private void abc(object sender,EventArgs e)
                     {
                       //设置表头的宽度
                        foreach (object o in this.al)
                        {
                         ((TopHeaderColumn)o).Width=0;
                        foreach (int i in ((TopHeaderColumn)o).ColumnCollection)
                        {   ((TopHeaderColumn)o).Width+=this.dataGrid1.TableStyles[0].GridColumnStyles[i].Width;
                        }
                        }
                      }

                     private void dataGrid1_Scroll(object sender, System.EventArgs e)
                     {
                       this.dataGrid1.Refresh();
                     }

      上面的代码实现了两层表头,至于三层表头也同理。

      关于如何实现DataGrid多层表头,许多网友都提到,目前好像没有一种特别好的方便的方法。如果那位网友发现了更好的方法,请给我留一条短训告知,谢谢。


相关文章
对该文的评论