You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在aiogram 3中实现多元素分页?一次展示5个元素

修改方案:将单商品分页改为每页5个商品

以下是针对你的aiogram 3机器人代码的修改,实现每页展示5个商品并保留分页按钮功能:

1. 调整分页器默认配置

修改Paginator类的默认每页商品数量,将per_page默认值从1改为5:

import math

class Paginator:
    def __init__(self, array: list | tuple, page: int=1, per_page: int=5):  # 修改默认每页数量为5
        self.array = array
        self.per_page = per_page
        self.page = page
        self.len = len(self.array)
        # math.ceil - 向上取整为整数
        self.pages = math.ceil(self.len / self.per_page)

    def __get_slice(self):
        start = (self.page - 1) * self.per_page
        stop = start + self.per_page
        return self.array[start:stop]

    def get_page(self):
        page_items = self.__get_slice()
        return page_items

    def has_next(self):
        if self.page < self.pages:
            return self.page + 1
        return False

    def has_previous(self):
        if self.page > 1:
            return self.page - 1
        return False

2. 更新商品列表展示逻辑

改写products函数,整合当前页所有商品的信息到消息内容中:

from aiogram.types import InputMediaPhoto

def pages(paginator: Paginator):
    btns = dict()
    if paginator.has_previous():
        btns["◀ 上一页"] = "previous"

    if paginator.has_next():
        btns["下一页 ▶"] = "next"

    return btns

async def products(session, level, category, page):
    products = await orm_get_products(session, category_id=category)

    paginator = Paginator(products, page=page)
    page_products = paginator.get_page()  # 获取当前页的所有商品(最多5个)

    # 生成多商品的文本内容
    caption_parts = []
    for idx, product in enumerate(page_products, start=1):
        caption_parts.extend([
            f"<strong>商品 {idx}</strong>",
            f"<strong>{product.name}</strong>",
            product.description,
            f"价格: {round(product.price, 2)}",
            "-------------------------"
        ])
    # 添加分页信息
    caption_parts.append(f"<strong>第 {paginator.page} 页 / 共 {paginator.pages} 页</strong>")
    final_caption = "\n".join(caption_parts)

    # 使用当前页第一个商品的图片作为展示图(需处理空列表情况)
    image = InputMediaPhoto(
        media=page_products[0].image if page_products else "",
        caption=final_caption,
        parse_mode="HTML"  # 确保HTML格式生效
    )

    pagination_btns = pages(paginator)

    kbds = get_products_btns(
        level=level,
        category=category,
        page=page,
        pagination_btns=pagination_btns,
        # 若需给每个商品添加操作按钮,可在此扩展逻辑
    )

    return image, kbds

async def get_menu_content(
        session: AsyncSession,
        level: int,
        menu_name: str,
        category: int | None = None,
        page: int | None = None,
):
    if level == 0:
        return await main_menu(session, level, menu_name)
    elif level == 1:
        return await catalog(session, level, menu_name)
    elif level == 2:
        return await products(session, level, category, page)

补充说明

  • 若需展示多商品图片,可将InputMediaPhoto替换为InputMediaGroup,循环添加每个商品的图片与对应描述。
  • 确保get_products_btns函数能正确处理分页按钮的回调逻辑,点击时传递正确的page参数。
  • 当商品数量不足5个时,分页器会自动适配,仅展示现有商品。

内容的提问来源于stack exchange,提问作者Alexander

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.25 19:04:52