我正在尝试将智慧融合在Vue props
和data
属性的语义上。在下面的代码中,item
子级组件从父级接受newItem
。子组件将item
(对模糊性很抱歉)定义为this.newItem
。父级传入newItem
而不是item
来避免直接修改父级组件值的禁止。
控制台没有显示警告,但我想知道是否仅因为Vue rendering(?)机制无法识别违规。在开发工具中可以看到子item
只是在创建对传入newItem
的引用,因此从本质上讲,该道具仍在直接修改。
我应该使用item
构造函数来初始化子Item
吗?还是孩子必须改为发出某种由父母处理的“取消编辑”事件?
cancelEdit
将_cachedItem
分配给item
,与分配给newItem
相同(?):
// An item
Vue.component('item', {
props: [
'newItem'
],
data: function() {
return {
item: this.newItem,
editing: false,
_cachedItem: null
}
},
methods: {
startEdit: function() {
debugger
this._cachedItem = new Item(this.item.id, this.item.text);
this.editing = true;
},
cancelEdit: function() {
debugger
this.item = this._cachedItem;
this._cachedItem = null;
this.editing = false;
},
finishEdit: function() {
debugger
this.editing = false;
},
},
...
父模板:
Vue.component('items', {
props: {
'items': {
type: Array,
},
'item-type': {
type: String
}
...
<item
v-for="(item, index) in items"
v-bind:newItem="item"
v-bind:key="item.id"
v-on:remove="removeItem(index)" />
...
答案 0 :(得分:1)
在JavaScript中,对象是通过引用传递的。 Vue docs清楚地说明了..
请注意,JavaScript中的对象和数组是通过引用传递的,因此 如果prop是数组或对象,则使对象或数组本身发生突变 子组件中的元素将影响父状态。
如果您想避免这种行为,可以create deep clones放置对象。像这样..
item: JSON.parse(JSON.stringify(this.newItem)),
将创建对象的完全独立的本地副本。如果您想使两个对象保持同步,则可以通过事件向父对象传达将值变异的意图,并让其更新它自己的对象副本。解决此问题的一种优雅方法是使用.sync modifier。