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

如何让分页Partial适配多控制器、多ViewModel及多视图场景?

通用分页Partial视图改造方案

要让分页Partial支持多控制器/视图复用,核心是把硬编码的控制器、Action以及路由参数动态化,下面是具体实现步骤:

1. 扩展分页模型(可选,提升灵活性)

修改BasePageableModel,添加路由相关属性,用于传递目标控制器、Action及额外查询参数:

public class BasePageableModel
{
    // 原有分页属性保留
    public int PageNumber { get; set; }
    public int PageSize { get; set; }
    public int TotalPages { get; set; } // 注意:原代码循环误用了PageSize,需替换为总页数TotalPages
    public bool HasPreviousPage { get; set; }
    public bool HasNextPage { get; set; }

    // 新增路由配置属性
    public string ControllerName { get; set; }
    public string ActionName { get; set; }
    // 传递额外查询参数(如搜索关键词、分类ID等)
    public RouteValueDictionary RouteValues { get; set; } = new RouteValueDictionary();
}

2. 改造分页Partial视图

将硬编码的路由信息替换为模型动态值,同时保留额外参数:

@model CTA_Client.Models.BasePageableModel

@if (Model.TotalPages > 1) // 总页数大于1时才显示分页
{
    <div class="center-block text-center">
        <ul class="pagination mb-lg-0 mb-5">
            <!-- 上一页 -->
            <li class="page-item page-prev @(Model.HasPreviousPage == false ? "disabled" : "")">
                <a class="page-link" tabindex="-1" 
                   asp-controller="@Model.ControllerName" 
                   asp-action="@Model.ActionName" 
                   asp-all-route-data="@Model.RouteValues"
                   asp-route-PageNumber="@(Model.PageNumber - 1)">Prev</a>
            </li>

            <!-- 页码列表 -->
            @for (int i = 1; i <= Model.TotalPages; i++)
            {                   
                <li class="page-item @(i == Model.PageNumber ? "active" : "")">
                    <a class="page-link" 
                       asp-controller="@Model.ControllerName" 
                       asp-action="@Model.ActionName" 
                       asp-all-route-data="@Model.RouteValues"
                       asp-route-PageNumber="@i">@i</a>
                </li>
            }       

            <!-- 下一页 -->
            <li class="page-item page-next @(Model.HasNextPage == false ? "disabled" : "")">
                <a class="page-link" 
                   asp-controller="@Model.ControllerName" 
                   asp-action="@Model.ActionName" 
                   asp-all-route-data="@Model.RouteValues"
                   asp-route-PageNumber="@(Model.PageNumber + 1)">Next</a>
            </li>
        </ul>
    </div>
}

注意:原代码循环条件使用Model.PageSize(每页条数)是逻辑错误,需改为Model.TotalPages(总页数)。

3. 父视图传递参数

根据场景选择不同的参数传递方式:

方式1:手动指定路由(跨控制器分页场景)

@Html.Partial("~/Views/Shared/_pagination.cshtml", new BasePageableModel
{
    PageNumber = Model.PagingFilteringContext.PageNumber,
    PageSize = Model.PagingFilteringContext.PageSize,
    TotalPages = Model.PagingFilteringContext.TotalPages,
    HasPreviousPage = Model.PagingFilteringContext.HasPreviousPage,
    HasNextPage = Model.PagingFilteringContext.HasNextPage,
    ControllerName = "Blog",
    ActionName = "List",
    // 保留当前视图的路由参数,避免分页时丢失查询条件
    RouteValues = new RouteValueDictionary(ViewContext.RouteData.Values)
})

方式2:自动获取当前路由(同控制器分页场景)

如果分页跳转的是当前控制器的Action,可直接在Partial中获取路由信息,无需手动赋值模型属性:
在Partial视图顶部添加:

@{
    var currentController = ViewContext.RouteData.Values["controller"].ToString();
    var currentAction = ViewContext.RouteData.Values["action"].ToString();
}

然后将视图中asp-controller="@Model.ControllerName"替换为asp-controller="@currentController",asp-action="@Model.ActionName"替换为asp-action="@currentAction"即可。

4. 适配多业务模型

只要你的BlogPagingFilteringModel、ProductPagingFilteringModel等继承自BasePageableModel,并在控制器中正确赋值分页及路由属性,即可在对应视图中直接复用:

// 电商商品列表视图示例
@Html.Partial("~/Views/Shared/_pagination.cshtml", Model.PagingFilteringContext)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.17 18:24:53