elementui 的 table 组件回显问题
"vue": "^2.7.16",
"element-ui": "^2.15.14",
问题描述:
场景:首先我们是通过接口获取到数据之后 然后将返回的数据回显到表格上面
问题:直接将后端返回的数据循环的通过toggleRowSelection进行回显,发现无法选中!
问题出现的原因
通过 element 源码发现,table 在回显的时候必须使用表格里面的对象(实际是引用的地址),但实际上后端返回的数据对象是另一个对象地址 两者不是一样的 所以无法回显
源码地址:https://github.com/ElemeFE/element/blob/v2.15.14/packages/table/src/util.js
export function toggleRowStatus(statusArr, row, newVal) {
let changed = false;
const index = statusArr.indexOf(row);
const included = index !== -1;
const addRow = () => {
statusArr.push(row);
changed = true;
};
const removeRow = () => {
statusArr.splice(index, 1);
changed = true;
};
if (typeof newVal === 'boolean') {
if (newVal && !included) {
addRow();
} else if (!newVal && included) {
removeRow();
}
} else {
if (included) {
removeRow();
} else {
addRow();
}
}
return changed;
}
在做对比的时候使用了 const index = statusArr.indexOf(row)。
因为table的数据是来自列表接口返回的list,而选中的模版是从详情接口里面获取的,对象的引用改变了。
所以 statusArr.indexOf(row) 找不到对象,toggleRowSelection 不会生效。
所以想要生效,只能将详情的数据取找 table 的数据 将找到的 table 数据通过toggleRowSelection进行回显。
全部代码:
<template>
<div>
<el-table
ref="multipleTable"
:data="tableData"
tooltip-effect="dark"
style="width: 100%"
row-key="id"
@select="handleSingleSelect"
>
<el-table-column
type="selection"
width="55"
reserve-selection
></el-table-column>
<el-table-column label="日期" width="120">
<template slot-scope="scope">{{ scope.row.date }}</template>
</el-table-column>
<el-table-column prop="id" label="id" width="120"></el-table-column>
<el-table-column prop="name" label="姓名" width="120"></el-table-column>
<el-table-column
prop="address"
label="地址"
show-overflow-tooltip
></el-table-column>
</el-table>
<div style="margin-top: 20px">
<span>需要回显的数据</span>
<br>
<div v-for="(item, index) in beforeSelect" :key="index">{{ item }}</div>
</div>
<div style="margin-top: 20px">
<el-button @click="clearAllSelection()">清除所有选中</el-button>
<el-button @click="correctDisplayBeforeSelection()">
回显之前选中的数据(正确的方式)
</el-button>
<el-button @click="errorDisplayBeforeSelection()">
回显之前选中的数据(错误的方式)
</el-button>
<br>
------------
<br>
<el-button @click="getResponseSelectionData()">
模拟后端返回的数据
</el-button>
<el-button @click="correctResponseDisplayBeforeSelection()">
回显后端返回的的数据(正确的方式)
</el-button>
<el-button @click="errorResponseDisplayBeforeSelection()">
回显后端返回的的数据(错误的方式)
</el-button>
<br>
<br>
<el-button @click="clearBeforeSelection()">
清空需要回显的数据
</el-button>
</div>
</div>
</template>
<script>
export default {
data() {
return {
tableData: [
{
date: '2016-05-03',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 0,
},
{
date: '2016-05-02',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 1,
},
{
date: '2016-05-04',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 2,
},
{
date: '2016-05-01',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 3,
},
{
date: '2016-05-08',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 4,
},
{
date: '2016-05-06',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 5,
},
{
date: '2016-05-07',
name: '王小虎',
address: '上海市普陀区金沙江路 1518 弄',
id: 6,
},
],
multipleSelection: [],
beforeSelect: [],
};
},
methods: {
clearAllSelection() {
this.$refs.multipleTable.clearSelection();
},
correctDisplayBeforeSelection() {
this.beforeSelect.forEach((s) => {
this.$refs.multipleTable.toggleRowSelection(s, true);
});
},
errorDisplayBeforeSelection() {
const copyData = JSON.parse(JSON.stringify(this.beforeSelect))
copyData.forEach((s) => {
this.$refs.multipleTable.toggleRowSelection(s, true);
});
},
getResponseSelectionData() {
const responseData = [
{
// date: '2016-05-06',
// name: '王小虎',
// address: '上海市普陀区金沙江路 1518 弄',
id: 5,
},
{
// date: '2016-05-07',
// name: '王小虎',
// address: '上海市普陀区金沙江路 1518 弄',
id: 6,
},
];
this.beforeSelect = responseData
},
handleSingleSelect(selection) {
console.log('selection', selection);
this.beforeSelect = selection;
},
clearBeforeSelection() {
this.beforeSelect = []
},
errorResponseDisplayBeforeSelection() {
this.beforeSelect.forEach((s) => {
this.$refs.multipleTable.toggleRowSelection(s, true);
});
},
correctResponseDisplayBeforeSelection() {
this.tableData.forEach(s => {
this.beforeSelect.forEach(v => {
if (s.id === v.id) {
this.$refs.multipleTable.toggleRowSelection(s, true);
}
})
})
}
},
};
</script>