2‐2 元件之間的溝通傳遞 - daniel-qa/Vue GitHub Wiki

2-2 元件之間的溝通傳遞

p.s 這裡的外層,指的是一開始 Vue.createApp() 的資料

p.s 跟 function 傳參數的方式類似

前面一個小節我們快速介紹了 Vue.js 元件系統的特性,以及元件內部的基本結構。 那麼在這個小節中,我們繼續對元件與元件之間各種傳遞資料的方式來做說明。

props

前面我們提到,Vue.js 每個元件的實體狀態、模板等作用範圍都應該要是獨立的, 這意味著我們不能(也不應該)在子元件的模組「直接」去修改父元件,甚至是另一個元件的資料

這樣除了元件因為耦合程度過高維護不易,也可能產生難以追蹤的錯誤。

  • 複利用這個元件: 我們希望這個元件可以根據「外部」傳入的資料來反映出不同的結果

因為不能直接取用,那麼上下層元件之間,要從外部引進資料,就需要透過 props 屬性來引用外部的狀態

使用方式很簡單,我們只要在自訂的子元件上使用上一章介紹過的 v-bind 指令:

<div id="app">
  <!-- 這是外層元件的msg -->
  <h3>{{ msg }}</h3>
  <!-- 這裡的 v-bind: parent-msg 可以簡寫為:parent-msg
  <my-component v-bind: parent-msg="msg"></my-component>
</div>
const app = Vue.createApp({
  data () {
    return {
      msg:"這是外層元件的msg"
}
  }
});

app.component('my-component', {
  template:
  <div class="component"> 
    <div> 從 props 來的 parentMsg ==> {{ parentMsg }} </div>
    <div> 自己的 msg ==> {{ msg }} </div>
  </div>",
  props: ["parentMsg"],
  data () {
    return {
      msg:'這是子元件的msg'
  }
 }
});

app.mount('#app');

像這樣,我們可以在內層元件內透過 props 屬性宣告要從「外部」引用進來的屬性名稱, 並且在外層模板使用內層元件標籤時,以 v-bind 指令來將資料傳遞進來。

另外,這裡要特別注意的是, props 與子元件命名的情況一樣,若我們是以 HTML 作為模板的時候,因為 HTML 不分大小寫的關係,像 parentMsg 這樣的駝峰式寫法,在模板裡要轉換成連字號 (kebab-case) parent-msg 來使用。

在內層元件 (或稱子元件) 宣告 props 屬性,最簡單的方式就是透過「陣列」的型態,

app.component('my-component', {
  props: ['props1', 'props2', 'props3', ...],
  //下略...
});

這樣我們就可以透過 HTML 標籤內的屬性將外層的狀態引入至對應 Props

<my-component
  :props1="..."
  :props2="..."
  :props3="..."></my-component>

替-props-指定資料格式

當然,若是我們希望允許多種不同格式的 prop ,則可以透過陣列的形式來指定:

props:{

something:{
  type: [String, Number]
  }
}

以物件作為 props 傳遞

這裡有一個簡單的 Vue 組件範例,展示如何通過 props 傳遞一個物件。

首先,假設我們要建立一個名為 UserProfile 的組件,該組件會接收一個用戶資料的物件作為 prop。

UserProfile.vue

<template>
  <div class="user-profile">
    <h2>{{ user.name }}</h2>
    <p>Email: {{ user.email }}</p>
    <p>Age: {{ user.age }}</p>
  </div>
</template>

<script>
export default {
  name: 'UserProfile',
  props: {
    user: {
      type: Object,
      required: true,
    },
  },
};
</script>

<style scoped>
.user-profile {
  border: 1px solid #ccc;
  padding: 16px;
  border-radius: 8px;
}
</style>
  • 使用該組件

在父組件中,我們可以這樣使用 UserProfile 組件,並傳遞一個用戶物件:

<template>
  <div>
    <UserProfile :user="userData" />
  </div>
</template>

<script>
import UserProfile from './UserProfile.vue';

export default {
  components: {
    UserProfile,
  },
  data() {
    return {
      userData: {
        name: 'John Doe',
        email: '[email protected]',
        age: 30,
      },
    };
  },
};
</script>
⚠️ **GitHub.com Fallback** ⚠️