VueJs 向非父组件发送数据

Sending data to a non parent component in VueJs

我正在尝试在 VueJs 中复制 TODO MVC。 (请查看此代码笔:http://codepen.io/sankalpsingha/pen/gwymJg) 我使用以下代码创建了一个名为 'todo-list' 的组件:

Vue.component('todo-list',{
  template: '#todo-list',
  props: ['todo'],
  data: function() {
    return {
    // Let us set up a isEditing Boolean so that we can know if the user
    // will edit something and we need to change the state to reflect it.
      isEditing: false,
    }
  },
  methods: {
    enableEditing: function() {
      this.isEditing = true;
    },
    editTodo: function(todo) {
      // todo.todo = todo.todo.trim();
      this.isEditing = false;
    },
    removeTodo: function(todo) {
      //this.todos.$remove(todo); // --> This part is not working?
    }
  }
});

但是,我在应用程序实例中定义了数据:

var app = new Vue({
  el: '#todo-section',
  data: {
    newTodo: '',
    todos: [
      {
        id: 1,
        todo: 'Go to the grocery',
        completed: false,
      },
      {
        id: 2,
        todo: 'See the movie',
        completed: true,
      },
      {
        id: 3,
        todo: 'Jack Reacher : Tom Cruise',
        completed: false,
      }
    ]
  },
  methods: {
    addTodo: function() {
      // This will not allow any empty items to be added.
      if(this.newTodo.trim() == '') {
        return;
      }
      this.todos.push({
        todo: this.newTodo.trim(),
        completed: false,
      });
      this.newTodo = '';
    }
  }
});

我无法从列表中删除单个待办事项。我的猜测是我必须向应用程序实例发送一条发出消息并在那里放置一个侦听器以从中删除数据?如何删除数据?

当我尝试通过单击您的 codePen 示例中的 x 按钮进行删除时,我看到错误:this.$parent.todos.$remove 不是一个函数。

我没有深入研究你的代码。但是尝试使用 this.$parent 访问父组件方法并不是一个好主意。原因:一个组件可以在任何地方使用,假设它有一个带有特定 属性 或方法的 $parent 是有风险的。

正如您在问题中所建议的,您需要使用子组件中的 $emit 来删除数据。

几天前这里还有一个类似的问题,为此我创建了一个jsFiddle:https://jsfiddle.net/mani04/4kyzkgLu/

子组件的代码如下:

<button @click="$emit('delete-row')">Delete</button>

这会向父组件发送一个事件。父组件可以使用 v-on 订阅该事件,如该 jsFiddle 示例中所示。

这是另一个问题供参考:

最好在父级中使用您的方法(DeleteTodo、EditTodo...)。

var app = new Vue({
  el: '#app',
  data: {
    newTodo: '',
    todos: [{
      id: 1,
      title: 'Go to the grocery',
      completed: false
    }, {
      id: 2,
      title: 'See the movie',
      completed: true
    }, {
      id: 3,
      title: 'Jack Reacher : Tom Cruise',
      completed: false
    }]
  },

  methods: {
    addTodo: function() {
      this.todos.push({
        todo: this.newTodo.trim(),
        completed: false
      });
      this.newTodo = ''
    },

    deleteTodo: function(todo) {
      this.todos = this.todos.filter(function(i) {
        return i !== todo
      })
    }
  }
});
<div id="app">
  <ul>
    <li v-for="todo in todos">{{ todo.title }}
      <button @click.prevent="deleteTodo(todo)">
        Delete
      </button>
    </li>
  </ul>
</div>

<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.0.3/vue.js"></script>