Vue 中的高阶组件
了解了这些,接下来我们就可以开始着手实现 Vue
高阶组件了,为了让大家有一个直观的感受,我仍然会使用 React
与 Vue
进行对比的讲解。首先是一个基本的 Vue
组件,我们常称其为被包装组件( WrappedComponent
),假设我们的组件叫做 BaseComponent
:
base-component.vue
<template> <div> <span @click="handleClick">props: {{test}}</span> </div> </template> <script> export default { name: 'BaseComponent', props: { test: Number }, methods: { handleClick () { this.$emit('customize-click') } } } </script>
我们观察一个 Vue
组件主要观察三点: props
、 event
以及 slots
。对于 BaseComponent
组件而言,它接收一个数字类型的 props
即 test
,并发射一个自定义事件,事件的名称是: customize-click
,没有 slots
。我们会这样使用该组件:
<base-component @customize-click="handleCustClick" :test="100" />
现在我们需要 base-component
组件每次挂载完成的时候都打印一句话: I have already mounted
,同时这也许是很多组件的需求,所以按照 mixins
的方式,我们可以这样做,首先定义个 mixins
:
export default { name: 'BaseComponent', props: { test: Number }, mixins: [ consoleMixin ] methods: { handleClick () { this.$emit('customize-click') } } }
然后在 BaseComponent
组件中将 consoleMixin
混入:
export default { name: 'BaseComponent', props: { test: Number }, mixins: [ consoleMixin ] methods: { handleClick () { this.$emit('customize-click') } } }
这样使用 BaseComponent
组件的时候,每次挂载完成之后都会打印一句 I have already mounted
,不过现在我们要使用高阶组件的方式实现同样的功能,回忆高阶组件的定义: 接收一个组件作为参数,返回一个新的组件 ,那么此时我们需要思考的是,在 Vue
中组件是什么?有的同学可能会有疑问,难道不是函数吗?对, Vue
中组件是函数没有问题,不过那是最终结果,比如我们在单文件组件中的组件定义其实就是一个普通的选项对象,如下:
export default { name: 'BaseComponent', props: {...}, mixins: [...] methods: {...} }
这不就是一个纯对象吗?所以当我们从单文件中导入一个组件的时候: