做者:HelloGitHub-追梦人物html
文中所涉及的示例代码,已同步更新到 HelloGitHub-Team 仓库python
在 经过 Django Pagination 实现简单分页 中,咱们实现了一个简单的分页导航。但效果有点差强人意,咱们只能点上一页和下一页的按钮进行翻页。比较完善的分页效果应该像下面这样,但想实现这样一种效果,Django Pagination 内置的 API 已无能为力。接下来咱们将经过拓展 Django Pagination 来实现下图这样比较完善的分页效果。git
一个比较完善的分页效果应该具备如下特性,就像上图展现的那样,不少网站都采用了相似这种的分页导航方式。github
若是须要本身来实现分页效果,咱们会怎么作呢?先来分析一下导航条的组成部分,能够看到整个分页导航条其实能够分红 7 个部分:web
所以咱们的思路是,在视图中依据上述规则生成页码列表,而后在模板中循环显示页码列表就能够了。有了思路,实现起来其实也并不很难。不过对于这类常见需求,别人早就帮咱们实现好了,本着不重复造轮子的原则,直接拿来用就好。django
咱们第一次开始接触 django 第三方拓展,在此以前咱们一直都基于 django 自己咱们提供的功能在开发,然而 django 强大的地方就在于海量的第三方应用供咱们挑选,几乎大部分 web 开发中的需求,django 都能找到他人已经写好的第三方应用,拿来即用。编程
事实上,正确的 django 开发姿式应该是这样的:api
以咱们的分页功能举例:bash
首先咱们上面分析了分页需求的实现。而后我在 GitHub 上经过 django pagination 关键词进行搜索,在比较了多个 star 数比较高的项目后,发现 django-pure-pagination 文档最清晰,使用最简单,所以决定将这个应用集成到咱们的博客来。值得一提的是,尽管这个应用显示做者最后一次更新代码在 4 年前,但我粗略浏览了一下源码,发现其依赖的 django api 4 年来异常稳定,因此确保能在 django 2.2 中使用。app
接下来咱们就来使用它,首先安装它:
$ pipenv install django-pure-pagination
而后将它注册到 INSTALLED_APPS
里:
INSTALLED_APPS = [ # ... 'pure_pagination', # 分页 'blog.apps.BlogConfig', # 注册 blog 应用 'comments.apps.CommentsConfig', # 注册 comments 应用 ]
修改一下 IndexView
,让它继承 django-pure-pagination 提供的 PaginationMixin
,这个混入类将为咱们提供上述提到的分页功能。
class IndexView(PaginationMixin, ListView): model = Post template_name = 'blog/index.html' context_object_name = 'post_list' paginate_by = 10
而后咱们能够在 common.py 配置中配置一下分页的效果,这是 django-pure-pagination 提供的配置项,用于个性化配置分页效果:
# django-pure-pagination 分页设置 PAGINATION_SETTINGS = { 'PAGE_RANGE_DISPLAYED': 4, # 分页条当前页先后应该显示的总页数(两边均匀分布,所以要设置为偶数), 'MARGIN_PAGES_DISPLAYED': 2, # 分页条开头和结尾显示的页数 'SHOW_FIRST_PAGE_WHEN_INVALID': True, # 当请求了不存在页,显示第一页 }
在模板中须要分页的地方,调用分页对象的 render 方法就能够了,好比在 index.html 中:
{% if is_paginated %} {{ page_obj.render }} {% endif %}
注意这里 page_obj 是分页后的对象列表,具体请参考上一篇文章的讲解。render 方法会自动帮咱们渲染一个预先定义好的分页条,至此,分页功能就完成了。
有时候预约义的分页条并不能知足咱们的需求,咱们能够经过自定义的模板来覆盖预约义的模板。django 查找模板的顺序是,首先在项目配置的模板根路径寻找(咱们项目中配的是 templates 文件夹),没有找到的话,再去应用的 templates 目录下寻找。分页模板预约义的路径为 pure_pagination/pagination.html,因此咱们能够在项目模板根路径下创建一个如出一辙的文件结构,这样 django 就会首先找到咱们的模板,从而应用咱们自定义的模板,而不是预约义的模板。
在 templates 目录下新建一个 pure_pagination 目录,而后创建一个 pagination.html 文件。
接下来即是在模板中设置分页导航了,将导航条的七个部分的数据一一展示便可,示例代码以下:
<div class="text-center pagination" style="width: 100%"> <ul> {% if page_obj.has_previous %} <li><a href="?{{ page_obj.previous_page_number.querystring }}" class="prev">‹‹ </a></li> {% else %} <li><span class="disabled prev">‹‹ </span></li> {% endif %} {% for page in page_obj.pages %} {% if page %} {% ifequal page page_obj.number %} <li class="current"><a href="#">{{ page }}</a></li> {% else %} <li><a href="?{{ page.querystring }}" class="page">{{ page }}</a></li> {% endifequal %} {% else %} ... {% endif %} {% endfor %} {% if page_obj.has_next %} <li><a href="?{{ page_obj.next_page_number.querystring }}" class="next"> ››</a> </li> {% else %} <li><span class="disabled next"> ››</span></li> {% endif %} </ul> </div>
多添加几篇文章,在示例中就能够看到分页效果了。要使分页导航更加美观,经过设置其 CSS 样式便可。
『讲解开源项目系列』——让对开源项目感兴趣的人再也不畏惧、让开源项目的发起者再也不孤单。跟着咱们的文章,你会发现编程的乐趣、使用和发现参与开源项目如此简单。欢迎留言联系咱们、加入咱们,让更多人爱上开源、贡献开源~