點燈坊

失くすものさえない今が強くなるチャンスよ

使用 Named Slot 對 Component 傳入多筆 HTML

Sam Xiao's Avatar 2024-02-21

在 Component Tag 間只能傳送一筆 HTML,若要傳遞多筆 HTML,則要透過 <template> 使用 Named Slot。

Version

Vue 3.4

Named Slot

named001

  • 三個區塊都是由 slot 傳進 component

App.vue

<template>
  <MyCounter :initialCount="count">
    <template #header>
      <h2>Hello Count</h2>
    </template>
    <template #default>
      <span class="hello-count">Count:</span>
    </template>
    <template #footer>
      <h4>Copy Right Sam</h4>
    </template>
  </MyCounter>
</template>

<script setup>
import { ref } from 'vue'
import MyCounter from '@/components/MyCounter.vue'

let count = ref(0)
</script>

<style scoped>
.hello-count {
  color: brown;
  font-weight: 700;
}
</style>

Line 3

<template #header>
  <h2>Hello Count</h2>
</template>
  • <template>:將要傳入的 HTML 由 <template> 包起來傳進 slot,為 HTML 5 的新 tag,預設不會顯示,專給 JavaScript 或 framework 自己運用,不同 framework 用法不一樣
  • #v-slot 的縮寫,後面指定 slot 名稱

Line 6

<template #default>
  <span class="hello-count">Count:</span>
</template>
  • #default:指定傳入 default slot

沒有名稱的 slot 稱為 default slot,一個 component 只能有一個 default slot

MyCounter

MyCounter.vue

<template>
  <header>
    <slot name="header"></slot>
  </header>
  <main>
    <button @click="onClick">+</button>
    <slot>Current count:</slot>
    {{ count }}
  </main>
  <footer>
    <slot name="footer"></slot>
  </footer>
</template>

<script setup>
import { ref } from 'vue'

let props = defineProps({ initialCount: Number })
let count = ref(props.initialCount)

let onClick = () => count.value++
</script>

<style scoped>
header {
  border-style: solid;
  border-color: blue;
  width: fit-content;
}

main {
  border-style: solid;
  border-color: red;
  width: fit-content;
}

footer {
  border-style: solid;
  border-color: blueviolet;
  width: fit-content;
}
</style>

Line 2

<header>
  <slot name="header"></slot>
</header>
  • <header>:HTML 5 的新 tag,定義 header 邏輯區塊,相當於可讀性的 <div>
  • name:定義 slot 名稱

Line 5

<main>
  <button @click="onClick">+</button>
  <slot>Current count:</slot>
  {{ count }}
</main>
  • <main>:HTML 5 的新 tag,定義 main 邏輯區塊,相當於可讀性的 <div>
  • <slot>:為指定 name 即為 default slot

Line 10

<footer>
  <slot name="footer"></slot>
</footer>
  • <main>:HTML 5 的新 tag,定義 footer 邏輯區塊,相當於可讀性的 <div>

Conclusion

  • 當 component 內有多段 HTML 都希望由外層提供時,可使用 Named Slot 一次傳進多段 HTML