• 114.实现手动分页效果


    分页

    在网站的开发当中,我们常常需要将各种列表中的数据分页显示,想要实现分页的效果,就可以通过django.core.Paginator.Paginator和django.core.Paginator.Page来实现。

    1. 比如,将Paginator_pageAPP中表article中的range(1,100)的数据分页显示,每页显示10条数据,可以实现手动分页的效果。
    (1)首先在models.py文件中定义模型Article,示例代码如下:
    from django.db import models
    
    
    class Article(models.Model):
        title = models.CharField(max_length=100)
        content = models.CharField(max_length=100)
        create_time = models.DateTimeField(auto_now_add=True)
    
        class Meta:
            db_table = 'paginator_page'
    
    
    (2)在views.py文件中为数据库中的表paginator_page添加1-99条数据,示例代码如下:
    from django.http import HttpResponse
    from .models import Article
    
    def index(request):
        articles = []
        for page in range(1,100):
            <!--将遍历的每一个page都赋值给Article中的title和content字段-->
            article = Article(title='标题:{}'.format(page), content='内容:{}'.format(page))
            <!--将所有的article对象都添加到列表articles中-->
            articles.append(article)
        <!--采用bulk_create()方法将列表中所有的实例对象都添加到数据库中-->
        Article.objects.bulk_create(articles)
        return HttpResponse('success')
    
    (3)将所有的数据分页显示。这就涉及到了我们之前提到的ListView类,就需要通过ListView来新创建一个类视图,实现我们的分页效果。views.py文件中示例代码如下:
    from django.views.generic from ListView
    from django.http import HttpResponse
    
    class Paginator_page_view(ListView):
        <!--指定这个类视图属于哪个模型-->
        model = Article
        <!--指定模板的名字,在该视图中定义的所有参数都会传递到该模板中-->
        template_name = 'paginator_page/static/paginator_page.html'
        <!--指定参数在模板中可以通过什么名字进行获取-->
        context_object_name = 'articles'
        <!--指定每页的数据量-->
        paginate_by = 10
        <!--指定数据在显示的时候按哪个字段进行排序-->
        ordering = 'create_time'
        <!--指定在输入url更改页数是的参数名-->
        page_kwarg = 'p'
        
        
        <!--重写类视图的get_context_data()方法,同时要调用类的get_context_data()方法,将类视图中的所有参数进行保存,,以防之后会用到-->
        def get_context_data(self, request, *args, **kwargs):
            context = super(Paginator_page_view, self).get_context_data(**kwargs)
            return context
            
        <!--同时可以重写类视图的get_queryset(self)方法,不调用Article.objects的all方法返回所有的数据。-->
        def get_queryset(self):
            return Article.objects.filter(id__lte=80)
    
    (4)在项目的urls.py文件中进行视图函数与url之间的映射,示例代码如下:
    from . import views
    from django.urls import path, include
    
    
    urlpatterns = [
        path('paginator/', include('Paginator_page.urls')),
    ]
    
    
    (5)在Paginator_pageAPP中的urls.py文件中进行视图与url的映射,示例代码如下:
    from . import views
    from .views import Paginator_page_view
    from django.urls import path
    
    app_name = 'Paginator_page'
    
    urlpatterns = [
    <!--采用as_view()方法将类转换为类视图-->
        path('', Paginator_page_view.as_view(), name='page'),
    ]
    
    (6)在paginator_page/static/paginator_page.html中实现分页(这种情况下会显示每一页,这种不是太方便。接下来会进行完善),示例代码如下:
        <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@3.3.7/dist/css/bootstrap.min.css"
              integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
    
    <!--显示数据-->
    <!--首先可以将数据库中所有的数据进行遍历,提取数据的title信息进行显示-->
    {% for article in articles %}
        {{% article.title %}}
    {% endfor %}
    
    <!--实现分页效果-->
    <!--判断上一页-->
    <!--首先判断是否还有上一页,如果还有上一页,就要进行跳转,如果没有下一页就要在点击上一页时显示禁止样式的图标,并且不会进行任何跳转。这个可以通过page_obj.has_previous来实现-->
    <ul class="pagination">
        {% if page_obj.has_previous%}
        <!--如果存在上一页的话,就使用page_obj上的属性previous_page_number获取上一页的页数进行跳转和显示-->
            <li><a href="{% url 'Paginator_page:page' %}?p={{ page_obj.previous_page_number}}">{{ page_obj.previous_page_number }}</a></li>
        {% else %}
        <!--否者的话,就将上一页标识为不能点击:即为disabled。-->
            <li class="disabled"><a href="javascript:void(0);">上一页</a></li>
        {% endif %}
        
        
    <!--判断中间页-->
        {% for page in paginator.range_page %}
            {% if page == page_obj.number %}
                <li class='disabled'><a href="javascript:void(0);">{{ page_obj.number }}</a></li>
            {% else %}
                <li><a href="{% url 'Paginator_page:page' %}?p={{ page }}">{{ page }}</a></li>
            {% endif %}
        {% endfor %}
        
        
    <!--判断下一页-->
    <!--判断下一页是否存在,如果存在,就调用page_obj上的属性next_page_number获取下一页的页数,并且进行跳转和显示-->
        {% if page_obj.has_next %}
            <li><a href="{% url 'Paginator_page:page' %}?p={{ page_obj.next_page_number }}">{{ page_obj.next_page_number }}</a></li>
        {% else %}
        <!--如果没有下一页的话,就将下一页标识为不能点击的禁止样式,即为disabled-->
            <li class='disabled'><a href="javascript:void(0);">下一页</a></li>
        {% endif %}
    </ul>
    
    (7)完善在paginator_page/static/paginator_page02.html中实现显示部分分页,示例代码如下:
    from django.views.generic import ListView
    from django.http import HttpResponse
    from .models import ListView
    
    
    class Paginator_page_view02(ListView):
        model = Article
        template_name = 'paginator_page/static/paginator_page02.html'
        context_object_name = 'articles'
        paginate_by = 10
        ordering = 'create_time'
        page_kwarg = 'p'
        
        def get_context_data(self, request, *args, **kwargs):
            context = super(Paginator_page_view02, self).get_context_data(**kwargs)
            paginator = context.get('paginator')
            page_obj = context.get('page_obj')
            
            <!--调用自定义函数,并且且传递参数进去,获取返回值-->
            pagination_data = self.get_pagination_data(paginator, page_obj)
            <!--将获取的数据添加到context中-->
            context.update(pagination_data)
            return context
        
        
        <!--自定义一个函数:用来接收paginator和paage_obj-->
        <!--其中around_count参数代表的是每页左右两边最显示两页-->
        def get_pagination_data(self, paginator,page_obj, around_count=2):
            current_page = page_obj.number
            num_pages = paginator.num_pages
            
            left_has_more = False
            right_has_more = False
            
            if current_page <= around_count + 2:
                left_pages = range(1, current_page)
            else:
                lefT_has_more = True
                left_pages = range(current_page-around_count, current_page)
                
            if current_page >= num_pages-around_count - 1:
                right_page = range(current_page, num_pages)
            else:
                right_has_more = True
                right_page = range(current_page+1, current_page+around_count+1)
                
            return context={
                'left_pages': left_pages,
                'right_pages': right_pages,
                'num_pages': num_pages,
                'left_has_more': left_has_more,
                'right_has_more': right_has_more,
                'current_page': current_page,
            }
    
    (8)paginator_page/static/paginator_page02.html中示例代码如下:
        <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@3.3.7/dist/css/bootstrap.min.css"
              integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
    
    <ul>
    {# 上一页 #}
        {% if page_obj.has_previous %}
            <li><a href="{% url 'paginator_page:page02' %}?p={{ page_obj.previous_page_number }}">上一页</a></li>
        {% else %}
            <li class="disabled"><a href="javascript: void(0);">上一页</a></li>
        {% endif %}
    
        {% if left_has_more %}
            <li><a href="{% url 'paginator_page:page02' %}?p=1">1</a></li>
            <li><a href="javascript:void(0);">...</a></li>
        {% endif %}
    
    {# 中间页 #}
    {#  left页  #}
        {% for left_page in left_pages %}
            <li><a href="{% url 'paginator_page:page02' %}?p={{ left_page }}">{{ left_page }}</a></li>
        {% endfor %}
    
    {#  中间页  #}
        <li><a href="{% url 'paginator_page:page02' %}?p={{ current_page }}">{{ current_page }}</a></li>
    
    {#  right页  #}
        {% for right_page in right_pages %}
            <li><a href="{% url 'paginator_page:page02' %}?p={{ right_page }}">{{ right_page }}</a></li>
        {% endfor %}
    
        {% if right_has_more %}
            <li><a href="javascript:void(0);">...</a></li>
            <li><a href="{% url 'paginator_page:page02' %}?p={{ num_pages }}">{{ num_pages }}</a></li>
        {% endif %}
    
    
    {# 下一页 #}
        {% if page_obj.has_next %}
            <li><a href="{% url 'paginator_page:page02' %}?p={{ page_obj.next_page_number }}">下一页</a></li>
        {% else %}
            <li class="disabled"><a href="javascript:void(0);">下一页</a></li>
        {% endif %}
    
    </ul>
    
    
    始于才华,忠于颜值;每件事情在成功之前,看起来都是天方夜谭。一无所有,就是无所不能。
  • 相关阅读:
    AS3.0纯代码编写的两款loading效果
    AS3.0 Vector的运用
    java 垃圾回收总结(1)
    as3垃圾回收机制
    AS3.0 效率优化
    数组去重的方法
    javascript 的垃圾回收机制讲一下
    浅拷贝和深拷贝
    判断 js 类型的方式
    前端安全问题?
  • 原文地址:https://www.cnblogs.com/guyan-2020/p/12306201.html
Copyright © 2020-2023  润新知