最简单的方法在DataGrid中自定义样式列(通过继承可以在Datagrid中使用下拉列表框,日期控件等)

在.Net中使用最普遍的表格控件当属DataGrid,初看起来它的功能不强,实际上它是由很多子控件堆砌而成的,如果熟悉其基本事件的处理过程,则可以做出很强大功能的表格控件。

这里是自定义样式列的基类,继承的DataGridTextBoxColumn类
using System;
using System.Collections;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Windows.Forms;

namespace System.Windows.Forms
{
    
/// <summary>
    
/// DataGrid自定义列的基类
    
/// </summary>

    public abstract class DataGridCustomColumn : System.Windows.Forms.DataGridTextBoxColumn
    
{
        
protected Control ctrl;
        CurrencyManager _source;
        
int _iRowNum;

        
public DataGridCustomColumn()
        
{
        }


        
protected void Init()
        
{
            ctrl.Enter
+=new EventHandler(ctrl_Enter);
            ctrl.Leave
+=new EventHandler(ctrl_Leave);
            ctrl.Visible
=false;
        }

        
        
private void ctrl_Enter(object sender, EventArgs e)
        
{
            
if(ReadOnly)
            
{
                Control control
=(Control)sender;
                control.Visible
=false;
            }

            
this.DataGridTableStyle.DataGrid.Select(this.DataGridTableStyle.DataGrid.CurrentRowIndex);

        }


        
private void ctrl_Leave(object sender, EventArgs e)
        
{
            
try
            
{
                
this.SetColumnValueAtRow(_source,_iRowNum ,Value);
            }

            
catch{}
            ctrl.Visible 
= false;
        }

        
public virtual object Value
        
{
            
get{return null;}
            
set{}
        }

        
protected override void Edit(CurrencyManager source, int rowNum, Rectangle bounds, bool readOnly, string instantText, bool cellIsVisible)
        
{
            
if (!this.DataGridTableStyle.DataGrid.Controls.Contains(ctrl)) this.DataGridTableStyle.DataGrid.Controls.Add(ctrl);
            _iRowNum 
= rowNum;
            _source  
= source;
            ctrl.Bounds 
= bounds;
            
            
try
            
{
                Value 
= this.GetColumnValueAtRow(_source, _iRowNum);            
            }

            
catch{}
            ctrl.Visible 
= true;
            ctrl.Focus();
        }

        
public Control control
        
{
            
get
            
{
                
return ctrl;
            }

        }

    }

}

下拉列表框样式类

namespace System.Windows.Forms
{
    
/// <summary>
    
/// 下拉列表框样式列
    
/// </summary>

    public class DataGridComboBoxColumn : System.Windows.Forms.DataGridCustomColumn
    
{
        ComboBox _cbo
=new ComboBox();

        
public DataGridComboBoxColumn()
        
{
            ctrl
=_cbo;
            Init();
        }

        
public override object Value
        
{
            
get
            
{
                
return _cbo.Text;
            }

            
set
            
{
                
try
                
{
                    _cbo.Text 
= (string)value;
                }

                
catch{}
            }

        }

        
public void FillComboBox(string [] comboList)
        
{
            _cbo.Items.AddRange(comboList);
        }

    }

}
日期样式类
namespace System.Windows.Forms
{
    
/// <summary>
    
/// 时间日期样式列
    
/// </summary>

    public class DataGridDatetimeColumn: System.Windows.Forms.DataGridCustomColumn
    
{
        DateTimePicker _dt;
        
public DataGridDatetimeColumn()
        
{
            _dt
=new DateTimePicker();
            ctrl
=_dt;
            Init();
        }

        
public override object Value
        
{
            
get
            
{
                
return _dt.Value;
            }

            
set
            
{
                
try
                
{
                    _dt.Value 
= (DateTime)value;
                }

                
catch{}
            }

        }


    }

}

其它的样式可以自己继承DataGridCustomColumn类,只需要重写一个基类方法,可谓是最简单的在Datagrid中实现自定义样式列的办法。
下面是测试效果的代码
public void GridComboBoxSample()
        
{
            
//生成一个DataTable(表)
            DataTable t = new DataTable("PersonInfo");
            t.Columns.Add(
"Name",typeof(string));
            t.Columns.Add(
"Address",typeof(string));
            t.Columns.Add(
"birthday",typeof(DateTime));
            t.Rows.Add(
new string[]{"yinzx","China","2000-01-01"});
            
            
//生成一个DataGridTableStyle(表样式)
            DataGridTableStyle ts = new DataGridTableStyle();
            
            DataGridTextBoxColumn c1 
= new DataGridTextBoxColumn();
            DataGridComboBoxColumn c2 
= new DataGridComboBoxColumn();  
            DataGridDatetimeColumn c3
=new DataGridDatetimeColumn();
            c1.MappingName 
= c1.HeaderText  = "Name";
            c2.MappingName 
= c2.HeaderText  = "Address";
            c3.MappingName
=c3.HeaderText="birthday";
            c2.FillComboBox(
new string[]{"China","Canada","France"});
            ts.MappingName 
= "PersonInfo";
            ts.GridColumnStyles.Add(c1);
            ts.GridColumnStyles.Add(c2);
            ts.GridColumnStyles.Add(c3);
            
            
//把表及表样式绑定到grd上
            dataGrid1.TableStyles.Add(ts);
            dataGrid1.DataSource 
= t;

注:把ReadOnly属性设置为真,可以实现VB中MSHFlex中的整行选择的效果。

本文参考了网上流行的增加下拉列表框的代码,因被转载的次数太多,无法得知原作者,在这里向原作者致歉。
注:把ReadOnly属性设置为真,可以实现VB中MSHFlex中的整行选择的效果。本文参考了网上流行的增加下拉列表框的代码,因被转载的次数太多,无法得知原作者,在这里向原作者致歉。
posted @ 2005-04-23 11:03  一味  阅读(4111)  评论(4编辑  收藏  举报