共计 3667 个字符,预计需要花费 10 分钟才能阅读完成。
什么是混合 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 是独立的