ListView com DataPager não está funcionando
Pergunta
De tudo que li, parecia que a adição de paginação a um controle ListView deve ser simples morto, mas ele não está funcionando para mim. Depois de adicionar os controles ListView e DataPager à forma e fiação-los juntos, eu estou recebendo um comportamento muito estranho. O DataPager limita corretamente o tamanho da página do ListView, mas clicando nos botões de paginação não afeta o ListView em tudo. Os botões de paginação parecem pensar que estão fazendo eles são trabalho, como o último botão é desativado quando você vai para a última página, etc., mas o ListView nunca muda. Além disso, leva dois cliques no DataPager para obtê-lo a fazer qualquer coisa, ou seja, clicando na última vez não faz nada, mas clicando nele uma segunda vez faz com que o DataPager de reagir como se a última página está agora selecionado.
A única coisa que posso pensar é que eu estou ligando o DataSource em tempo de execução (para um objeto LINQ), não usando um controle LinqDataSource ou qualquer coisa. Alguém viu esse comportamento? Estou fazendo algo errado? Aqui está o código que estou usando:
<asp:DataPager ID="HistoryDataPager" runat="server" PagedControlID="HistoryListView" PageSize="10">
<Fields>
<asp:NextPreviousPagerField ButtonType="Button" ShowFirstPageButton="true" ShowLastPageButton="true" />
</Fields>
</asp:DataPager>
<asp:ListView ID="HistoryListView" runat="server">
...
</asp:ListView>
No code-behind:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not IsPostBack Then
HistoryListView.DataSource = From x in myContext.myTables ...
DataBind()
End If
End Sub
Solução
Dê uma olhada no ListViewPagedDataSource.
private ListViewPagedDataSource GetProductsAsPagedDataSource(DataView dv)
{
// Limit the results through a PagedDataSource
ListViewPagedDataSource pagedData = new ListViewPagedDataSource();
pagedData.DataSource = dv;
pagedData.MaximumRows = dv.Table.Rows.Count;
pagedData.TotalRowCount = dpTop.PageSize;
if (Request.QueryString[dpTop.QueryStringField] != null)
pagedData.StartRowIndex = (Convert.ToInt32(Request.QueryString[dpTop.QueryStringField]) - 1) * dpTop.PageSize;
else
pagedData.StartRowIndex = 0;
return pagedData;
}
No entanto, eu tenho um problema ver a última página. O DataPager salta para a primeira página, mas os dados exibidos na última página.
Outras dicas
Precisamos exibição de lista vincular novamente no evento OnPreRender.
protected override void OnPreRender(EventArgs e)
{
ListView1.DataBind();
base.OnPreRender(e);
}
- Atualização
Depois de trabalhar em algumas exibições de lista com asp.net ajax, eu vi uma solução que faz mais sentido do que o descrito acima. Faria normalmente dados ligamento Listview no método de carregamento da página ou de um manipulador de eventos clique de botão e quando não há volta pós a ligação de dados seriam perdidos como descrito acima no problema. Então, precisamos de dados ligam novamente em propriedades da página mudaram manipulador de eventos para a exibição de lista.
ListView_PagePropertiesChanged(object sender, EventArgs e)
{
ListView.DataSource=someDatasource;
ListView.DataBind()
}
One More Solução , a sua simples, basta entrar "ID" em "query string" a partir do banco de dados, agora definida para a propriedade Pager Controle como [QueryStringField = "ID"] como:
<asp:DataPager ID="DataPagerProducts" runat="server" QueryStringField="ID" PageSize="3">
<Fields>
<asp:NextPreviousPagerField ShowFirstPageButton="True" ShowNextPageButton="False" />
<asp:NumericPagerField />
<asp:NextPreviousPagerField ShowLastPageButton="True" ShowPreviousPageButton="False" />
</Fields>
</asp:DataPager>
Nota:. se não Woking, em seguida, definir também [ PagedControlID="ListView_Name" ]
Bind o listview na pré do DataPager tornar evento não no carregamento da página. Por favor, veja a solução aqui
Além disso, se a fonte de dados do seu ListView é alterado (por exemplo, se a exibição de dados com base em parâmetros de busca), não se esqueça de repor o pager cada vez que a fonte de dados é atualizado. Com um ListView este não é tão simples como controlos alguns outros ligados a dados (por exemplo GridView):
private void ResetListViewPager()
{
DataPager pager = (DataPager)ListViewMembers.FindControl("DataPager1");
if (pager != null)
{
CommandEventArgs commandEventArgs = new CommandEventArgs(DataControlCommands.FirstPageCommandArgument, "");
// MAKE SURE THE INDEX IN THE NEXT LINE CORRESPONDS TO THE CORRECT FIELD IN YOUR PAGER
NextPreviousPagerField nextPreviousPagerField = pager.Fields[0] as NextPreviousPagerField;
if (nextPreviousPagerField != null)
{
nextPreviousPagerField.HandleEvent(commandEventArgs);
}
// THIS COMMENTED-OUT SECTION IS HOW IT WOULD BE DONE IF USING A NUMERIC PAGER RATHER THAN A NEXT/PREVIOUS PAGER
//commandEventArgs = new CommandEventArgs("0", "");
//NumericPagerField numericPagerField = pager.Fields[0] as NumericPagerField;
//if (numericPagerField != null)
//{
// numericPagerField.HandleEvent(commandEventArgs);
//}
}
}
<asp:ListView ID="ListView1" runat="server" DataSourceID="sdsImages">
<ItemTemplate>
<div class="photo sample12">
<asp:Image ID="img_Galerie" runat="server" ImageUrl='<%# "~/imageHandler.ashx?ID=" + Eval("ImageID") %>' />
</div>
</ItemTemplate>
</asp:ListView>
<asp:DataPager ID="DataPager1" runat="server" PagedControlID="ListView1" PageSize="3" QueryStringField="ImageID">
<Fields>
<asp:NextPreviousPagerField ShowFirstPageButton="True" ShowNextPageButton="False" />
<asp:NumericPagerField />
<asp:NextPreviousPagerField ShowLastPageButton="True" ShowPreviousPageButton="False" />
</Fields>
</asp:DataPager>
<asp:SqlDataSource ID="sdsImages" runat="server"
ConnectionString="<%$ ConnectionStrings:DBCS %>"
SelectCommand="SELECT ImageID FROM Images ">
tente o seguinte:
protected void ListView1_PagePropertiesChanging(object sender, PagePropertiesChangingEventArgs e)
{
DataPager1.SetPageProperties(e.StartRowIndex, e.MaximumRows, false);
ListView1.DataSource = productList;
ListView1.DataBind();
DataPager1.DataBind();
}