Skip to content

Components Basics ​

āωāĻĒāĻžāĻĻāĻžāύāϗ⧁āϞāĻŋ āφāĻŽāĻžāĻĻ⧇āϰ UI-āϕ⧇ āĻ¸ā§āĻŦāĻžāϧ⧀āύ āĻāĻŦāĻ‚ āĻĒ⧁āύāσāĻŦā§āϝāĻŦāĻšāĻžāϰāϝ⧋āĻ—ā§āϝ āĻ…āĻ‚āĻļ⧇ āĻŦāĻŋāĻ­āĻ•ā§āϤ āĻ•āϰāϤ⧇ āĻāĻŦāĻ‚ āĻĒā§āϰāϤāĻŋāϟāĻŋ āĻ…āĻ‚āĻļāϕ⧇ āφāϞāĻžāĻĻāĻžāĻ­āĻžāĻŦ⧇ āϚāĻŋāĻ¨ā§āϤāĻž āĻ•āϰāĻžāϰ āĻ…āύ⧁āĻŽāϤāĻŋ āĻĻ⧇āϝāĻŧāĨ¤ āĻāĻ•āϟāĻŋ āĻ…ā§āϝāĻžāĻĒāϕ⧇ āύ⧇āĻ¸ā§āĻŸā§‡āĻĄ āωāĻĒāĻžāĻĻāĻžāύ⧇āϰ āĻāĻ•āϟāĻŋ āĻŸā§āϰāĻŋāϤ⧇ āϏāĻ‚āĻ—āĻ āĻŋāϤ āĻ•āϰāĻž āϏāĻžāϧāĻžāϰāĻŖ:

Component Tree

āĻāϟāĻŋ āφāĻŽāϰāĻž āϝ⧇āĻ­āĻžāĻŦ⧇ āύ⧇āϟāĻŋāĻ­ HTML āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϕ⧇ āύ⧇āĻ¸ā§āϟ āĻ•āϰāĻŋ āϤāĻžāϰ āϏāĻžāĻĨ⧇ āϖ⧁āĻŦ āĻŽāĻŋāϞ, āϤāĻŦ⧇ Vue āϤāĻžāϰ āύāĻŋāϜāĻ¸ā§āĻŦ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻŽāĻĄā§‡āϞ āĻĒā§āϰāϝāĻŧā§‹āĻ— āĻ•āϰ⧇ āϝāĻž āφāĻŽāĻžāĻĻ⧇āϰ āĻĒā§āϰāϤāĻŋāϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āĻ•āĻžāĻ¸ā§āϟāĻŽ āĻŦāĻŋāώāϝāĻŧāĻŦāĻ¸ā§āϤ⧁ āĻāĻŦāĻ‚ āϝ⧁āĻ•ā§āϤāĻŋ āĻāύāĻ•ā§āϝāĻžāĻĒāϏ⧁āϞ⧇āϟ āĻ•āϰāϤ⧇ āĻĻ⧇āϝāĻŧāĨ¤ Vue āύ⧇āϟāĻŋāĻ­ āĻ“āϝāĻŧ⧇āĻŦ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āϏāĻžāĻĨ⧇āĻ“ āϏ⧁āĻ¨ā§āĻĻāϰāĻ­āĻžāĻŦ⧇ āϖ⧇āϞ⧇āĨ¤ āφāĻĒāύāĻŋ āϝāĻĻāĻŋ Vue āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻāĻŦāĻ‚ āύ⧇āϟāĻŋāĻ­ āĻ“āϝāĻŧ⧇āĻŦ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āĻŽāĻ§ā§āϝ⧇ āϏāĻŽā§āĻĒāĻ°ā§āĻ• āϏāĻŽā§āĻĒāĻ°ā§āϕ⧇ āφāĻ—ā§āϰāĻšā§€ āĻšāύ, āĻāĻ–āĻžāύ⧇ āφāϰāĻ“ āĻĒāĻĄāĻŧ⧁āύāĨ¤

Defining a Component ​

āĻāĻ•āϟāĻŋ āĻŦāĻŋāĻ˛ā§āĻĄ āĻ¸ā§āĻŸā§‡āĻĒ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻžāϰ āϏāĻŽāϝāĻŧ, āφāĻŽāϰāĻž āϏāĻžāϧāĻžāϰāĻŖāϤ .vue āĻāĻ•ā§āϏāĻŸā§‡āύāĻļāύ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āĻāĻ•āϟāĻŋ āĻĄā§‡āĻĄāĻŋāϕ⧇āĻŸā§‡āĻĄ āĻĢāĻžāχāϞ⧇ āĻĒā§āϰāϤāĻŋāϟāĻŋ Vue āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϕ⧇ āϏāĻ‚āĻœā§āĻžāĻžāϝāĻŧāĻŋāϤ āĻ•āϰāĻŋ - āϝāĻž Single-File Component (āϏāĻ‚āĻ•ā§āώ⧇āĻĒ⧇ SFC):

vue
<script>
export default {
  data() {
    return {
      count: 0
    }
  }
}
</script>

<template>
  <button @click="count++">You clicked me {{ count }} times.</button>
</template>
vue
<script setup>
import { ref } from 'vue'

const count = ref(0)
</script>

<template>
  <button @click="count++">You clicked me {{ count }} times.</button>
</template>

āĻāĻ•āϟāĻŋ āĻŦāĻŋāĻ˛ā§āĻĄ āĻ¸ā§āĻŸā§‡āĻĒ āĻŦā§āϝāĻŦāĻšāĻžāϰ āύāĻž āĻ•āϰāĻžāϰ āϏāĻŽāϝāĻŧ, āĻāĻ•āϟāĻŋ Vue āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϕ⧇ āĻāĻ•āϟāĻŋ āĻĒā§āϞ⧇āχāύ āϜāĻžāĻ­āĻžāĻ¸ā§āĻ•ā§āϰāĻŋāĻĒā§āϟ āĻ…āĻŦāĻœā§‡āĻ•ā§āϟ āĻšāĻŋāϏāĻžāĻŦ⧇ āϏāĻ‚āĻœā§āĻžāĻžāϝāĻŧāĻŋāϤ āĻ•āϰāĻž āϝ⧇āϤ⧇ āĻĒāĻžāϰ⧇ āϝ⧇āĻ–āĻžāύ⧇ Vue-āύāĻŋāĻ°ā§āĻĻāĻŋāĻˇā§āϟ āĻŦāĻŋāĻ•āĻ˛ā§āĻĒ āϰāϝāĻŧ⧇āϛ⧇:

js
export default {
  data() {
    return {
      count: 0
    }
  },
  template: `
    <button @click="count++">
      You clicked me {{ count }} times.
    </button>`
}
js
import { ref } from 'vue'

export default {
  setup() {
    const count = ref(0)
    return { count }
  },
  template: `
    <button @click="count++">
      You clicked me {{ count }} times.
    </button>`
  // Can also target an in-DOM template:
  // template: '#my-template-element'
}

āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟāϟāĻŋ āĻāĻ–āĻžāύ⧇ āϜāĻžāĻ­āĻžāĻ¸ā§āĻ•ā§āϰāĻŋāĻĒā§āϟ āĻ¸ā§āĻŸā§āϰāĻŋāĻ‚ āĻšāĻŋāϏāĻžāĻŦ⧇ āχāύāϞāĻžāχāύ āĻ•āϰāĻž āĻšāϝāĻŧ⧇āϛ⧇, āϝāĻž Vue āĻĢā§āϞāĻžāχāϤ⧇ āĻ•āĻŽā§āĻĒāĻžāχāϞ āĻ•āϰāĻŦ⧇āĨ¤ āφāĻĒāύāĻŋ āĻāĻ•āϟāĻŋ āφāχāĻĄāĻŋ āύāĻŋāĻ°ā§āĻŦāĻžāϚāĻ•āĻ“ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύ āϝ⧇āϟāĻŋ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻĻāĻŋāϕ⧇ āύāĻŋāĻ°ā§āĻĻ⧇āĻļ āĻ•āϰ⧇ (āϏāĻžāϧāĻžāϰāĻŖāϤ āύ⧇āϟāĻŋāĻ­ <template> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ) - Vue āĻāϰ āϏāĻžāĻŽāĻ—ā§āϰ⧀āϕ⧇ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āωāĻ¤ā§āϏ āĻšāĻŋāϏāĻžāĻŦ⧇ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻŦ⧇⧎

āωāĻĒāϰ⧇āϰ āωāĻĻāĻžāĻšāϰāĻŖāϟāĻŋ āĻāĻ•āϟāĻŋ āĻāĻ•āĻ• āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϕ⧇ āϏāĻ‚āĻœā§āĻžāĻžāϝāĻŧāĻŋāϤ āĻ•āϰ⧇ āĻāĻŦāĻ‚ āĻāϟāĻŋ āĻāĻ•āϟāĻŋ .js āĻĢāĻžāχāϞ⧇āϰ āĻĄāĻŋāĻĢāĻ˛ā§āϟ exports āĻšāĻŋāϏāĻžāĻŦ⧇ export āĻ•āϰ⧇, āϤāĻŦ⧇ āφāĻĒāύāĻŋ āĻāĻ•āχ āĻĢāĻžāχāϞ āĻĨ⧇āϕ⧇ āĻāĻ•āĻžāϧāĻŋāĻ• āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ exports āĻ•āϰāϤ⧇ āύāĻžāĻŽ export āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύāĨ¤

Using a Component ​

TIP

āφāĻŽāϰāĻž āĻāχ āĻ—āĻžāχāĻĄā§‡āϰ āĻŦāĻžāĻ•āĻŋ āĻ…āĻ‚āĻļ⧇āϰ āϜāĻ¨ā§āϝ SFC āϏāĻŋāύāĻŸā§āϝāĻžāĻ•ā§āϏ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻŦ - āφāĻĒāύāĻŋ āĻāĻ•āϟāĻŋ āĻŦāĻŋāĻ˛ā§āĻĄ āĻ¸ā§āĻŸā§‡āĻĒ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϛ⧇āύ āĻŦāĻž āύāĻž āĻ•āϰāϛ⧇āύ āϤāĻž āύāĻŋāĻ°ā§āĻŦāĻŋāĻļ⧇āώ⧇ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āϚāĻžāϰāĻĒāĻžāĻļ⧇āϰ āϧāĻžāϰāĻŖāĻžāϗ⧁āϞāĻŋ āĻāĻ•āχāĨ¤ Examples āĻŦāĻŋāĻ­āĻžāĻ—āϟāĻŋ āωāĻ­āϝāĻŧ āĻĒāϰāĻŋāĻ¸ā§āĻĨāĻŋāϤāĻŋāϤ⧇āχ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻĻ⧇āĻ–āĻžāϝāĻŧāĨ¤

āĻāĻ•āϟāĻŋ āϚāĻžāχāĻ˛ā§āĻĄ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇, āφāĻŽāĻžāĻĻ⧇āϰ āĻāϟāĻŋāϕ⧇ āĻĒā§āϝāĻžāϰ⧇āĻ¨ā§āϟ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āχāĻŽā§āĻĒā§‹āĻ°ā§āϟ āĻ•āϰāϤ⧇ āĻšāĻŦ⧇āĨ¤ āϧāϰ⧇ āύāĻŋāĻšā§āĻ›āĻŋ āφāĻŽāϰāĻž āφāĻŽāĻžāĻĻ⧇āϰ āĻ•āĻžāωāĻ¨ā§āϟāĻžāϰ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϕ⧇ ButtonCounter.vue āύāĻžāĻŽāĻ• āĻāĻ•āϟāĻŋ āĻĢāĻžāχāϞ⧇āϰ āĻ­āĻŋāϤāϰ⧇ āϰ⧇āϖ⧇āĻ›āĻŋ, āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϟāĻŋ āĻĢāĻžāχāϞ⧇āϰ āĻĄāĻŋāĻĢāĻ˛ā§āϟ āĻāĻ•ā§āϏāĻĒā§‹āĻ°ā§āϟ āĻšāĻŋāϏ⧇āĻŦ⧇ āωāĻ¨ā§āĻŽā§āĻ•ā§āϤ āĻšāĻŦ⧇:

vue
<script>
import ButtonCounter from './ButtonCounter.vue'

export default {
  components: {
    ButtonCounter
  }
}
</script>

<template>
  <h1>Here is a child component!</h1>
  <ButtonCounter />
</template>

āφāĻŽāĻžāĻĻ⧇āϰ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āĻŸā§‡ āχāĻŽā§āĻĒā§‹āĻ°ā§āϟ āĻ•āϰāĻž āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻāĻ•ā§āϏāĻĒā§‹āϜ āĻ•āϰāϤ⧇, āφāĻŽāĻžāĻĻ⧇āϰ āĻāϟāĻŋāϕ⧇ ' āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϏ' āĻŦāĻŋāĻ•āĻ˛ā§āĻĒ⧇āϰ āϏāĻžāĻĨ⧇ āϰ⧇āϜāĻŋāĻ¸ā§āϟāĻžāϰ āĻ•āϰāϤ⧇ āĻšāĻŦ⧇āĨ¤ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϟāĻŋ āϤāĻžāϰāĻĒāϰ⧇ āύāĻŋāĻŦāĻ¨ā§āϧāĻŋāϤ āϕ⧀ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āĻāĻ•āϟāĻŋ āĻŸā§āϝāĻžāĻ— āĻšāĻŋāϏāĻžāĻŦ⧇ āωāĻĒāϞāĻŦā§āϧ āĻšāĻŦ⧇āĨ¤

vue
<script setup>
import ButtonCounter from './ButtonCounter.vue'
</script>

<template>
  <h1>Here is a child component!</h1>
  <ButtonCounter />
</template>

<script setup> āĻāϰ āϏāĻžāĻĨ⧇, āφāĻŽāĻĻāĻžāύāĻŋ āĻ•āϰāĻž āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋ āĻ¸ā§āĻŦāϝāĻŧāĻ‚āĻ•ā§āϰāĻŋāϝāĻŧāĻ­āĻžāĻŦ⧇ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āĻŸā§‡ āωāĻĒāϞāĻŦā§āϧ āĻ•āϰāĻž āĻšāϝāĻŧāĨ¤

āĻāϟāĻŋ āφāĻŽāĻĻāĻžāύāĻŋ āύāĻž āĻ•āϰ⧇āχ āĻāĻ•āϟāĻŋ āĻĒā§āϰāĻĻāĻ¤ā§āϤ āĻ…ā§āϝāĻžāĻĒ⧇āϰ āϏāĻŽāĻ¸ā§āϤ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āϜāĻ¨ā§āϝ āωāĻĒāϞāĻŦā§āϧ āĻ•āϰ⧇, āĻŦāĻŋāĻļā§āĻŦāĻŦā§āϝāĻžāĻĒā§€ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āύāĻŋāĻŦāĻ¨ā§āϧāύ āĻ•āϰāĻžāĻ“ āϏāĻŽā§āĻ­āĻŦāĨ¤ āĻ—ā§āϞ⧋āĻŦāĻžāϞ āĻŦāύāĻžāĻŽ āĻ¸ā§āĻĨāĻžāύ⧀āϝāĻŧ āϰ⧇āϜāĻŋāĻ¸ā§āĻŸā§āϰ⧇āĻļāύ⧇āϰ āĻ­āĻžāϞ⧋-āĻŽāĻ¨ā§āĻĻ āφāϞ⧋āϚāύāĻž āĻ•āϰāĻž āĻšāϝāĻŧ⧇āϛ⧇ āĻĄā§‡āĻĄāĻŋāϕ⧇āĻŸā§‡āĻĄ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āϰ⧇āϜāĻŋāĻ¸ā§āĻŸā§āϰ⧇āĻļāύ āĻŦāĻŋāĻ­āĻžāϗ⧇āĨ¤

āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋ āφāĻĒāύāĻŋ āϝāϤāĻŦāĻžāϰ āϚāĻžāύ āϤāϤāĻŦāĻžāϰ āĻĒ⧁āύāϰāĻžāϝāĻŧ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻž āϝ⧇āϤ⧇ āĻĒāĻžāϰ⧇:

template
<h1>Here are many child components!</h1>
<ButtonCounter />
<ButtonCounter />
<ButtonCounter />

āϞāĻ•ā§āĻˇā§āϝ āĻ•āϰ⧁āύ āϝ⧇ āĻŦā§‹āϤāĻžāĻŽāϗ⧁āϞāĻŋāϤ⧇ āĻ•ā§āϞāĻŋāĻ• āĻ•āϰāĻžāϰ āϏāĻŽāϝāĻŧ, āĻĒā§āϰāϤāĻŋāϟāĻŋ āϤāĻžāϰ āύāĻŋāϜāĻ¸ā§āĻŦ, āĻĒ⧃āĻĨāĻ• count āĻŦāϜāĻžāϝāĻŧ āϰāĻžāϖ⧇āĨ¤ āĻ•āĻžāϰāĻŖ āĻĒā§āϰāϤāĻŋāĻŦāĻžāϰ āφāĻĒāύāĻŋ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϞ⧇, āĻāϰ āĻāĻ•āϟāĻŋ āύāϤ⧁āύ āωāĻĻāĻžāĻšāϰāĻŖ āϤ⧈āϰāĻŋ āĻšāϝāĻŧāĨ¤

SFC-āϤ⧇, āύ⧇āϟāĻŋāĻ­ HTML āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻĨ⧇āϕ⧇ āφāϞāĻžāĻĻāĻž āĻ•āϰāϤ⧇ āϚāĻžāχāĻ˛ā§āĻĄ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āϜāĻ¨ā§āϝ PascalCase āĻŸā§āϝāĻžāĻ— āύāĻžāĻŽ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻžāϰ āĻĒāϰāĻžāĻŽāĻ°ā§āĻļ āĻĻ⧇āĻ“āϝāĻŧāĻž āĻšāϝāĻŧāĨ¤ āϝāĻĻāĻŋāĻ“ āύ⧇āϟāĻŋāĻ­ HTML āĻŸā§āϝāĻžāϗ⧇āϰ āύāĻžāĻŽāϗ⧁āϞāĻŋ āϕ⧇āϏ-āϏāĻ‚āĻŦ⧇āĻĻāύāĻļā§€āϞ, āϤāĻŦ⧇ Vue SFC āĻāĻ•āϟāĻŋ āϏāĻ‚āĻ•āϞāĻŋāϤ āĻŦāĻŋāĻ¨ā§āϝāĻžāϏ āϤāĻžāχ āφāĻŽāϰāĻž āĻāϤ⧇ āϕ⧇āϏ-āϏāĻ‚āĻŦ⧇āĻĻāύāĻļā§€āϞ āĻŸā§āϝāĻžāĻ— āύāĻžāĻŽāϗ⧁āϞāĻŋ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āϏāĻ•ā§āώāĻŽāĨ¤ āφāĻŽāϰāĻž āĻŸā§āϝāĻžāĻ— āĻŦāĻ¨ā§āϧ āĻ•āϰāϤ⧇ /> āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇āĻ“ āϏāĻ•ā§āώāĻŽāĨ¤

āφāĻĒāύāĻŋ āϝāĻĻāĻŋ āφāĻĒāύāĻžāϰ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟāϗ⧁āϞāĻŋ āϏāϰāĻžāϏāϰāĻŋ āĻāĻ•āϟāĻŋ DOM-āĻ āϰāϚāύāĻž āĻ•āϰ⧇āύ (āϝ⧇āĻŽāύ āĻāĻ•āϟāĻŋ āύ⧇āϟāĻŋāĻ­ <template> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟ āĻšāĻŋāϏāĻžāĻŦ⧇), āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟāϟāĻŋ āĻŦā§āϰāĻžāωāϜāĻžāϰ⧇āϰ āύ⧇āϟāĻŋāĻ­ HTML āĻĒāĻžāĻ°ā§āϏāĻŋāĻ‚ āφāϚāϰāϪ⧇āϰ āĻ…āϧ⧀āύ āĻšāĻŦ⧇āĨ¤ āĻāχ āϧāϰāύ⧇āϰ āĻ•ā§āώ⧇āĻ¤ā§āϰ⧇, āφāĻĒāύāĻžāϕ⧇ 'āĻ•āĻžāĻŦāĻžāĻŦ-āϕ⧇āϏ' āĻāĻŦāĻ‚ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āϜāĻ¨ā§āϝ āĻ¸ā§āĻĒāĻˇā§āϟ āĻ•ā§āϞ⧋āϜāĻŋāĻ‚ āĻŸā§āϝāĻžāĻ— āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āĻšāĻŦ⧇:

template
<!-- if this template is written in the DOM -->
<button-counter></button-counter>
<button-counter></button-counter>
<button-counter></button-counter>

āφāϰāĻ“ āĻŦāĻŋāĻļāĻĻ āĻŦāĻŋāĻŦāϰāϪ⧇āϰ āϜāĻ¨ā§āϝ in-DOM template parsing caveats āĻĻ⧇āϖ⧁āύāĨ¤

Passing Props ​

āϝāĻĻāĻŋ āφāĻŽāϰāĻž āĻāĻ•āϟāĻŋ āĻŦā§āϞāĻ— āϤ⧈āϰāĻŋ āĻ•āϰāĻŋ, āϤāĻžāĻšāϞ⧇ āφāĻŽāĻžāĻĻ⧇āϰ āϏāĻŽā§āĻ­āĻŦāϤ āĻāĻ•āϟāĻŋ āĻŦā§āϞāĻ— āĻĒā§‹āĻ¸ā§āĻŸā§‡āϰ āĻĒā§āϰāϤāĻŋāύāĻŋāϧāĻŋāĻ¤ā§āĻŦāĻ•āĻžāϰ⧀ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻĒā§āϰāϝāĻŧā§‹āϜāύ āĻšāĻŦ⧇āĨ¤ āφāĻŽāϰāĻž āϚāĻžāχ āϝ⧇ āϏāĻŽāĻ¸ā§āϤ āĻŦā§āϞāĻ— āĻĒā§‹āĻ¸ā§āϟ āĻāĻ•āχ āĻ­āĻŋāĻœā§āϝ⧁āϝāĻŧāĻžāϞ āϞ⧇āφāωāϟ āĻļ⧇āϝāĻŧāĻžāϰ āĻ•āϰ⧁āĻ•, āĻ•āĻŋāĻ¨ā§āϤ⧁ āĻ­āĻŋāĻ¨ā§āύ āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟ āϏāĻšāĨ¤ āĻāχ āϧāϰāύ⧇āϰ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āωāĻĒāϝ⧋āĻ—ā§€ āĻšāĻŦ⧇ āύāĻž āϝāĻĻāĻŋ āύāĻž āφāĻĒāύāĻŋ āĻāϟāĻŋāϤ⧇ āĻĄā§‡āϟāĻž āĻĒāĻžāĻ āĻžāϤ⧇ āĻĒāĻžāϰ⧇āύ, āϝ⧇āĻŽāύ āύāĻŋāĻ°ā§āĻĻāĻŋāĻˇā§āϟ āĻĒā§‹āĻ¸ā§āĻŸā§‡āϰ āĻļāĻŋāϰ⧋āύāĻžāĻŽ āĻāĻŦāĻ‚ āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟ āφāĻŽāϰāĻž āĻĒā§āϰāĻĻāĻ°ā§āĻļāύ āĻ•āϰāϤ⧇ āϚāĻžāχāĨ¤ āϝ⧇ āϝ⧇āĻ–āĻžāύ⧇ āĻĒā§āϰāĻĒāϏ āφāϏāĻž.

āĻĒā§āϰāĻĒāϗ⧁āϞāĻŋ āĻšāϞ āĻ•āĻžāĻ¸ā§āϟāĻŽ āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝāϗ⧁āϞāĻŋ āϝāĻž āφāĻĒāύāĻŋ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āύāĻŋāĻŦāĻ¨ā§āϧāύ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύāĨ¤ āφāĻŽāĻžāĻĻ⧇āϰ āĻŦā§āϞāĻ— āĻĒā§‹āĻ¸ā§āϟ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āĻāĻ•āϟāĻŋ āĻļāĻŋāϰ⧋āύāĻžāĻŽ āĻĒāĻžāϏ āĻ•āϰāĻžāϰ āϜāĻ¨ā§āϝ, props āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āĻāχ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϟāĻŋ āĻ—ā§āϰāĻšāĻŖ āĻ•āϰ⧇ āĻāĻŽāύ āĻĒā§āϰāĻĒāϏ⧇āϰ āϤāĻžāϞāĻŋāĻ•āĻžāϝāĻŧ āφāĻŽāĻžāĻĻ⧇āϰ āĻāϟāĻŋ āĻ˜ā§‹āώāĻŖāĻž āĻ•āϰāϤ⧇ āĻšāĻŦ⧇āĨ¤ āĻŦāĻŋāĻ•āĻ˛ā§āĻĒdefineProps āĻŽā§āϝāĻžāĻ•ā§āϰ⧋:

BlogPost.vue
vue
<script>
export default {
  props: ['title']
}
</script>

<template>
  <h4>{{ title }}</h4>
</template>

āϝāĻ–āύ āĻāĻ•āϟāĻŋ āĻŽāĻžāύ āĻāĻ•āϟāĻŋ āĻĒā§āϰāĻĒ āĻ…ā§āϝāĻžāĻŸā§āϰāĻŋāĻŦāĻŋāωāĻŸā§‡ āĻĒāĻžāϏ āĻ•āϰāĻž āĻšāϝāĻŧ, āϤāĻ–āύ āĻāϟāĻŋ āϏ⧇āχ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āωāĻĻāĻžāĻšāϰāϪ⧇ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒāĻŋāωāĻŸā§‡āĻĄ āĻĒā§āϰāĻĒāĻžāĻ°ā§āϟāĻŋ āĻšāϝāĻŧ⧇ āϝāĻžāϝāĻŧāĨ¤ āϏ⧇āχ āĻ•āĻŽā§āĻĒāĻŋāωāĻŸā§‡āĻĄ āĻĒā§āϰāĻĒāĻžāĻ°ā§āϟāĻŋāϰ āĻŽāĻžāύ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āĻŸā§‡āϰ āĻŽāĻ§ā§āϝ⧇ āĻāĻŦāĻ‚ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ this āĻĒā§āϰ⧇āĻ•ā§āώāĻžāĻĒāĻŸā§‡ āĻ…ā§āϝāĻžāĻ•ā§āϏ⧇āϏāϝ⧋āĻ—ā§āϝ, āĻ āĻŋāĻ• āĻ…āĻ¨ā§āϝ āϕ⧋āύ⧋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻ•āĻŽā§āĻĒāĻŋāωāĻŸā§‡āĻĄ āĻĒā§āϰāĻĒāĻžāĻ°ā§āϟāĻŋāϰ āĻŽāϤ⧋āĨ¤

BlogPost.vue
vue
<script setup>
defineProps(['title'])
</script>

<template>
  <h4>{{ title }}</h4>
</template>

defineProps āĻšāϞ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒāĻžāχāϞ-āϟāĻžāχāĻŽ āĻŽā§āϝāĻžāĻ•ā§āϰ⧋ āϝāĻž āĻļ⧁āϧ⧁āĻŽāĻžāĻ¤ā§āϰ <script setup>-āĻāϰ āĻŽāĻ§ā§āϝ⧇āχ āωāĻĒāϞāĻŦā§āϧ āĻāĻŦāĻ‚ āĻ¸ā§āĻĒāĻˇā§āϟāĻ­āĻžāĻŦ⧇ āφāĻŽāĻĻāĻžāύāĻŋ āĻ•āϰāĻžāϰ āĻĒā§āϰāϝāĻŧā§‹āϜāύ āύ⧇āχāĨ¤ āĻ˜ā§‹āώāĻŋāϤ āĻĒā§āϰāĻĒāϗ⧁āϞāĻŋ āĻ¸ā§āĻŦāϝāĻŧāĻ‚āĻ•ā§āϰāĻŋāϝāĻŧāĻ­āĻžāĻŦ⧇ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āĻŸā§‡āϰ āĻ•āĻžāϛ⧇ āĻĒā§āϰāĻ•āĻžāĻļāĻŋāϤ āĻšāϝāĻŧāĨ¤ defineProps āĻāĻ•āϟāĻŋ āĻ…āĻŦāĻœā§‡āĻ•ā§āϟāĻ“ āĻĢ⧇āϰāϤ āĻĻ⧇āϝāĻŧ āϝāĻžāϤ⧇ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āĻĒāĻžāϏ āĻ•āϰāĻž āϏāĻŽāĻ¸ā§āϤ āĻĒā§āϰāĻĒ āĻĨāĻžāϕ⧇, āϝāĻžāϤ⧇ āφāĻŽāϰāĻž āĻĒā§āϰāϝāĻŧā§‹āϜāύ⧇ āϜāĻžāĻ­āĻžāĻ¸ā§āĻ•ā§āϰāĻŋāĻĒā§āĻŸā§‡ āϏ⧇āϗ⧁āϞāĻŋ āĻ…ā§āϝāĻžāĻ•ā§āϏ⧇āϏ āĻ•āϰāϤ⧇ āĻĒāĻžāϰāĻŋ:

js
const props = defineProps(['title'])
console.log(props.title)

āφāϰ⧋ āĻĻ⧇āϖ⧁āύ: Typing Component Props

āφāĻĒāύāĻŋ āϝāĻĻāĻŋ <script setup> āĻŦā§āϝāĻŦāĻšāĻžāϰ āύāĻž āĻ•āϰ⧇āύ, āϤāĻžāĻšāϞ⧇ āĻĒā§āϰāĻĒāϏāϕ⧇ props āĻŦāĻŋāĻ•āĻ˛ā§āĻĒ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āĻ˜ā§‹āώāĻŖāĻž āĻ•āϰāĻž āωāϚāĻŋāϤ āĻāĻŦāĻ‚ āĻĒā§āϰāĻĒāϏ āĻ…āĻŦāĻœā§‡āĻ•ā§āϟāϟāĻŋ āĻĒā§āϰāĻĨāĻŽ āφāĻ°ā§āϗ⧁āĻŽā§‡āĻ¨ā§āϟ āĻšāĻŋāϏ⧇āĻŦ⧇ setup()-āĻ āĻĒāĻžāϏ āĻ•āϰāĻž āĻšāĻŦ⧇:

js
export default {
  props: ['title'],
  setup(props) {
    console.log(props.title)
  }
}

āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āφāĻĒāύāĻžāϰ āĻĒāĻ›āĻ¨ā§āĻĻ āĻŽāϤ⧋ āĻ…āύ⧇āĻ•āϗ⧁āϞāĻŋ āĻĒā§āϰāĻĒ āĻĨāĻžāĻ•āϤ⧇ āĻĒāĻžāϰ⧇ āĻāĻŦāĻ‚ āĻĄāĻŋāĻĢāĻ˛ā§āϟāϰ⧂āĻĒ⧇, āϝ⧇āϕ⧋āύ āĻŽāĻžāύ āϝ⧇āϕ⧋āύ āĻĒā§āϰāĻĒ⧇ āĻĒāĻžāϏ āĻ•āϰāĻž āϝ⧇āϤ⧇ āĻĒāĻžāϰ⧇āĨ¤

āĻāĻ•āĻŦāĻžāϰ āĻāĻ•āϟāĻŋ āĻĒā§āϰāĻĒ āύāĻŋāĻŦāĻ¨ā§āϧāĻŋāϤ āĻšāϝāĻŧ⧇ āϗ⧇āϞ⧇, āφāĻĒāύāĻŋ āĻāϟāĻŋāϤ⧇ āĻāĻ•āϟāĻŋ āĻ•āĻžāĻ¸ā§āϟāĻŽ āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ āĻšāĻŋāϏāĻžāĻŦ⧇ āĻĄā§‡āϟāĻž āĻĒā§āϰ⧇āϰāĻŖ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύ, āϝ⧇āĻŽāύ:

template
<BlogPost title="My journey with Vue" />
<BlogPost title="Blogging with Vue" />
<BlogPost title="Why Vue is so fun" />

āĻāĻ•āϟāĻŋ āϏāĻžāϧāĻžāϰāĻŖ āĻ…ā§āϝāĻžāĻĒ⧇, āϤāĻŦ⧇, āφāĻĒāύāĻžāϰ āϏāĻŽā§āĻ­āĻŦāϤ āφāĻĒāύāĻžāϰ āĻ…āĻ­āĻŋāĻ­āĻžāĻŦāĻ• āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āĻĒā§‹āĻ¸ā§āĻŸā§‡āϰ āĻāĻ•āϟāĻŋ āĻ…ā§āϝāĻžāϰ⧇ āĻĨāĻžāĻ•āĻŦ⧇:

js
export default {
  // ...
  data() {
    return {
      posts: [
        { id: 1, title: 'My journey with Vue' },
        { id: 2, title: 'Blogging with Vue' },
        { id: 3, title: 'Why Vue is so fun' }
      ]
    }
  }
}
js
const posts = ref([
  { id: 1, title: 'My journey with Vue' },
  { id: 2, title: 'Blogging with Vue' },
  { id: 3, title: 'Why Vue is so fun' }
])

āϤāĻžāϰāĻĒāϰ v-for āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āĻĒā§āϰāĻ¤ā§āϝ⧇āĻ•āϟāĻŋāϰ āϜāĻ¨ā§āϝ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āϰ⧇āĻ¨ā§āĻĄāĻžāϰ āĻ•āϰāϤ⧇ āϚāĻžāύ:

template
<BlogPost
  v-for="post in posts"
  :key="post.id"
  :title="post.title"
 />

āϞāĻ•ā§āĻˇā§āϝ āĻ•āϰ⧁āύ āĻ•āĻŋāĻ­āĻžāĻŦ⧇ v-bind āϏāĻŋāύāĻŸā§āϝāĻžāĻ•ā§āϏ (:title="post.title") āĻĄāĻžāϝāĻŧāύāĻžāĻŽāĻŋāĻ• āĻĒā§āϰāĻĒ āĻŽāĻžāύ āĻĒāĻžāϏ āĻ•āϰāϤ⧇ āĻŦā§āϝāĻŦāĻšā§ƒāϤ āĻšāϝāĻŧāĨ¤ āĻāϟāĻŋ āĻŦāĻŋāĻļ⧇āώāĻ­āĻžāĻŦ⧇ āωāĻĒāϝ⧋āĻ—ā§€ āϝāĻ–āύ āφāĻĒāύāĻŋ āϏāĻ āĻŋāĻ• āĻŦāĻŋāώāϝāĻŧāĻŦāĻ¸ā§āϤ⧁ āϜāĻžāύ⧇āύ āύāĻž āϝ⧇ āφāĻĒāύāĻŋ āϏāĻŽāϝāĻŧ⧇āϰ āφāϗ⧇ āϰ⧇āĻ¨ā§āĻĄāĻžāϰ āĻ•āϰāϤ⧇ āϝāĻžāĻšā§āϛ⧇āύāĨ¤

āφāĻĒāĻžāϤāϤ āĻĒā§āϰāĻĒāϏ āϏāĻŽā§āĻĒāĻ°ā§āϕ⧇ āφāĻĒāύāĻžāϰ āĻāϤāϟ⧁āϕ⧁āχ āϜāĻžāύāĻž āĻĻāϰāĻ•āĻžāϰ, āĻ•āĻŋāĻ¨ā§āϤ⧁ āĻāĻ•āĻŦāĻžāϰ āφāĻĒāύāĻŋ āĻāχ āĻĒ⧃āĻˇā§āĻ āĻžāϟāĻŋ āĻĒāĻĄāĻŧāĻž āĻļ⧇āώ āĻ•āϰ⧇ āĻāĻŦāĻ‚ āĻāϰ āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟāϤ⧇ āĻ¸ā§āĻŦāĻžāĻšā§āĻ›āĻ¨ā§āĻĻā§āϝ āĻŦā§‹āϧ āĻ•āϰāϞ⧇, āφāĻŽāϰāĻž āĻĒā§āϰāĻĒāϏ āĻāϰ āϏāĻŽā§āĻĒā§‚āĻ°ā§āĻŖ āύāĻŋāĻ°ā§āĻĻ⧇āĻļāĻŋāĻ•āĻž āĻĒāĻĄāĻŧāϤ⧇ āĻĒāϰ⧇ āĻĢāĻŋāϰ⧇ āφāϏāĻžāϰ āĻĒāϰāĻžāĻŽāĻ°ā§āĻļ āĻĻāĻŋāχāĨ¤

Listening to Events ​

āϝ⧇āĻšā§‡āϤ⧁ āφāĻŽāϰāĻž āφāĻŽāĻžāĻĻ⧇āϰ <BlogPost> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϟāĻŋ āĻĄā§‡āϭ⧇āϞāĻĒāĻŽā§‡āĻ¨ā§āϟ āĻ•āϰāĻŋ, āĻ•āĻŋāϛ⧁ āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ⧇āϰ āϜāĻ¨ā§āϝ āĻ…āĻ­āĻŋāĻ­āĻžāĻŦāϕ⧇āϰ āϏāĻžāĻĨ⧇ āĻŦā§āϝāĻžāĻ• āφāĻĒ āϝ⧋āĻ—āĻžāϝ⧋āϗ⧇āϰ āĻĒā§āϰāϝāĻŧā§‹āϜāύ āĻšāϤ⧇ āĻĒāĻžāϰ⧇āĨ¤ āωāĻĻāĻžāĻšāϰāĻŖāĻ¸ā§āĻŦāϰ⧂āĻĒ, āφāĻŽāϰāĻž āĻĒ⧃āĻˇā§āĻ āĻžāϰ āĻŦāĻžāĻ•āĻŋ āĻ…āĻ‚āĻļāϟāĻŋāϕ⧇ āĻĄāĻŋāĻĢāĻ˛ā§āϟ āφāĻ•āĻžāϰ⧇ āϰ⧇āϖ⧇ āĻŦā§āϞāĻ— āĻĒā§‹āĻ¸ā§āĻŸā§‡āϰ āĻĒāĻžāĻ ā§āϝāϕ⧇ āĻŦāĻĄāĻŧ āĻ•āϰāĻžāϰ āϜāĻ¨ā§āϝ āĻāĻ•āϟāĻŋ āĻ…ā§āϝāĻžāĻ•ā§āϏ⧇āϏāĻŋāĻŦāĻŋāϞāĻŋāϟāĻŋ āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ āĻ…āĻ¨ā§āϤāĻ°ā§āϭ⧁āĻ•ā§āϤ āĻ•āϰāĻžāϰ āϏāĻŋāĻĻā§āϧāĻžāĻ¨ā§āϤ āύāĻŋāϤ⧇ āĻĒāĻžāϰāĻŋāĨ¤

āĻ…āĻ­āĻŋāĻ­āĻžāĻŦāĻ•āĻĻ⧇āϰ āĻŽāĻ§ā§āϝ⧇, āφāĻŽāϰāĻž āĻāĻ•āϟāĻŋ āĻĒā§‹āĻ¸ā§āϟāĻĢāĻ¨ā§āϟ āϏāĻžāχāϜ āϝ⧋āĻ— āĻ•āϰ⧇ āĻāχ āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝāϟāĻŋāϕ⧇ āϏāĻŽāĻ°ā§āĻĨāύ āĻ•āϰāϤ⧇ āĻĒāĻžāϰāĻŋ data propertyref:

js
data() {
  return {
    posts: [
      /* ... */
    ],
    postFontSize: 1
  }
}
js
const posts = ref([
  /* ... */
])

const postFontSize = ref(1)

āϝāĻž āϏāĻŽāĻ¸ā§āϤ āĻŦā§āϞāĻ— āĻĒā§‹āĻ¸ā§āĻŸā§‡āϰ āĻĢāĻ¨ā§āϟ āϏāĻžāχāϜ āύāĻŋāϝāĻŧāĻ¨ā§āĻ¤ā§āϰāĻŖ āĻ•āϰāϤ⧇ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āĻŸā§‡ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻž āϝ⧇āϤ⧇ āĻĒāĻžāϰ⧇:

template
<div :style="{ fontSize: postFontSize + 'em' }">
  <BlogPost
    v-for="post in posts"
    :key="post.id"
    :title="post.title"
   />
</div>

āĻāĻ–āύ āφāϏ⧁āύ <BlogPost> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āĻŸā§‡ āĻāĻ•āϟāĻŋ āĻŦā§‹āϤāĻžāĻŽ āϝ⧋āĻ— āĻ•āϰāĻŋ:

BlogPost.vue
vue
<!-- omitting <script> -->
<template>
  <div class="blog-post">
    <h4>{{ title }}</h4>
    <button>Enlarge text</button>
  </div>
</template>

āĻŦā§‹āϤāĻžāĻŽāϟāĻŋ āĻāĻ–āύāĻ“ āĻ•āĻŋāϛ⧁ āĻ•āϰ⧇ āύāĻž - āφāĻŽāϰāĻž āĻ…āĻ­āĻŋāĻ­āĻžāĻŦāĻ•āĻĻ⧇āϰ āϏāĻžāĻĨ⧇ āϝ⧋āĻ—āĻžāϝ⧋āĻ— āĻ•āϰāϤ⧇ āĻŦā§‹āϤāĻžāĻŽāϟāĻŋ āĻ•ā§āϞāĻŋāĻ• āĻ•āϰāϤ⧇ āϚāĻžāχ āϝ⧇ āĻāϟāĻŋ āϏāĻŽāĻ¸ā§āϤ āĻĒā§‹āĻ¸ā§āĻŸā§‡āϰ āĻĒāĻžāĻ ā§āϝāϕ⧇ āĻŦāĻĄāĻŧ āĻ•āϰāĻŦ⧇⧎ āĻāχ āϏāĻŽāĻ¸ā§āϝāĻžāϟāĻŋ āϏāĻŽāĻžāϧāĻžāύ āĻ•āϰāĻžāϰ āϜāĻ¨ā§āϝ, āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋ āĻāĻ•āϟāĻŋ āĻ•āĻžāĻ¸ā§āϟāĻŽ āχāϭ⧇āĻ¨ā§āϟ āϏāĻŋāĻ¸ā§āĻŸā§‡āĻŽ āĻĒā§āϰāĻĻāĻžāύ āĻ•āϰ⧇āĨ¤ āĻ…āĻ­āĻŋāĻ­āĻžāĻŦāĻ• āϚāĻžāχāĻ˛ā§āĻĄāϰ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āχāĻ¨ā§āϏāĻŸā§āϝāĻžāĻ¨ā§āϏ⧇ v-on āĻŦāĻž @ āĻĻāĻŋāϝāĻŧ⧇ āϝ⧇āϕ⧋āύ⧋ āχāϭ⧇āĻ¨ā§āϟ āĻļā§‹āύāĻžāϰ āϜāĻ¨ā§āϝ āĻŦ⧇āϛ⧇ āύāĻŋāϤ⧇ āĻĒāĻžāϰ⧇āύ, āĻ āĻŋāĻ• āϝ⧇āĻŽāύāϟāĻŋ āφāĻŽāϰāĻž āĻāĻ•āϟāĻŋ āύ⧇āϟāĻŋāĻ­ DOM āχāϭ⧇āĻ¨ā§āĻŸā§‡ āĻ•āϰāĻŦ:

template
<BlogPost
  ...
  @enlarge-text="postFontSize += 0.1"
 />

āϤāĻžāϰāĻĒāϰ āϚāĻžāχāĻ˛ā§āĻĄ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻŦāĻŋāĻ˛ā§āϟ-āχāύ $emit āĻĒāĻĻā§āϧāϤāĻŋ āĻ•āϞ āĻ•āϰ⧇ āχāϭ⧇āĻ¨ā§āĻŸā§‡āϰ āύāĻžāĻŽ āĻĒāĻžāϏ āĻ•āϰ⧇ āύāĻŋāĻœā§‡āχ āĻāĻ•āϟāĻŋ āχāϭ⧇āĻ¨ā§āϟ āύāĻŋāĻ°ā§āĻ—āϤ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇:

BlogPost.vue
vue
<!-- omitting <script> -->
<template>
  <div class="blog-post">
    <h4>{{ title }}</h4>
    <button @click="$emit('enlarge-text')">Enlarge text</button>
  </div>
</template>

@enlarge-text="postFontSize += 0.1" āĻļā§āϰ⧋āϤāĻžāϕ⧇ āϧāĻ¨ā§āϝāĻŦāĻžāĻĻ, āĻ…āĻ­āĻŋāĻ­āĻžāĻŦāĻ• āχāϭ⧇āĻ¨ā§āϟāϟāĻŋ āĻĒāĻžāĻŦ⧇āύ āĻāĻŦāĻ‚ postFontSize-āĻāϰ āĻŽāĻžāύ āφāĻĒāĻĄā§‡āϟ āĻ•āϰāĻŦ⧇āύāĨ¤

āφāĻŽāϰāĻž āϐāĻšā§āĻ›āĻŋāĻ•āĻ­āĻžāĻŦ⧇ emits āĻŦāĻŋāĻ•āĻ˛ā§āĻĒ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āύāĻŋāĻ°ā§āĻ—āϤ āχāϭ⧇āĻ¨ā§āϟ āĻ˜ā§‹āώāĻŖāĻž āĻ•āϰāϤ⧇ āĻĒāĻžāϰāĻŋ defineEmits āĻŽā§āϝāĻžāĻ•ā§āϰ⧋:

BlogPost.vue
vue
<script>
export default {
  props: ['title'],
  emits: ['enlarge-text']
}
</script>
BlogPost.vue
vue
<script setup>
defineProps(['title'])
defineEmits(['enlarge-text'])
</script>

āĻāϟāĻŋ āϏāĻŽāĻ¸ā§āϤ āχāϭ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϕ⧇ āύāĻĨāĻŋāϭ⧁āĻ•ā§āϤ āĻ•āϰ⧇ āϝāĻž āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āύāĻŋāĻ°ā§āĻ—āϤ āĻ•āϰ⧇ āĻāĻŦāĻ‚ āϐāĻšā§āĻ›āĻŋāĻ•āĻ­āĻžāĻŦ⧇ āϤāĻžāĻĻ⧇āϰ āϝāĻžāϚāĻžāχ āĻ•āϰ⧇āĨ¤ āĻāϟāĻŋ Vue-āϕ⧇ āϚāĻžāχāĻ˛ā§āĻĄ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻŽā§‚āϞ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āύ⧇āϟāĻŋāĻ­ āĻļā§āϰ⧋āϤāĻž āĻšāĻŋāϏāĻžāĻŦ⧇ āĻĒā§āϰāϝāĻŧā§‹āĻ— āĻ•āϰāĻž āĻāĻĄāĻŧāĻžāϤ⧇āĻ“ āĻ…āύ⧁āĻŽāϤāĻŋ āĻĻ⧇āϝāĻŧāĨ¤

defineProps āĻāϰ āĻŽāϤ⧋, defineEmits āĻļ⧁āϧ⧁āĻŽāĻžāĻ¤ā§āϰ <script setup>-āĻ āĻŦā§āϝāĻŦāĻšāĻžāϰāϝ⧋āĻ—ā§āϝ āĻāĻŦāĻ‚ āφāĻŽāĻĻāĻžāύāĻŋ āĻ•āϰāĻžāϰ āĻĒā§āϰāϝāĻŧā§‹āϜāύ āύ⧇āχāĨ¤ āĻāϟāĻŋ āĻāĻ•āϟāĻŋ emit āĻĢāĻžāĻ‚āĻļāύ āĻĒā§āϰāĻĻāĻžāύ āĻ•āϰ⧇ āϝāĻž $emit āĻĒāĻĻā§āϧāϤāĻŋāϰ āϏāĻŽāϤ⧁āĻ˛ā§āϝāĨ¤ āĻāϟāĻŋ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ <script setup> āĻŦāĻŋāĻ­āĻžāϗ⧇ āχāϭ⧇āĻ¨ā§āϟ āύāĻŋāĻ°ā§āĻ—āϤ āĻ•āϰāϤ⧇ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻž āϝ⧇āϤ⧇ āĻĒāĻžāϰ⧇, āϝ⧇āĻ–āĻžāύ⧇ $emit āϏāϰāĻžāϏāϰāĻŋ āĻ…ā§āϝāĻžāĻ•ā§āϏ⧇āϏāϝ⧋āĻ—ā§āϝ āύāϝāĻŧ:

vue
<script setup>
const emit = defineEmits(['enlarge-text'])

emit('enlarge-text')
</script>

See also: Typing Component Emits

āφāĻĒāύāĻŋ āϝāĻĻāĻŋ <script setup> āĻŦā§āϝāĻŦāĻšāĻžāϰ āύāĻž āĻ•āϰ⧇āύ, āϤāĻžāĻšāϞ⧇ āφāĻĒāύāĻŋ emits āĻŦāĻŋāĻ•āĻ˛ā§āĻĒ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āύāĻŋāĻ°ā§āĻ—āϤ āχāϭ⧇āĻ¨ā§āϟ āĻ˜ā§‹āώāĻŖāĻž āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύāĨ¤ āφāĻĒāύāĻŋ āϏ⧇āϟāφāĻĒ āĻĒā§āϰāϏāĻ™ā§āϗ⧇āϰ āĻāĻ•āϟāĻŋ āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ āĻšāĻŋāϏāĻžāĻŦ⧇ emits āĻĢāĻžāĻ‚āĻļāύāϟāĻŋ āĻ…ā§āϝāĻžāĻ•ā§āϏ⧇āϏ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύ (āĻĻā§āĻŦāĻŋāϤ⧀āϝāĻŧ āφāĻ°ā§āϗ⧁āĻŽā§‡āĻ¨ā§āϟ āĻšāĻŋāϏāĻžāĻŦ⧇ setup() āĻ āĻĒāĻžāϏ āĻ•āϰāĻž āĻšāϝāĻŧ⧇āϛ⧇):

js
export default {
  emits: ['enlarge-text'],
  setup(props, ctx) {
    ctx.emit('enlarge-text')
  }
}

āĻ•āĻžāĻ¸ā§āϟāĻŽ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āχāϭ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋ āϏāĻŽā§āĻĒāĻ°ā§āϕ⧇ āφāĻĒāύāĻžāϰ āφāĻĒāĻžāϤāϤ āĻāϤāϟ⧁āϕ⧁āχ āϜāĻžāύāĻž āĻĻāϰāĻ•āĻžāϰ, āĻ•āĻŋāĻ¨ā§āϤ⧁ āĻāĻ•āĻŦāĻžāϰ āφāĻĒāύāĻŋ āĻāχ āĻĒ⧃āĻˇā§āĻ āĻžāϟāĻŋ āĻĒāĻĄāĻŧāĻž āĻļ⧇āώ āĻ•āϰ⧇ āĻāĻŦāĻ‚ āĻāϰ āϏāĻžāĻŽāĻ—ā§āϰ⧀āϰ āϏāĻžāĻĨ⧇ āĻ¸ā§āĻŦāĻžāĻšā§āĻ›āĻ¨ā§āĻĻā§āϝ āĻŦā§‹āϧ āĻ•āϰāϞ⧇, āφāĻŽāϰāĻž āϏāĻŽā§āĻĒā§‚āĻ°ā§āĻŖ āύāĻŋāĻ°ā§āĻĻ⧇āĻļāĻŋāĻ•āĻžāϟāĻŋ Custom Events āĻĒāĻĄāĻŧāĻžāϰ āϜāĻ¨ā§āϝ āĻĒāϰ⧇ āĻĢāĻŋāϰ⧇ āφāϏāĻžāϰ āĻĒāϰāĻžāĻŽāĻ°ā§āĻļ āĻĻāĻŋāχāĨ¤

Content Distribution with Slots ​

āĻ āĻŋāĻ• HTML āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āĻŽāϤ⧋, āĻāϟāĻŋ āĻĒā§āϰāĻžāϝāĻŧāĻļāχ āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡ āϏāĻžāĻŽāĻ—ā§āϰ⧀ āĻĒā§āϰ⧇āϰāĻŖ āĻ•āϰāϤ⧇ āϏāĻ•ā§āώāĻŽ āĻšāĻ“āϝāĻŧāĻž āĻĻāϰāĻ•āĻžāϰ⧀, āϝ⧇āĻŽāύ:

template
<AlertBox>
  Something bad happened.
</AlertBox>

āϝāĻž āĻ•āĻŋāϛ⧁ āϰ⧇āĻ¨ā§āĻĄāĻžāϰ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇:

āĻāϟāĻŋ āĻĄā§‡āĻŽā§‹ āωāĻĻā§āĻĻ⧇āĻļā§āϝ⧇āϰ āϜāĻ¨ā§āϝ āĻāĻ•āϟāĻŋ āĻ¤ā§āϰ⧁āϟāĻŋ

āĻ–āĻžāϰāĻžāĻĒ āĻ•āĻŋāϛ⧁ āϘāĻŸā§‡āϛ⧇.

āĻāϟāĻŋ Vue āĻāϰ āĻ•āĻžāĻ¸ā§āϟāĻŽ <slot> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇ āĻ…āĻ°ā§āϜāύ āĻ•āϰāĻž āϝ⧇āϤ⧇ āĻĒāĻžāϰ⧇:

AlertBox.vue
vue
<template>
  <div class="alert-box">
    <strong>This is an Error for Demo Purposes</strong>
    <slot />
  </div>
</template>

<style scoped>
.alert-box {
  /* ... */
}
</style>

āφāĻĒāύāĻŋ āωāĻĒāϰ⧇ āĻĻ⧇āĻ–āϤ⧇ āĻĒāĻžāĻŦ⧇āύ, āφāĻŽāϰāĻž <slot> āĻāĻ•āϟāĻŋ āĻ¸ā§āĻĨāĻžāύāϧāĻžāϰāĻ• āĻšāĻŋāϏāĻžāĻŦ⧇ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻŋ āϝ⧇āĻ–āĻžāύ⧇ āφāĻŽāϰāĻž āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟāϟāĻŋ āϝ⧇āϤ⧇ āϚāĻžāχ - āĻāĻŦāĻ‚ āĻāϟāĻžāχāĨ¤ āϏāĻŽā§āĻĒāĻ¨ā§āύ āĻ•āϰāĻž āĻšāϝāĻŧ⧇āϛ⧇!

āφāĻĒāĻžāϤāϤ āĻ¸ā§āϞāϟ āϏāĻŽā§āĻĒāĻ°ā§āϕ⧇ āφāĻĒāύāĻžāϰ āĻāϤāϟ⧁āϕ⧁āχ āϜāĻžāύāĻž āĻĻāϰāĻ•āĻžāϰ, āĻ•āĻŋāĻ¨ā§āϤ⧁ āĻāĻ•āĻŦāĻžāϰ āφāĻĒāύāĻŋ āĻāχ āĻĒ⧃āĻˇā§āĻ āĻžāϟāĻŋ āĻĒāĻĄāĻŧāĻž āĻļ⧇āώ āĻ•āϰ⧇ āĻāĻŦāĻ‚ āĻāϰ āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟāϤ⧇ āĻ¸ā§āĻŦāĻžāĻšā§āĻ›āĻ¨ā§āĻĻā§āϝ āĻŦā§‹āϧ āĻ•āϰāϞ⧇, āφāĻŽāϰāĻž Slots āĻāϰ āϏāĻŽā§āĻĒā§‚āĻ°ā§āĻŖ āύāĻŋāĻ°ā§āĻĻ⧇āĻļāĻŋāĻ•āĻž āĻĒāĻĄāĻŧāϤ⧇ āĻĒāϰ⧇ āĻĢāĻŋāϰ⧇ āφāϏāĻžāϰ āĻĒāϰāĻžāĻŽāĻ°ā§āĻļ āĻĻāĻŋāχāĨ¤

Dynamic Components ​

āĻ•āĻ–āύāĻ“ āĻ•āĻ–āύāĻ“, āĻŸā§āϝāĻžāĻŦāϝ⧁āĻ•ā§āϤ āχāĻ¨ā§āϟāĻžāϰāĻĢ⧇āϏ⧇āϰ āĻŽāϤ⧋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āĻŽāĻ§ā§āϝ⧇ āĻ—āϤāĻŋāĻļā§€āϞāĻ­āĻžāĻŦ⧇ āĻ¸ā§āϝ⧁āχāϚ āĻ•āϰāĻž āĻĻāϰāĻ•āĻžāϰ⧀:

āωāĻĒāϰ⧇āϰāϟāĻŋ Vue āĻāϰ <component> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻĻā§āĻŦāĻžāϰāĻž āĻŦāĻŋāĻļ⧇āώ is āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ⧇āϰ āĻĻā§āĻŦāĻžāϰāĻž āϏāĻŽā§āĻ­āĻŦ āĻšāϝāĻŧ⧇āϛ⧇:

template
<!-- Component changes when currentTab changes -->
<component :is="currentTab"></component>
template
<!-- Component changes when currentTab changes -->
<component :is="tabs[currentTab]"></component>

āωāĻĒāϰ⧇āϰ āωāĻĻāĻžāĻšāϰāϪ⧇, :is-āĻ āĻĒāĻžāϏ āĻ•āϰāĻž āĻŽāĻžāύāϟāĻŋāϤ⧇ āϝ⧇ āϕ⧋āύ⧋ āĻāĻ•āϟāĻŋ āĻĨāĻžāĻ•āϤ⧇ āĻĒāĻžāϰ⧇:

  • āĻāĻ•āϟāĻŋ āύāĻŋāĻŦāĻ¨ā§āϧāĻŋāϤ component āύāĻžāĻŽ āĻ¸ā§āĻŸā§āϰāĻŋāĻ‚, āĻŦāĻž
  • imported āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻ…āĻŦāĻœā§‡āĻ•ā§āϟ

āφāĻĒāύāĻŋ āύāĻŋāϝāĻŧāĻŽāĻŋāϤ HTML āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āϤ⧈āϰāĻŋ āĻ•āϰāϤ⧇ is āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āĻĒāĻžāϰ⧇āύāĨ¤

<component :is="..."> āĻĻāĻŋāϝāĻŧ⧇ āĻāĻ•āĻžāϧāĻŋāĻ• āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻŽāĻ§ā§āϝ⧇ āĻ¸ā§āϝ⧁āχāϚ āĻ•āϰāĻžāϰ āϏāĻŽāϝāĻŧ, āĻāĻ•āϟāĻŋ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āφāύāĻŽāĻžāωāĻ¨ā§āϟ āĻ•āϰāĻž āĻšāĻŦ⧇ āϝāĻ–āύ āĻāϟāĻŋ āĻĨ⧇āϕ⧇ āϏ⧁āχāϚ āĻ•āϰāĻž āĻšāĻŦ⧇āĨ¤ āφāĻŽāϰāĻž āĻŦāĻŋāĻ˛ā§āϟ-āχāύ <KeepAlive> āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻĻāĻŋāϝāĻŧ⧇ āύāĻŋāĻˇā§āĻ•ā§āϰāĻŋāϝāĻŧ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϕ⧇ "āĻœā§€āĻŦāĻŋāϤ" āĻĨāĻžāĻ•āϤ⧇ āĻŦāĻžāĻ§ā§āϝ āĻ•āϰāϤ⧇ āĻĒāĻžāϰāĻŋāĨ¤

in-DOM Template Parsing Caveats ​

āφāĻĒāύāĻŋ āϝāĻĻāĻŋ āϏāϰāĻžāϏāϰāĻŋ DOM-āĻ āφāĻĒāύāĻžāϰ Vue āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āϞāĻŋāĻ–āϛ⧇āύ, Vue-āϕ⧇ DOM āĻĨ⧇āϕ⧇ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āĻ¸ā§āĻŸā§āϰāĻŋāĻ‚ āĻĒ⧁āύāϰ⧁āĻĻā§āϧāĻžāϰ āĻ•āϰāϤ⧇ āĻšāĻŦ⧇āĨ¤ āĻāϟāĻŋ āĻŦā§āϰāĻžāωāϜāĻžāϰ⧇āϰ āύ⧇āϟāĻŋāĻ­ HTML āĻĒāĻžāĻ°ā§āϏāĻŋāĻ‚ āφāϚāϰāϪ⧇āϰ āĻ•āĻžāϰāϪ⧇ āĻ•āĻŋāϛ⧁ āϏāϤāĻ°ā§āĻ•āϤāĻžāϰ āĻĻāĻŋāϕ⧇ āύāĻŋāϝāĻŧ⧇ āϝāĻžāϝāĻŧāĨ¤

TIP

āĻāϟāĻŋ āϞāĻ•ā§āώ āĻ•āϰāĻž āωāϚāĻŋāϤ āϝ⧇ āύ⧀āĻšā§‡ āφāϞ⧋āϚāύāĻž āĻ•āϰāĻž āϏ⧀āĻŽāĻžāĻŦāĻĻā§āϧāϤāĻžāϗ⧁āϞāĻŋ āĻļ⧁āϧ⧁āĻŽāĻžāĻ¤ā§āϰ āϤāĻ–āύāχ āĻĒā§āϰāϝ⧋āĻœā§āϝ āĻšāĻŦ⧇ āϝāĻĻāĻŋ āφāĻĒāύāĻŋ āϏāϰāĻžāϏāϰāĻŋ DOM-āĻ āφāĻĒāύāĻžāϰ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟāϗ⧁āϞāĻŋ āϞāĻŋāĻ–āϛ⧇āύ⧎ āφāĻĒāύāĻŋ āϝāĻĻāĻŋ āύāĻŋāĻŽā§āύāϞāĻŋāĻ–āĻŋāϤ āωāĻ¤ā§āϏ āĻĨ⧇āϕ⧇ āĻ¸ā§āĻŸā§āϰāĻŋāĻ‚ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰ⧇āύ āϤāĻŦ⧇ āϏ⧇āϗ⧁āϞāĻŋ āĻĒā§āϰāϝ⧋āĻœā§āϝ āĻšāĻŦ⧇ āύāĻž:

  • āĻāĻ•āĻ• āĻĢāĻžāχāϞ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ
  • āχāύāϞāĻžāχāύāĻĄ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āĻ¸ā§āĻŸā§āϰāĻŋāĻ‚ (e.g. template: '...')
  • <script type="text/x-template">

Case Insensitivity ​

HTML āĻŸā§āϝāĻžāĻ— āĻāĻŦāĻ‚ āĻ…ā§āϝāĻžāĻŸā§āϰāĻŋāĻŦāĻŋāωāĻŸā§‡āϰ āύāĻžāĻŽāϗ⧁āϞāĻŋ āĻ…āĻ•ā§āώāϰ-āϏāĻ‚āĻŦ⧇āĻĻāύāĻļā§€āϞ, āϤāĻžāχ āĻŦā§āϰāĻžāωāϜāĻžāϰāϗ⧁āϞāĻŋ āĻŦāĻĄāĻŧ āĻšāĻžāϤ⧇āϰ āĻ…āĻ•ā§āώāϰāϗ⧁āϞāĻŋāϕ⧇ āϛ⧋āϟ āĻšāĻžāϤ⧇āϰ āĻ…āĻ•ā§āώāϰ āĻšāĻŋāϏāĻžāĻŦ⧇ āĻŦā§āϝāĻžāĻ–ā§āϝāĻž āĻ•āϰāĻŦ⧇āĨ¤ āĻāϰ āĻŽāĻžāύ⧇ āĻšāϞ āφāĻĒāύāĻŋ āϝāĻ–āύ āχāύ-āĻĄā§‹āĻŽ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟāϗ⧁āϞāĻŋ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϛ⧇āύ, āϤāĻ–āύ PascalCase āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āύāĻžāĻŽ āĻāĻŦāĻ‚ āĻ•ā§āϝāĻžāĻŽā§‡āϞāϕ⧇āϏāĻĄ āĻĒā§āϰāĻĒ āύāĻžāĻŽ āĻŦāĻž v-on āχāϭ⧇āĻ¨ā§āĻŸā§‡āϰ āύāĻžāĻŽāϗ⧁āϞāĻŋāϕ⧇ āϤāĻžāĻĻ⧇āϰ āĻ•āĻžāĻŦāĻžāĻŦ-āϕ⧇āϏāĻĄ (āĻšāĻžāχāĻĢ⧇āύ-āĻĄāĻŋāϞāĻŋāĻŽāĻŋāĻŸā§‡āĻĄ) āϏāĻŽāϤ⧁āĻ˛ā§āϝ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āĻšāĻŦ⧇:

js
// camelCase in JavaScript
const BlogPost = {
  props: ['postTitle'],
  emits: ['updatePost'],
  template: `
    <h3>{{ postTitle }}</h3>
  `
}
template
<!-- kebab-case in HTML -->
<blog-post post-title="hello!" @update-post="onUpdatePost"></blog-post>

Self Closing Tags ​

āφāĻŽāϰāĻž āĻĒā§‚āĻ°ā§āĻŦāĻŦāĻ°ā§āϤ⧀ āϕ⧋āĻĄ āύāĻŽā§āύāĻžāϗ⧁āϞāĻŋāϤ⧇ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āϜāĻ¨ā§āϝ āĻ¸ā§āĻŦ-āĻ•ā§āϞ⧋āϜāĻŋāĻ‚ āĻŸā§āϝāĻžāĻ— āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻ›āĻŋ:

template
<MyComponent />

āĻāϰ āĻ•āĻžāϰāĻŖ āĻšāϞ Vue-āĻāϰ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āĻĒāĻžāĻ°ā§āϏāĻžāϰ />āϕ⧇ āϝ⧇ āϕ⧋āύ⧋ āĻŸā§āϝāĻžāĻ— āĻļ⧇āώ āĻ•āϰāĻžāϰ āχāĻ™ā§āĻ—āĻŋāϤ āĻšāĻŋāϏ⧇āĻŦ⧇ āϏāĻŽā§āĻŽāĻžāύ āĻ•āϰ⧇, āϤāĻžāϰ āϧāϰāύ āύāĻŋāĻ°ā§āĻŦāĻŋāĻļ⧇āώ⧇āĨ¤

āχāύ-āĻĄā§‹āĻŽ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟāϗ⧁āϞāĻŋāϤ⧇, āϤāĻŦ⧇, āφāĻŽāĻžāĻĻ⧇āϰ āĻ…āĻŦāĻļā§āϝāχ āϏāĻ°ā§āĻŦāĻĻāĻž āĻ¸ā§āĻĒāĻˇā§āϟ āĻ•ā§āϞ⧋āϜāĻŋāĻ‚ āĻŸā§āϝāĻžāĻ— āĻ…āĻ¨ā§āϤāĻ°ā§āϭ⧁āĻ•ā§āϤ āĻ•āϰāϤ⧇ āĻšāĻŦ⧇:

template
<my-component></my-component>

āĻāϰ āĻ•āĻžāϰāĻŖ āĻšāϞ HTML āĻ¸ā§āĻĒ⧇āĻ• āĻļ⧁āϧ⧁āĻŽāĻžāĻ¤ā§āϰ āĻ•āĻŋāϛ⧁ āύāĻŋāĻ°ā§āĻĻāĻŋāĻˇā§āϟ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻ•ā§āϞ⧋āϜāĻŋāĻ‚ āĻŸā§āϝāĻžāĻ—āϗ⧁āϞāĻŋāϕ⧇ āĻŦāĻžāĻĻ āĻĻ⧇āĻ“āϝāĻŧāĻžāϰ āĻ…āύ⧁āĻŽāϤāĻŋ āĻĻ⧇āϝāĻŧ, āϏāĻŦāĻšā§‡āϝāĻŧ⧇ āϏāĻžāϧāĻžāϰāĻŖ āĻšāϞ <input> āĻāĻŦāĻ‚ <img>āĨ¤ āĻ…āĻ¨ā§āϝ āϏāĻŦ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āϜāĻ¨ā§āϝ, āφāĻĒāύāĻŋ āϝāĻĻāĻŋ āĻ•ā§āϞ⧋āϜāĻŋāĻ‚ āĻŸā§āϝāĻžāĻ—āϟāĻŋ āĻŦāĻžāĻĻ āĻĻ⧇āύ, āϤāĻžāĻšāϞ⧇ āύ⧇āϟāĻŋāĻ­ HTML āĻĒāĻžāĻ°ā§āϏāĻžāϰ āĻŽāύ⧇ āĻ•āϰāĻŦ⧇ āφāĻĒāύāĻŋ āĻ•āĻ–āύāχ āĻ“āĻĒ⧇āύāĻŋāĻ‚ āĻŸā§āϝāĻžāĻ—āϟāĻŋ āĻŦāĻ¨ā§āϧ āĻ•āϰ⧇āύāύāĻŋāĨ¤ āωāĻĻāĻžāĻšāϰāĻŖāĻ¸ā§āĻŦāϰ⧂āĻĒ, āύāĻŋāĻŽā§āύāϞāĻŋāĻ–āĻŋāϤ āĻ¸ā§āύāĻŋāĻĒ⧇āϟ:

template
<my-component /> <!-- we intend to close the tag here... -->
<span>hello</span>

will be parsed as:

template
<my-component>
  <span>hello</span>
</my-component> <!-- but the browser will close it here. -->

Element Placement Restrictions ​

āĻ•āĻŋāϛ⧁ HTML āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ, āϝ⧇āĻŽāύ <ul>, <ol>, <table> āĻāĻŦāĻ‚ <select>-āĻāϰ āĻŽāĻ§ā§āϝ⧇ āϕ⧀ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āωāĻĒāĻ¸ā§āĻĨāĻŋāϤ āĻšāϤ⧇ āĻĒāĻžāϰ⧇ āϤāĻžāϰ āωāĻĒāϰ āϏ⧀āĻŽāĻžāĻŦāĻĻā§āϧāϤāĻž āϰāϝāĻŧ⧇āϛ⧇ āĻāĻŦāĻ‚ āĻ•āĻŋāϛ⧁ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āϝ⧇āĻŽāύ <li>, <tr>, āĻāĻŦāĻ‚ <option> āĻļ⧁āϧ⧁āĻŽāĻžāĻ¤ā§āϰ āĻ•āĻŋāϛ⧁ āĻ…āĻ¨ā§āϝāĻžāĻ¨ā§āϝ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āĻŸā§‡āϰ āĻŽāĻ§ā§āϝ⧇ āωāĻĒāĻ¸ā§āĻĨāĻŋāϤ āĻšāϤ⧇ āĻĒāĻžāϰ⧇āĨ¤

āĻāχ āϧāϰāύ⧇āϰ āĻŦāĻŋāϧāĻŋāύāĻŋāώ⧇āϧ āφāϛ⧇ āĻāĻŽāύ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϰ āϏāĻžāĻĨ⧇ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻžāϰ āϏāĻŽāϝāĻŧ āĻāϟāĻŋ āϏāĻŽāĻ¸ā§āϝāĻžāϰ āĻĻāĻŋāϕ⧇ āĻĒāϰāĻŋāϚāĻžāϞāĻŋāϤ āĻ•āϰāĻŦ⧇āĨ¤ āωāĻĻāĻžāĻšāϰāĻŖ āĻ¸ā§āĻŦāϰ⧂āĻĒ:

template
<table>
  <blog-post-row></blog-post-row>
</table>

āĻ•āĻžāĻ¸ā§āϟāĻŽ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ <blog-post-row> āĻ…āĻŦ⧈āϧ āĻŦāĻŋāώāϝāĻŧāĻ…āĻŦāĻœā§‡āĻ•ā§āϟ āĻšāĻŋāϏāĻžāĻŦ⧇ āωāĻ¤ā§āϤ⧋āϞāύ āĻ•āϰāĻž āĻšāĻŦ⧇, āϝāĻžāϰ āĻĢāϞ⧇ āĻšā§‚āĻĄāĻŧāĻžāĻ¨ā§āϤ āϰ⧇āĻ¨ā§āĻĄāĻžāϰ āĻ•āϰāĻž āφāωāϟāĻĒ⧁āĻŸā§‡ āĻ¤ā§āϰ⧁āϟāĻŋ āĻĻ⧇āĻ–āĻž āĻĻāĻŋāĻŦ⧇āĨ¤ āφāĻŽāϰāĻž āĻāĻ•āϟāĻŋ āϏāĻŽāĻžāϧāĻžāύ āĻšāĻŋāϏāĻžāĻŦ⧇ āĻŦāĻŋāĻļ⧇āώ is āĻŦ⧈āĻļāĻŋāĻˇā§āĻŸā§āϝ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāϤ⧇ āĻĒāĻžāϰāĻŋ:

template
<table>
  <tr is="vue:blog-post-row"></tr>
</table>

TIP

āϝāĻ–āύ āύ⧇āϟāĻŋāĻ­ āĻāχāϚāϟāĻŋāĻāĻŽāĻāϞ āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋāϤ⧇ āĻŦā§āϝāĻŦāĻšāĻžāϰ āĻ•āϰāĻž āĻšāϝāĻŧ, āϤāĻ–āύ āĻāĻ•āϟāĻŋ Vue āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟ āĻšāĻŋāϏāĻžāĻŦ⧇ āĻŦā§āϝāĻžāĻ–ā§āϝāĻž āĻ•āϰāĻžāϰ āϜāĻ¨ā§āϝ is āĻāϰ āĻŽāĻžāύ āĻ…āĻŦāĻļā§āϝāχ vue: āĻāϰ āϏāĻžāĻĨ⧇ āĻĒā§āϰāĻŋāĻĢāĻŋāĻ•ā§āϏ āĻ•āϰāĻž āωāϚāĻŋāϤāĨ¤ āĻ¸ā§āĻĨāĻžāύ⧀āϝāĻŧ āĻ•āĻžāĻ¸ā§āϟāĻŽāĻžāχāϜāĻĄ āĻŦāĻŋāĻ˛ā§āϟ-āχāύ elements āύāĻŋāϝāĻŧ⧇ āĻŦāĻŋāĻ­ā§āϰāĻžāĻ¨ā§āϤāĻŋ āĻāĻĄāĻŧāĻžāϤ⧇ āĻāϟāĻŋ āĻĒā§āϰāϝāĻŧā§‹āϜāύāĨ¤

āĻāĻ–āύāĻ•āĻžāϰ āϜāĻ¨ā§āϝ āχāύ-āĻĄā§‹āĻŽ āĻŸā§‡āĻŽāĻĒā§āϞ⧇āϟ āĻĒāĻžāĻ°ā§āϏāĻŋāĻ‚ āϏāϤāĻ°ā§āĻ•āϤāĻž āϏāĻŽā§āĻĒāĻ°ā§āϕ⧇ āφāĻĒāύāĻžāϰ āĻāϤāϟ⧁āϕ⧁āχ āϜāĻžāύāĻž āĻĻāϰāĻ•āĻžāϰ - āĻāĻŦāĻ‚ āφāϏāϞ⧇, Vue āĻāϰ Essentials āĻāϰ āĻļ⧇āώāĨ¤ āĻ…āĻ­āĻŋāύāĻ¨ā§āĻĻāύ! āĻļ⧇āĻ–āĻžāϰ āϜāĻ¨ā§āϝ āĻāĻ–āύāĻ“ āφāϰāĻ“ āĻ…āύ⧇āĻ• āĻ•āĻŋāϛ⧁ āφāϛ⧇, āĻ•āĻŋāĻ¨ā§āϤ⧁ āĻĒā§āϰāĻĨāĻŽā§‡, āφāĻŽāϰāĻž Vue āĻāϰ āϏāĻžāĻĨ⧇ āĻ…āύ⧁āĻļā§€āϞāύ āĻ•āϰāĻž āϜāĻ¨ā§āϝ āĻŦāĻŋāϰāϤāĻŋ āύ⧇āĻ“āϝāĻŧāĻžāϰ āĻĒāϰāĻžāĻŽāĻ°ā§āĻļ āĻĻāĻŋāχ - āĻŽāϜāĻžāĻĻāĻžāϰ āĻ•āĻŋāϛ⧁ āϤ⧈āϰāĻŋ āĻ•āϰ⧁āύ, āĻ…āĻĨāĻŦāĻž āφāĻĒāύāĻŋ āϝāĻĻāĻŋ āχāϤāĻŋāĻŽāĻ§ā§āϝ⧇ āύāĻž āĻ•āϰ⧇ āĻĨāĻžāϕ⧇āύ āϤāĻŦ⧇ āĻ•āĻŋāϛ⧁ Examples āĻĻ⧇āϖ⧁āύāĨ¤

āĻāĻ•āĻŦāĻžāϰ āφāĻĒāύāĻŋ āϝ⧇ āĻœā§āĻžāĻžāύāϟāĻŋ āĻšāϜāĻŽ āĻ•āϰ⧇āϛ⧇āύ āϤāĻžāϤ⧇ āĻ¸ā§āĻŦāĻžāĻšā§āĻ›āĻ¨ā§āĻĻā§āϝ āĻŦā§‹āϧ āĻ•āϰāϞ⧇, āĻ•āĻŽā§āĻĒā§‹āύ⧇āĻ¨ā§āϟāϗ⧁āϞāĻŋ āϏāĻŽā§āĻĒāĻ°ā§āϕ⧇ āĻ—āĻ­ā§€āϰāĻ­āĻžāĻŦ⧇ āφāϰāĻ“ āϜāĻžāύāϤ⧇ āĻ—āĻžāχāĻĄā§‡āϰ āϏāĻžāĻĨ⧇ āĻāĻ—āĻŋāϝāĻŧ⧇ āϝāĻžāύāĨ¤

Components Basics has loaded