Vue3技术求助:如何通过模态框文本输入修改克隆对象名称
解决方案:用 Async/Await 等待用户对话框输入
你的问题核心是打开对话框后未等待用户完成输入就执行了后续逻辑,导致specific.value为空。通过将对话框操作封装为 Promise,配合 async/await 就能实现等待用户输入的效果,具体修改如下:
1. 修正基础响应式定义
首先把控制对话框的dialog改成响应式 ref 变量(原代码里的非响应式定义会导致视图不更新):
const dialog = ref(false)
2. 封装对话框为异步操作
创建一个返回 Promise 的函数,用来等待用户点击保存按钮:
let dialogResolve = null const openDialog = () => { return new Promise(resolve => { dialogResolve = resolve specific.value = '' // 清空上次输入残留值 dialog.value = true // 打开对话框 }) }
3. 修改模板的保存按钮逻辑
给保存按钮绑定自定义处理函数,点击时传递用户输入并关闭对话框:
<v-card-actions> <v-btn @click="dialog = false">取消</v-btn> <v-btn @click="handleSave" type="submit">Save</v-btn> </v-card-actions>
在脚本中实现handleSave:
const handleSave = () => { dialog.value = false dialogResolve(specific.value) // 将用户输入传递给Promise的resolve }
4. 改造addSkill为异步函数
用await等待对话框的输入结果,再执行技能添加逻辑:
async function addSkill(skill) { // 等待用户完成输入,获取输入值 const inputValue = await openDialog() // 如果用户取消对话框(输入为空),直接返回不执行添加 if (!inputValue) return const newSkill = structuredClone(skill) // 替换name中的占位符,或根据需求拼接输入值 newSkill.name = skill.name.replace('(specify language)', `(${inputValue})`) // 注意:若skillList是静态导入的数据,必须转为响应式ref数组才能更新视图 skillList.push(newSkill) }
完整修改后代码
模板部分
<!-- 技能列表 --> <li v-for="skill in skillList" :key="skill.id"> {{ skill.name }} <span><btn @click="addSkill(skill)">Add Skill</btn></span> </li> <!-- Vuetify 对话框 --> <v-dialog v-model="dialog"> <v-card> <v-card-title>Specific Item</v-card-title> <v-text-field v-model.lazy="specific" placeholder="请输入语言名称"></v-text-field> <v-card-actions> <v-btn @click="dialog = false">取消</v-btn> <v-btn @click="handleSave" type="submit">Save</v-btn> </v-card-actions> </v-card> </v-dialog>
脚本部分
<script setup> import { ref } from 'vue' // 注意:静态导入的技能列表需转为响应式ref数组,否则视图不更新 import rawSkillList from "@/data/skillList.json" const skillList = ref([...rawSkillList]) const specific = ref('') const dialog = ref(false) let dialogResolve = null const openDialog = () => { return new Promise(resolve => { dialogResolve = resolve specific.value = '' dialog.value = true }) } const handleSave = () => { dialog.value = false dialogResolve(specific.value) } async function addSkill(skill) { const inputValue = await openDialog() if (!inputValue) return const newSkill = structuredClone(skill) newSkill.name = skill.name.replace('(specify language)', `(${inputValue})`) skillList.push(newSkill) } </script>
额外提示
- 如果你的
skillList是直接导入的静态文件,必须转为 ref 响应式数组,否则添加新元素后视图不会自动更新 structuredClone用于深拷贝对象,适合复杂结构的技能数据;如果是简单对象,也可以用{...skill}替代- 可根据需求给取消按钮添加逻辑,点击时传递空值,在
addSkill中判断后终止操作
内容的提问来源于stack exchange,提问作者user2924137
相关产品推荐
相关产品推荐

