关于Oxite的分页实现机制

关键的类型:

1、IPageOfList<T>,其定义如下:

public interface IPageOfList<T> : IList<T>
    {
        int PageIndex { get; }
        int PageSize { get; }
        int TotalPageCount { get; }
        int TotalItemCount { get; }
    }

在DDD(领域驱动设计,在没有去看这个之前,我本不知道Oxite整体上为什么会是现在这个样子的)中就是值对象了。这个接口有一个具体实现,是PageOfList<T>,这个类同时集成了List<T>接口,而且,这个类型也是一个值对象,是用来保存本次分页的数据项,还有当前的分页状态的类型。

public PageOfList(IEnumerable<T> items, int pageIndex, int pageSize, int totalItemCount)
        {
            AddRange(items); //List<T>提供的方法,把各个项添加进去,然后设置相应的分页状态。
            PageIndex = pageIndex;
            PageSize = pageSize;
            TotalItemCount = totalItemCount;
            TotalPageCount = (int)Math.Ceiling(totalItemCount / (double)pageSize);
        }

2、IQueryableExtensions

public static class IQueryableExtensions
    {
        public static PageOfList<T> GetPage<T>(this IQueryable<T> query, int pageIndex, int pageSize)
        {
            return new PageOfList<T>(query.Skip(pageIndex * pageSize).Take(pageSize), pageIndex, pageSize, query.Count());
        }
    }

定义了有一个拓展方法,返回对于数据仓储查询结果的一个PageOfList<T> 对象。

3、

接下来我们以Post类型为例,进行如下分析:IPostService的一些方法定义

        IPageOfList<Post> GetPosts(int pageIndex, int pageSize, DateTime? sinceDate);
        IPageOfList<Post> GetPosts(int pageIndex, int pageSize, Tag tag, DateTime? sinceDate);
        IPageOfList<Post> GetPosts(int pageIndex, int pageSize, Area area, DateTime? sinceDate);
        IPageOfList<Post> GetPosts(int pageIndex, int pageSize, ArchiveData archive);
        IPageOfList<Post> GetPosts(int pageIndex, int pageSize, SearchCriteria criteria, DateTime? sinceDate);
        IPageOfList<Post> GetPostsWithDrafts(int pageIndex, int pageSize);

看看IPostServices的定义,我们可以看到,获取Posts列表返回的对象就是IPageOfList<T>类型。其实一开始看到这我觉得很奇怪,怎么IQueryable<T>能转换成IPageOfList<T>类型呢?其实这两个接口都继承了IEnumerable<T>。

接下来,阅读View/Post/List.aspx的代码,我们可以发现,这个页面引用了

Oxite.Model.Extensions和Oxite.Mvc.Extensions这两个拓展方法的命名空间。

Oxite.Mvc.Extensions里面有HtmlHelperExtensions拓展了HtmlHelper,其中,有Pager相关的拓展方法。

我们仔细看,会发现有这么一句,

<%=Html.PageState((IPageOfList<Post>)Model.List, (k, v) => Model.Localize(k, v))%> //{0}-{1} of {2} {0}是当前的页索引,{1}是当前pagesize的最后一页,{2}是总的页数。

<% Html.RenderPartial("PostListMedium"); %> //以中等大小输出Post标题以及ShortBody。

<%=Html.PostListPager((IPageOfList<Post>)Model.List, (k,v) => Model.Localize(k,v)) %> //列出页码,还有显示前一页、下一页

具体例子,参考这个,http://visitmix.com/Articles,也就是mix online,Oxite学习的好地方。

posted @ 2009-12-07 18:37  幸运猴子  阅读(436)  评论(0编辑  收藏  举报