Vue 3 Cheat Sheet
Tags: vue, webdev, tutorial
Published: 2021-03-25 03:55:12

Hey there DEV.to community!

First of all, before going into the cheat sheet, I want to wish everyone a happy Nowruz as it indicates the beginning of a new year (being 1400 in the Shamsi (Jalali) calendar right now) and/or the beginning of the spring season to whomever in whichever country celebrate this event. So happy new year and happy Nowruz. As I am writing this post it is the 5th of Farvardin, 1400 which is 5 days past the new year :).

As you might know, if you are an ambitious Vue developer, Vue has released its version 3 not so long ago. This version had some major changes and some minor ones. Here I am listing them as a cheat sheet so you can to them whenever you want just as I might refer to my own post anytime XD. And this post will be just a little bit more than a cheat sheet since some features require more describing.

Some code examples are from [Vue's official documentation](https://v3.vuejs.org/).

I believe Vue 3 has made a huge step forward into making Vue a way better solution for large-scale, enterprise application development than it was before.

# Table of content

- [New way to create](#new-way-to-create)
- [Configuration scope](#configuration-scope)
- [Composition API](#composition-api)
    - [ref](#composition-api-ref)
- [Fragments](#fragments)
- [Teleport](#teleport)

# New way to create <a name="new-way-to-create"></a>

Previously, what we used to do was to instantiate a new Vue instance, and mount it in an element (usually being the `#app`) as below:

```javascript
import Vue from 'vue'
import App from './App.vue'

new Vue({
    render: h => h(App)
}).$mount('#app')
```

Now what we have to do is to call the `createApp` method from `'vue'` to create a new app and then mount it in an element:

```javascript
import { createApp } from 'vue'
import App from './App.vue'

const app = createApp(App)

app.mount('#app')
```

# Configuration scope <a name="configuration-scope"></a>

In Vue 3, instead of configuring the Vue global object directly, for adding plugins and etc, you can configure your object instance instead.

Previously:

```javascript
import Vue from 'vue'
import App from './App.vue'

Vue.use(YOUR_PLUGIN)

new Vue({
    render: h => h(App)
}).$mount('#app')
```

New way:

```javascript
import { createApp } from 'vue'
import App from './App.vue'

const app = createApp(App)

app.use(YOUR_PLUGIN)

app.mount('#app')
```

# Composition API <a name="composition-api"></a>

As much as it sounds really dangerous when you read this feature's name, it is a super simple and very useful feature. This feature lets you split your component into smaller pieces, simply put. This allows you to use repeatable parts of your components without needing to code them again.

Given that you have to components, named `Fruits` and `Countries` and in them, you have a list and an input to search in the list to see if the user's input exists or not.

This is a very simple example so you don't get frustrated :D.

The search function uses a very simple linear search algorithm. Given that you can share this function over components using the `setup` method in Vue 3. Everything that the `setup` method returns are available in your component.

Here is an example:

For `Fruits`:

```vue
<template>
  <div>
    <label>
      Search in fruits:
      <input type="text" v-model="userInput"/>
    </label>
    <button @click="search">Search</button>
  </div>
</template>

<script>
import {ref} from 'vue'
import { search as searchFunction } from '@/compositions/search-function'

export default {
  setup() {
    let list = ref(['apple', 'orange', 'banana', 'mango', 'pineapple'])
    let userInput = ref(null)

    const search = () => {
      searchFunction(userInput, list)
    }

    return {
      list,
      userInput,
      search
    }
  }
}
</script>
```

And for `Countries`:

```vue
<template>
  <div>
    <label>
      Search in countries:
      <input type="text" v-model="userInput"/>
    </label>
    <button @click="search">Search</button>
  </div>
</template>

<script>
import {ref} from 'vue'
import {search as searchFunction} from "@/compositions/search-function";

export default {
  setup() {
    let list = ref(['Iran', 'Spain', 'Turkey', 'US', 'China', 'France'])
    let userInput = ref(null)

    const search = () => {
      searchFunction(userInput, list)
    }

    return {
      list,
      userInput,
      search
    }
  }
}
</script>
```

As you can see we imported a simple function called `search` as `searchFunction` so it doesn't conflict with the search function we use in the template (although it doesn't matter since Vue will call from its own methods, better safe than sorry XD).

{% codesandbox composition-api-1bu94 %}

## ref <a name="composition-api-ref"></a>

You can make every variable reactive using the `ref` method imported from `vue`. If you have a React background, this acts similar to `useState` in React. Using this method you can create a reactive variable and return it in your `setup` method. The argument that the `ref` method receives is the default value (initial value).

```javascript
import {ref} from 'vue'

export default {
  setup() {
    let name = ref('Adnan')

    return {
      name
    }
  }
}
```

If you are still confused about the Composition API, feel free to check [Vue's official documentation about Composition API](https://v3.vuejs.org/guide/composition-api-introduction.html#standalone-computed-properties), as it offers the best explanation.

# Fragments <a name="fragments"></a>

Fragments let you return multiple root nodes (elements) from your components without needing to wrapping them inside another element such as a `div`. This way you won't have redundant elements in your DOM.

Here is a simple component called `Boxes.vue`:

```vue
<template>
  <div id="box-one" />
  <div id="box-two" />
</template>

<script>
export default {

}
</script>

<style lang="scss" scoped>
#box-one {
  background: red;
  width: 100px;
  height: 100px;
}

#box-two {
 background: blue;
  width: 150px;
  height: 150px;
}
</style>
```

{% codesandbox fragments-eiqgn %}

# Teleport <a name="teleport"></a>

Teleport lets you teleport your elements (Duh!). This means although semantically your element might reside inside another element it is possible to move it inside another one. Like your page's body. This is super helpful in scenarios such as a modal.

Here is sample:
```vue
<template>
  <teleport to="body">
    <div class="modal" v-if="isModalActive">
      Boom! I teleported!
    </div>
  </teleport>
  <button @click="isModalActive = !isModalActive">{{ isModalActive ? 'Close' : 'Open' }} modal</button>
</template>

<script>
export default {
  data() {
    return {
      isModalActive: false
    }
  }
}
</script>

<style scoped>
.modal {
  background: #aaaaaa;
  padding: 10px;
  border-radius: 7px;
  position: absolute;
  top: 10px;
  right: 10px;
}
</style>
```

{% codesandbox teleport-47yyy %}

As you can see in the code sandbox since the element that our component is in has a relative position it means that if an absolute element is set inside it, the mentioned element will be bound inside it. Using the teleport feature we've moved our `.modal` so its parent would be the body. This way it will still be controlled by the component it is defined in but the placement in the DOM will be different.

It is possible to use a `#` to determine an id of an element as a destination as below:

```vue
<template>
  <teleport to="#where-your-want">
    <div class="modal" v-if="isModalActive">
      Boom! I teleported!
    </div>
  </teleport>
  <button @click="isModalActive = !isModalActive">{{ isModalActive ? 'Close' : 'Open' }} modal</button>
</template>
```

---

These were the most drastic things you've wanted to learn about Vue 3. I hope you enjoyed it!

BTW! Check out my free Node.js Essentials E-book here:

{% link https://dev.to/adnanbabakan/nodejs-essentials-free-e-book-5319 %}