[.net][ASP.net]Création d’un DataList Paginé
Emilien Martinez | 30 juillet 2008 | 13:52Le datalist, au même titre que le repeater, est un composant très intéressant :
-il permet un binding de données très simple
-Présente des fonctionnalités de personnalisation très avancés.
Seulement, un de ces (rares) inconvénients et de ne pas supporter la pagination. C’est pourquoi j’ai entrepris depuis quelques heures la création d’un user control basé sur un datalist, et supportant une pagination (pour le moment simpliste).
L’objectif étant d’avoir un composant capable de paginer automatiquement un ObjectDataSource.
Pour cela le composant est constitué d’un DataList et de deux boutons. Les propriétés accessibles sont la DataSource ainsi que la taille de page.
Au niveau du fichier .ascx rien de particulier n’est à signaler.
Le composant fonctionne sur un mode itératif :
- A partir de l’objet que retourne l’ObjectDataSource (IEnumerable) on créer une ArratList. J’ai fais ce choix afin de pouvoir rapidement accéder à un indice précis.
- Ensuite l’itération sur l’ArrayList retourne une List contenant les objets d’une seule page. Cette List est passée comme DataSource du DataList.
Le tout étant de recommencer la dernière opération pour un changement de page.
La méthode pour conserver l’index courant n’est vraiment pas élégante (passage de l’index en session). Il serait probablement plus judicieux de passer par une variable de viewstate…
Au final nous avons le fichier suivant :
Note : AppliDocument est une classe métier de l’application qui à servi pour l’exemple.
public partial class dlPaged : System.Web.UI.UserControl
{
private IEnumerable _dataSource;
private int _pageSize;
private ArrayList _iterateList = new ArrayList();
private int _currentPage = 0;
private int _nbPage;
public int PageSize
{
get { return _pageSize; }
set { _pageSize = value; }
}
public IEnumerable DataSource
{
get { return _dataSource; }
set { _dataSource = value; }
}
protected void Page_Load(object sender, EventArgs e)
{
if (IsPostBack)
{
_currentPage = (int)Session[“indexpage”];
this.getSource();
dl.DataSource = this.paginateSource((_currentPage * _pageSize));
dl.DataBind();
_nbPage = (int)Math.Ceiling((decimal)_iterateList.Count % _pageSize)+1;
lbPreced.Visible = true;
lbSuiv.Visible = true;
}
else
{
Session[“indexpage”] = 0;
lbPreced.Visible = false;
lbSuiv.Visible = false;
_nbPage = 0;
}
}
protected void lbPreced_Click(object sender, EventArgs e)
{
if (_currentPage > 0)
{
_currentPage–;
Session[“indexpage”] = _currentPage;
}
dl.DataSource = this.paginateSource((_currentPage * _pageSize));
dl.DataBind();
}
protected void lbSuiv_Click(object sender, EventArgs e)
{
if (_currentPage <= _nbPage)
{
_currentPage++;
Session[“indexpage”] = _currentPage;
}
dl.DataSource = this.paginateSource((_currentPage*_pageSize));
dl.DataBind();
}
private void getSource()
{
foreach (AppliDocument doc in _dataSource)
{
_iterateList.Add(doc);
}
}
private List<AppliDocument> paginateSource(int index)
{
int lastIndex = index + _pageSize;
List<AppliDocument> toReturn = new List<AppliDocument>();
while (index < lastIndex)
{
if (index < _iterateList.Count)
{
toReturn.Add((AppliDocument)_iterateList[index]);
index++;
}
else
{
break;
}
}
Session[“index”] = IndexControl(lastIndex) ;
return toReturn;
}
}
Au final, il ne reste plus qu’à intégrer le composant dans un page : pour cela, il suffit d’enregistrer le composant et de l’ajouter dans la page :
Pour l’enregistrement :
<%@ Register Src=”~/dlPaged.ascx” TagName=”pagedDl” TagPrefix=”zubrowkalib”%>
Pour l’ajout :
<zubrowkalib:pagedDl PageSize=”2″ ID=”dlpage” runat=”server”/>
Enfin, il faut binder la DataSource au composant : il faut pour cela affecter la propriété DataSource du composant lors de l’évènement nécessitant le binding et dans le Page_Load de la page.
this.dlpage.DataSource = AppliDocumentManager.GetDocumentsByKeyword(txtSearch.Text);





