1

I am trying to create a simple webpage where I can add or remove textboxes using vue.js.

new Vue({
  el: "#app",
 data() {
    return {
      list: []
    };
  },
  methods: {
    deleteFromList(index) {
      this.list.splice(index, 1);
    },
    addItem() {
      this.list.push({});
    }
  }
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<!DOCTYPE html>
<html>
  <head>
    <title>App</title>
    <meta charset="UTF-8" />
    <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
  </head>
<body>
    <div id="app">
         <button @click="addItem()">Add 1</button>
      <ul>
          <li v-for="(item, index) in list":key="index">
            <textarea rows="1" cols="30">{{item}}</textarea>
            <button @click="deleteFromList(index)">Delete</button>
          </li>
      </ul>
    </div>

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

I added a snippet to the page (I think you need to expand or make it full screen to see the result properly), my problem is that on Delete button it doesn't remove the corresponding row, but the last one. Has anyone any idea about how can I do this work fine?

Thank you very much :)

1 Answer 1

1

It is actually removing the correct item out of the array, but you're not seeing it because you're not changing the value of the model only the textarea which is not tied to the value instead its just cached to :key="index", below is an example which should show that, simply by adding a counter you can see it's deleting the correct object.

Vue.config.productionTip = false;
Vue.config.devtools = false;
new Vue({
  el: "#app",
  data() {
    return {
      list: [],
      counter: 0,
    };
  },
  methods: {
    deleteFromList(index) {
      this.list.splice(index, 1);
    },
    addItem() {
      this.list.push(this.counter++);
    }
  }
});
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>

<div id="app">
  <button @click="addItem()">Add 1</button>
  <ul>
    <li v-for="(item, index) in list" :key="index">
      <textarea rows="1" cols="30">{{item}}</textarea>
      <button @click="deleteFromList(index)">Delete</button>
    </li>
  </ul>

  <pre>{{ list }}</pre>
</div>

To fix the issue and have dynamic changing values/model you should use v-model on the value and indexOf when removing.

Vue.config.productionTip = false;
Vue.config.devtools = false;
new Vue({
  el: "#app",
  data() {
    return {
      list: []
    };
  },
  methods: {
    deleteFromList(item) {
      this.list.splice(this.list.indexOf(item), 1);
    },
    addItem() {
      this.list.push('');
    }
  }
});
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>

<div id="app">
  <button @click="addItem()">Add 1</button>
  <ul>
    <li v-for="(item, index) in list" :key="index">
      <textarea rows="1" cols="30" v-model="list[index]"></textarea>
      <button @click="deleteFromList(item)">Delete</button>
    </li>
  </ul>
</div>

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.