VueJS 在不更改父数据的情况下编辑道具的正确方法 [英] VueJS right way to edit prop without changing parent data

查看:36
本文介绍了VueJS 在不更改父数据的情况下编辑道具的正确方法的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我的父 vue 组件中,我有一个 user 对象.

如果我将该用户对象作为道具传递给子组件:

并且在我的子组件中更新 user.name,它也会在父组件中更新.

我想编辑子组件中的用户对象,而不会将更改反映在父组件中的用户对象中.

是否有比使用以下方法克隆对象更好的方法:JSON.parse(JSON.stringify(obj))?

解决方案

您不必使用 JSON 对象.

const child = {道具:[用户"],数据(){返回 {localUser: Object.assign({}, this.user)}}}

在您的孩子内部使用 localUser(或任何您想调用的名称).

编辑

我已经修改了为这个问题的另一个答案创建的小提琴来演示上述概念,@user3743266 询问

<块引用>

我自己正在处理这个问题,我发现这非常有用.你的例子效果很好.在孩子中,你创造了一个获取道具副本的数据中的元素,并且子项工作与副本.有趣且有用,但是……我不清楚如果其他内容修改了本地副本,则何时更新父母.我修改了你的小提琴,删除了 v-ifs 所以一切都是可见,并复制编辑组件.如果您将名称修改为一个组件,另一个是孤立的,没有变化?

当前组件如下所示:

Vue.component('edit-user', {模板:`<div><input type="text" v-model="localUser.name"><button @click="$emit('save', localUser)">保存</button><button @click="$emit('cancel')">取消</button>

`,道具:['用户'],数据() {返回 {localUser: Object.assign({}, this.user)}}})

因为我的设计决定使用用户的本地副本,@user3743266 是正确的,组件不会自动更新.property user 已更新,但 localUser 未更新.在这种情况下,如果你想在属性改变时自动更新本地数据,你需要一个观察者.

Vue.component('edit-user', {模板:`<div><input type="text" v-model="localUser.name"><button @click="$emit('save', localUser)">保存</button><button @click="$emit('cancel')">取消</button>

`,道具:['用户'],数据() {返回 {localUser: Object.assign({}, this.user)}},手表:{用户(新用户){this.localUser = Object.assign({}, newUser)}}})

这是更新的fiddle.

这使您可以完全控制本地数据何时/是否更新或发出.例如,您可能希望在更新本地状态之前检查条件.

 观看:{用户(新用户){如果(条件)this.localUser = Object.assign({}, newUser)}}

正如我在别处所说的,有时您可能希望利用可变的对象属性,但有时您可能需要更多控制.

In my parent vue component I have a user object.

If I pass that user object to a child component as a prop:

<child :user="user"></child>

and in my child component I update user.name, it will get updated in the parent as well.

I want to edit the user object in child component without the changes being reflected in the user object that is in parent component.

Is there a better way to achieve this than cloning the object with: JSON.parse(JSON.stringify(obj))?

解决方案

You don't have to use the JSON object.

const child = {
  props:["user"],
  data(){
    return {
      localUser: Object.assign({}, this.user)
    }
  }
}

Use localUser (or whatever you want to call it) inside your child.

Edit

I had modified a fiddle created for another answer to this question to demonstrate the above concept and @user3743266 asked

I'm coming to grips with this myself, and I'm finding this very useful. Your example works well. In the child, you've created an element in data that takes a copy of the prop, and the child works with the copy. Interesting and useful, but... it's not clear to me when the local copy gets updated if something else modifies the parent. I modified your fiddle, removing the v-ifs so everything is visible, and duplicating the edit component. If you modify name in one component, the other is orphaned and gets no changes?

The current component looks like this:

Vue.component('edit-user', {
  template: `
  <div>
    <input type="text" v-model="localUser.name">
    <button @click="$emit('save', localUser)">Save</button>
    <button @click="$emit('cancel')">Cancel</button>
  </div>
  `,
  props: ['user'],
  data() {
    return {
      localUser: Object.assign({}, this.user)
    }
  }
})

Because I made the design decision to use a local copy of the user, @user3743266 is correct, the component is not automatically updated. The property user is updated, but localUser is not. In this case, if you wanted to automatically update local data whenever the property changed, you would need a watcher.

Vue.component('edit-user', {
  template: `
  <div>
    <input type="text" v-model="localUser.name">
    <button @click="$emit('save', localUser)">Save</button>
    <button @click="$emit('cancel')">Cancel</button>
  </div>
  `,
  props: ['user'],
  data() {
    return {
      localUser: Object.assign({}, this.user)
    }
  },
  watch:{
    user(newUser){
        this.localUser = Object.assign({}, newUser)
    }
  }
})

Here is the updated fiddle.

This allows you full control over when/if the local data is updated or emitted. For example, you might want to check a condition before updating the local state.

  watch:{
    user(newUser){
      if (condition)
        this.localUser = Object.assign({}, newUser)
    }
  }

As I said elsewhere, there are times when you might want to take advantage of objects properties being mutable, but there are also times like this where you might want more control.

这篇关于VueJS 在不更改父数据的情况下编辑道具的正确方法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
前端开发最新文章
热门教程
热门工具
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆