feat: 增加分页组件

This commit is contained in:
Argo Window10 2019-11-28 15:22:01 +08:00
parent 5b05c4b9ab
commit 6004c0c8f1
8 changed files with 252 additions and 16 deletions

View File

@ -0,0 +1,53 @@
using Bootstrap.Admin.Extensions;
using Microsoft.AspNetCore.Components;
using Microsoft.JSInterop;
using System;
using System.Threading.Tasks;
namespace Bootstrap.Admin.Components
{
/// <summary>
/// 分页组件基类
/// </summary>
public class PaginationBase : ComponentBase
{
/// <summary>
/// 获得/设置 页码总数
/// </summary>
[Parameter]
public int PageCount { get; set; } = 0;
/// <summary>
///
/// </summary>
[Parameter]
public int PageIndex { get; set; } = 1;
/// <summary>
///
/// </summary>
[Inject]
protected IJSRuntime? JSRuntime { get; set; }
/// <summary>
///
/// </summary>
public Action<int>? ClickPageCallback { get; set; }
/// <summary>
///
/// </summary>
protected void MovePrev()
{
if (PageIndex > 1) ClickPageCallback?.Invoke(PageIndex - 1);
}
/// <summary>
///
/// </summary>
protected void MoveNext()
{
if (PageIndex < PageCount) ClickPageCallback?.Invoke(PageIndex + 1);
}
}
}

View File

@ -0,0 +1,54 @@
using Microsoft.AspNetCore.Components;
using Microsoft.JSInterop;
using System.Collections.Generic;
namespace Bootstrap.Admin.Components
{
/// <summary>
/// 表格组件类
/// </summary>
public class TableBase<TItem> : ComponentBase
{
/// <summary>
///
/// </summary>
[Inject]
protected IJSRuntime? JSRuntime { get; set; }
/// <summary>
///
/// </summary>
[Parameter]
public string Id { get; set; } = "";
/// <summary>
///
/// </summary>
[Parameter]
public RenderFragment? TableHeader { get; set; }
/// <summary>
///
/// </summary>
[Parameter]
public RenderFragment<TItem>? RowTemplate { get; set; }
/// <summary>
///
/// </summary>
[Parameter]
public RenderFragment? TableFooter { get; set; }
/// <summary>
///
/// </summary>
[Parameter]
public IEnumerable<TItem> Items { get; set; } = new TItem[0];
/// <summary>
/// 数据
/// </summary>
[Parameter]
public int ItemsCount { get; set; } = 0;
}
}

View File

@ -21,7 +21,7 @@
</select> </select>
</div> </div>
<div class="form-group col-sm-6 col-md-auto flex-sm-fill justify-content-sm-end align-self-sm-end"> <div class="form-group col-sm-6 col-md-auto flex-sm-fill justify-content-sm-end align-self-sm-end">
<button type="button" id="btn_query" class="btn btn-primary btn-fill"><i class="fa fa-search" aria-hidden="true"></i><span>查询</span></button> <button type="button" id="btn_query" class="btn btn-primary btn-fill" @onclick="e => Query(1)"><i class="fa fa-search" aria-hidden="true"></i><span>查询</span></button>
</div> </div>
</div> </div>
</form> </form>
@ -47,7 +47,21 @@
查询结果 查询结果
</div> </div>
<div class="card-body"> <div class="card-body">
<table></table> <Table Id="tb_Dict" Items="Items" TItem="Bootstrap.Security.BootstrapDict" ItemsCount="ItemsCount">
<TableHeader>
<th>字典标签</th>
<th>字典名称</th>
<th>字典代码</th>
<th>字典分类</th>
</TableHeader>
<RowTemplate>
<td>@context.Category</td>
<td>@context.Name</td>
<td>@context.Code</td>
<td>@context.Define</td>
</RowTemplate>
</Table>
<Pagination @ref="Pagination" PageCount="PageCount" PageIndex="PageIndex"></Pagination>
</div> </div>
</div> </div>
<div id="tableButtons" class="d-none"> <div id="tableButtons" class="d-none">
@ -102,5 +116,45 @@
</Modal> </Modal>
@code { @code {
[Parameter]
public IEnumerable<BootstrapDict> Items { get; set; } = new BootstrapDict[0];
[Parameter]
public int ItemsCount { get; set; } = 0;
[Parameter]
public int PageCount { get; set; } = 0;
[Parameter]
public int PageIndex { get; set; } = 1;
protected int PageItem { get; set; } = 20;
protected Pagination? Pagination { get; set; }
protected override void OnInitialized()
{
Query(1);
}
protected override void OnAfterRender(bool firstRender)
{
if (firstRender && Pagination != null) Pagination.ClickPageCallback = pageIndex =>
{
if (pageIndex != PageIndex)
{
Query(pageIndex);
StateHasChanged();
}
};
}
protected void Query(int pageIndex)
{
var data = DataAccess.DictHelper.RetrieveDicts();
ItemsCount = data.Count();
Items = data.Skip((pageIndex - 1) * PageItem).Take(PageItem);
PageCount = (int)Math.Ceiling(data.Count() * 1.0d / PageItem);
PageIndex = pageIndex;
}
} }

View File

@ -0,0 +1,19 @@
@inherits PaginationBase
<nav class="d-flex align-items-center" aria-label="分页组件">
<div class="pagination-bar">显示第 1 到第 20 条记录,总共 264 条记录 每页显示 条记录</div>
<ul class="pagination">
<li class="page-item" @onclick="MovePrev"><div class="page-link" aria-label="上一页"><i class="fa fa-angle-double-left"></i></div></li>
<CascadingValue Value="this">
@for (int i = 1; i <= PageCount; i++)
{
<PaginationItem Active="i == PageIndex" PageIndex="i"></PaginationItem>
}
</CascadingValue>
<li class="page-item" @onclick="MoveNext"><div class="page-link" aria-label="下一页"><i class="fa fa-angle-double-right"></i></div></li>
</ul>
</nav>
@code {
}

View File

@ -0,0 +1,29 @@
<li class="@(Active ? "page-item active" : "page-item")" @onclick="ClickPage"><div class="page-link" aria-label="@string.Format("第 {0} 页", PageIndex)">@PageIndex</div></li>
@code {
/// <summary>
///
/// </summary>
[Parameter]
public bool Active { get; set; }
/// <summary>
///
/// </summary>
[CascadingParameter]
public Pagination? Pagination { get; set; }
/// <summary>
///
/// </summary>
[Parameter]
public int PageIndex { get; set; } = 0;
/// <summary>
///
/// </summary>
protected void ClickPage()
{
Pagination?.ClickPageCallback?.Invoke(PageIndex);
}
}

View File

@ -0,0 +1,21 @@
@typeparam TItem
@inherits TableBase<TItem>
<table class="table table-striped table-bordered table-hover">
<thead>
<tr>@TableHeader</tr>
</thead>
<tbody>
@foreach (var item in Items)
{
<tr>@RowTemplate?.Invoke(item)</tr>
}
</tbody>
<tfoot>
<tr>@TableFooter</tr>
</tfoot>
</table>
@code {
}

View File

@ -13,6 +13,7 @@
@using Microsoft.AspNetCore.Mvc @using Microsoft.AspNetCore.Mvc
@using Microsoft.Extensions.Configuration @using Microsoft.Extensions.Configuration
@using Microsoft.JSInterop @using Microsoft.JSInterop
@using Longbow.Web.Mvc
@using System.Linq @using System.Linq
@using System.Net @using System.Net
@using System.Net.Http @using System.Net.Http

View File

@ -1,20 +1,16 @@
nav { .nav-link-bar {
margin-bottom: 10px; border: 1px solid #dee2e6;
border-top-left-radius: 0.25rem;
border-top-right-radius: 0.25rem;
padding: 0.5rem 1rem;
background-color: #fff;
} }
nav .nav-link-bar { nav .dropdown .nav-link-close.dropdown-toggle:after {
border: 1px solid #dee2e6; display: none;
border-top-left-radius: 0.25rem; }
border-top-right-radius: 0.25rem;
padding: 0.5rem 1rem;
background-color: #fff;
}
nav .dropdown .nav-link-close.dropdown-toggle:after { .dropdown-item, .nav-tabs .nav-link .fa, .nav-link, .nav-link-bar, .page-link {
display: none;
}
.dropdown-item, .nav-tabs .nav-link .fa, .nav-link, .nav-link-bar {
cursor: pointer; cursor: pointer;
} }
@ -62,3 +58,12 @@
.nav-link-close { .nav-link-close {
padding: 0.5rem 1rem; padding: 0.5rem 1rem;
} }
.table th, .table td {
padding: 0.5rem;
}
.pagination-bar {
flex: 1 1 auto;
margin-bottom: 1rem;
}