在实现“新增”和“编辑”打开弹窗时,其实是打开的同一个弹窗,只不过“编辑”需要回显。
我利用currentId来判断是新增弹窗还是编辑弹窗。
<addEmployee
v-model:open="addOpen"
@ok="handleAddOk"
:currentId="currentId"
/>
当点击的是“新增”按钮的时候,我会传递一个空字符串过去赋值给currentId。
<a-button class="add_operator" @click="showModal">新增操作员</a-button>
const showModal = () => {
currentId.value = "";
addOpen.value = true;
};
当点击的是“编辑”按钮的时候,我会传当前行的id过去赋值给currentId。
<template #bodyCell="{ column, value, record }">
<template v-if="column.key === 'actions'">
<a class="actions" @click="editModal(record)">编辑</a>
</template>
</template>
const editModal = (record: any) => {
currentId.value = record.id;
addOpen.value = true;
};
在子组件中,就可以通过判断当前“prop.currentId"是否有值来确定是“新增”还是“编辑” 。
const addOpen = ref(props.addOpen);
const currentId = ref(props.currentId);
const modalTitle = computed(() => (props.currentId ? "编辑" : "新增"));
通过watch来监听判断是否调用详情接口来进行回显(如果props.currentId为空,那就清空表单的值,如果props.currentId有值,那就调用接口获取详情)
watch(
() => props.currentId,
(newVal) => {
currentId.value = newVal;
props.currentId ? getMoreInfo() : formRef.value?.resetFields();
}
);
注意,在调用获取详情的接口前,要先清空表单的值
(Object.assign的复制规则中有一点:当目标对象中的属性已经有值,并且源对象中的对应属性为 null
或 undefined
,则目标对象中的属性值不会改变)
比如说我点击第一行数据,我去调用详情接口,拿到了数据,并且其中的a是有值的,
那当我点击第二行数据,我去调用详情接口,拿到了数据,但是其中的a是空的,那么此时的 Object.assign(formState, res.data);就不会复制a第二次拿到的空值。
这就意味着,我去回显第二条数据的时候,其中的a的值是第一条数据的,那这样肯定是不对的。(比如第一条数据的性别字段,值是男,第二条数据的性别字段,值原本反的是空,回显的时候第二条数据显示性别字段的值显示的是第一条数据的值——男)
所以为了解决这个问题,可以在每次去调接口获取详情前,都先清空一下表单的值。
const getMoreInfo = async () => {
formRef.value?.resetFields();
const res = await MoreInfo(currentId.value);
Object.assign(formState, res.data);
};