Пейджер для DataList.
Как-то мне попался жуткий и громоздкий код пейджера на AspNetMania, от которого мне аж дурно стало и я решил выложить свой вариант. Он существенно короче и вполне нормально работает в нескольких проектах. К тому же, он сделан на бейсике, а не на шарпе. Прежде всего - для чего нужны пейджеры? Странно, но MS оснастил GridView пейджером, а DataList - нет. Между тем, DataList явно более гибкий и удобный инструмент. Ну хотя бы потому, что он позволяет НЕСКОЛЬКО ЭЛЕМЕНТОВ ДАННЫХ РАЗМЕСТИТЬ В ОДНУ СТРОКУ. Примерно так, как на рисунке слева. С другой стороны, стандартный пейджер у GridView - кривой, дальше некуда. Он вычитывает из базы ВСЕ ЭЛЕМЕНТЫ ДАННЫХ для отображения ДАЖЕ ОДНОЙ СТРАНИЦЫ. Странная кривизна. Ну у нас сто тысяч фрагментов данных - длинных-длинных, таких что вычитывание их из на Web-сервер может продолжаться ЧАСАМИ. Но нужна нам 10005-я страничка из пяти таких форагментов - для чего же читать все? Поэтому любой ASP2-программер в первую очередь начинает с написания своего пейджера. Мой пейджер, который без изменения перекочевал во множество моих проектов - перед вами. |
00001: Imports Microsoft.VisualBasic 00002: 00003: ''' <summary> 00004: ''' Формирует тег пейджера 00005: ''' </summary> 00006: Public Class PagerTag 00007: Dim _MaxPageNum As Integer 00008: Dim _CurPageNum As Integer 00009: Dim HtmlTag As New StringBuilder("<div style='font-size:small'>") 00010: 00011: Public ReadOnly Property MaxPageNum() As Integer 00012: Get 00013: Return _MaxPageNum 00014: End Get 00015: End Property 00016: Public ReadOnly Property CurPageNum() As Integer 00017: Get 00018: Return _CurPageNum 00019: End Get 00020: End Property 00021: 00022: Public Function GetHtmlTag(ByVal RecordsetCount As Integer, ByVal CurrentPageNum As Integer) As String 00023: Dim KolPages As Integer = CInt(RecordsetCount \ CInt(System.Configuration.ConfigurationManager.AppSettings("PageSize"))) 00024: If KolPages = 0 Then 00025: 'это вариант, когда все элементы умещаются на первой страничке - просто "0" без ссылки генерить не будем 00026: _MaxPageNum = 0 00027: _CurPageNum = 0 00028: Exit Function 00029: End If 00030: If RecordsetCount Mod CInt(System.Configuration.ConfigurationManager.AppSettings("PageSize")) > 0 Then KolPages += 1 00031: If KolPages = 1 Then 00032: 'это вариант, когда все элементы умещаются на первой страничке - просто "0" без ссылки генерить не будем 00033: _MaxPageNum = 0 00034: _CurPageNum = 0 00035: Exit Function 00036: End If 00037: _MaxPageNum = KolPages 00038: If CurrentPageNum > KolPages - 1 Then 00039: _CurPageNum = KolPages - 2 'уменьшили номер - если вдруг задано больше чем реальное количество страниц 00040: Else 00041: _CurPageNum = CurrentPageNum 00042: End If 00043: For I As Integer = 0 To KolPages - 1 00044: If I <> CurrentPageNum Then 00045: HtmlTag.Append("<a href='" & URL.Parse("p", I.ToString) & "'>" & I.ToString & "</a> ") 'тынц на таком линке будет Not IsPostback 00046: Else 00047: HtmlTag.Append(I.ToString & " ") 00048: End If 00049: Next 00050: HtmlTag.Append("</div>") 00051: Return HtmlTag.ToString 00052: End Function 00053: End Class
Как вы видете, это простейший класс для формирования последовательности чисел, со ссылками, в которых параметром, передаваемым методом GET - выступает номер странички. В отличие от других пейджеров, мне лень было формировать тут троеточие, если страничек слишком много - если вы захотите его добавить - это две строчки. Этот класс удобно в Custom-контрол уложить, чтобы использовать в разных проектах.
Теперь посмотрим, как его вызывать.
00001: 'сначала дернули общее количество данных для пейджера 00002: Dim DV1_c As Data.DataView = GetUserDataCount.Select(New DataSourceSelectArguments) 00003: Dim MyPager As New PagerTag 00004: PagerPlace.Text = MyPager.GetHtmlTag(DV1_c(0)("Count"), GetUserDataStrip.SelectParameters("PageNum").DefaultValue) 00005: 'пейджер определит если задан слишком большой номер и спозиционируеутся на последнюю страничку 00006: If MyPager.CurPageNum < GetUserDataStrip.SelectParameters("PageNum").DefaultValue Then GetUserDataStrip.SelectParameters("PageNum").DefaultValue = MyPager.CurPageNum 00007: 'теперь соственно метаданные о рисунках - текущую порцию для пейджера 00008: GetUserDataStrip.SelectParameters("GroupID").DefaultValue = g.Value 00009: Dim DV1 As Data.DataView = GetUserDataStrip.Select(New DataSourceSelectArguments) 00010: If DV1 IsNot Nothing Then 00011: DataList1.DataSource = DV1 00012: DataList1.DataBind() 00013: Else 00014: Throw New Exception("Не сработал GetUserDataStrip") 00015: End If
Вызов его на страничке заключается в этих 15 строчках. Вы спросите - почему я не вынес их в конструктор этого класса или в сам метод, раз этот код повторяется?
Ответ прост. Я бы хотел конфигурить процедуры даступа к данным с удобным дизайн-таймовым интрефейсом. Да, это противоречит изысканным теоретическим концепциям - но это ЖУТКО УДОБНО. К тому же легко модицифируемо и проверяемо прямо в дизайн-таймовом интерфейсе студии:
|