Vue 克隆问题

Vue cloning issue

我正在学习 vue,我想做的一件事是克隆元素。我正在玩这段代码:

var multiple = new Vue({
    el: '#vue',
    data: {

    },
    methods: {
        cloneWidget(e) {
            let widgets = document.getElementById('widgets');
            let widget = document.getElementById('widget');
            clone = widget.cloneNode(true);
            clone.id = Math.round(Math.random()*100);
            widgets.appendChild(clone);            
        },
        deleteClone(e) {
            e.target.parentNode.remove();            
        }
    }
});
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8">    
    <link href="styles.css" rel="stylesheet" />    
    <link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">    
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0-beta/css/materialize.min.css">
    <script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.js"></script>    
  </head>
  <body>
    <h1>Cloning</h1>

    <div id="vue">
      <form @submit.prevent>
        <div id="widgets">
          <div id="widget">
            <div>
              <label for="field1">Field 1:</label>
              <input type="text" name="field1">
            </div>
            <div>
              <label for="field2">Field 2:</label>
              <input type="text" name="field2">
            </div>
            <i class="material-icons delete" @click="deleteClone">delete</i>
          </div>          
        </div>
        <button @click="cloneWidget">Add Widget</button>
      </form>
    </div>

    <script src="app.js"></script>
  </body>
</html>

但是,deleteClone 方法永远不会在原始 div="widget" 之外被调用。

我似乎无法弄清楚为什么事件侦听器没有附加到克隆。 cloneNode() 会弄乱 Vue 吗?

使用 Vue,通常你想根据 数据 来思考。这是您修改后的示例,以便为小部件数组中的每个对象呈现一个小部件。

在这种情况下,数组的内容没有多大意义;您可能希望数组中每个对象的属性都与您的输入字段相匹配,但这只是一个示例。

var multiple = new Vue({
    el: '#vue',
    data: {
      widgets:[{}]
    },
    methods: {
        addWidget() {
          this.widgets.push({})      
        },
        removeWidget(widget) {
           this.widgets.splice(this.widgets.findIndex(w => w === widget), 1)            
        }
    }
});
<script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.js"></script>
<link href="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0-beta/css/materialize.min.css" rel="stylesheet"/>

    <h1>Cloning</h1>

    <div id="vue">
      <form @submit.prevent>
        <div id="widgets">
          <div v-for="widget in widgets">
            <div>
              <label for="field1">Field 1:</label>
              <input type="text" name="field1">
            </div>
            <div>
              <label for="field2">Field 2:</label>
              <input type="text" name="field2">
            </div>
            <i class="material-icons delete" @click="removeWidget(widget)">delete</i>
          </div>          
        </div>
        <button @click="addWidget">Add Widget</button>
      </form>
    </div>

在大多数情况下,您想避免直接操作 DOM,让 Vue 为您完成工作。