前言
父子组件通信,都是单项的,很多时候需要双向通信。方法如下:
- 通过.sync修饰符
- 通过v-model指令
1、.sync修饰符
实例:
父组件
:msg.sync="fatherValue"
<template lang="pug">
.wrap
h2 fatherValue:
h3(v-text="fatherValue")
Button(type="primary" @click="fatherValueChange") 点击父组件值改变
hr
HelloWorld(:msg.sync="fatherValue")
</template>
<script>
// @ is an alias to /src
import HelloWorld from '@/components/HelloWorld.vue'
export default {
name: 'home',
data () {
return {
fatherValue: 100
}
},
methods: {
fatherValueChange () {
this.fatherValue++
}
},
components: {
HelloWorld
}
}
</script>
子组件
this.$emit('update:msg', this.childValueChange())
<template lang="pug">
#div
h2 childValue
h3(v-text="msg")
Button(type="primary" @click="childValueChangeEmit") 点击子组件值改变
</template>
<script>
export default {
name: 'HelloWorld',
props: {
msg: Number
},
methods: {
childValueChange () {
return this.msg + 1
},
childValueChangeEmit () {
this.$emit('update:msg', this.childValueChange())
}
}
}
</script>
<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped lang="stylus">
</style>
2、v-model指令
父组件
v-model="fatherValue"
<template lang="pug">
.wrap
h2 fatherValue:
h3(v-text="fatherValue")
Button(type="primary" @click="fatherValueChange") 点击父组件值改变
hr
HelloWorld(v-model="fatherValue")
</template>
<script>
// @ is an alias to /src
import HelloWorld from '@/components/HelloWorld.vue'
export default {
name: 'home',
data () {
return {
fatherValue: 100
}
},
methods: {
fatherValueChange () {
this.fatherValue++
}
},
components: {
HelloWorld
}
}
</script>
子组件方式一:默认input事件类型
<template lang="pug">
#div
h2 childValue
h3(v-text="value")
Button(type="primary" @click="childValueChangeEmit") 点击子组件值改变
</template>
<script>
export default {
name: 'HelloWorld',
props: {
value: Number
},
methods: {
childValueChange () {
return this.value + 1
},
childValueChangeEmit () {
this.$emit('input', this.childValueChange())
}
}
}
</script>
<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped lang="stylus">
</style>
子组件方式二:自定义事件类型
<template lang="pug">
#div
h2 childValue
h3(v-text="msg")
Button(type="primary" @click="childValueChangeEmit") 点击子组件值改变
</template>
<script>
export default {
name: 'HelloWorld',
/*
允许一个自定义组件在使用 v-model 时定制 prop 和 event 。
默认情况下,一个组件上的 v-model 会把 value 用作 prop 且把 input 用作 event,
但是一些输入类型比如单选框和复选框按钮可能想使用 value prop 来达到不同的目的。
使用 model 选项可以回避这些情况产生的冲突。
详见:https://cn.vuejs.org/v2/api/#model
*/
model: {
prop: 'msg',
event: 'click'
},
props: {
msg: Number
},
methods: {
childValueChange () {
return this.msg + 1
},
childValueChangeEmit () {
this.$emit('click', this.childValueChange())
}
}
}
</script>
<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped lang="stylus">
</style>
子组件方式三:子组件自定义data值
<template lang="pug">
#div
h2 childValue
h3(v-text="value")
Button(type="primary" @click="childValueChange") 点击子组件值改变
</template>
<script>
export default {
name: 'HelloWorld',
props: {
value: Number
},
data () {
return {
childDataValue: this.value
}
},
watch: {
value (val) {
this.childDataValue = val
},
childDataValue (val) {
this.$emit('input', val)
}
},
methods: {
childValueChange () {
return this.childDataValue++
}
}
}
</script>
<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped lang="stylus">
</style>