INTRODUCTION
Have you ever made a Vue.js component only to think how can I generalize this better in a more object-oriented way? That is the situation I found myself in when I started to read about using Vue.js’s props and its event handling with $emit. However, this topic isn’t the most accessible in the world I’m still trying to refine my technique to be honest with you, however I thought I would share the tips and tricks I have picked up to facilitate some sharing of information.
THE VUE.JS COMPONENT
The Vue docs say that components are a “reusable Vue instances with a name” but the way I prefer to think about them is as the user controls you can make in winForms. This may be because I came up as a .net developer, so this makes the most sense to me. More specifically a vue component is a vue file or chunk of vue code in another file that represents a set of code that can be referenced in multiple places. The fact that it can be reused automatically makes me want to make it as object oriented as possible. For this reason, I try to limit components to prop’s going in and $emit’s going out. In my opinion this also makes the code much easier to follow and tends to be the easiest way to understand something. If you can tell me what goes in and what comes out I don’t really need to know anything else to have a basic understanding of something. So let me show you our model component for today:
And when it runs
This is our shiny new component at least it’s the starting point right now we could put this every were and it wouldn’t be any more functional just a dumb button and not reactive label but we can fix that. The first thing I think we should do is set up some props so that we can change the text in the button and in the label. This will allow us to bind our own strings to that text making our totally useless component slightly more interesting.
Now we can change the text from the parent of this component but there is an issue we should address before we move on. It is not a great practice to leave your props in array format. You are shorting yourself on what information you can bake into a component like for instance its type, if it is a required property, and what a default should be; Pretty useful stuff right so let’s fix that, now our code looks like this.
and when it runs it looks like this:
For the next step we need to add the binding to the parent the simplest way to accomplish this would simply be to put the variables in the data field. Then we could use v-bind to link to the two strings. However, before we can bind to all the components we can fit into our html we have to reference the component in the Vue. This is fairly simple I always just import it before the export default section and then add it to my components field inside the export default our parent code now looks like this.
One thing to note before we move on is that in the components field I removed the upper case letters and separated the components name with kebob case. This is due to a limitation in html and it seems to me to be fairly standard practice to separate words with minus symbols. It’s the way I’ve done it for a while now and I haven’t had a problem with it. Oh, a look at the running code I almost forgot
Now the final thing to make our component useful little buton label combo is to add an event to it. In vue this takes the employment of the $emit method. The $emit as I have come to think about it throws an event back up to the parent. The most basic case of this is just to have it tell the parent something with no parameters like so in the component:
And handling it in the parent is as easy as:
The $emit can be used to a far greater effect though when you add arguments let’s say for instance we wanted out button component to keep track of how many times it was pressed. Then we want it to send that information back to the parent when the button is clicked how could we accomplish this. Simple we could put a count in the data of the child Vue, increment it in the clicked call before we call the $emit and then send off the clicked event with the count as the parameter.
Now I know what you’re thinking, should we really call two separate things in a click call on a button. The answer is probably not, and the syntax police may raid my house at this very moment. However, I am confident you can write a method and the Vue docs are awesome so if you have any question on it look there or I would be happy to answer in the comments.
The follow up question is how can i have my parent handle this new information it is being sent by my component? The answer is as if it were any other event I wrote mine to display how many times the button was clicked in an alert, but you could do whatever you want with your new information.
And the proof it works
Thanks so much for reading this is my very first blog post ever so forgive me if I broke some rule or did something wrong. I know I can make mistakes so please teach me something in the comments if I did something wrong with my code, or my writing I am always trying to learn new things. If there is any other aspect of vue you would like me to go into, please let me know. Thank you for reading.
-Nick