Getting Started with Vue.js: Lesson 19 of 25

Components: Gif Box

Up Next

Components: Gif Grid

Autoplaying in 7 seconds!


Now that we have our code in two different grid sections, we can start to see that we are repeating a giant chunk of code in two places. This doesn't make for scalable code, especially when we want to keep our code DRY (Don't Repeat Yourself).

Vue gives us components, which are an essential part of Vue.


Components allow us to encapsulate reusable code into a component. At it's core, a component allows us to define a template and data that will be reused across our application.

Table of Contents

    All Vue components are also Vue instances, so they will look very similar when creating them. Here's an example of a Vue component:

    Vue.component('my-component', {
        template: `
            <a href="/link-goes-here">I'm a Reusable Component!</a>

    We have just created a global component! Notice that the template is using the ES6 template strings. Now we can use this in our HTML like so:


    Vue will parse the template and when it finds this custom component, it will inject the template there.

    Gif Box Component

    To create a component for our app, let's build one to make the gif-box section reusable.

    Vue.component('gif-box', {
        template: `
            <div class="gif-box">
                <a :href="gif.url">
                  <img class="gif-image" :src="gif.images.original.url">
                    <img :src="gif.user.avatar_url" height="35" width="35">
                    {{ gif.user.display_name }}

    We have just copied and pasted all that gif-box code into a new gif-box component.

    Getting Data into a Component

    We are using the gif variable inside of this component, but how does Vue know where to get that? We are using it in our loop, but this component has no idea that outside variable exists.

    Vue components have their own isolated scope and it's best practice to always explicitly pass in the data a component will need. This means a component will be completely autonomous and just work with what it's given.

    We'll be using Props to get data into a component.

    In our component, we use a gif variable. Let's tell our component where to get it from (a parent component).

    Vue.component('gif-box', {
        props: ['gif'],
        template: `

    We've added the props array to our Vue component. Now this component knows that it should be given a gif object in order to render its own template.

    Using a Vue Component

    To use the component, we can use it in our HTML and bind the gif into it:

    <gif-box v-bind:gif="gif"></gif-box>

    We are binding to the :gif input just like we would bind to any normal HTML attribute.

    Refactoring Our Template

    We can clean up our code by using this new gif-box in two locations, our searched gifs grid and the trending gifs grid:

    <!-- our template -->
    <section id="app" class="section container">    
      <!-- SEARCH ========================================== -->
      <h2 class="title">Search</h2>
      <input type="text" class="input" name="query" v-model="query" @keyup="searchGifs">
      <div class="columns is-multiline" v-if="searchedGifs">
        <div class="column is-one-quarter" v-for="gif in searchedGifs">
          <gif-box :gif="gif"></gif-box>
      <!-- TRENDING ======================================= -->
      <h2 class="title">Trending</h2>
      <div class="columns is-multiline" v-if="trendingGifs">
        <div class="column is-one-quarter" v-for="gif in trendingGifs">
          <gif-box :gif="gif"></gif-box>

    Chris Sevilleja

    173 posts

    Co-founder of Slapping the keyboard until something good happens.