render函数特点
- render函数和模板一样,模板可以做的事情它都可以做
- render函数是最接近编译器的函数
- render函数返回vnode
- 模板和jsx会先编译成render函数然后在返回vnode
- 组件树中的所有 VNode 必须是唯一的,如果真的需要重复很多次的元素/组件,你可以使用工厂函数来实现
- 渲染函数中没有与v-model的直接对应——你必须自己实现相应的逻辑
- Vue 选项中的render函数若存在,则 Vue 构造函数不会从template选项或通过el选项指定的挂载元素中提取出的 HTML 模板编译渲染函数。
- render函数一般结合函数式组件来用,函数式组件只是函数,所以渲染开销也低很多
- 只要在原生的 JavaScript 中可以轻松完成的操作,Vue 的渲染函数就不会提供专有的替代方法
render函数注意点
- createElement第一个参说若是组件,则第三个参数可省略,即使写上去了也无效
- createElement的第二个参数可省略不写
- render函数在on事件中可监听组件$emit发出的事件
函数式组件特点
- 无状态 (没有响应式数据也就是无data,即使在组件中声明了data也是不可用的)
- 没有实例 (没有this上下文,普通文件this指向window,在单文件中this指向null)
为什么要用函数式组件
-
函数式组件只是函数,无状态 (没有响应式数据),不需要递归监听data中的数据,也没有实例 (没有this上下文),所以渲染开销相比于模板低很多,所以用于渲染静态数据非常高效
-
作为包装组件时它非常有用,如果有多个组件,可以有选择的渲染某个组件
-
方便开发者定义很逻辑清晰的组件
函数式组件在单文件组件中的应用
如果在单文件组件中声明了函数式组件,不可再用render函数【因为vue-loader是把template转换成render函数 templete和render函数不能共存】 vue单文件里并没有render方法,因此不会执行
错误示例
解决办法有3种
https://codesandbox.io/s/vue-template-ok0ei
https://codesandbox.io/s/vuejsceshidanyemianzujianzuohanshushizujian-hfvst
render函数渲染多个值
render: function(createElement) {
return createElement('div', [
createElement('span', '123'),
createElement('span', '456')
])
}
iview2.0表格中使用render函数
原理
其实就是我们引入的表格组件 表格组件是一个js文件 这个js文件是函数式组件和render函数结合来使用的【详细需要看源码】 iview3.0之后废弃了表格中使用render函数
排坑
iview2.0表格中使用render函数 在scope下css不起作用
后记
想要查看一个组件的模板被编译后的渲染函数很简单,只需要在访问 this.$options.render 即可
注意 空格也会被createElement()渲染
<div>
<base-component>
<h2 slot="slot1">BaseComponent slot</h2>
<p>default slot</p>
</base-component>
</div>
转换后
var render = function() {
var _vm = this
var _h = _vm.$createElement
var _c = _vm._self._c || _h
return _c(
"div",
[
_c("base-component", [
_c("h2", { attrs: { slot: "slot1" }, slot: "slot1" }, [
_vm._v("BaseComponent slot")
]),
_vm._v(" "),
_c("p", [_vm._v("default slot")])
])
],
1
)
}