iT邦幫忙

2021 iThome 鐵人賽

DAY 29
0
Modern Web

30 天我與 Vue 的那些二三事系列 第 29

Day 29 - 用Mixins來共用方法

相信經過了前面二十幾天的洗禮,小夥伴們應該都對Vue有了一定的掌握度了吧~
今天要來提到的是Vue的Mixins。

甚麼是Mixins?

Mixin 是一種讓元件之間彼此共用方法的方法,可以將常使用的方法獨立抽出放在mixins,避免重複出現。
使用Mixin,可以讓所有 component 的選項都可以拿來使用 (created, computed…),當 component 使用 mixin 時,mixin 本身的選項都會和 component 自己的選項混合在一起。
雖然Mixins在Vue3中被composition api取代,不過我們這裡還是繼續來看一下。
例如下面的例子中,我們定義了一個mixin物件,並在component中進行使用。

var myMixin = {
  created: function () {
    this.hello()
  },
  methods: {
    hello: function () {
      console.log('hello from mixin!')
    }
  }
}
var Component = Vue.extend({
  mixins: [myMixin]
})

var component = new Component() // => "hello from mixin!"

原始碼:
https://codepen.io/adjwcmzg/pen/WNEQOdx

選項合併 Option Merging

不過,既然是混入原本不屬於元件的方法,就有可能會與原本的元件方法產生衝突。
當元件和mixin對象含有同名選項時,這些選項將會進行合併,並在發生衝突時以元件數據優先。

如果是hook的話(Created, etc.),將會被合併成一個陣列,所以不管是元件的還是mixins的,都會被執行,不過mixins的會早於元件本身。

var mixin = {
  created: function() {
    console.log('mixin hook called');
  },
};

new Vue({
  mixins: [mixin],
  created: function() {
    console.log('component hook called');
  },
});

原始碼:
https://codepen.io/adjwcmzg/pen/jOLbwKy

不過如果是Methods, Components and Directives話,有衝突時會無條件選用元件的 option。

var mixin = {
  methods: {
    foo: function() {
      console.log('foo');
    },
    conflicting: function() {
      console.log('from mixin');
    },
  },
};

var vm = new Vue({
  mixins: [mixin],
  methods: {
    bar: function() {
      console.log('bar');
    },
    conflicting: function() {
      console.log('from self');
    },
  },
});

vm.foo();
vm.bar();
vm.conflicting();

從Console可以看出,Mixins中的"from mixins"被捨去了。

原始碼:
https://codepen.io/adjwcmzg/pen/GRvpEYR

Global Mixin

不過,看到這邊,那你一定會想,那我可以全域引用mixins物件嗎?
答案當然是肯定的,不過一旦全域引用,就會影響所有的Vue實例以及之後建立的Component,包括第三方元件喔,所以要謹慎使用。

Vue.mixin({
  created: function() {
    var myOption = this.$options.myOption;
    if (myOption) {
      console.log(myOption);
    }
  },
});

new Vue({
  myOption: 'Hello World!',
});

原始碼:
https://codepen.io/adjwcmzg/pen/WNEQOLR


Hi, I am Grant.

個人部落格 - https://grantliblog.wordpress.com/
個人網站 - https://grantli-website.netlify.app/#/mainpage
我的寫作專題 - https://vocus.cc/user/5af2e9b5fd89780001822db4#


上一篇
Day 28 - Vue 與 HTTP請求 (3)
下一篇
Day 30 - 終點亦是起點
系列文
30 天我與 Vue 的那些二三事30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言