Home
Products
Forums
Help
Publish Article
Go Freelance

Paging In DataList Control

Downloads

If you are seeing this section and do not see download links, this means that you are not logged into our site. If you already are a member, click on the login link and login into site and come back to this page for downloading the control files. If you are not a member, click on registration link to become a Winista member and download the control for free.

DataList paging

ASP.Net provides a very generic but very flexible DataList where you can control the apperance of each item in your data source. This control lacks a very useful feature of paging. Recently for development of product collection page on Pardesi Fashion site we needed to use DataList control. But the product data set was so large that we had no choice to figure out how we are going to do paging to display all the data. This article is explanation of that implementation and we have attached a scaled down version of that implementation as sample project with this article.

Since there is no built in support for paging in DataList that means we have to maintain the curent page index and page index is user asking for. There could be two ways to keep track of this parameter. One would be to handle server side events when user clicks on the pager links and then keep track of the index number. And second would be to pass page index parameters in query string. I prefer using the later approach because it gives an advantage in better search engine optimization (SEO) of your pages. When each pager link is a different URL the search engine gets to spider each page for that dataset.

Implementation

The control is declared on the page as usual DataList controll. To implement paging we added two Panel controls, one at the top of the list and one at the bottom.

<asp:Panel ID="TopPager_Panel" runat="server" BackColor="AliceBlue" 
	BorderWidth="1" BorderStyle="Dashed"></asp:Panel>
 <div>
   <asp:DataList ID="Paging_DataList" runat="server" RepeatDirection="Horizontal" 
	RepeatColumns="2" BackColor="White" BorderColor="#CC9966" BorderStyle="None" 
	BorderWidth="1px" CellPadding="4" GridLines="Both">
	<ItemTemplate>
		<div>
		<span><b>SKU:</b></span> <span><%#Eval("SKU") %></span>
		</div>
		<div>
			<span><b>Name:</b></span> <span><%#Eval("Name") %></span>
		</div>
	</ItemTemplate>
  </asp:DataList>
 </div>
<asp:Panel ID="BottomPager_Panel" runat="server" BackColor="AliceBlue" 
	BorderWidth="1" BorderStyle="Dashed"></asp:Panel>
							

The pager links were built by adding Hyperlink controls at run time inside the Panel controls based on total pages that needed to be displayed.

private void BindPager()
{
  if (_totalPages <= 1)
  {
	TopPager_Panel.Visible = BottomPager_Panel.Visible = false;
	return;
  }

  TopPager_Panel.Visible = BottomPager_Panel.Visible = true;
  for (int i = 0; i < _maxPagesInPager; i++)
  {
	HyperLink topLink = new HyperLink();
	HyperLink bottomLink = new HyperLink();
	LiteralControl topLiteral = new LiteralControl("&nbsp;");
	LiteralControl bottomLiteral = new LiteralControl("&nbsp;");
	topLink.Text = bottomLink.Text = (i + 1).ToString();
	if (_pageIdx != (i + 1))
	{
		topLink.NavigateUrl = bottomLink.NavigateUrl = 
		  String.Format("~/Default.aspx?pageidx={0}", i + 1);
	}

	TopPager_Panel.Controls.Add(topLink);
	TopPager_Panel.Controls.Add(topLiteral);
	BottomPager_Panel.Controls.Add(bottomLink);
	BottomPager_Panel.Controls.Add(bottomLiteral);
  }
}							
							

Aa you can notice from the code snippet above that each pager link passes the page index in query string parameter. This parameter is used to get appropriare slice of the data to bind to the control.

The main part of the implementation is how to get slice of data that will be used to bind with DataList control. There are 2 approaches you can take in this.

  • First approach will be to take advantage of new ROW_NUMBER function in Sql Server 2005 where you can specify in your select statement start and end row index numbers in the dataset. Here is and example from Sql Server 2005 documentation.
    USE AdventureWorks;
    GO
    WITH OrderedOrders AS
    (SELECT SalesOrderID, OrderDate,
    ROW_NUMBER() OVER (order by OrderDate)as RowNumber
    FROM Sales.SalesOrderHeader ) 
    SELECT * 
    FROM OrderedOrders 
    WHERE RowNumber between 50 and 60;
    							
    								
    The advantage of this approach will be that it saves you trouble of caching the whole result set and then slicing it up as nneded. The drawback of this approach is that it puts a dependency on your solution on using Sql Server 2005 which may or may not be an option all the time.
  • Second approaach will be to get slices of the data from your result set and bind that to your control. This approach requires you to fetch the full set before hand and then extract slices from it. But it frees you from dependencies on underlying technologoies. And we took this approach because we host our solutions on different type of database servers.
    private void GetProductsFromDatabase()
    {
    	SqlConnection conn = new SqlConnection(Products_DataSource.ConnectionString);
    	SqlDataAdapter sqlda = 
    	 new SqlDataAdapter(new SqlCommand(Products_DataSource.SelectCommand, conn));
    	_productsDataSet = new DataSet("products_set");
    	sqlda.Fill(_productsDataSet);
    
    	_productsList = new List<Product>();
    	foreach (DataRow dr in _productsDataSet.Tables[0].Rows)
    	{
    		Product prod = Product.LoadFromDataRow(dr);
    		_productsList.Add(prod);
    	}
    }
    
    private List<Product> GetProductsListForPage(int pageIdx, int pageSize, List<Product> srcList)
    {
    	int start = pageIdx * pageSize;
    	int end = start + pageSize;
    	if (end > srcList.Count - 1)
    	{
    		end = srcList.Count - 1;
    	}
    
    	List<Product> slicedList = new List<Product>();
    	for (int i = start; i < end; i++)
    	{
    		slicedList.Add(srcList[i]);
    	}
    	return slicedList;
    }								
    								

Sample Project

The attached sample was created in Visual Studio 2008. We did not use any API from .Net 3.5 or things like that. So if you want to simply port the code over to Visual Studio 2005 or Visual Studio 2003 project, simple copy the page and code file in your project and you should be good to go.

Go Freelance
Home     About us     Contact us    Copyright    Privacy Policy    Return Policy    Advertisers
Copyright © Netomatix