什么是混合 mixin
首先,谈到混合 mixin 这个词,并不是只有 vue 中才有混合的概念。其实在 css 的预处理器 less 或者 stylus 或者 scss 中也有相似的混合函数 mixin 的概念。只不过 css 预处理器中的混合是用来实现款式的复用的。而 vue 中的混合 mixin 是用来实现性能的复用的。
less 预处理器混合 mixin 的用法步骤参见我之前的文章:https://segmentfault.com/a/11…
官网是如何定义混合 mixin 的
文档是这样定义的
混入 (mixin) 提供了一种非常灵活的形式,来散发 Vue 组件中的可复用性能。一个混入对象能够蕴含任意组件选项。当组件应用混入对象时,所有混入对象的选项将被“混合”进入该组件自身的选项。
咋一看,说的不太接地气,那咱们来用大白话翻译一下吧
大白话翻译
-
混入 (mixin) 提供了一种非常灵活的形式
混入性能很叼
-
来散发 Vue 组件中的可复用性能
应用混入能够实现在.vue 组件中的重复使用的性能。想想有哪些重复使用的性能呢?比方做后盾管理系统经常须要应用的分页性能、比方我的项目中很多的中央都要应用的弹出 Message 音讯提醒性能。其实有很多,本文就以分页性能利用场景举例说明
-
一个混入对象能够蕴含任意组件选项
混合是个对象?哇,传说中的面向对象 OOP 的思维,混合更有点继承的滋味吧。混合蕴含任意组件选项?组件选项不就是 data、computed、watch、methods 以及各种生命周期钩子吗,也就是说混合中也能够像组件中那样定义这些组件选项,以供‘混入’应用
-
当组件应用混入对象时,所有混入对象的选项将被“混合”进入该组件自身的选项
在 vue 中应用一个‘货色’,个别的套路大抵都是 定义 –> 引入 –> 注册 –> 应用。既然在某个.vue 中应用混合,那么引入了当前,就相当于领有混合中的货色了。
理论应用步骤(分页组件应用混合)
先看一下最终的效果图
假如咱们的我的项目中有两个路由页面都用到了分页组件,分页个别搭配表格,为了不便简洁,这里的话,咱们就不放表格了。咱们要用 mixin 实现这样的分页成果
第一步,新建好我的项目
-
App.vue 文件搁置对应路由导航和视图构造
// App.vue 文件 <template> <div id="app"> <div class="top"> <router-link to="/"> 路由页面一 </router-link> <router-link to="/about"> 路由页面二 </router-link> </div> <div class="bottom"> <router-view></router-view> </div> </div> </template>
-
路由中这样定义一下
import Vue from 'vue' import VueRouter from 'vue-router' Vue.use(VueRouter) const router = new VueRouter({ routes: [ { path: "/", component: resolve => require(['../views/home.vue'], resolve), }, { path: "/about", component: resolve => require(['../views/about.vue'], resolve), }, ] }) export default router
-
home.vue 和 about.vue 应用饿了么 UI 的分页组件(about.vue 文件就不搁置了,构造基本上一样的)
<template> <div> <div class="block"> <span class="demonstration"> 第 11111 个分页中应用混合 </span> <el-pagination @size-change="handleSizeChange" @current-change="handleCurrentChange" :page-sizes="[10, 20, 30, 40]" :current-page="paging.pageIndex" :page-size="paging.pageSize" :total="paging.total" layout="total, sizes, prev, pager, next, jumper" background > </el-pagination> </div> </div> </template> <script> export default { name: "home", data() { return { paging: { pageIndex: 1, pageSize: 10, total: 100, }, }; }, methods: {handleSizeChange(val) { this.paging.pageIndex = 1; this.paging.pageSize = val; }, handleCurrentChange(val) {this.paging.pageIndex = val;}, }, }; </script>
这样的话,两个路由页面的分页成果都有了。只不过还没用到 mixin。这个案例中因为 home.vue 和 about.vue 文件中都有分页性能,而应用分页性能就要定义
第几页 pageIndex、每页显示几条 pageSize、总条数 total、翻页扭转的办法 handleCurrentChange、和条数扭转的办法 handleSizeChange
这些变量和办法。这些变量和办法就属于公共的复用的代码,因为可能好多中央都要用到,咱们能够把这些复用的搁置在混合文件中,哪里须要应用,哪里就混入进来即可。
第二步(定义一个 mixin 文件并裸露)
第三步(引入混合注册并应用混合)
-
首先把本来写好的 data 中的分页变量和 methods 中的分页办法删除掉
当然删掉了会报错,因为分页组件须要这些变量和办法,所以接下来咱们应用混合进来的变量和办法
-
引入混合并注册应用
<template> <div> <div class="block"> <span class="demonstration"> 第 11111 个分页中应用混合 </span> <el-pagination @size-change="handleSizeChange" @current-change="handleCurrentChange" :page-sizes="[10, 20, 30, 40]" :current-page="paging.pageIndex" :page-size="paging.pageSize" :total="paging.total" layout="total, sizes, prev, pager, next, jumper" background > </el-pagination> </div> </div> </template> <script> // 引入混合 import mixin from '../mixin/index' export default { name: "home", mixins: [mixin] // 注册即应用 }; </script>
另外一个 about.vue 文件也如法炮制即可,就能实现想要的性能了。篇幅无限不赘述
补充一(查看具体引入的混合)
其实也能够换个角度了解,就是混合是把混合文件中定义的变量办法之类的挂载到某个具体的.vue 文件上,也就是挂载到某个具体的 vue 示例上,所以咱们打印这个 vue 示例,是能够看到挂载进来的 mixin 代码的,如下:
<script>
import mixin from '../mixin/index' // 引入混合
export default {
name: "home",
mixins: [mixin], // 注册即应用
mounted() {console.log('打印 vue 示例 this,查看混合',this);// 看这里、看这里、看这里
},
};
</script>
打印后果如下:
很显然,混合中的变量和办法曾经被挂载到这个 vue 组件实例上了,既然挂载到这个示例上了,也就意味着,在 template 中的 html 代码外面能够应用了,所以应用混合确实能够使得咱们写代码变得更加优雅
补充二(mixin 代码与组件代码抵触了怎么办)
- 首先,不要反复
混合中定义的代码就不要与组件中的代码一样 - 其次,以组件中的为准
简而言之,组件中没有的,混合中有,就把混合的拿过去;组件中有的,混合中也有,就不要混 合中的,只保留组件中的
补充三(全局混入,个别不要去应用)
上述代码案例咱们应用的是部分的 mixin,其实也挺不便,哪里须要应用,就哪里去引入混合。应用全局混合尽管省去了,引入注册的这一步,然而全局混合中定义的变量和办法,在每个组件上都会挂载下来,这样的话也不太好。毕竟官网也揭示咱们,应用全局混入肯定要分外小心
总结
mixin VS vuex
应用 vuex 也能够治理状态,和混合的区别就是 vuex 中的数据一但扭转,所有的相干的依赖 vuex 中的都会扭转,然而应用 mixin,不过呈现这样的状况。毕竟 vuex 是专用的,mixin 是独立的