You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Vue中如何基于数组动态增删slot字段?删除slot总移除最后一项怎么解决

问题原因

  • v-for绑定的:key使用了数组下标index。当你删除某一行后,剩余数组的下标会重新排列,Vue的Diff算法会默认复用下标对应的DOM节点,导致静态slot内容出现渲染错位。你观察到输入框能正常删除,是因为输入框绑定了row.value和每行数据响应式关联,Vue能正确跟踪值的变化,而静态插槽没有和行数据做绑定,所以复用后出现错位。
  • 你使用了固定名称的具名插槽name="fields",同一个组件内同名的具名插槽只会被注入一次父级传入的内容,循环中的所有插槽本质上复用的是同一份静态内容,自然无法和对应的行做绑定删除。

解决方案

第一步:给每行数据加唯一标识,替换掉index作为key

修改addRow方法,新增行时生成唯一ID作为每行的固定标识,避免用下标做key:

removeRow(index){
  this.rows.splice(index, 1);
},
addRow(){
  this.rows.push({
    id: Date.now() + Math.random(), // 只要保证唯一即可,也可以自己维护自增ID
    value: 'test'
  })
}

修改v-for的key绑定:

<div v-for="(row, index) in rows" :key="row.id">
      <div class="d-flex justify-content-between ">
        <slot name="fields" :row="row" :index="index">
        </slot>
        <input  v-model="row.value" />
        <button @click="removeRow(index)" type="button" class="btn btn-primary waves-effect waves-float waves-light height-10-per  " >
          Remove <i class="fa fa-times-circle"></i>
        </button>
      </div>
    </div>

第二步:父组件改用作用域插槽语法传入内容

作用域插槽可以给循环的每一行单独传递插槽内容,父组件调用时写法如下(不需要用到行数据也可以不接收参数,只要用作用域插槽的写法就能保证每行的插槽独立):

<!-- 父组件使用示例 -->
<your-component :rows="rows">
  <template v-slot:fields="{ row, index }">
    <!-- 这里放你原来要传入插槽的HTML内容 -->
  </template>
</your-component>

简化方案(如果插槽内容固定不需要父级动态传入)

如果插槽里的内容是固定的,完全不需要父级传递,直接把插槽内容写到组件内部的v-for循环里即可,不需要用插槽,自然不会有渲染错位问题。

内容的提问来源于stack exchange,提问作者Madmunster

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.03 07:57:04