# 需求:
1. 输入框可自由并独立的输入;
2. 点击‘复制并新增’按钮就复制上一条数据并将 dom 元素也复制下来;
3. 复制下来的输入框均可独立输入修改,不会影响上一条;
# 思考:
1.Vue3 是数据驱动,往这个方向去实现,而不是想着去操作 Dom;
2. 数据结构:整个表单数据可以是数组,那么每个元素是对象,一个对象代表一组输入框的数据,每个属性则对应每个输入框具体数据;
3. 采用 v-for 将数组循环出来,如果是空数组,界面将没有任何显示,但又不能给数据;
4. 针对 3 先声明一个对象,每个属性为空,作为用户初始输入的容器;
5. 每次复制新增就是将数组里最后一个元素复制下来并增加到数组里;
6. 如果直接这样去实现,则会出现修改一个输入框,联动每一行的该输入框一起修改了;
7. 给每个对象增加唯一标识,使各自成为不同对象,并将该属性绑定给:key。
# 源码 demo 如下:
<template> | |
<Button @click="copyElement">复制并新增</Button> | |
<div v-for="item in list" :key="item.index"> | |
<Input v-model:value="item.id" /> | |
<Input v-model:value="item.name" /> | |
<Input v-model:value="item.num" /> | |
<Input v-model:value="item.age" /> | |
</div> | |
<script lang="ts" setup> | |
interface item { | |
index: number; | |
id?: number; | |
name?: string; | |
num?: number; | |
age?: string; | |
} | |
// 必须先声明一个对象作为初始填充容器 | |
const list = ref<Array<item>>([ | |
{ index: 0, id: undefined, name: undefined, num: undefined, age: undefined }, | |
]); | |
function copyElement() { | |
// 每次复制最后一个数据 | |
const result = list.value[list.value.length - 1]; | |
const addItem = { | |
index: result.index + 1, // 唯一标识必须不同 | |
id: result.id, | |
name: result.name, | |
num: result.num, | |
age: result.age, | |
}; | |
list.value.push(addItem); | |
console.log(list); | |
} | |
</script> | |
</template> |
原创不易,如果对你有所帮助,还请不吝打赏~