<template> <!-- 显示表格 --> <div class="h-100 page-table" ref="tableBox" v-loading="listInfo.loading" element-loading-text="加载中" element-loading-spinner="el-icon-loading" element-loading-background="rgba(0,0,0,0.8)"> <el-table class="h-100" :data="data" row-key="id" default-expand-all :class="className" :max-height="listInfo.tableHeight" :header-cell-style="{textAlign:'center'}" :tree-props="{children: 'children', hasChildren: 'hasChildren'}" @select-all="handleSelectionChange" @selection-change="handleSelectionChange" > <el-table-column v-if="checkBox" type="selection" width="55" align="center" :selectable="checkboxInit" /> <el-table-column v-if="tabIndex" label="序号" align="center" :width="fieldList.length === 0 ? '' : 60" > <template slot-scope="scope"> <span>{{ scope.$index + 1 + (listInfo.query.current - 1) * listInfo.query.size }}</span> </template> </el-table-column> <el-table-column v-for="(item, index) in fieldList" :key="index" :prop="item.value" :label="item.label" :fixed="item.fixed" :align="item.align ? item.align : 'center'" :width="item.width" :min-width="`${item.minWidth}`" :show-overflow-tooltip="item.tooltip" > <template slot-scope="scope"> <!-- solt自定义列--> <template v-if="item.type === 'slot'"> <slot :name="'col-' + item.value" :row="scope.row" /> </template> <!-- 嵌套表格 --> <template v-else-if="item.children"> <el-table-column v-for="(childItem, childIndex) in item.children" :key="childIndex" :prop="childItem.value" :label="childItem.label" align="center" :width="item.width" :min-width="item.minWidth" /> </template> <!-- 图片 --> <el-image v-else-if="item.type === 'image' && scope.row[item.value]" :src="scope.row[item.value]" fit="fill"></el-image> <!-- 其他 --> <span v-else> {{ getDataName({dataList: listTypeInfo[item.list], value: 'value', label: 'key', data: scope.row[item.value]}) || '-' }} </span> </template> </el-table-column> <el-table-column v-if="handle" :key="'handle'" :fixed="handle.fixed" align="center" :label="handle.label" :width="handle.width" > <template v-slot="scope"> <template v-for="(item, index) in handle.btList"> <!-- 自定义操作类型 --> <slot v-if="item.slot" :name="`bt-${item.event}`" :data="{item, row: scope.row}"/> <!-- 操作按钮 --> <el-button v-if="!item.slot && item.show && (!item.ifRender || item.ifRender(scope.row))" :key="index" :size="item.size || 'small'" :type="item.type" :icon="item.icon" v-has="item.has ? item.has : ''" :disabled="item.disabled" :loading="scope.row[item.loading]" @click="handleClick(item.event, scope.row, scope.$index)" > {{ item.label }} </el-button> </template> </template> </el-table-column> </el-table> <!-- 分页组件 --> <template v-if="pagination"> <el-pagination background layout="total, sizes, prev, pager, next, jumper" :total="listInfo.total" :pager-count="5" :page-sizes="[10, 20, 30, 40]" :page-size="listInfo.query.size" :current-page.sync="listInfo.query.current" @current-change="handleCurrentChange" @size-change="handleSizeChange" /> </template> </div> </template> <script> export default{ props:{ //自定义样式名 className:{ type:String }, //获取数据的接口 apiUrl:{ type:String }, //是否显示序号 tabIndex:{ type:Boolean, default:false }, //表格字段配置 fieldList:{ type:Array, default:()=>{ return [] } }, //刷新 refresh:{ type:Number }, //重置当前页 initCurpage:{ type:Number }, //表格数据 data:{ type:Array }, //是否有选中框 checkBox:{ type:Boolean, default:false }, //操作栏配置 handle:{ type:Object }, //监听高度 listenHeight:{ type:Boolean, default:true }, //类型列表 listTypeInfo:{ type:Object, default:()=>{ return {} } }, //是否分页 pagination:{ type:Boolean, default:false }, //查询条件 query:{ type: Object, default: () => { return {} } }, //表格最大高度 tableHeight:{ type:Number }, //表格数据展示类型 tableType:{ type:String }, loading:{ type:Boolean, default:true }, //用于区分多个表格选中的结果 type:{ type:String, default:'all' } }, data(){ return{ //列表相关 listInfo:{ tableHeight:null, //表格最大高度 total:0, //总条数 loading:false, //加载动画 query:{ //查询条件 current:1, //当前页 size:10, //每页条数 } }, } }, watch:{ initCurpage(){ this.listInfo.query.current = 1 }, refresh:{ handler(newVal,oldVal){ if (this.apiUrl === '') return this.getList(this.apiUrl) }, deep: true } }, mounted(){ setTimeout(() =>{ this.listInfo.tableHeight = this.getTableHeight() },0) window.addEventListener('resize', () => { this.listInfo.tableHeight = this.getTableHeight() }) }, methods:{ // 处理参数 handleParams(){ const obj = {} for (const key in this.query) { // if (this.query[key] || this.query[key] === 0) { obj[key] = this.query[key] // } } // 如果不需要分页,则无分页相关参数 const dataObj = this.pagination ? {data:obj} : {data:{}} return this.pagination ? { ...this.listInfo.query, ...dataObj } : dataObj }, //选中数据 handleSelectionChange(rows){ this.$emit('handleEvent', this.type, rows); }, //派发按钮点击事件 handleClick(event, data, index){ this.$emit('handleClick', event, data, index); }, /** * 通过key找到在列表中对应的显示 * @param {Object} obj * @param obj.dataList 数据列表 * @param obj.value 数据的值对应的字段名称 例如 'value' * @param obj.label 数据的说明对应的字段名称 例如 'label' * @param obj.data 当前传入的数据值 * @return name 返回当前传入值在数组中对应的名字 */ getDataName(obj){ let name = obj.data if (Array.isArray(obj.dataList) && obj.dataList.length > 0) { for (let i = 0; i < obj.dataList.length; i++) { if (obj.dataList[i][obj.value] === obj.data) { name = obj.dataList[i][obj.label] } } } return name }, handleCurrentChange(val){ this.listInfo.query.current = val //当前页 this.$emit('currentPage',val) this.getList(this.apiUrl) }, handleSizeChange(val){ this.listInfo.query.size = val //当前一页多少条 this.getList(this.apiUrl) }, //获取数据 getList(url){ // return new Promise((resolve, reject)=>{ //每次调用接口自动绑定最新数据 this.listInfo.loading = true this.$http.post(url,this.handleParams()).then(res=>{ this.listInfo.loading = false if(res.data.code === 200 || res.data.code === 1){ //使外面可以访问到表格数据 let arr = Array.isArray(res.data.data) ? res.data.data : res.data.data.list if(this.tableType === 'tree'){ arr = this.$fn.handleTree(arr) } if(arr){ arr.forEach(item => { item.createTime = this.$fn.switchTime(item.createTime, 'YYYY-MM-DD hh:mm:ss') item.updateTime = this.$fn.switchTime(item.updateTime, 'YYYY-MM-DD hh:mm:ss') }) this.$emit('update:data', arr) }else{ this.$emit('update:data', []) } if(this.pagination){ this.listInfo.total = res.data.data.total } // resolve(res) }else{ this.$message({ showClose: true, message: res.data.msg, type: 'error', duration: 3000 }) // reject() } }).catch((err)=>{ console.log(err) this.listInfo.loading = false // reject() }) // }) }, //得到表格高度 getTableHeight(){ //当表格存在的时候才执行操作 if (document.getElementsByClassName('el-table').length === 0) { return } let _baseHeight = this.pagination ? 42 : 0 if(this.$refs.tableBox && this.$refs.tableBox.offsetHeight){ let resultHeight = this.$refs.tableBox.offsetHeight let _height = resultHeight -_baseHeight return _height } }, //判断是否可以被选中 checkboxInit(row,index){ if(row.registered){ return 0 //不可勾选 }else{ return 1 //可勾选 } } } } </script> <style lang="scss" scoped> /deep/ .el-table{ @include fd(); // .el-table__body tr.hover-row>td{ // background-color: transparent; // } .el-table__body tr.hover-row>td{ background-color: #043031 !important; } .el-table__fixed-right::before, .el-table__fixed::before{ background-color: transparent; } .el-table__fixed-right-patch{ background-color: aqua; } .el-table__fixed-right-patch{ border-bottom-color: aqua; } .el-table__body-wrapper{ flex: 1; } } /deep/ .el-pagination{ margin-top: 10px; } /deep/ .el-pagination.is-background{ .el-pager li:not(.disabled).active{ color: #fff; background-color: #409EFF !important; } } </style>