I'm trying to synchronize a prop between a parent and child in vue.js.
I have a parent component that includes a child component with a prop. When the prop changes in the parent, the prop is updated in the child and when the prop changes in the child, the parent is updated.
I started with this example:
The html where my component is mounted
<div>
<div id="app">
</div>
</div>
And the parent + child:
Vue.component('myinput', {
template: '<div><input v-model="mytext" /></div>',
props: ['text'],
data() {
return {
mytext: this.text
}
}
})
const vm = new Vue({
el: '#app',
template: '<div> <myinput :text="mytext"></myinput> <p> {{mytext}} </p></div>',
data() {
return {
mytext: "Hello World!"
}
}
});
Since I cannot mutate the props, I need a local copy [Example Codepen].
If I want my parent component to be updated when the child change, I need to $emit
the value.
For that, I created a wrapper around mytext
in the child component:
computed: {
wrapperMyText: {
get() {
return this.mytext;
},
set(v) {
this.mytext = v;
this.$emit('update:text', v);
}
}
I use wrapperMyText in the model. [Example Codepen]
Now, if I want the binding the other way (parent to child) I need to add a watcher in the child.
watch: {
text(v) {
this.mytext = v;
}
},
In the example, there is only one prop, I need to create a watcher and a computed property. If I have 5 properties, I will need 5 watchers and 5 computed properties. That means the component code is polluted (too much code) with all this stuff. So my questions are:
Is this the standard pattern to sync a prop?
Is it better in this case to use a Store (like vuex)?
Why is so much code necessary to do a simple case?
After reflection, it seems I'm trying to re code v-model with properties.
A single computed property will accomplish everything you are attempting.
Here is your updated pen.
So to answer your questions: