Vue子组件修改props中的值

17,984

问题:

子组件想修改父组件传来的值(props中的值)。普通的修改会报错,因为这个值是单向的,只能传进来,要是想修改就要用v-model

error

[Vue warn]: Avoid mutating a prop directly since the value will be overwritten whenever the parent component re-renders. Instead, use a data or computed property based on the prop's value. Prop being mutated: "content"

解决办法

方法一:使用v-model

父组件

<template>
    <div>
        <PropsChild v-model="contentData"></PropsChild>
		// 一个组件上的 v-model默认对应其子组件的props的value
    </div>
</template>
<script>
    import PropsChild from './component/PropsChild.vue'
    export default {
        data() {
            return {
                contentData:'我是父组件的数据********'
            }
        },
        components:{PropsChild}
    }
</script>

子组件

<template>
    <div>
        <div>我是子组件,==》 父组件传递过来的数据 {{ handlerContent }}</div>
    </div>
</template>
<script>
    export default {
        data() {
            return {
                handlerContent: this.value,
            }
        },
        props:['value'],
        mounted() {
            this.handlerContent = '子组件在mounted生命周期修改'
        },
    }
</script>

具体为什么这么写,vue文档里有交待=》

cn.vuejs.org/v2/guide/co…

一个组件上的 v-model 默认会利用名为 value 的 prop

方法二:使用.sync修饰符

父组件

<template>
    <div>
        <PropsChild v-bind:content.sync="parentContent"></PropsChild>
        <!-- 给v-bind添加了sync,那么子组件中就有一个事件可以触发 update:xxx自定义事件并且传递要修改的值 -->
    </div>
</template>
<script>
    import PropsChild from './component/PropsChild.vue'
    export default {
        data() {
            return {
                parentContent:'我是父组件的数据********'
            }
        },
        components:{
            PropsChild
        }
    }
</script>

子组件

<template>
    <div>
        <button @click="btnTest">我是子组件,{{ lasterContent }}</button>
    </div>
</template>
<script>
    export default {
        data() {
            return {
                lasterContent: this.content
            }
        },
        props:{
            content:{
                type:String
            }
        },
        watch: {
            content(val) {
                this.lasterContent = val;
            }
        },
        methods: {
            btnTest() {
                this.lasterContent = '哈哈,在子组件中改变了父组件传递过来的数据';
                this.$emit('update:content',this.lasterContent);
            }
        },
    }
</script>

注意点:

在父组件中需要用到 v-bind 和 .sync

1、在子组件中需要定义一个变量,接收父组件传递过来的值

2、使用watch监听父组件传递过来的值,使中间变量与父组件传递过来的值保持一致

3、子组件中需要使用this.$emit('update:xxx',要修改的值); 触发父组件中数据更新