开发vue时,有时候需要根据应用场景生成的动态的vue组件,vue为我们提供比较常用的两种对接方式:
- 使用component标签元素
- 使用render渲染函数
使用component标签元素
直接配置组件名、属性、值和事件
<template>
<component
:is="config.name"
v-bind="config.props"
v-on="config.on"
v-model="config.value"
:class="config.class"
:style="config.style"
></component>
</template>
<script>
export default {
data() {
return {
config: {
name: "el-input-number",
props: {
size: "small"
},
on: {
input: function(data) {}
},
value: 10
}
};
}
};
</script>
优点:编写简单、方便,容易上手;原生元素(如:input)也可使用
缺点:不支持原生事件
使用render渲染函数
需要定义一个中间组件,它起着桥梁的作用;它的作用就相当于上面的component,只不过component由系统实现了,这个中间组件由用户实现。
(具体的案例可见vue-easy-form,其动态组件的实现方式就是利用了render渲染函数)
export default {
render: function(createElement) {
createElement(
this.config.name, // tag name 标签名称 https://www.cnblogs.com/tugenhua0707/p/7528621.html
{
attrs: this.config.attrs, //attrs为原生属性
// style: this.config.style,
class: this.config.class,
style: this.config.style,
// DOM属性
domProps: {
// innerHTML: "baz"
// value: this.config.value
},
// 组件props
props: this.config.props,
// 事件监听器在 `on` 属性内
on: this.config.on,
// 原生事件
nativeOn: this.config.nativeOn,
// 作用域插槽的格式为
// { name: props => VNode | Array<VNode> }
scopedSlots: {
default: props => createElement('span', props.text)
}
}
);
},
props: {
config: {
type: Object,
required: true,
default: () => {
return {};
}
}
},
methods: {}
};
优点:编程式的写法,编写自由
缺点:由于编写自由,所有的功能都要重新实现。(比如原生元素的<input type="checkbox"/>的双向绑定)
项目选择
- 若项目是基于业务的,所有的开发代码都在项目中,使用component标签元素作为动态组件的桥梁一般都够用;
- 若项目是一个独立的类库,作为第三方组件提供给别人使用,最好使用render渲染函数实现动态组件,这样实现的功能比较齐全。