起因
之前一直用的是 antdv 1.x + vue2 版本, 后面看到vue2即将停止支持的消息,索性利用这个契机将新项目迁移到 antdv 4.x + vue3。
插点题外话,不得不说新旧版本之间变化还是挺多的,尝试用 vue3 + ts 写过一段时间,ts强制类型声明是个让我难受的点,虽然类型声明是个好习惯,但是对于数据类型众多而功能单一的小项目而言,代价太过沉重。所以还是用回了js。
antdv1.x 和 antdv4.x 之间变化也是很大,有些1.x上能正常运行的代码移植过来后就出现了水土不服,例如本篇文章的主角 table customRender
antdv 1.x 回顾
在1.x时期,如果我需要定制一段 column 渲染模板,可以直接用{js}scopedSlots: { customRender: "action" }} 来定义:
<template>
<a-table :colums="colums" :data-source="data">
<span slot="action" slot-scope="text, record">
<a @click="handleEdit(record)">Edit</a>
<a-divider type="vertical" />
<a-popconfirm
title="操作不可回退, 确定删除?"
ok-text="Yes"
cancel-text="No"
@confirm="handleDelete(record)"
>
<a>Delete</a>
</a-popconfirm>
</span>
</a-table>
</template>
<script lang="js">
const columns = [
{
title: "Action",
key: "action",
scopedSlots: { customRender: "action" }
}
]
export default {
data () {
return {
columns,
data: [{}]
}
},
methods: {
handleEdit (record) {
console.log('edit record', record)
// Do something here
},
handleDelete (record) {
console.log('delete record', record)
// Do something here
}
}
}
</script>
可惜的是这个参数在3.x中被移除了,下面我们来看看3.x之后的版本如何定义渲染模板
antdv 3.x 之后
官方示例
官方给出的示例一般用 {js}column.key === 'xxx' 来分别渲染不同column内容
<template>
<a-table :colums="colums" :data-source="data">
<template #bodyCell="{ column, record, text }">
<template v-if="column.key === 'action'">
<a @click="handleEdit(record)">Edit</a>
<a-divider type="vertical" />
<a-popconfirm
title="操作不可回退, 确定删除?"
ok-text="Yes"
cancel-text="No"
@confirm="handleDelete(record)"
>
<a>Delete</a>
</a-popconfirm>
</template>
</template>
</a-table>
</template>
<script lang="js">
const columns = [
{
title: "Action",
dataIndex: "action",
key: "action"
}
]
export default {
data () {
return {
columns,
data: [{}]
}
},
...(同上,省略)
}
</script>
column一多就会导致代码臃肿,充满了一堆 v-if v-else-if 判断。
这时候可以考虑利用customRender 来定制展示内容。
customRender 版本
根据官方文档 描述
| 参数 | 说明 | 类型 | 默认值 |
|---|---|---|---|
| customRender | 生成复杂数据的渲染函数,参数分别为当前行的值,当前行数据,行索引 | {js}Function({text, record, index, column}) {} | - |
然而上面的信息就是官方文档对于customRender 的所有描述了,没错,一个demo都没有。查阅多方资料后,终于摸清了用法。
customRender 为一个函数类型,需要返回一个Vnodes 作为渲染模板。上面示例写法如下:
<template>
<a-table :colums="colums" :data-source="data" />
</template>
<script lang="js">
import {h} from "vue"
import {Divider, Popconfirm} from "ant-design-vue"
const columns = [
{
title: "Action",
dataIndex: "action",
key: "action",
customRender: (value) => {
return h('div', [
h('a', {onClick: () => handleEdit(value.record)}, 'Edit'),
h(Divider, {type: 'vertical'}),
h(Popconfirm, {
title: "操作不可回退,确定删除?",
okText: "Yes",
cancelText: "No",
onConfirm: () => handleDelete(value.record)
}, () => { return h('a', 'Delete')}),
])
}
}
]
...(同上,省略)
</script>
vue 提供了 {js}h() 函数用于创建 vnodes, 具体用法可参考官方文档。
值得注意的是,**组件的监听事件需要通过 onXxx 形式书写 , **例如Popconfirm 中的 confirm 需要写为 onConfirm
除此之外, Popconfirm 的 children 部分需要写成 {js}() => { return h('a', 'Delete')} 的形式, 如果写成 {js}[h('a', 'Delete'], 则会出现如下警告:
[Vue warn]: Non-function value encountered for default slot. Prefer function slots for better performance.
2431

被折叠的 条评论
为什么被折叠?



