我希望能够允许用户更改默认页面大小 (paginate_by)。我当前的页面大小设置为 10;我想要按钮,比如 25、50 和所有。
我正在使用 postgresql 11.4 运行 Django 2.2 和 Python 3.73。我的 views.py 创建一个查询集并设置分页。我的 prod_list.html 模板以每页十行的方式正确显示页面中的数据。
这是我目前在 views.py 中的内容:
class ProdViewSet(viewsets.ModelViewSet):
queryset = Proddetails.objects.all()
serializer_class = ProdSerializer
class ProdListView(ListView):
model = Proddetails
template_name = 'prod_list.html'
# added for pagination
context_object_name = 'prods' #Default: object_list
paginate_by = 10
Run Code Online (Sandbox Code Playgroud)
我希望能够让我的用户更改每页的行数。我想我需要根据用户单击的按钮重置paginate_by,但我该怎么做?
谢谢 -
铝
好吧,我试图发表评论,但这并没有给我足够的空间。我希望这是执行此操作的正确方法:
非常感谢; 这样做的伎俩。不过,我修改了它以给我带页码的按钮,但我得到了一个奇怪的行为。我有一个 for 循环,用于将页码作为按钮输出:
{% for i in DataPaginated.paginator.page_range %}
{% if DataPaginated.number == i %}
<button class="w3-button w3-amber">{{ i }} </button>
{% else %}
<a href="?page={{ i }}" class="w3-button">{{ i }}</a>
{% endif %}
{% endfor %}
Run Code Online (Sandbox Code Playgroud)
如果分页设置为默认值 10,这将正常工作并显示三页(有 24 个项目)。如果我将分页更改为 20,它起初看起来是正确的并显示两页。但是,如果我单击第二页,它会将我的分页更改回 10,再次显示三页,并将我放在三页中的第二页。我可以做些什么来将我的分页锁定在表单选择的设置中?
小智 8
您不需要重写 get 方法,正确的方法是重写该方法get_paginate_by:
class VideoView(ListView):
template_name = "pages/videos.html"
model = models.Video
paginate_by = 10
def get_paginate_by(self, queryset):
return self.request.GET.get("paginate_by", self.paginate_by)
Run Code Online (Sandbox Code Playgroud)
现在您可以过滤:http://localhost:8000/videos/?paginate_by=40
问候。
from django.core.paginator import Paginator, PageNotAnInteger, EmptyPage
class ProdListView(ListView):
model = Proddetails
template_name = 'prod_list.html'
# added for pagination
context_object_name = 'prods' #Default: object_list
paginate_by = 10
def get(self, request):
paginate_by = request.GET.get('paginate_by', 10) or 10
data = self.model.objects.all()
paginator = Paginator(data, paginate_by)
page = request.GET.get('page')
try:
paginated = paginator.get_page(page)
except PageNotAnInteger:
paginated = paginator.get_page(1)
except EmptyPage:
paginated = paginator.page(paginator.num_pages)
return render(request, self.template_name, {'DataPaginated':paginated, 'paginate_by':paginate_by})
Run Code Online (Sandbox Code Playgroud)
你应该把它放在你的模板中以允许用户选择分页。您可以使用 GET 方法通过表单发送分页数量。视图可能会得到它。
一旦视图获得方法 GET 传递的数据(分页编号),它就会处理请求,然后它会给您一个响应,其中包括您应该在模板中呈现的分页数据。
<form method="GET">
<select name="paginate_by" id="">
<option value="10">10</option>
<option value="20">10</option>
<option value="30">30</option>
<option value="50">50</option>
</select>
<input type="submit" value="Paginate">
</form>
<!-- RENDER YOU LIST HERE. Now context_object_name must be DataPaginated or whatever name you call it-->
<div class="pagination">
<span class="step-links">
{% if DataPaginated.has_previous %}
<a href="?page=1¶m={{param}}">« first</a>
<a href="?page={{ DataPaginated.previous_page_number }}¶m={{param}}">previous</a>
{% endif %}
<span class="current">
Page {{ DataPaginated.number }} of {{ DataPaginated.paginator.num_pages }}.
</span>
{% if DataPaginated.has_next %}
<a href="?page={{ DataPaginated.next_page_number }}¶m={{param}}">next</a>
<a href="?page={{ DataPaginated.paginator.num_pages }}¶m={{param}}">last »</a>
{% endif %}
</span>
</div>
Run Code Online (Sandbox Code Playgroud)
.get_page
.get_page 方法是在 Django 2.0 中添加的。在旧版本上,您将需要
try:
paginated = paginator.page(page)
except PageNotAnInteger:
paginated = paginator.page(1)
except EmptyPage:
paginated = paginator.page(paginator.num_pages)
Run Code Online (Sandbox Code Playgroud)
您可以在执行此操作时检查您正在使用的版本manage.py runserver。就我而言,它是version 1.11.17.
(ECOMME~1) C:\Users\HP\EcommerceProject>python manage.py runserver
Django version 1.11.17, using settings 'EcommerceProject.settings'
Starting development server at http://127.0.0.1:8000/
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1645 次 |
| 最近记录: |