Communication between Vue components

Cover image

we will use this sandbox to illustrate communication between different components, feel free to fork and play with it. I used tailwind for my styling. You'll need this when you have set a data property a component and you would like to render the data in another component or even mutate the data

{% codesandbox nwy6njnl3j %}

#parent to child communication props allow one-way communication between a parent component and a child component. In the sandbox above, app.vue is our parent component with role as a data property, we want to pass the data from app component to ViewUser component, to do this we register a props property to ViewUser, this is an array with strings and in each string we specify properties which should be settable from outside, the name we set in our string has to match the name we use in our template.

ViewUser

To pass the prop we v-bind the prop name to the data property in the parent component where we render the template <div class="flex"><ViewUser :role="role" /></div>

we can use props like a normal property, access it with this and run a method like seen in the example

  methods: {
    reverseRole() {
      return this.role
        .split('')
        .reverse()
        .join('');
    }
  }

To validate props we use the object syntax. If a requirement isn’t met, Vue will warn you in the browser’s JavaScript console at development time

  props: {
    role: String
  },

other validators to props are: Number, Boolean, Array, Object, Date, Function and Symbol

#child to parent To demonstrate this we will make a button that will revert the role back to 'frontend developer' and pass the value from the child component- ViewUser.vue to the root component which is app.vue, for this we will use custom events. The child will emit a new event when data changes and the parent listens

when we initialize the vue instance we get the emit method, on emit we specify the name we want to emit and the data as the second argument as this.$emit('rolewasreset', this.mutatedrole);. we listen to the event emitted with the v-on directive or the shorthand @ in the selector of the component emitting the event inside the root component, the name must much the name we gave to emit event in our case the name was rolewasreset

customevents

passing the event <ViewUser :role="role" @rolewasreset="role = $event;" />

note that we didn't mutate the prop directly but we defined a local data property that uses the prop as its initial value. if you do so you will get an warning in the console

#sibling to sibling For sibling to sibling communication, we will use eventBus. note that we can also use Vuex which we will not use in this example.

In our main.js, we create a new vue instance and store it in a constant which we export. we import in our edituser and viewuser where we emit the event and listen to the event respectively. eventBus is a vue instance, so we get the $emit method by default

edituser.vue

in a method inside our edituser component we call eventbus passing the required parameters eventBus.$emit('ageWasEdited', this.newAge);

viewuser.vue

we listen to the event in our viewuser component inside the create lifecycle hook using eventBus.$on('ageWasEdited', newAge => { this.newAge = newAge; the first parameter is the name of the event while the second is the data which is always a callback.

if we also render age in our root component you will notice once we edit the age the change won't reflect, meaning data is not passed to the parent then to the child receiving the data.

Hope this helped you understand how to communicate between components