最近有个需求是用表格渲染大量数据,寻常使用用el-table渲染时,发现浏览器崩溃了눈_눈 。需要有效的解决方案来确保应用的流畅性,在这里记录一下Virtualized Table虚拟化表格动态渲染大量数据的用法。
Element Plus 官网中的虚拟化表格UI比较丑,我们需要改一下,跟el-table基本保持。
编辑
实现步骤
-
渲染表格
在模板部分,我们使用 el-table-v2 组件来渲染表格,并通过插槽自定义单元格内容。其中header-cell插槽可自定义表头,一行显示,超出显示...,鼠标悬停显示tooltip。cell插槽渲染行数据与此类似(也许出于性能考虑,el-table-v2鼠标悬停显示的是原生:title的形式)。需要注意的是,虚拟化表格的宽高是必传的,且是数字的类型。
<el-table-v2 border :data="tableData" :columns="tableColumns" :width="tableWidth" :height="tableHeight" fixed>
<template #header-cell="{ column }">
<el-tooltip effect="dark" :content="column.title" placement="top" raw-content>
<span class="line-clamp-1 break-all">{{ column.title }}</span>
</el-tooltip>
</template>
<template #cell="{ column, rowData }">
<el-tooltip
effect="dark"
:content="rowData[column.dataKey]"
placement="top"
raw-content
v-if="rowData[column.dataKey]"
>
<span class="line-clamp-1 break-all">{{ rowData[column.dataKey] }}</span>
</el-tooltip>
</template>
</el-table-v2>
-
引入TypeScript类型
import type { Column } from 'element-plus'
-
设置表格数据和列
通过 API 请求获取数据,并动态生成表格列。
const tableData = ref<Record<string, any>[]>([])
const tableColumns = computed<Column[]>(() => {
if (!getDataPageApi.response?.data?.fieldList) return []
let obj = getDataPageApi.response?.data?.fieldList[0]
let list = []
list.push({
dataKey: IndexKey.key,
key: IndexKey.key,
title: IndexKey.label,
width: 100,
fixed: true,
})
for (const key in obj) {
if (Object.prototype.hasOwnProperty.call(obj, key)) {
list.push({
dataKey: key,
key: key,
title: key,
width: 200,
})
}
}
return list
})
-
计算表格宽高
根据窗口大小动态设置表格的宽高,并监听窗口变化以调整布局。
const tableWidth = ref(0)
const tableHeight = computed(() => {
const headerH = 50
const rowH = 50
if (tableData.value.length < 10) {
return headerH + rowH * tableData.value.length
} else {
return rowH * 10 + headerH
}
})
const onTableWidthChange = () => {
const table = document.getElementById('myTable')
tableWidth.value = table?.offsetWidth! || 0
}
window.addEventListener('resize', onTableWidthChange)
-
样式定制
我们通过 scoped 样式自定义表格的外观,确保其在各种屏幕尺寸上都能良好显示。
<style lang="less" scoped>
:deep(.el-table-v2__header-cell) {
flex: 1 !important;
background-color: #e7e7e7;
color: #00000088;
box-shadow: -1px 0 0 0 #ebeef5 inset; /* 仅在右边显示阴影 */
&:last-child {
box-shadow: none;
}
}
:deep(.el-table-v2__row-cell) {
flex: 1 !important;
box-shadow: -1px 0 0 0 #ebeef5 inset; /* 仅在右边显示阴影 */
&:last-child {
box-shadow: none;
}
}
</style>
实现效果
总体效果
编辑
表头超出显示省略号
编辑
以上就是虚拟化表格动态渲染大量数据的实现啦^-^