基于element-ui的 分页表格组件
文章目录
- 实现思路
- 组件代码
- 使用案例
- 系列文章
实现思路
搜索网上的分页表格案例,大部分是使用for循环来渲染表格列,那样只能支持纯展示的数据,对于需要特殊处理的字段无法支持(eg:案例中的’状态’列,需要将状态码转换成中文)。
为了解决这个问题,使用了插槽特性 (了解一下插槽)。
基于组件化思想,利用elemeut-ui 的 <el-table>
和 <el-pagination>
封装一个前端分页表格组件。使用方式基本和<el-table>
一样,组件样式大家看着调。
组件功能
- 分页功能开关
- 支持前端分页
- 支持分页参数的设置
效果图
组件代码
代码稍长,必要的注释都注明在代码中,文末附使用案例。建议先跑起来使用案例看效果,再深入代码。
代码上传在 前端代码在线编辑器codesandbox 中,可直接查看编辑:此链接
了解下 codesanbox
<template>
<el-container class="page-table-ctn">
<el-table v-bind="$attrs" v-on="$listeners" :data="filterData" ref="pageTable">
<slot></slot>
</el-table>
<el-footer class="footer" v-if="paging">
<div class="size-info">
<span v-if="totalSize > 1">显示第 {
{
start}} 条到第 {
{
end}} 条的数据,</span>
共{
{
totalSize }} 条数据
</div>
<el-pagination
v-bind="$attrs"
v-on="$listeners"
:pager-count="5"
:layout="layout"
:page-sizes="pageSizes"
:page-size="currPageSize"
:current-page="currPage"
:total="totalSize"
style="float:right"
@current-change="handleCurrentChange"
@size-change="handleSizeChange"
></el-pagination>
</el-footer>
</el-container>
</template>
<script>
export default {
name: "page-table",
props: {
data: {
type: Array,
require: true,
default: []
},
currentPage: {
type: Number,
default: 1
},
pageSize: {
type: Number,
default: 10
},
pageSizes: {
type: Array,
default: () => [10, 30, 50, 100]
},
layout: {
type: String,
default: "sizes, prev, pager, next, jumper"
},
// 是否分页,默认为true,即分页。(不分页时将每页条数设置最大。)
paging: {
type: Boolean,
default: true
}
},
data() {
return {
allData: this.data, // 全量表格数据(前端分页)
filterData: [], // 表格展示数据
start: 1,
end: 1,
totalSize: this.data.length,
currPageSize: this.paging ? this.pageSize : Number.MAX_SAFE_INTEGER,
currPage: this.currentPage
};
},
methods: {
handleSizeChange(value) {
this.currPage = 1;
this.currPageSize = value;
this.handleChange();
},
handleCurrentChange(value) {
this.currPage = value;
this.handleChange();
},
handleChange(reset) {
// reset:是否重置页码
if (reset) {
this.currPage = 1;
}
this.renderTable();
},
renderTable() {
if (this.totalSize > this.currPageSize) {
// 总行数大于一页
let startIndex = (this.currPage - 1) * this.currPageSize,
endIndex = this.currPage * this.currPageSize;
this.start = startIndex + 1;
this.end = this.totalSize < endIndex ? this.totalSize : endIndex;
this.filterData = this.allData.slice(startIndex, endIndex); //[start,end)
} else if (this.totalSize > 0) {
// 总行数小于等于一页
this.currPage = 1;
this.start = 1;
this.end = this.totalSize;
this.filterData = this.allData;
} else {
// 无数据
this.currPage = 1;
this.start = 0;
this.end = 0;
this.filterData = [];
}
},
setData(value) {
this.allData = value;
this.totalSize = value.length;
this.renderTable();
},
//<el-table>自带的方法 start
setCurrentRow(row) {
this.$refs.pageTable.setCurrentRow(row);
}
//...
//<el-table>自带的方法 end
},
watch: {
data() {
this.setData(this.data ? this.data : []);
}
},
mounted() {
}
};
</script>
<style lang="scss" scoped>
.page-table-ctn {
> .el-table {
width: auto;
margin: 14px;
border: 1px solid #ebeef5;
border-bottom: unset;
}
> .footer {
height: 40px !important;
.size-info {
display: inline;
font-size: 12px;
color: #666666;
}
}
}
</style>
使用案例
<template>
<div>
前端分页案例:
1.设置表格数据
<PageTable
:data="tableData"
:currentPage=2
:pageSizes="[3,5,10]"
:pageSize=5
:paging=true
ref="dataTable"
>
<el-table-column type="selection" width="55"></el-table-column>
<el-table-column label="账号" prop="name"></el-table-column>
<el-table-column label="名称" prop="nickname"></el-table-column>
<el-table-column label="邮箱" prop="email"></el-table-column>
<el-table-column label="状态">
<template slot-scope="scope">{
{
scope.row.state%2===0?'正常':'锁定' }}</template>
</el-table-column>
<el-table-column label="操作" width="100">
<template slot-scope="scope">
<el-button size="small" type="text" @click.stop="clickFunc(scope.row)">操作按钮</el-button>
</template>
</el-table-column>
</PageTable>
</div>
</template>
<script>
// 引入表格组件
import PageTable from "./PageTable.vue";
export default {
components: {
PageTable // 引用表格组件
},
data() {
return {
tableData: []
};
},
methods: {
queryData() {
// 模拟后台数据
let data = [];
for (var i = 1; i <= 23; i++) {
data.push({
name: i, nickname: i, email: i, state: i });
}
this.tableData = data;
},
clickFunc(row) {
// console.log(row);
alert(JSON.stringify(row));
}
},
mounted() {
// 发起查询请求
this.queryData();
}
};
</script>
<style lang="scss" scoped>
</style>
系列文章
- 分页表格组件
- 动态列分页表格组件(动态控制表格列的显隐)
- 后端分页表格组件
- 终极分页表格组件(前/后端分页、动态列)
end
还没有评论,来说两句吧...