MVC项目中的分页实现例子
在开发项目中,写了一个分页实现的例子,现在把源代码贴上,以供以后写代码时参考
在列表的头部,有如下显示,
这个代表一个页面显示10条记录,总共22条记录。
这个是页面底部的显示
那么如何来显示这个分页效果,如何来写一个泛型的通用的分页类实现分页效果呢
第1个类 Paging.cs
这个类包括分页需要的一些变量,包括 页面数PageCount, 上面图片中Previous,Next是否显示, 以及Previous 和 Next对应的链接URL, 以及组成URL的各部分
using System;
using System.Collection.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web; public class Paging
{
public string PrependStr = string.Empty;
public string UrlPart;
public string NextHrefUrl = "";
public string PrevHrefUrl = "";
public bool IsPreviousVisible = false;
public bool IsNextVisible = false; private int _pageCount;
private string _summary; public int[] Numbers {get; set;}
public int PageSize {get; set;} public int PageNo
{
get
{
int pageNo = ;
if(HttpContext.Current.Request["page"] != null && !String.IsNullOrEmpty(HttpContext.Current.Request["page"]))
{
Int32.TryParse(HttpContext.Current.Request["page"], out pageNo);
}
return pageNo; } } public void BindPaging(string urlPart, int recordCount, int pageSize, string prependStr, string summary)
{ _pageCount = (int)Math.Ceiling((decimal)recordCount / pageSize);
UrlPart = urlPart.Split('?')[];
_summary = summary;
PrependStr = prependStr; Numbers = new int[_pageCount];
for(int i = ; i <= _pageCount; i++)
Numbers[i-] = i; PrepagePaging(); } protected void PreparePaging()
{
if(PageNo == )
IsPreviousVisible = false; if (PageNo == && _pageCount == )
{
IsPreviousVisible = false;
IsNextVisible = false; }
else if (PageNo == && PageNo < _pageCount)
{
IsPreviousVisible = false;
IsNextVisible = true;
NextHrefUrl = UrlPart + "?page=" + (PageNo + ).ToString() + PrependStr;
}
else if (PageNo > && PageNo < _pageCount)
{
IsPreviousVisible = true;
PrevHrefUrl = UrlPart + "?page=" + (PageNo - ).ToString() + PrependStr;
IsNextVisible = true;
NextHrefUrl = UrlPart + "?page=" + (PageNo + ).ToString() + PrependStr;
}
else if (PageNo == _pageCount)
{
IsPreviousVisible = true;
PrevHrefUrl = UrlPart + "?page=" + (PageNo - ).ToString() + PrependStr;
IsNextVisible = false;
} } }
上面这个类是分页需要的类,我们当然还需要一个类,来实现分页中的实际页面,也就是PagedResult, 但是因为我们并不知道页面中的具体内容,我们是要做一个通用的例子,所以,使用泛型来实现
第2个类 PagedResult.cs
我们来看看这个类, 我们先定义一个泛型接口 IPagedResult<T>
public interface IPagedResult<T>
{
ICollection<T> Result {get;} int Total {get;}
int CurrentPage {get; set;}
int PageCount {get; set;}
int PageSize {get; set;}
int RowCount {get; set;} bool IsEmpty {get;} void Add(T entity); string GetCurrentPageRangeString(); }
接下来我们再定义一个泛型类PagedResult<T>,来继承这个泛型接口
public class PagedResult<T> : IPagedResult<T>
{
private readonly Collection<T> _result;
private readonly int _total; //依赖注入 构造函数
public PagedResult(IEnumerable<T> result, int total)
{
_result = new Collection<T>(new List<T>(result)); // 这里也是一个小知识点,可以通过new List(IEnumerable) 把IEnumerable类型转为List类型
_total = total; } public PagedResult() : this(new List<T>(),)
{ } public int CurrentPage {get; set;} public bool IsEmpty
{ get
{
return _result.Count == ;
}
} public int PageCount {get; set;}
public int PageSize {get; set;} public ICollection<T> Result
{
get
{
return _result;
}
} public int RowCount {get; set;} public int Total
{
get
{
return _total;
}
} public void Add(T entity)
{
_result.Add(entity);
} public string GetCurrentPageRangeText()
{
CurrentPage = CurrentPage == ? : CurrentPage;
var start = PageSize * (CurrentPage - ) + ;
var end = CurrentPage * PageSize <= Total ? start + PageSize - : Total;
if(Total == )
return "No results found"; string resultsOf = "results of";
string showing = "Showing"; return string.Format("{0} {1} - {2} {3} {4}", showing, start, end, resultsOf, Total); } }
我们还需要一个类,是根据类的结果列表来获取它的页结果列表PagedResult, 这是一个帮助类. 我们给它取名为PaginationHelper.cs
public static class PaginationHelper
{ public static int TotalPage(int total, int rowPerPage)
{
if((total == ) || (rowPerPage == ))
{
return ;
} if((total % rowPerPage) == )
{
return total / rowPerPage; } double result = Convert.ToDouble(total / rowPerPage); result = Math.Ceiling(result); return Convert.ToInt32(result) + ; } public static int StartIndex(int? page, int rowPerPage)
{
return (page.HasValue && (page.Value > )) ? ((page.Value -) * rowPerPage) : ; } public static PagedResult<T> GetPagedResultSet<T>(IEnumerable<T> resultSet, int pageSize, int? currentPage)
{
if(resultSet == null)
return new PagedResult<T>();
var result = new List<T>(resultSet); //这个是把IEnumerable转换为List的方法
var resultCount = result.Count; var startIndex = StartIndex(currentPage, pageSize);
var results = result.Skip(startIndex).Take(pageSize); // 这里放的是当前这个页面的结果列表,因为我们在View中需要列出当前那页的结果列表
var pageTotals = TotalPage(resultCount,pageSize); if(currentPage.HasValue && currentPage > pageTotals)
currentPage = null; var pageResultSet = new PagedResult<T>(results,resultCount)
{
CurrentPage = currentPage.HasValue ? currentPage.Value : ,
PageCount = pageTotals,
PageSize = pageSize }; return pagedResultSet; } public static PagedResult<T> GetPagedResult<T>(Func<IEnumerable<T>> func, int pageSize, int? currentPageIndex) where T : class
{
return GetPagedResultSet(func(), pageSize, currentPageIndex); }
现在我们开始写这个View
写这个图显示的View, 它用的Model 就是上面的Paging.cs, 我们可以看到,这个类Paging.cs没有关注分页的内容是什么,也就是它拥有完全的通用性,无论分页中的内容具体是什么,都可以使用这个来实现这个图示例的分页,那我们现在来看看这个View是怎么写的
Paging.cshtml
@inherits UmbracoViewPage<Paging> @if (Model.Numbers.Length > )
{ <div class="row">
<div class="col-md-6">
<div class="pagination-page">
<ul>
@if (Model.IsPreviousVisible)
{
<li>
<a href="@Model.PrevHref">Previous</a>
</li>
}
@foreach (var number in Model.Numbers)
{
var urlHref = Model.UrlPart + "?page=" + (number).ToString() + Model.PrependStr;
<li class="@(number == Model.PageNo ? "active" : string.Empty)">
<a href="@urlHref">@number</a>
</li>
}
@if (Model.IsNextVisible)
{
<li>
<a href="@Model.NextHref">Next</a>
</li>
}
</ul>
</div>
</div>
</div>
}
这里面还有一些css 我就不贴在这里了,CSS及格式可以自己设置调整
接下来我们就来看看分页内容的实现,也就是说每一页中的内容的实现
我们举个例子,这个列表是News的列表,每页显示10条News,每一条News上的title上是一个链接,点击这个链接会打开一个新的页面(有这个news的URL去链接到另一个页面)来显示这个news的全部内容
显示每页News内容的页面,所使用的Model是NewsSearchResult, 具体如下
NewsSearchResult.cs
public class NewsSearchResult
{ public NewsSearchResult()
{ } public int? PageNo {get; set;} public IPagedResult<NewsResult> NewsResults {get; set;} public Paging Paging {get; set;} }
可以看到,它这里用到了我们上面定义的Paging类,已经接口IPagedResult<T>, 里面又有一个类NewsResult, 定义的是每一个News所包含的一些基本属性(title, url等), 我们来看看它的定义
NewsResult.cs
public class NewsResult
{ public string NewsTitle {get; set;} public string NewsDesc {get; set;} public string NewsDate {get; set;} public string PageUrl {get; set;} }
定义好了model后,我们来看看MVC中的Controller的实现,我们取名为SearchController.cs
SearchController.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc; public class SearchController : Controller
{ public ActionResult Render()
{
return View("NewsListSearch.cshtml", BuildInitialModel()); } public NewsSearchResult BuildInitialModel()
{
NewsSearchResult model = new NewsSearchResult();
model.PageNo = !string.IsNullOrEmpty(Request["page"]) ? Int32.Parse(Request["page"]) : ;
List<NewsResult> newsResults = GetAllNewsList();
Paging paging = new Paging();
IPagedResult<NewsResult> pagedResultSet = null;
pagedResultSet = PaginationHelper.GetPagedResultSet(newsResults,,paging.PageNo); //每页面显示10条结果
paging.BindPaging(Request.RawUrl, pagedResultSet.Total,,string.Empty,string.Empty);
model.Paging = paging;
model.NewsResults = pagedResultSet;
return model; } private List<NewsResult> GetAllNewsList()
{
List<NewsResult> allNewsResults = new List<NewsResult>{ new NewsResult {NewsTitle = "News 1", NewsDesc = "This is the description for News 1", NewsDate = "2017-01", PageUrl = "www.ournews.com/list/news1"},
new NewsResult {NewsTitle = "News 2", NewsDesc = "This is the description for News 2", NewsDate = "2017-02", PageUrl = "www.ournews.com/list/news2"},
new NewsResult {NewsTitle = "News 3", NewsDesc = "This is the description for News 3", NewsDate = "2017-03", PageUrl = "www.ournews.com/list/news3"},
new NewsResult {NewsTitle = "News 4", NewsDesc = "This is the description for News 4", NewsDate = "2017-04", PageUrl = "www.ournews.com/list/news4"},
new NewsResult {NewsTitle = "News 5", NewsDesc = "This is the description for News 5", NewsDate = "2017-05", PageUrl = "www.ournews.com/list/news5"},
new NewsResult {NewsTitle = "News 6", NewsDesc = "This is the description for News 6", NewsDate = "2017-06", PageUrl = "www.ournews.com/list/news6"},
new NewsResult {NewsTitle = "News 7", NewsDesc = "This is the description for News 7", NewsDate = "2017-07", PageUrl = "www.ournews.com/list/news7"},
new NewsResult {NewsTitle = "News 8", NewsDesc = "This is the description for News 8", NewsDate = "2017-08", PageUrl = "www.ournews.com/list/news8"},
new NewsResult {NewsTitle = "News 9", NewsDesc = "This is the description for News 9", NewsDate = "2017-09", PageUrl = "www.ournews.com/list/news9"},
new NewsResult {NewsTitle = "News 10", NewsDesc = "This is the description for News 10", NewsDate = "2017-10", PageUrl = "www.ournews.com/list/news10"},
new NewsResult {NewsTitle = "News 11", NewsDesc = "This is the description for News 11", NewsDate = "2017-11", PageUrl = "www.ournews.com/list/news11"},
new NewsResult {NewsTitle = "News 12", NewsDesc = "This is the description for News 12", NewsDate = "2017-12", PageUrl = "www.ournews.com/list/news12"},
new NewsResult {NewsTitle = "News 13", NewsDesc = "This is the description for News 13", NewsDate = "2018-01", PageUrl = "www.ournews.com/list/news13"},
new NewsResult {NewsTitle = "News 14", NewsDesc = "This is the description for News 14", NewsDate = "2018-02", PageUrl = "www.ournews.com/list/news14"},
new NewsResult {NewsTitle = "News 15", NewsDesc = "This is the description for News 15", NewsDate = "2018-03", PageUrl = "www.ournews.com/list/news15"},
new NewsResult {NewsTitle = "News 16", NewsDesc = "This is the description for News 16", NewsDate = "2018-04", PageUrl = "www.ournews.com/list/news16"},
new NewsResult {NewsTitle = "News 17", NewsDesc = "This is the description for News 17", NewsDate = "2018-05", PageUrl = "www.ournews.com/list/news17"},
new NewsResult {NewsTitle = "News 18", NewsDesc = "This is the description for News 18", NewsDate = "2018-06", PageUrl = "www.ournews.com/list/news18"},
new NewsResult {NewsTitle = "News 19", NewsDesc = "This is the description for News 19", NewsDate = "2018-07", PageUrl = "www.ournews.com/list/news19"},
new NewsResult {NewsTitle = "News 20", NewsDesc = "This is the description for News 20", NewsDate = "2018-08", PageUrl = "www.ournews.com/list/news20"},
new NewsResult {NewsTitle = "News 21", NewsDesc = "This is the description for News 21", NewsDate = "2018-09", PageUrl = "www.ournews.com/list/news21"},
new NewsResult {NewsTitle = "News 22", NewsDesc = "This is the description for News 22", NewsDate = "2018-10", PageUrl = "www.ournews.com/list/news22"},
new NewsResult {NewsTitle = "News 23", NewsDesc = "This is the description for News 23", NewsDate = "2018-11", PageUrl = "www.ournews.com/list/news23"},
new NewsResult {NewsTitle = "News 24", NewsDesc = "This is the description for News 24", NewsDate = "2018-12", PageUrl = "www.ournews.com/list/news24"} } }
}
现在我们来看看这个展示结果页面的View, 也就是每一个页面实际显示的View ===> NewsList.cshtml
@inherits UmbracoViewPage<NewsSearchResult>
<div class="col-md-12">
<div class="support-item" style="padding-bottom:0px">
@foreach (var newsResult in Model.NewsResults.Result)
{
<a href="@newsResult.PageUrl">@newsResult.NewsTitle</a> <div>
<p class="small">@newsResult.NewsDesc</p>
<a href="@newsResult.PageUrl">
<span class="small">Read News ›</span>
</a>
</div>
</div>
</div> }
</div>
</div>
这上面的 Model.NewsResults.Result 里面是当前页面的那个10条News结果
最后,我们来看看页面顶部的 显示当前News记录顺序的View, 就是显示如下图示的View
我们给这个View取名为ShowingDesc.cshtml, 内容如下
@inherits UmbracoViewPage<NewsSearchResult> <div class="col-md-6">
@if (Model.NewsResults.Total > )
{
<p class="pagination-result" style="text-align: left;">
<strong> @Model.NewsResults.GetCurrentPageRangeString() </strong> </p>
} </div>
到目前为止,页面的3部分都有了,分别是 ShowingDesc.cshtml, NewsList.cshtml,Paging.cshtml 我们把它们组成最后的显示页面 NewsListSearch.cshtml
@inherits Umbraco.Web.Mvc.UmbracoViewPage<NewsSearchResult> <div class="col-md-12"> @Html.Partial("ShowingDesc.cshtml", Model)
<hr />
</div> @Html.Partial("NewsList.cshtml", Model)
<div class="col-md-12">
@Html.Partial("Paging.cshtml", Model.Paging)
</div>
最新文章
- lvs+keepalived
- 单表60亿记录等大数据场景的MySQL优化和运维之道
- Open source packages on self-driving car
- 基于案例贯通 Spark Streaming 流计算框架的运行源码
- CreateProcessW记录
- 小生经验贴 --- adapter的数据更新
- Struts2 文件上传,下载,删除
- android图片缓存框架Android-Universal-Image-Loader(二)
- VLV INDEX
- tomcat 7 启动报错:java.lang.NoSuchMethodError: javax.servlet.ServletContext.getSessionCookieConfig()Ljavax/servlet/SessionCookieConfig的解决
- MySQL中MyISAM与InnoDB区别
- jQuery 学习02——效果:隐藏/显示、淡入淡出、滑动、动画、停止动画、Callback、链
- C166 8位字节位运算赋值-代码优化
- sql随机抽取数据
- mininet invalid literal for int() with base 10: &#39;cpu.cfs_period_us:&#39;
- Windows运行命令
- 明明想在学校中请一些同学一起做一项问卷调查,为了实验的客观性,他先用计算机生成了N个1到1000之间的随机整数(N≤1000),对于其中重复的数字,只保留一个,把其余相同的数去掉,不同的数对应着不同的学生的学号。然后再把这些数从
- Go之Channel详解
- 【python】网络编程-UDP协议套接字
- Jmeter使用JDBC链接数据库进行压力测试