django项目中通用的分页组件

文章目录

分页组件

应用分页组件,需要以下两个步骤:

  1. 视图函数中:(先获取queryset,将request和queryset传入分页组件对象中,得到生成的html标签)

    python 复制代码
    def customer_list(request):
        # 所有数据
        queryset = models.Customer.objects.filter(active=1).select_related('level')
    
        pager = Pagination(request, queryset)
        context = {
            "queryset": queryset[pager.start:pager.end],
            "pager_string": obj.html()
        }
        return render(request, 'customer_list.html', context)
  2. 在页面上:(直接引用即可)

    html 复制代码
    {% for row in queryset %}
        {{row.id}}
    {% endfor %}
    
    <ul class="pagination">
        {{ pager_string }}
    </ul>

pager组件代码

python 复制代码
import copy
from django.utils.safestring import mark_safe


class Pagination(object):
    """ 分页 """

    def __init__(self, request, query_set, per_page_count=10):
        """
        :param request: 需要用request对象中的GET中的数据进行校验和处理
        :param query_set: 查询数据库得到的查询集
        :param per_page_count: 每页显示几条数据
        """
        # 防止分页操作对后续的使用request.GET有影响
        self.query_dict = copy.deepcopy(request.GET)

        # 将self.query_dict._mutable设置为True:表示query_dict可修改,默认为False
        self.query_dict._mutable = True

        # 拿到总数据据数
        self.query_set = query_set
        total_count = query_set.count()
        self.total_count = total_count

        # 计算出总共有多少页面
        self.total_page, div = divmod(total_count, per_page_count)
        if div:
            self.total_page += 1

        # 对url中的请求参数进行校验处理,决定显示那一页
        page = request.GET.get('page')
        if not page:
            page = 1
        else:
            if not page.isdecimal():
                page = 1
            else:
                page = int(page)
                if page <= 0:
                    page = 1
                else:
                    if page > self.total_page:
                        page = self.total_page
        self.page = page

        # 每页数据条数
        self.per_page_count = per_page_count

        # 页面第一条数据
        self.start = (page - 1) * per_page_count
        # 页面最后一条数据
        self.end = page * per_page_count

    def html(self):
        """
        :return: 生成的当前页面的分页栏html
        """
        pager_list = []
        if not self.total_page:
            return ""

        # 求出生成的分页栏html显示的页面范围
        if self.total_page <= 11:
            # 总页码小于11
            start_page = 1
            end_page = self.total_page
        else:
            # 总页码比较多
            # 判断当前页 <=6: 1~11
            if self.page <= 6:
                start_page = 1
                end_page = 11
            else:
                if (self.page + 5) > self.total_page:
                    # 显示最后10页
                    start_page = self.total_page - 10
                    end_page = self.total_page
                else:
                    # 显示前后5页
                    start_page = self.page - 5
                    end_page = self.page + 5

        # 添加url中的参数,而不是替换:?&age=19&name=123&page=1
        # 首页
        self.query_dict.setlist('page', [1])
        pager_list.append('<li><a href="?{}">首页</a></li>'.format(self.query_dict.urlencode()))

        # 上一页
        if self.page > 1:
            self.query_dict.setlist('page', [self.page - 1])
            pager_list.append('<li><a href="?{}">上一页</a></li>'.format(self.query_dict.urlencode()))

        # 当前页+前后5页
        for i in range(start_page, end_page + 1):
            self.query_dict.setlist('page', [i])
            if i == self.page:
                item = '<li class="active"><a href="?{}">{}</a></li>'.format(self.query_dict.urlencode(), i)
            else:
                item = '<li><a href="?{}">{}</a></li>'.format(self.query_dict.urlencode(), i)
            pager_list.append(item)

        # 下一页
        if self.page < self.total_page:
            self.query_dict.setlist('page', [self.page + 1])
            pager_list.append('<li><a href="?{}">下一页</a></li>'.format(self.query_dict.urlencode()))

        # 尾页
        self.query_dict.setlist('page', [self.total_page])
        pager_list.append('<li><a href="?{}">尾页</a></li>'.format(self.query_dict.urlencode()))

        pager_list.append('<li class="disabled"><a>数据{}条{}页</a></li>'.format(self.total_count, self.total_page))
        pager_string = mark_safe("".join(pager_list))
        return pager_string


  def queryset(self):
      """
      :return: 生成的当前页面的展示数据
      """
      if self.total_count:
          return self.query_set[self.start:self.end]
      return self.query_set

可能用到django框架中QueryDict知识点,可以看看Django框架中的:QueryDict(处理url参数)
若有错误与不足请指出,关注DPT一起进步吧!!!

相关推荐
LZXCyrus27 分钟前
【杂记】vLLM如何指定GPU单卡/多卡离线推理
人工智能·经验分享·python·深度学习·语言模型·llm·vllm
Enougme30 分钟前
Appium常用的使用方法(一)
python·appium
懷淰メ36 分钟前
PyQt飞机大战游戏(附下载地址)
开发语言·python·qt·游戏·pyqt·游戏开发·pyqt5
hummhumm1 小时前
第 22 章 - Go语言 测试与基准测试
java·大数据·开发语言·前端·python·golang·log4j
hummhumm1 小时前
第 28 章 - Go语言 Web 开发入门
java·开发语言·前端·python·sql·golang·前端框架
每天吃饭的羊2 小时前
python里的数据结构
开发语言·python
卡卡_R-Python2 小时前
UCI Heart Disease Data Set—— UCI 心脏病数据集介绍
python·plotly·django·virtualenv·pygame
饮长安千年月2 小时前
浅谈就如何解出Reverse-迷宫题之老鼠走迷宫的一些思考
python·网络安全·逆向·ctf
好看资源平台2 小时前
网络爬虫——爬虫项目案例
爬虫·python
豌豆花下猫2 小时前
Python 潮流周刊#78:async/await 是糟糕的设计(摘要)
后端·python·ai