详解Vue的mixin策略


Posted in Vue.js onNovember 19, 2020

我之前一直以为mixin的合并是以组件内的优先,即mixin的内容如果和组件内有冲突的,以组件内为准,确实存在这种情况,但是vue指定的策略更详细,下面分别记录各种情况对应的合并策略

基本

当一个组件使用mixin的时候,所有mixin的选项会被混入到组件自己的选项中, 这部分没什么好说的,直接看代码

// define a mixin object
const myMixin = {
 created() {
  this.hello()
 },
 methods: {
  hello() {
   console.log('hello from mixin!')
  }
 }
}

// define an app that uses this mixin
const app = Vue.createApp({
 mixins: [myMixin]
})

app.mount('#mixins-basic') // => "hello from mixin!"

选项的合并策略

这里的选项指的就是 data methods和生命周期钩子函数这些选项,他们的会采取不同的合并策略

像data,methods,components,directives这样的会被合并进同一个对象中,并且遇到冲突项以组件的为准

const myMixin = {
 data() {
  return {
   message: 'hello',
   foo: 'abc'
  }
 }
}

const app = Vue.createApp({
 mixins: [myMixin],
 data() {
  return {
   message: 'goodbye',
   bar: 'def'
  }
 },
 created() {
  console.log(this.$data) // => { message: "goodbye", foo: "abc", bar: "def" }
 }
})
const myMixin = {
 methods: {
  foo() {
   console.log('foo')
  },
  conflicting() {
   console.log('from mixin')
  }
 }
}

const app = Vue.createApp({
 mixins: [myMixin],
 methods: {
  bar() {
   console.log('bar')
  },
  conflicting() {
   console.log('from self')
  }
 }
})

const vm = app.mount('#mixins-basic')

vm.foo() // => "foo"
vm.bar() // => "bar"
vm.conflicting() // => "from self"

而对于钩子函数就不是简单的替换了,如果有同名的,他们会被一起合并进数组中,然后依次调用,且mixin的钩子函数会率先被调用

const myMixin = {
 created() {
  console.log('mixin hook called')
 }
}

const app = Vue.createApp({
 mixins: [myMixin],
 created() {
  console.log('component hook called')
 }
})

// => "mixin hook called"
// => "component hook called"

全局混入和自定义选项

const app = Vue.createApp({
 myOption: 'hello!'
})

// inject a handler for `myOption` custom option
app.mixin({
 created() {
  const myOption = this.$options.myOption
  if (myOption) {
   console.log(myOption)
  }
 }
})

app.mount('#mixins-global') // => "hello!"

上述代码,我们在全局创建了一个自定义选项,然后进行了全局混入处理,但是需要注意的是,这会影响到这个app所有的子组件:

const app = Vue.createApp({
 myOption: 'hello!'
})

// inject a handler for `myOption` custom option
app.mixin({
 created() {
  const myOption = this.$options.myOption
  if (myOption) {
   console.log(myOption)
  }
 }
})

// add myOption also to child component
app.component('test-component', {
 myOption: 'hello from component!'
})

app.mount('#mixins-global')

// => "hello!"
// => "hello from component!"

我们可以看到,对于自定义选项这不是简单的替换,而是分别调用,当然我们也可以制定我们自己的合并策略:

const app = Vue.createApp({})

app.config.optionMergeStrategies.customOption = (toVal, fromVal) => {
 // return mergedVal
}

合并策略接收两个参数,分别是指定项在父实例和子实例的值,当使用mixin的时候我们可以查看打印什么:

const app = Vue.createApp({
 custom: 'hello!'
})

app.config.optionMergeStrategies.custom = (toVal, fromVal) => {
 console.log(fromVal, toVal)
 // => "goodbye!", undefined
 // => "hello", "goodbye!"
 return fromVal || toVal
}

app.mixin({
 custom: 'goodbye!',
 created() {
  console.log(this.$options.custom) // => "hello!"
 }
})

可以看到第一次从mixin打印,然后从app打印。

注意事项

  • mixin很容易造成冲突,你得确保不会有冲突的属性名,来避免冲突,这会造成额外的负担
  • 复用性有限,因为mixin不能接受参数,所以逻辑是写定的,不灵活

所以官方推荐使用 Composition Api来组织逻辑

以上就是详解Vue的mixin策略的详细内容,更多关于Vue的mixin策略的资料请关注三水点靠木其它相关文章!

Vue.js 相关文章推荐
vue实现购物车的小练习
Dec 21 Vue.js
vue中watch的用法汇总
Dec 28 Vue.js
vue+element UI实现树形表格
Dec 29 Vue.js
基于Vue3.0开发轻量级手机端弹框组件V3Popup的场景分析
Dec 30 Vue.js
Vue中强制组件重新渲染的正确方法
Jan 03 Vue.js
vue+vant 上传图片需要注意的地方
Jan 03 Vue.js
Vue实现一种简单的无限循环滚动动画的示例
Jan 10 Vue.js
SSM VUE Axios详解
Oct 05 Vue.js
vue动态绑定style样式
Apr 20 Vue.js
vue 自定义组件添加原生事件
Apr 21 Vue.js
Vue OpenLayer 为地图绘制风场效果
Apr 24 Vue.js
el-table-column 内容不自动换行的解决方法
Aug 14 Vue.js
一篇超完整的Vue新手入门指导教程
Nov 18 #Vue.js
vue3.0实现点击切换验证码(组件)及校验
Nov 18 #Vue.js
在Vue中使用Echarts可视化库的完整步骤记录
Nov 18 #Vue.js
详解vue实现坐标拾取器功能示例
Nov 18 #Vue.js
Vue如何循环提取对象数组中的值
Nov 18 #Vue.js
vue在图片上传的时候压缩图片
Nov 18 #Vue.js
Vue +WebSocket + WaveSurferJS 实现H5聊天对话交互的实例
Nov 18 #Vue.js
You might like
使用sockets:从新闻组中获取文章(三)
2006/10/09 PHP
关于PHP二进制流 逐bit的低位在前算法(详解)
2013/06/13 PHP
php上传文件,创建递归目录的实例代码
2013/10/18 PHP
Yii中CGridView关联表搜索排序方法实例详解
2014/12/03 PHP
微信支付开发动态链接Native支付
2016/07/12 PHP
Yii2实现跨mysql数据库关联查询排序功能代码
2017/02/10 PHP
jQuery 页面 Mask实现代码
2010/01/09 Javascript
js实现右下角可关闭最小化div(可用于展示推荐内容)
2013/06/24 Javascript
jQuery实现可展开折叠的导航效果示例
2016/09/12 Javascript
jquery select2的使用心得(推荐)
2016/12/04 Javascript
Html5+jQuery+CSS制作相册小记录
2016/12/30 Javascript
angular.JS实现网页禁用调试、复制和剪切
2017/03/31 Javascript
webpack学习--webpack经典7分钟入门教程
2017/06/28 Javascript
Nodejs之http的表单提交
2017/07/07 NodeJs
详解node+express+ejs+bootstrap构建项目
2017/09/27 Javascript
vue基础之使用get、post、jsonp实现交互功能示例
2019/03/12 Javascript
微信小程序实现发送模板消息功能示例【通过openid推送消息给用户】
2019/05/05 Javascript
浅谈JS中this在各个场景下的指向
2019/08/14 Javascript
vue使用echarts图表自适应的几种解决方案
2020/12/04 Vue.js
小程序实现列表倒计时功能
2021/01/29 Javascript
[34:39]Secret vs VG 2018国际邀请赛淘汰赛BO3 第二场 8.23
2018/08/24 DOTA
python学习教程之使用py2exe打包
2017/09/24 Python
python实现多层感知器
2019/01/18 Python
Django模板Templates使用方法详解
2019/07/19 Python
解决pytorch-yolov3 train 报错的问题
2020/02/18 Python
德国隐形眼镜店:LuckyLens
2018/07/29 全球购物
高中运动会入场词
2014/02/14 职场文书
2014年元旦联欢会活动策划方案
2014/02/16 职场文书
日化店促销方案
2014/03/26 职场文书
优秀护士先进事迹
2014/05/08 职场文书
高一课前三分钟演讲稿
2014/09/13 职场文书
2015年转正工作总结范文
2015/04/02 职场文书
员工工作失职检讨书范文!
2019/07/03 职场文书
Pandas数据类型之category的用法
2021/06/28 Python
嵌入式Redis服务器在Spring Boot测试中的使用教程
2021/07/21 Redis
golang连接MySQl使用sqlx库
2022/04/14 Golang