赞
踩
今天在搬砖的时候发现了一个问题,当用el-table组件画表格,并且存在合并行时,鼠标浮动的高亮样式有些问题,如下图。
可以看到虽然已经合并成为了一行但是,高亮部分的显示样式仍然是分家状态。由于我画的表格需要有固定列,虽然百度了一些大神的方法,但是仍然没有完全解决我的问题。
找了好久,发现了两个可以解决同时包含固定列和合并列表格高亮错位问题的方法。
方法一
- <template>
- <el-table
- :row-class-name="tableRowClassName"
- :data="tableData"
- :span-method="objectSpanMethod"
- border
- style="width: 100%; margin-top: 20px"
- @cell-mouse-enter="handleCellMouseEnter"
- @cell-mouse-leave="handleCellMouseLeave">
- <el-table-column
- prop="id"
- fixed
- label="ID"
- width="180"/>
- <el-table-column
- prop="name"
- fixed
- label="姓名"/>
- <el-table-column
- prop="amount1"
- label="数值 1(元)"/>
- <el-table-column
- prop="amount2"
- label="数值 2(元)"/>
-
- <el-table-column
- prop="amount3"
- label="数值 3(元)"/>
- <el-table-column
- prop="amount4"
- label="数值 4(元)"/>
- </el-table>
- </template>
-
- <script>
- data() {
- return {
- currentIndex: '',
- tableData: [{
- id: '12987122',
- name: '王小虎',
- order: '1',
- amount1: '234',
- amount2: '3.2',
- amount4: '4.43',
- amount3: 10
- }, {
- id: '12987123',
- name: '王小虎',
- order: '1',
- amount1: '165',
- amount2: '4.43',
- amount4: '4.43',
- amount3: 12
- },
- {
- id: '12987124',
- name: '王小虎',
- amount1: '324',
- amount2: '1.9',
- order: '2',
- amount4: '4.43',
- amount3: 9
- }, {
- id: '12987125',
- name: '王小虎',
- amount1: '621',
- amount2: '2.2',
- order: '2',
- amount4: '4.43',
- amount3: 17
- }, {
- id: '12987126',
- name: '王小虎',
- amount1: '539',
- order: '3',
- amount2: '4.1',
- amount4: '4.43',
- amount3: 15
- }]
- }
- }
- methods: {
-
- // 鼠标移入
- handleCellMouseEnter(row, column, rowIndex, columnIndex) {
- //标记当前是哪个分组
- this.currentIndex = row.order
- },
- // 鼠标移出
- handleCellMouseLeave() {
- //移出是清空光标
- this.currentIndex = ''
- },
- tableRowClassName({ row, column, rowIndex, columnIndex }) {
- //逻辑判断决定是否修改样式,如果分组一致则使用同一个样式
- if (row.order == this.currentIndex) {
- return 'hover-bg'
- } else {
- return ''
- }
- },
- // 合并行方法
- objectSpanMethod({ row, column, rowIndex, columnIndex }) {
- if (columnIndex === 0 || columnIndex === 1) {
- if (rowIndex % 2 === 0) {
- return {
- rowspan: 2,
- colspan: 1
- }
- } else {
- return {
- rowspan: 0,
- colspan: 0
- }
- }
- }
- }
- }
- </script>
-
- <style lang="scss" scoped>
-
- .el-table{
- border: 1px solid #e6e6e6;
- /deep/ thead th {
- background-color: #f5f5f5;
- }
- /deep/ tr {
- height: 20px;
- }
- /deep/ .el-table__body .el-table__row.hover-bg td{
- background-color: #F5F7FA;
- }
- }
- </style>

方法一是通过el-table自带的 ‘row-class-name‘ 属性实现的,原理是每当鼠标切换一个行时,都会触发tableRowClassName方法,通过order判断是否为同一组的数据,如果是则修改样式。
方法二
- // 鼠标移入
- handleCellMouseEnter(row, column, cell, event) {
- this.$nextTick(() => {
- //获取鼠标移入时的tbody结点
- const tbody = this.$el.querySelector('.el-table__body-wrapper table tbody')
- //循环获取tr结点
- for (let i = 0; i < tbody.children.length; i++) {
- const tr = tbody.children[i]
- //逻辑判断,这步已经获取到了tr所以tableData[i]与tr是一致的
- if (this.tableData[i].order == row.order) {
- //改变tr的背景颜色
- tr.style.background = '#f5f5f5'
- //循环获取td,改变td的样式
- for (let j = 0; j < tr.children.length; j++) {
- const td = tr.children[j]
- td.style.background = '#f5f5f5'
- }
- } else {
- tr.style.background = '#fff'
- for (let j = 0; j < tr.children.length; j++) {
- const td = tr.children[j]
- td.style.background = '#fff'
- }
- }
- }
-
- //这部分是为了修改固定列部分样式的代码,逻辑与上面的一致
- const tbody_fix = this.$el.querySelector('.el-table__fixed table tbody')
- for (let i = 0; i < tbody_fix.children.length; i++) {
- const tr = tbody_fix.children[i]
-
- if (this.tableData[i].order == row.order) {
- tr.style.background = '#f5f5f5'
- for (let j = 0; j < tr.children.length; j++) {
- const td = tr.children[j]
- td.style.background = '#f5f5f5'
- }
- } else {
- tr.style.background = '#fff'
- for (let j = 0; j < tr.children.length; j++) {
- const td = tr.children[j]
- td.style.background = '#fff'
- }
- }
- }
- })
-
- },
- // 鼠标移出
- handleCellMouseLeave(row, column, cell, event) {
- //与鼠标移入的逻辑一致
- this.$nextTick(() => {
- const tbody = this.$el.querySelector('.el-table__body-wrapper table tbody')
- for (let i = 0; i < tbody.children.length; i++) {
- const tr = tbody.children[i]
-
- if (this.tableData[i].order == row.order) {
- tr.style.background = '#fff'
- for (let j = 0; j < tr.children.length; j++) {
- const td = tr.children[j]
- td.style.background = '#fff'
- }
- }
- }
-
- //这部分是为了修改固定列部分样式的代码
- const tbody_fix = this.$el.querySelector('.el-table__fixed table tbody')
- for (let i = 0; i < tbody_fix.children.length; i++) {
- const tr = tbody_fix.children[i]
-
- if (this.tableData[i].order == row.order) {
- tr.style.background = '#fff'
- for (let j = 0; j < tr.children.length; j++) {
- const td = tr.children[j]
- td.style.background = '#fff'
- }
- }
- }
- })
- },

方法二是直接通过nextTick获取结点样式进行逻辑判断修改样式实现的。
实现效果:
需要注意的是,这两种方法都需要事先将准备渲染的list进行分组,例如 tableData中的order就相当于一个组id,带有相同的order值的数据,显示的样式应该是一致的;这个无需特意添加,比如要求name相同的分为一组则name就可以作为组id,如果实在没有的话,那就需要手动循环进行添加啦!
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。