/* * FileName: lb-table.vue * Remark: element table * Project: lb-element-table * Author: 任超 * File Created: Tuesday, 19th March 2019 9:55:27 am * Last Modified: Tuesday, 19th March 2019 9:55:34 am * Modified By: 任超 */ <template> <div :class="['lb-table', customClass]"> <el-table v-if="!heightNumSetting" class="table-fixed" :row-style="{ height: '50px' }" ref="elTable" :border='border' :row-class-name="tableRowClassName" :show-header='showHeader' @row-click="singleElection" v-bind="$attrs" :height="tableHeight" v-on="$listeners" :data="data" style="width: 100%" :span-method="this.merge ? this.mergeMethod : this.spanMethod"> <el-table-column width="45" align="center" v-if="isRadio"> <template slot-scope="scope"> <el-radio v-model="selected" :label="scope.$index"></el-radio> </template> </el-table-column> <lb-column v-bind="$attrs" v-for="(item, index) in column" :key="index" :column="item"> </lb-column> </el-table> <el-table v-else ref="elTable" class="table-fixed heightNumSetting" :row-style="{ height: '50px' }" :border='border' :row-class-name="tableRowClassName" :show-header='showHeader' @row-click="singleElection" v-bind="$attrs" :max-height="maxHeight" :height="tableHeight" v-on="$listeners" :data="data" style="width: 100%" :span-method="this.merge ? this.mergeMethod : this.spanMethod"> <el-table-column width="45" align="center" v-if="isRadio"> <template slot-scope="scope"> <el-radio v-model="selected" :label="scope.$index"></el-radio> </template> </el-table-column> <lb-column v-bind="$attrs" v-for="(item, index) in column" :key="index" :column="item"> </lb-column> </el-table> <br> <el-pagination class="lb-table-pagination" v-if="pagination" v-bind="$attrs" v-on="$listeners" background layout="total, prev, pager, next" @current-change="paginationCurrentChange" :style="{ 'margin-top': paginationTop, 'text-align': paginationAlign }"> </el-pagination> </div> </template> <script> import LbColumn from './lb-column' export default { props: { column: Array, data: Array, spanMethod: Function, pagination: { type: Boolean, default: true, }, isRadio: { type: Boolean, default: false, }, border: { type: Boolean, default: true, }, showHeader: { type: Boolean, default: true, }, paginationTop: { type: String, default: '0', }, heightNum: { type: Number, default: 0, }, maxHeight: { type: Number, default: 500 }, minHeight: { type: Number, default: 160 }, heightNumSetting: { type: Boolean, default: false, }, customClass: { type: String, default: '', }, paginationAlign: { type: String, default: 'left', }, calcHeight: { type: Number, default: 170 }, merge: Array, }, components: { LbColumn, }, /** * @description: data * @author: renchao */ data () { return { tableHeight: 'auto', mergeLine: {}, mergeIndex: {}, selected: '' } }, /** * @description: created * @author: renchao */ created () { this.getMergeArr(this.data, this.merge) this.getHeight() }, computed: { dataLength () { return [] || this.data.length }, }, methods: { /** * @description: 单选 * @param {*} row * @author: renchao */ singleElection (row) { this.selected = this.data.indexOf(row); // this.$emit('row-click', row) }, /** * @description: tableRowClassName * @author: renchao */ tableRowClassName ({ row, rowIndex }) { if (rowIndex % 2 === 1) { return 'interlaced'; } }, /** * @description: getHeight * @author: renchao */ getHeight () { if (!this.heightNumSetting) { let _this = this if (this.heightNum == 0) { _this.$nextTick(() => { if (document.querySelector(".tags-view-container")) { window.addEventListener('resize', () => { if (_this.calcHeight == 170) { _this.tableHeight = _this.calcHeightx(170) } else { _this.tableHeight = _this.calcHeightx(_this.calcHeight) } }); if (_this.calcHeight == 170) { _this.tableHeight = _this.calcHeightx(170) } else { _this.tableHeight = _this.calcHeightx(_this.calcHeight) } } else { window.addEventListener('resize', () => { _this.tableHeight = _this.calcHeightx(_this.calcHeight) }); _this.tableHeight = _this.calcHeightx(_this.calcHeight) } }) } else { _this.tableHeight = window.innerHeight - _this.heightNum } } else { this.$nextTick(() => { let arr = document.getElementsByClassName('heightNumSetting'); [...arr].forEach(item => { this.minHeight && (item.style.minHeight = this.minHeight + 'px') }) }) } }, /** * @description: calcHeightx * @param {*} value * @param {*} wappered * @author: renchao */ calcHeightx (value, wappered = true) { //项目自定义的公共header部分的高度,可忽略 let header = document.querySelector(".from-clues-header").offsetHeight; //value为动态计算table界面高度时,减去的其他空白部分,需自行在调试找到临界值,剩下的就是table表格的高度(包含header+body部分) value = value == undefined ? 100 : value; if (document.querySelector(".tags-view-container")) { let tagsView = document.querySelector(".tags-view-container").offsetHeight; var res = window.innerHeight - parseInt(header) - value - parseInt(tagsView); } else { var res = window.innerHeight - parseInt(header) - value; } if (wappered) { //通过原生方法,获取dom节点的高度------获取element-ui table表格body的元素 let wapper = window.document.getElementsByClassName('el-table__body-wrapper'); //通过原生方法,获取dom节点的高度------获取element-ui table表格header的元素 let header = window.document.getElementsByClassName('el-table__header-wrapper'); //必须加延时,要不然赋不上去值 setTimeout(() => { //通过上边计算得到的table高度的value值,减去table表格的header高度,剩下的通过dom节点直接强行赋给table表格的body wapper[0].style.height = (value - header[0].clientHeight) }, 100) } return res; }, /** * @description: clearSelection * @author: renchao */ clearSelection () { this.$refs.elTable.clearSelection() }, /** * @description: toggleRowSelection * @author: renchao */ toggleRowSelection (row, selected) { this.$refs.elTable.toggleRowSelection(row, selected) }, /** * @description: toggleAllSelection * @author: renchao */ toggleAllSelection () { this.$refs.elTable.toggleAllSelection() }, /** * @description: toggleRowExpansion * @param {*} row * @param {*} bsm * @author: renchao */ toggleRowExpansion (row, expanded) { this.$refs.elTable.toggleRowExpansion(row, expanded) }, /** * @description: setCurrentRow * @param {*} row * @author: renchao */ setCurrentRow (row) { this.$refs.elTable.setCurrentRow(row) }, /** * @description: setCurrentRow * @author: renchao */ clearSort () { this.$refs.elTable.clearSort() }, /** * @description: clearFilter * @param {*} columnKey * @author: renchao */ clearFilter (columnKey) { this.$refs.elTable.clearFilter(columnKey) }, /** * @description: doLayout * @author: renchao */ doLayout () { this.$refs.elTable.doLayout() }, /** * @description: sort * @param {*} prop * @param {*} order * @author: renchao */ sort (prop, order) { this.$refs.elTable.sort(prop, order) }, /** * @description: paginationCurrentChange * @param {*} val * @author: renchao */ paginationCurrentChange (val) { this.$emit('p-current-change', val) }, /** * @description: getMergeArr * @param {*} tableData * @param {*} merge * @author: renchao */ getMergeArr (tableData, merge) { if (!merge) return this.mergeLine = {} this.mergeIndex = {} merge.forEach((item, k) => { tableData.forEach((data, i) => { if (i === 0) { this.mergeIndex[item] = this.mergeIndex[item] || [] this.mergeIndex[item].push(1) this.mergeLine[item] = 0 } else { if (data[item] === tableData[i - 1][item]) { this.mergeIndex[item][this.mergeLine[item]] += 1 this.mergeIndex[item].push(0) } else { this.mergeIndex[item].push(1) this.mergeLine[item] = i } } }) }) }, /** * @description: mergeMethod * @author: renchao */ mergeMethod ({ row, column, rowIndex, columnIndex }) { const index = this.merge.indexOf(column.property) if (index > -1) { const _row = this.mergeIndex[this.merge[index]][rowIndex] const _col = _row > 0 ? 1 : 0 return { rowspan: _row, colspan: _col, } } }, }, watch: { /** * @description: merge * @author: renchao */ merge () { this.getMergeArr(this.data, this.merge) }, /** * @description: dataLength * @author: renchao */ dataLength () { this.getMergeArr(this.data, this.merge) } }, } </script> <style rel="stylesheet/scss" scoped lang="scss"> .lb-table { margin-top: 1px; .interlaced { background: #fafcff; border: 1px solid #ebf2fa; } } /deep/.el-table .cell { padding-left: 3px; padding-right: 3px; } /deep/.el-radio__label { display: none; } </style>