1. 程式人生 > >Django - 分頁器(paginator)

Django - 分頁器(paginator)

目錄

一、分頁器 - 在頁面將資料庫內返回前端的資料進行分頁顯示

1-1 分頁器模組介紹 - from django.core.paginator import Paginator

 二、資料庫的批量新增

三、前端

四、檢視層傳輸資料


一、分頁器 - 在頁面將資料庫內返回前端的資料進行分頁顯示

 

1-1 分頁器模組介紹 - from django.core.paginator import Paginator

paginator=Paginator(book_list,10) 建立分頁器物件,兩個引數:object_list:物件列表, per_page:每頁顯示的條數
物件內屬性如下(物件.屬性)  
paginator.count 資料總條數(100條)
paginator.num_pages 總頁數(10頁)
paginator.page_range 頁碼數的列表,總頁數的索引範圍,如: (1,11),(11,21),取前不取後
current_page=paginator.page(5)
取到第 x 頁 ,返回一個Page物件
current_page.object_list 當前頁碼內所有的資料
Page物件內方法(物件.方法())  
current_page.*has_next() 當前頁碼,是否有下一頁
current_page.has_previous() 當前頁碼,是否有上一頁
current_page.next_page_number()
當前頁碼,下一頁頁碼數
current_page.previous_page_number() 當前頁碼,上一頁的頁碼數

 

 二、資料庫的批量新增

import os

if __name__ == '__main__':
    os.environ.setdefault("DJANGO_SETTINGS_MODULE", "paginator.settings")
    import django

    django.setup()

    from app01 import models

    # # 初級(迴圈批量插入)
    # for i in range(100):
    #     models.Book.objects.create(name='圖書%s' % i, price=10 + i)

    # 高階批量插入)
    # 先造成100本書, 放到列表中
    l= []
    for i in range(100):
        l.append(models.Book(name='圖書%s' % i, price=10 + i))
    # 批量插入,兩個引數,第一個是物件列表,第二個是一次插入的資料量,不填,預設一次全插入
    models.Book.objects.bulk_create(l)

三、前端

總結:

  • 結構:資料庫內容展示位於表格內 + 分頁結構(上一頁+設定顯示頁碼+下一個)
  • 注意:路由拼寫必須為'/路徑/',即必須開頭加斜槓,否則點選會自動在末位連續新增

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <!-- 最新版本的 Bootstrap 核心 CSS 檔案 -->
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css"
          integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
    <title>Title</title>
</head>
<body>
<div class="row">
    <div class="col-md-6 col-md-offset-3">

        {#資料庫內容展示在表格內#}
        <table class="table table-striped">
            <thead>
            <tr>
                <th>書名</th>
                <th>價格</th>
            </tr>
            </thead>
            <tbody>
            {% for book in current_page %}
                <tr>
                    <td>{{ book.name }}</td>
                    <td>{{ book.price }}</td>
                </tr>
            {% endfor %}

            </tbody>
        </table>

         {#分頁器實現,當前頁選擇#}
        <nav aria-label="Page navigation">
            <ul class="pagination">
                {#如果當前頁存在上一頁#}
                {% if current_page.has_previous %}
                    <li>
                        {# 上一頁按鈕跳轉到準確的上一頁,兩種寫法 #}
                        {#<a href="/index/?page={{ current_page_num|add:-1 }}" aria-label="Previous">#}
                        <a href="/index/?page={{ current_page.previous_page_number }}" aria-label="Previous">
                            <span aria-hidden="true">上一頁</span>
                        </a>
                    </li>
                {% else %}
                    <li class="disabled">   {# 若當前頁不存在上一頁,則按鈕disabled #}
                        <a href="" aria-label="Previous">
                            <span aria-hidden="true">上一頁</span>
                        </a>
                    </li>
                {% endif %}

                {# 迴圈頁碼數列表(1,11),(11,21) #}
                {% for foo in page_range %}

                    {% if current_page_num == foo %}
                        {# 當前頁碼等於迴圈到的頁碼數,變色#}
                        <li class="active"><a href="/index/?page={{ foo }}">{{ foo }}</a></li>
                    {% else %}
                        <li><a href="?page={{ foo }}">{{ foo }}</a></li>
                    {% endif %}

                {% endfor %}


                {#如果當前頁存在下一頁#}
                {% if current_page.has_next %}
                    <li>
                        {# 下一頁按鈕跳轉到準確的下一頁,兩種寫法 #}
                        {#<a href="/index/?page={{ current_page_num|add:1 }}" aria-label="Next">#}
                        <a href="/index/?page={{ current_page.next_page_number }}" aria-label="Next">
                            <span aria-hidden="true">下一頁</span>
                        </a>
                    </li>
                {% else %}
                    <li class="disabled"> {# 若當前頁不存在下一頁,則按鈕disabled #}
                        <a href="" aria-label="Next">
                            <span aria-hidden="true">下一頁</span>
                        </a>
                    </li>
                {% endif %}
            </ul>
        </nav>
    </div>

</div>
</body>
</html>

四、檢視層傳輸資料

總結:

  • 前臺傳資料給後臺:選擇的頁碼通過 <a href="" >內的路由進行跳轉,使用GET傳輸
  • 後臺傳輸資料給前臺:使用render傳輸 
  • 若url內未輸入捕捉頁碼或者輸入超出範圍的捕捉頁碼,通過異常捕捉並給一個初始值
from django.shortcuts import render, HttpResponse

# Create your views here.
from django.core.paginator import Paginator, EmptyPage
from app01 import models

def index(request):
    book_list = models.Book.objects.all()
    paginator = Paginator(book_list, 3)

    # 如果頁碼數多,確保顯示為固定的10個
    # 則,讓它顯示前5,後5,中間是當前在的頁碼

    try:  # 捕獲異常,若有人在url內輸入非範圍內的頁數,則顯示當前頁面為1
        current_page_num = int(request.GET.get('page'))
        current_page = paginator.page(current_page_num)
        print(current_page.object_list)

        # 總頁碼數,大於11的時候
        if paginator.num_pages > 11:
            # 當前頁碼數-5大於1的時候,page_range(頁碼數列表)應該是?
            # 當前頁碼數-5小於1的時候,page_range(頁碼數列表)都應該是 1-11
            if current_page_num - 5 < 1:
                # range 建立一個整數列表,取錢不取後
                page_range = range(1, 12)
            elif current_page_num + 5 > paginator.num_pages:
                # 當前頁碼數+5大於總頁碼數,總頁碼數往前推11個
                # 若總頁碼數為34,則從29頁到34頁都顯示相同的page_range
                # 總頁碼數-10,總頁碼數+1 --總頁碼數-10:顯示包括總頁碼數 總頁碼數+1:取前不取後
                page_range = range(paginator.num_pages - 10, paginator.num_pages + 1)
            else:
                page_range = range(current_page_num - 5, current_page_num + 6)
        else:
            # 小於11,有多少頁,就顯示多少頁
            page_range = paginator.page_range
    except Exception as e:
        current_page_num = 1
        current_page = paginator.page(current_page_num)
        page_range = range(1, 12)

    return render(request, 'index_next.html', locals())