vue 组件业务逻辑复用

2,000 阅读2分钟

前言

个人学习过程中的记录,便于后续的复习使用,如果有错误或者更高的方法,希望看到的大佬指出

组件业务逻辑复用

常用的有三种,mixinsHOC(高阶组件)Renderless组件

Mixins

Mixin是可以被一个子类或者一组子类轻松继承的类,目的是为了函数复用,可以全局注册Vue.mixin,会影响到所有的Vue实例,也可以在单文件中使用mixins:[xx],如果Mixin和组件中出现同名的钩子函数,函数将会合并成一个数组,并且会在组件自身的钩子函数之前调用,而methods,components和directive将会合并成一个对象,如果出现重复的键名,则保留组件中的键值

利用mixin做一个插件

做一个很简单的插件意思一下,调用$notify可以弹出一个窗口,窗口信息为传入的参数

Vue.use(plugin)

Vue.use(plugin)这一段代码应该都很熟悉,vuex,elementUI 等等都要使用这段代码安装插件,以便在vue中使用这些扩展的功能
下面的代码取自vue3,使用了ts书写,可以看出使用的插件需要提供一个PluginInstallFunction函数或者install对象 所以上述插件就很简单,下面直接贴代码,然后在main,js里面引入,然后Vue.use就行了,效果就不演示了,感兴趣的可以改造成alert自定义模板

  import Vue from "vue";

  const methods = {
    $notify: function(template) {
      alert(template);
    },
  };
  function install() {
    Vue.mixin({ methods });
  }
  export default { install };

缺点

打破了原有组件的封装,增加了组件的复杂度,而且可能出现命名冲突,并且只能对逻辑复用,不能对模板复用

renderless组件

由于hoc组件嵌套太深,组件复杂度高,调用起来很不方便,所以不太推荐使用,这里就不介绍了,所以直接介绍vue社区中用的比较多的renderless组件,可以将复用的逻辑沉淀在slot中,接口由插槽slot来暴露

slot

先了解一下插槽,插槽要讲的也不多,封装组件应该也经常使用,要讲的也就是如何在父模板中用子模板的数据,很简单,下面的代码演示了如何使用

//子组件 省略其他代码
<slot :data="data" name="context"></slot>
//父组件
<template v-slot:context="{ data }"
   >{{ data.name }}
</template>

renderless

就举一个正则校验的例子吧

Renderless组件

<template>
  <div>
    <slot name="inputText" :validate="validate"></slot>
    {{ errMsg }}
  </div>
</template>
//methods
validate() {
  let validate = this.rules.reduce((pre, cur) => {
    let check = cur && cur.test && cur.test(this.value);
    this.errMsg = check ? "" : cur.message;
    return pre && check;
  }, true);
  return validate;
},

父组件

//ComMultiplexing 为引入的上面的组件
<com-multiplexing :rules="rules" :value="num">
   <template v-slot:inputText="{ validate }">
      <input type="text" v-model="num" @blur="validate" />
   </template>
</com-multiplexing>
//。。。省略部分代码
data() {
    return {
      num: 1,
      rules: [
        {
          message: "请输入至少一个数字",
          test(value) {
            return /\d+/.test(value);
          },
        },
      ],
    };
  },

v-slot也可以直接写在com-multiplexing上面 <com-multiplexing v-slot:inputText="{ validate }" ></com-multiplexing>

复用

如果需要复用,则可以将rules和num更换变量即可,并且也可以在此基础上再次封装

    <com-multiplexing
      v-slot:inputText="{ validate }"
      :rules="rule"
      :value="text"
    >
      <input type="text" @blur="validate" v-model="text" />
    </com-multiplexing>

优点

符合依赖倒置原则,模板可以复用,不会出现命名冲突,复用的接口来源清晰