Extending the DataGrid Control

Introduction:

In this article, I will explain how to extend the DataGrid class to provide some new functionalities. Building new web controls from scratch is not the best solution in most of cases, just adding some new functionalities to existing .NET Web controls will save you time and provide more stability. In addition, they'll be more compatible with any new versions of .NET framework. 

Functionalities:

  • Add the total number of rows in the DataGrid footer.
  • Add Serial column

Source Code:

            Let's explain the code now step by step, first we have to create the class that will extend the DataGrid class: 

      using System;
     
using
System.Web.UI;
     
using
System.Web.UI.WebControls;
     
using
System.ComponentModel;
     
using
System.Collections ;
     
using
System.Data;
 
      [assembly:TagPrefix("BNaffa.Web.Ui.WebControls","ExtendedDG")]
 

     
namespace
BNaffa.Web.UI.WebControls
            {
      [    
       DefaultProperty("ShowNoRows"),    
 ToolboxData("<{0}:ExtendedDG runat=server></{0}:ExtendedDG>")
      ]
      public class ExtendedDG :
DataGrid
      {
     
// strings constants represent the view state indexes
            const string SHOW_NO_ROWS="ShowNoRows";
            const string NO_ROWS="NoOfRows";
            const string SHOW_SERIAL ="ShowSerial";

                 

     
// Constructor
     
public
ExtendedDG():base()
      {
      }
                       
     
// Properties & Methods go here
      }
 

Then, we'll add the following two properties:  

  • ShowNoRows [true/false]
  • ShowSerial [true/false]

         [Bindable(true),
             Category("Appearance")
            ]
            public bool
ShowNoRows
            {
                 
get
                  {
                  return Convert.ToBoolean(ViewState[SHOW_NO_ROWS]);
                  }
 
                 
set
                  {
                        ViewState[SHOW_NO_ROWS]= value;
                  }
            }
 
            [Bindable(true),
             Category("Appearance")
            ]
            public bool
ShowSerial
            {
                 
get
                  {
                  return Convert.ToBoolean(ViewState[SHOW_SERIAL]);
                  }
 
                 
set
                  {
                        ViewState[SHOW_SERIAL]= value;
                  }
            }
                   

 This private function  will check if we are in the design mode or in runtime mode:                                   

         private bool IsInDesignMode()
            {
                  if (this.Site != null)
                        return this.Site.DesignMode;
                  return false;
                 
            }
 

Total Number Of Rows Functionality:

Now we want to know the number of rows for current DataSource. Ok, how do we get that? One of solutions is to cast the data source property for the data grid to a data set or data table and get the number of rows. But I don't prefer this way!! I will give you a short way without casting cost.

We will override the method CreateColumnSet which be called when you invoke the method DataBind

protected override ArrayList CreateColumnSet
          
(PagedDataSource dataSource, bool useDataSource)

      {
      if (dataSource != null)
            ViewState[NO_ROWS] = dataSource.DataSourceCount;
            return base.CreateColumnSet (dataSource, useDataSource);
      }

As you see, this function will receive an object of type PagedDataSource, this object contains a DataSourceCount property,

Then we will save this number in the ViewState collection. Using this method, you can get the data source count without casting and with any type of data sources [DataSet, DataView, DataTable, ArrayList, etc...]

Now we will override the method OnItemCreated, to add the total number of rows in the DataGrid footer:

protected override void OnItemCreated(DataGridItemEventArgs e)
            {
                  base.OnItemCreated (e);
 
                  if (!IsInDesignMode())
// Only in Runtime Mode
                  {
                        if (e.Item.ItemType == ListItemType.Footer)
                        {
                              if(ShowNoRows && ShowFooter )
                              {
                              if(e.Item.Cells.Count > 0)
                              {
                              e.Item.Cells[0].Text = ViewState[NO_ROWS] + " Rows.";
                              }
                              }
                        }
                  }    
            }
 

Serial Column Functionality: 

Before writing the serial number to the DataGrid, we have to add a template column for the serial field, so we must have this class which implements the interface ITemplate and the method InstantiateIn:

      public class MyColumn:ITemplate
            {
                  public void InstantiateIn ( Control container )
                  {
                       
                  }    
            }
 

We will add this serial column in the OnOnit Method which handles the DataGrid initiation process:           

      protected override void OnInit(EventArgs e)
            {
                  base.OnInit (e);
                  if (! IsInDesignMode())
// Only in Runtime Mode
                  {
                        TemplateColumn tmpCol new TemplateColumn();
                        MyColumn myCol   new MyColumn();
                        tmpCol.ItemTemplate = myCol;
                        this.Columns.Add(tmpCol);                      
                  }
      }
 

Now we have to add the serials to the new Column, we will add another fragment code to the previous overridden method OnItemCreated, so it will be like this: 

protected override void OnItemCreated(DataGridItemEventArgs e)
            {
                  base.OnItemCreated (e);
                  if (!IsInDesignMode())
// Only in Runtime Mode
                  {
                        if (e.Item.ItemType == ListItemType.Footer)
                        {
                              if(ShowNoRows && ShowFooter )
                              {
                              if(e.Item.Cells.Count > 0)
                              {
                              e.Item.Cells[0].Text = ViewState[NO_ROWS] + " Rows.";
                              }
                              }
                        }
                        if (e.Item.ItemType == ListItemType.Header)
                        {
                              if(ShowSerial && ShowHeader )
                              {
                                    e.Item.Cells[0].Text = "#";
                              }
                        }

                        else
if (e.Item.ItemType == ListItemType.Item ||
                        e.Item.ItemType
== ListItemType.AlternatingItem )

                        {
                        if(ShowSerial)
                        {

                        e.Item.Cells
[0].Text= (e.Item.ItemIndex +
                        (this.PageSize*this.CurrentPageIndex ) + 1 ).ToString();
                        }
                        }
                  }    
}
                                

The important thing here is the equation that calculates the current row number, we will consider the current page index to work properly with DataGrid paging (e.Item.ItemIndex + (this.PageSize * this.CurrentPageIndex ) + 1 )    

Now you can compile the project and use the assembly to add new control to your toolbox tab in Visual Studio.NET., and you can use the new DatarGrid and set these properties ShowNoSerial, ShowSerial to true to show this functionality.

 

 

Download Source Code  and Sample!  

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值