Vue组件继承 -- 2

昨天写了一个根据本公司业务去继承 elementUi 组件的类,今天就悲催的发现,继承适用性不大;
尤其是对于 el-select 之类的组件,有内部绑定时,绑定的是外部组件的属性,而不是绑定的 el-select 组件的属性,
但是,俺的组件不能去控制外部父组件的属性;
于是今天又改写成 wrap 了,简单来说,
就是类似于 EhayInput 这样的 组件里面会包裹一个 el-input , 于这样   <template><el-input......</template> 的模板语法
但是需要实现几个目标: 
1. 组件需要能够自动把父组件传递的 prop 传递给里面的 el-input ;
就是 <EhayInput :max="10"></EhayInput> 这样写时, EhayInput 里面的 el-input 也应该自动绑定 max=10 

2. 自动向上传递事件
     也就是里面 el-input 的 focus 之类的事件应该会自动传递到 EhayInput , 类似于这样 <EhayInput @focus="focus"></EhayInput> 

3. 自动绑定 slot, 
    也就是里面EhayInput  的 slot 之类的定义应该会自动传递到里面的 el-input , 类似于这样   
   <EhayExample ref="wrap"><template slot="prepend">Http://</template></EhayExample>  这个 http:// 应该传递到 里面的 el-input 组件里面。。。

简单来说,就是尽量让组件用起来不变 或者 更加方便;

先来看看第一个目标,
1. 组件需要能够自动把父组件传递的 prop 传递给里面的 el-input ;
就是 <EhayInput :max="10"></EhayInput> 这样写时, EhayInput 里面的 el-input 也应该自动绑定 max=10 

这个貌似不难,有2个基本方法,
a. 老老实实的写 模板定义, 把被包裹的所有 prop 重新绑定到自己组件的 prop 上, 反正自己组件也是 mixins 了 ElInput 组件,所以自己的组件也肯定包含 ElInput 组件 所有的 prop 属性,直接绑定毫无问题;
<template>
<ElInput ref='innerOriginal'  :value='value'  :size='size'  :resize='resize'  :form='form'  :disabled='disabled'  :readonly='readonly'  :type='type'  :autosize='autosize'  :autocomplete='autocomplete'  :autoComplete='autoComplete'  :validateEvent='validateEvent'  :suffixIcon='suffixIcon'  :prefixIcon='prefixIcon'  :label='label'  :clearable='clearable'  :tabindex='tabindex' ></ElInput>
</template>   

b. 自动产生上面的模板字符串,并编译成为相应的 render 函数,
简单来说,就是把上面这个模板字符串自己拼凑出来,并编译成 render 函数
(如果你定义了 template, 这一步VUE会自动完成)

这个也很简单。。。。加一个 ref 是为了在自己的组件中能够引用里面这个 el-input 组件

class Compile {
  /**
   * 根据组件定义产生 组件的定义 template 字符串,并通过 Vue编译后,产生 render 函数;
   * @param c     ElementUI 组件的实例,好稀奇, 传入 elementUI.Input 应该是一个 class 定义,
   *              但是却传入了 类实例;
   */
  static compile(c: any): (createElement: any) => VNode {
    let result: string = '';
    result = "<" + c.name + " ref='innerOriginal' ";
    for (let prop in c.props) {   // 绑定组件中的属性
      result = result + ' :' + prop + "='" + prop + "' ";
    }

    result += ">";
   
    result += "</" + c.name + ">";
    console.log(result);
    return Vue.compile(result).render;
  }
}

然后我们再用 昨天提到的 方法继承一个 el-input 组件
 

/**
 * 自动完成组件
 * 使用方法,继承自  elementUI.Input, 和 elementUI.Input 一样使用即可;
 * <EhayInput entityTypeName='EH_Client' v-model='client'></EhayInput>
 * 但是有个问题,因为是远程查询,所以绑定时可能会
 */
@Component({
  template: `<div>abc</div>`, 
  render: Compile.compile(elementUI.Input),
})
export default class EhayInput extends Mixins(elementUI.Input)  {
.....

如果,你不理解 @Component, 请查看   
https://github.com/kaorun343/vue-property-decorator, 或者 https://github.com/vuejs/vue-class-component , 不过,
貌似不太可能,使用 vue + typescript , 很难不使用这2者之一。。。
以上2个项目代码质量极高,且文档非常优秀,上千个 Star 只有不到10个 Issues.

今天先到这儿。。
 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值