Vue-高阶组件实现

3,044 阅读2分钟

Vue组件中的渲染功能搭配JSX,实现HOC的方法

下方共有三个程序代码片段,分别为

  • Avatar 组件,为高阶组件函式的参数,接收高阶组件注入的属性
  • withFetchImage此范例中假设载入图片的流程会在不同组件中重复使用,因此建立一个HOC增加程序代码的替代性,此处使用setTimeout模拟图片非同步的载入
  • App.js 文件,范例中会在此组合HOC,合并HOC挂载

头像

接收上层传来的src属性

利用渲染功能产生虚拟大教堂,未在加上name属性情况下,Vue的开发工具会视为匿名成分,所以此处替组件加上命名,在开发上会有更好的体验

export default {
  name: 'Avatar',
  props: ['src'],
  render(h) {
    return (
      <img src={src} />
    );
  }
};

withFetchImage

首先,React,直接利用Spread Operator,将this.props重新接收到的Component参数(此处命名为InnerComponent),Vue的渲染函数对数据对象有更详细的定义,可参考数据对象的深度,因此需要特别处理需要替InnerComponent代理的属性

function withFetchImage(InnerComponent) {
  return {
    data() {
      return {
        url: 'http://via.placeholder.com/200x200'
      };
    },
    created() {
      setTimeout(() => {
        this.url = '.../avatar.jpg'
      }, 1000);
    },
    render(h) {
      const attributes = {
        attrs: this.$attrs,
        listeners: this.$listeners,
        style: this.$style,
        class: this.$class
      };
      return (
        <InnerComponent src={this.url} {...attributes} />
      );
    }
  }
};

App.js文件

import withFetchImage from './hocs/withFetchImage';
import Avatar from './components/Avatar';

const AvatarWithFetchImage = withFetchImage(Avatar);

export default {
  components: { AvatarWithFetchImage },
  render(h) {
    return (
      <div>
        <AvatarWithFetchImage />
      </div>
    );
  }
};

摘要

从头开始全面更新高级Vue.js功能

在Vue专案上,无论是使用mixins还是HOC都有各自的优缺点,例如高阶组件使用上,需要考虑过深的阶层造成开发,维护困难及性能上的大量消耗,mixins则是需要判断一些方法,属性来源,使用上非常不直觉。

Vue在3.0后的版本中,提供类似React Hook的解决方案,来处理组件间共同的操作逻辑,相信能改善大家长久以来,在管理逻辑之间取舍的问题,详细可以参考Vue基于函数的API RFC