Django 2.0 學習(19):Django 分頁器

Django 分頁器

要使用Django實現分頁功能,必須從Django中導入Paginator模塊(painator - 分頁器)
views.py
from django.shortcuts import render
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from BookSite.models import *css

def index(request):
"""
批量導入數據
book_list = []
for i in range(100):
book_list.append(Book(title="book"+str(i), price=30+i**2))
Book.objects.bulk_create(book_list)
"""html

"""
分頁器的使用
book_list = Book.objects.all()
paginator = Paginator(book_list, 10)
print("count:", paginator.count)        # 總數居
print("num_pages", paginator.num_pages)     # 總頁數
print("page_range", paginator.page_range)   # 頁面的列表

page_one = paginator.page(1)        # 第一頁的page對象
for i in range(page_one):           # 遍歷第1頁的全部數據對象
    print(i)
print(page_one.object_list)         # 第1頁全部數據

page_two = paginator.page(2)
print(page_two.has_next())                  # 是否有下一頁
print(page_two.next_page_number())          # 下一頁的頁碼
print(page_two.has_previous())              # 是否有上一頁
print(page_two.previous_page_number())      # 上一頁的頁碼

# 拋出錯誤
page = paginator.page(12)               # Error:EmptyPage
page = paginator.page("z")              # Error:PageNotAnInteger
"""

book_list = Book.objects.all()
paginator = Paginator(book_list, 10)
page = request.GET.get("page", 1)
current_page = int(page)

try:
    print(page)
    book_list = paginator.page(page)
except PageNotAnInteger:
    book_list = paginator.page(1)
except EmptyPage:
    book_list = paginator.page(paginator.num_pages)

return render(request, "index.html", {
    "book_list": book_list,
    "paginator": paginator,
    "current_page": current_page
})

def retrieve(request):
"""
批量導入
book_list = []
for i in range(100):
book_list.append(models.Book(title="book"+str(i), price=20+i*i))
models.Book.objects.bulk_create(book_list)
"""python

book_list = Book.objects.all()              # book_list打印的是一個對象 查詢全部的書
paginator = Paginator(book_list, 5)            # 這裏的book_list必須是一個集合對象,把全部的書分頁,每頁5個
print(paginator.page_range)                 # range(1, 4)
amount = request.GET.get("page", 2)         # 獲得頁數範圍 默認有1頁
print(amount, type(amount))
book_list = paginator.page(amount)          # 顯示第1頁的內容
return render(request, "retrieve.html", {
    "book_list": book_list,
    "page_range": paginator.page_range,
    "amount": int(amount),
    "paginator": paginator
})

```django

index.htmlbootstrap

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <link rel="stylesheet" href="https://cdn.bootcss.com/bootstrap/3.3.7/css/bootstrap.min.css" 
    integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
</head>
<body>

<div class="container">

    <h4>分頁器</h4>
    <ul>

        {% for book in book_list %}
             <li>{{ book.title }} -----{{ book.price }}</li>
        {% endfor %}

     </ul>


    <ul class="pagination" id="pager">

                 {% if book_list.has_previous %}
                    <li class="previous"><a href="/index/?page={{ book_list.previous_page_number }}">上一頁</a></li>
                 {% else %}
                    <li class="previous disabled"><a href="#">上一頁</a></li>
                 {% endif %}


                 {% for num in paginator.page_range %}

                     {% if num == currentPage %}
                       <li class="item active"><a href="/index/?page={{ num }}">{{ num }}</a></li>
                     {% else %}
                       <li class="item"><a href="/index/?page={{ num }}">{{ num }}</a></li>

                     {% endif %}
                 {% endfor %}



                 {% if book_list.has_next %}
                    <li class="next"><a href="/index/?page={{ book_list.next_page_number }}">下一頁</a></li>
                 {% else %}
                    <li class="next disabled"><a href="#">下一頁</a></li>
                 {% endif %}

            </ul>
</div>



</body>
</html>

分頁器擴展(views.py)app

def index(request):


    book_list=Book.objects.all()

    paginator = Paginator(book_list, 15)
    page = request.GET.get('page',1)
    currentPage=int(page)

    #  若是頁數十分多時,換另一種顯示方式
    if paginator.num_pages>30:

        if currentPage-5<1:
            pageRange=range(1,11)
        elif currentPage+5>paginator.num_pages:
            pageRange=range(currentPage-5,paginator.num_pages+1)

        else:
            pageRange=range(currentPage-5,currentPage+5)

    else:
        pageRange=paginator.page_range


    try:
        print(page)
        book_list = paginator.page(page)
    except PageNotAnInteger:
        book_list = paginator.page(1)
    except EmptyPage:
        book_list = paginator.page(paginator.num_pages)


    return render(request,"index.html",locals())

分頁組件

1.分頁的實現與使用url

class Pagination(object):
    """自定義分頁"""
    def __init__(self, current_page, total_count, base_url, params, pre_page_count=10, max_page_count=11):
        try:
            current_page = int(current_page)
        except Exception as e:
            current_page = 1
        if current_page <= 0:
            self.current_page = 1

        self.current_page = current_page
        self.total_count = total_count      # 數據總條數
        self.pre_page_count = pre_page_count        # 每頁顯示10條數據
        max_page_num, div = divmod(total_count, pre_page_count)       # 頁面上因該顯示的最大頁碼
        if div:
            max_page_num += 1
        self.max_page_num = max_page_num

        self.max_page_count = max_page_count        # 頁面上默認顯示11個頁碼(當前頁在中間)
        self.half_max_page_count = int((max_page_count-1)/2)
        self.base_url = base_url        # URL前綴

        import copy
        params = copy.deepcopy(params)      # request.GET
        params._mutable = True
        # 包含當前列表頁面全部的搜索條件
        # {source: [2, ], status: [2, ], gender: [2, ], consultant: [1, ], page: [2, ]}
        # self.params[page] = 8
        # self.params.urlencode()
        # source=2&status=2&gender=2&consultant=1&page=8
        # href = "/hosts/?source=2&status=2&gender=2&consultant=1&page=8"
        # href = "%s?%s" % (self.base_url, self.params.urlencode())
        self.params = params

    @property
    def start(self):
        render(self.current_page-1) * self.pre_page_count

    @property
    def end(self):
        return self.current_page * self.pre_page_count

    def page_html(self):
        # 若是總頁數小於等於11
        if self.max_page_num <= self.max_page_count:
            page_start = 1
            page_end = self.max_page_num
        else:       # 若是總頁數大於11
            # 若是當前頁小於等於5
            if self.current_page <= self.half_max_page_count:
                page_start = 1
                page_end = self.max_page_count
            else:       # 若是當前頁+5大於總頁碼
                if (self.current_page + self.half_max_page_count) > self.max_page_num:
                    page_end = self.max_page_num
                    page_start = self.max_page_num - self.max_page_count+1      # 倒着數11個
                else:
                    page_start = self.current_page - self.half_max_page_count
                    page_end = self.current_page - self.half_max_page_count
        page_list = []
        # {source:[2,], status:[2], gender:[2],consultant:[1],page:[1]}
        # 首頁
        self.params["page"] = 1
        first_page = '<li><a href="%s?%s">首頁</a></li>' % (self.base_url, self.params.urlencode(),)
        page_list.append(first_page)

        # 上一頁
        self.params["page"] = self.current_page-1
        if self.params["page"] < 1:
            previous_page = '<li class="disabled"><a href="%s?%s" aria-label="Previous">上一頁</span></a></li>' %
            (self.base_url, self.params.urlencode())
        else:
            previous_page = '<li><a href = "%s?%s" aria-label = "Previous" >上一頁</span></a></li>' % (
            self.base_url, self.params.urlencode())
        page_list.append(previous_page)

        # 中間頁碼
        for i in range(page_start, page_end + 1):
            self.params['page'] = i
            if i == self.current_page:
                temp = '<li class="active"><a href="%s?%s">%s</a></li>' % (self.base_url, self.params.urlencode(), i,)
            else:
                temp = '<li><a href="%s?%s">%s</a></li>' % (self.base_url, self.params.urlencode(), i,)
            page_list.append(temp)

            # 下一頁
        self.params["page"] = self.current_page + 1
        if self.params["page"] > self.max_page_num:
            self.params["page"] = self.current_page
            next_page = '<li class="disabled"><a href = "%s?%s" aria-label = "Next">下一頁</span></a></li >' % (
                self.base_url, self.params.urlencode())
        else:
            next_page = '<li><a href = "%s?%s" aria-label = "Next">下一頁</span></a></li>' % (
                self.base_url, self.params.urlencode())
        page_list.append(next_page)

        # 尾頁
        self.params['page'] = self.max_page_num
        last_page = '<li><a href="%s?%s">尾頁</a></li>' % (self.base_url, self.params.urlencode(),)
        page_list.append(last_page)

        return ''.join(page_list)

2.使用spa

# 自定義分頁組件的使用方法:
   pager_obj = Pagination(request.GET.get('page',1), len(HOST_LIST), request.path_info,request.GET)
   host_list = HOST_LIST[pager_obj.start:pager_obj.end]
   html = pager_obj.page_html()
   return render(request, 'hosts.html', {'host_list':host_list,"page_html":html})
相關文章
相關標籤/搜索