iT邦幫忙

2017 iT 邦幫忙鐵人賽
DAY 15
0
Modern Web

Vue.js 30天系列 第 15

Vue.js 15 - 組件/元件(Component) - 自訂事件及對外溝通

前面介紹過屬性

  • data (宣告內部狀態)
  • props (宣告對外介面 - 用於傳入資料)

這篇介紹這張圖的另外一半,用於傳出資訊的事件(event)
http://ithelp.ithome.com.tw/upload/images/20161230/20103424eUaLJoQkAN.png

Vue 1.x 的事件傳遞比較複雜

  • 監聽事件
    • $on
    • events屬性
  • 自用
    • $emit (組件內的事件)
  • 對外
    • $broadcast (父對子,向下傳遞)
    • $dispatch (子對父,向上傳遞)

事件傳遞方向自由,卻也混亂。

到了 Vue 2.x 只剩下

  • 監聽事件
    • $on
  • 對外
    • $emit (和1.x同名,但行為近似$dispatch,只對父層)

簡化後,事件觸發必定來自子組件。

這是官網一個計數器範例,前/後門來客量由兩個警衛獨立計算於各自的,大樓主任想即時計算總來客量。

<div id="counter-event-example">
  <p>總來客量: {{ total }}</p>
  <button-counter door="前門" v-on:increment="incrementTotal"></button-counter>
  <button-counter door="後門" v-on:increment="incrementTotal"></button-counter>
</div>
Vue.component('button-counter', {
  template: '<button v-on:click="increment">{{ door }}來客+1 ( {{ counter }} )</button>',
  props: ['door'],
  data: function () {
    return {
      counter: 0
    }
  },
  methods: {
    /* 來客+1 */
    increment: function () {
      this.counter += 1
      /* 通知主任,多了一人來客 */
      this.$emit('increment')
    }
  },
})
new Vue({
  el: '#counter-event-example',
  data: {
    total: 0
  },
  methods: {
    /* 主任得知來客+1,總來客量+1 */
    incrementTotal: function () {
      this.total += 1
    }
  }
})

事件就算不聽,頂多就是沒人處理罷了。
使得組件解耦合,有其獨立性,卻又維持對外溝通的彈性。

  <!-- 來客數不計算工作人員 -->
  <button-counter door="工作人員專用門"></button-counter>

以上介紹的是標準的 component 資料傳遞,非內建的傳遞方式後續再介紹(Vuex, Revue, Rxjs...etc.)


上一篇
Vue.js 14 - 組件/元件(Component) - 包裝方式及內部狀態
下一篇
Vue.js 16 - 組件/元件(Component) - 樣板宣告及動態插入內容
系列文
Vue.js 30天30

1 則留言

0
Andy Tsai
iT邦新手 5 級 ‧ 2018-10-31 18:10:13

怎麼跟 AngularJS 只有 13% 不一樣?

我要留言

立即登入留言