原地址

很多朋友对于长篇大论看不下去,有的呢是有接触过这些,所以我们今天吧总结写在前边。需要的朋友可以往下看: 
总结: 
1. render方法的实质就是生成template模板; 
2. 通过调用一个方法来生成,而这个方法是通过render方法的参数传递给它的; 
3. 这个方法有三个参数,分别提供标签名,标签相关属性,标签内部的html内容 
4. 通过这三个参数,可以生成一个完整的木模板

备注:

  1. render方法可以使用JSX语法,但需要Babel plugin插件;
  2. render方法里的第三个参数可以使用函数来生成多个组件(特别是如果他们相同的话),只要生成结果是一个数组,且数组元素都是VNode即可;

注意: 
render函数室友限制的,Vue.js 2.X支持,但是1.X无法使用。

说明: 
我们接着来,我们今天先来粗略的了解下render函数,后面我会用大量的代码进行说明,便于大家先简单的了解,后边我们在进行深入了解。

基础

什么是render函数呢?Vue官方给我们已经说明。 
VUE推荐在绝大多数情况下使用template来创建我们的HTML。然而在一些场景中,我们真的需要JavaScript的完全编程的能力,这就是render函数,它比template更接近编译器。

<h1><a name="hello-world" href="#hello-world">Hello world!</a>
</h1>

在HTML层,我们决定这样定义组件接口:

<anchored-heading :level="1">Hello world!</anchored-heading>

当我们开始写一个通过levelprop 动态生成heading 标签的组件,你可能很快想到这样实现:

<script type="text/x-template" id="anchored-heading-template"><h1 v-if="level === 1"><slot></slot></h1><h2 v-else-if="level === 2"><slot></slot></h2><h3 v-else-if="level === 3"><slot></slot></h3><h4 v-else-if="level === 4"><slot></slot></h4><h5 v-else-if="level === 5"><slot></slot></h5><h6 v-else-if="level === 6"><slot></slot></h6>
</script>
Vue.component('anchored-heading', {template: '#anchored-heading-template',props: {level: {type: Number,required: true}}
})

在这种场景中使用 template 并不是最好的选择:首先代码冗长,为了在不同级别的标题中插入锚点元素,我们需要重复地使用<slot></slot>

虽然模板在大多数组件中都非常好用,但是在这里它就不是很简洁的了。那么,我们来尝试使用render函数重写上面的例子:

Vue.component('anchored-heading', {render: function (createElement) {return createElement('h' + this.level,   // tag name 标签名称this.$slots.default // 子组件中的阵列)},props: {level: {type: Number,required: true}}
})

简单清晰很多!简单来说,这样代码精简很多,但是需要非常熟悉 Vue 的实例属性。在这个例子中,你需要知道当你不使用slot 属性向组件中传递内容时,比如 anchored-heading 中的 Hello world!, 这些子元素被存储在组件实例中的 $slots.default中。如果你还不了解, 在深入 render 函数之前推荐阅读实例属性API。

我们来一个生成模板对比,便于学习 
非使用render方法的情况下

<div id="app"><child :level="1">Hello world!</child>
</div>
<script type="text/x-template" id="template">
<div><h1 v-if="level === 1"><slot></slot></h1><h2 v-if="level === 2"><slot></slot></h2><h3 v-if="level === 3"><slot></slot></h3><h4 v-if="level === 4"><slot></slot></h4><h5 v-if="level === 5"><slot></slot></h5><h6 v-if="level === 6"><slot></slot></h6>
</div>
</script><script type="text/javascript">Vue.component('child', {template: '#template',props: {level: {type: Number,required: true}}
})new Vue({el: "#app"
})</script>

代码说明: 
1. 最下面的new Vue方法很明显,是new了一个Vue的实例,挂载点#app这个dom; 
2. Vue.component这部分代码,第一个参数表示注册了一个Vue的组件,标签名是child(即 <child> 标签会被替换); 
3. 第二个参数中,template属性表示取找id=“template”的标签(另注,这个标签是<script>,或者是<div>,或者是template,或者是其他,没有影响),然后将这个标签作为组件的模板; 
4. props表示传递给这个组件的变量,通过标签中的v-bind:level这种形式传递变量level的值等于1。在这里的写法是限制变量类型为number,并且强制需要; 
5. slot表示内容分发,具体来说,就是把组件替换的源html标签里的内容(如 <child> 标签里面的内容,不包含 <child> 标签本身,这里是Hello world!),发在 <slot> 标签所在的位置(即放在<h1>-<h2> 这样的标签内); 
6. 如果还不理解,可以运行该段代码查看结果,或者去看vue的官方文档说明; 
7. 总的来说,顺序如下:注册一个组件,这个组件有模板,这个模板里有一个变量,变量的值通过父组件来传递,然后根据变量的值,通过v-if命令显示对应的html标签内容,然后在父组件里使用这个组件,让子组件显示需要显示的内容。

这样的代码有一个缺陷,就是需要大量重复的代码。如<h1>~<h6>共六种情况。如果这样的模板比较复杂,比如<hx>标签里还有很多其他内容,显然会让人十分困扰,既不美观又不好用。 
使用render方法的情况

<div id="app"><child v-bind:level="2">Hello world!</child>
</div><script type="text/javascript">Vue.component('child', {render: function (createElement) {return createElement('h' + this.level, // tag name 标签名称this.$slots.default // 子组件中的阵列)},props: {level: {type: Number,required: true}}
})new Vue({el: "#app"
})</script>

码说明:

  1. 这里的代码和上面区别之处有两点: 
    其一,没有显式的模板内容,而是通过render方法生成; 
    其二,使用了createElement方法。
  2. 关于createElement方法,他是通过render函数的参数传递进来的,这个方法有三个参数: 
    第一个参数主要用于提供dom的html内容,类型可以是字符串、对象或函数。比如”div”就是创建一个 <div>标签 
    第二个参数(类型是对象)主要用于设置这个dom的一些样式、属性、传的组件的参数、绑定事件之类,具体可以参考 官方文档 里这一小节的说明 
    第三个参数(类型是数组,数组元素类型是VNode)主要用于说是该结点下有其他结点的话,就放在这里。

比如说,有需要分发的标签 <slot>,则通过 this.$slots.default 来获得,或许还有其他组件之类,可能需要被使用的,应该也是放在这里。 
个人初步理解是,在原本被替换的地方,例如例上面代码中的 <child> 标签,在其下的每个次一级标签为一个元素,放在 this.$slots.default这个数组中,例如上面的话,这个数组只有一个元素,但是以下代码: 

<child v-bind:level="2"><div>Hello</div><div> world!</div></child> 

这个数组中则有两个元素,分别是 <div>Hello</div> 和 <div> world!</div>例如 this.$slots.default[0] 则表示第一个标签。

另外,假如这2个元素中间有空格、换行符之类,那么数组中则有三个元素,那个空格、换行符则为第二个元素。这个属性有点类似dom的 childNodes属性,不是单纯以标签才算作子节点的。(但注意,不是完全相同)

有时候,我们可能想在里面添加其他的组件,例如将abc组件注册在里面。那么,我们首先要注册这个abc组件,然后将abc组件在数组里通过createElement来创建标签,只有通过这样的方式创建的abc标签,才能被abc组件使用。单纯输入字符串"<abc></abc>" 这样是不可以的。

如以下代码也是可行的(在通过render方法生成的模板中添加别的组件):

<div id="app"><child v-bind:level="2"><div>Hello</div><div> world!</div></child>
</div><script>Vue.component('abc', {template: "<div>abc</div>"
})Vue.component('child', {render: function (createElement) {console.log(this.$slots)return createElement('h' + this.level, // tag name 标签名称[this.$slots.default[0], createElement("abc"),                                this.$slots.default[1]] // 子组件中的阵列)},props: {level: {type: Number,required: true}}
})new Vue({el: "#app"
})</script>

显示结果是:

Hello
abc
world!

最后,如果想将原有内容全部使用(而不是只取部分标签),那么直接使用 this.$slots.default 作为第三个参数即可,他本身就是一个数组。

总而言之,createElement方法的作用就是动态的创建一个dom用于被render函数渲染,其中参数二和参数三可以选择性省略,参数二用于设置dom的样式、属性、事件等,参数三用于设置分发的内容,包括新增的其他组件。 
粗略理解的话,可以理解为:createElement( 标签名, 标签属性, 标签里的内容)。

这样的话,我们就有了一个组件的模板所需要的全部内容了。后边我们在深入的了解下render函数。

Vue2.0 render:h => h(App)

原地址:Vue2.0 render:h => h(App)

1 new Vue({
2
3   router,
4   store,
5   //components: { App }  vue1.0的写法
6   render: h => h(App)    vue2.0的写法
7 }).$mount('#app')

render函数是渲染一个视图,然后提供给el挂载,如果没有render那页面什么都不会出来

vue.2.0的渲染过程:

1.首先需要了解这是 es 6 的语法,表示 Vue 实例选项对象的 render 方法作为一个函数,接受传入的参数 h 函数,返回 h(App) 的函数调用结果。

2.其次,Vue 在创建 Vue 实例时,通过调用 render 方法来渲染实例的 DOM 树。

3.最后,Vue 在调用 render 方法时,会传入一个 createElement 函数作为参数,也就是这里的 h 的实参是 createElement 函数,然后 createElement 会以 APP 为参数进行调用,关于 createElement 函数的参数说明参见:Element-Arguments

结合一下官方文档的代码便可以很清晰的了解Vue2.0 render:h => h(App)的渲染过程。

[官方文档][1]

1 render: function (createElement) {
2     return createElement(
3       'h' + this.level,   // tag name 标签名称
4       this.$slots.default // 子组件中的阵列
5     )
6   }

为了方便仍然有疑惑的人,贴一个链接,

大概的翻译下:
render: h => h(App) 是下面内容的缩写:

render: function (createElement) {return createElement(App);
}

进一步缩写为(ES6 语法):

render (createElement) {return createElement(App);
}

再进一步缩写为:

render (h){return h(App);
}

按照 ES6 箭头函数的写法,就得到了:

render: h => h(App);

其中 根据 Vue.js 作者 Even You 的回复,h 的含义如下:

It comes from the term "hyperscript", which is commonly used in many virtual-dom implementations. "Hyperscript" itself stands for "script that generates HTML structures" because HTML is the acronym for "hyper-text markup language".

它来自单词 hyperscript,这个单词通常用在 virtual-dom 的实现中。Hyperscript 本身是指
生成HTML 结构的 script 脚本,因为 HTML 是 hyper-text markup language 的缩写(超文本标记语言)

个人理解:createElement 函数是用来生成 HTML DOM 元素的,也就是上文中的 generate HTML structures,也就是 Hyperscript,这样作者才把 createElement 简写成 h。

render函数介绍,以及 render: h =gt; h(App)相关推荐

  1. vue中的render函数介绍

    render函数是什么 简单的说,在 vue 中我们使用模板HTML语法组建页面的,使用 render 函数我们可以用js语言来构建DOM. 因为vue是虚拟DOM,所以在拿到template模板时也 ...

  2. iview render函数(vue render函数)

    iview 的render函数就是vue的render函数,iview常用在表格里面自定义内容,下面来看render函数常用的配置: 1. h是createdElement的简写,有3个参数: 语法: ...

  3. vue之Render函数

    (1)什么是Render函数 先来看一个场景,在博客网中,一般有一级标题.二级标题.三级标题...,为了方便分享url,它们都做成了锚点,点击后,会将内容加载网址后面,以#分隔. 例如'特性'是一个& ...

  4. vue iframe 中写script_vue: 单文件组件 render函数

    使用vue-cli创建的vue项目,如何在这种项目中使用组建? 首先创建项目.启动项目 我们再来了解一下目录结构,src文件夹是写逻辑代码的地方,public是最终渲染到浏览器的地方. 在public ...

  5. render注册一个链接组件_vue: 单文件组件 render函数

    使用vue-cli创建的vue项目,如何在这种项目中使用组建? 首先创建项目.启动项目 我们再来了解一下目录结构,src文件夹是写逻辑代码的地方,public是最终渲染到浏览器的地方. 在public ...

  6. vue中render函数的作用及解析

    在vue脚手架的main.js文件中,存在这样一段代码: 意思是对vue实例的配置,其中render函数的作用是,将h创建的Node节点信息return返回给Vue.js底层处理文件中的beforeM ...

  7. Vue的render函数

    1.template模板 父组件:App,子组件:Test app.vue中 <template><div id="app"><h1>这是app ...

  8. 十二、虚拟 DOM 和 render() 函数(1)

    本章概要 虚拟DOM render()函数 Vue.js 之所以执行性能高,一个很重要的原因就是它的虚拟 DOM 机制. 12.1 虚拟 DOM 浏览器在解析 HTML 文档时,会将文档中的元素.注释 ...

  9. render函数是什么,怎么用

    render函数是什么 简单的说,在vue中我们使用模板HTML语法组建页面的,使用render函数我们可以用js语言来构建DOM 因为vue是虚拟DOM,所以在拿到template模板时也要转译成V ...

最新文章

  1. 【Android 逆向】IDA 安装 ( 使用 IDA 分析 so 动态库 )
  2. Java:异常处理的一些注意事项
  3. JQuery-No.02 jTemplates模板学习笔记
  4. nginx设置http强制跳转https
  5. Hibernate中Cascade和Inverse
  6. 2d游戏中关于碰撞以及渲染层级关系
  7. Go多线程并发避免堵塞
  8. 一些利用开源浏览器核心开发专用浏览器的连接
  9. 微信读书vscode插件_想用 VSCode 写书?这款插件必须备上!
  10. 拼音排序mysql_MySQL拼音排序解决方案解决办法
  11. 冯俪 | 成为最好的你,才最有魅力!
  12. 【QCM2150】WCN3680 WFA认证11ac AP 4.2.23测试FAIL
  13. java获取明天的日期_使用java获取昨日的日期,今日的日期,明日的日期
  14. DXO 做了哪些测试?
  15. linux系统的版本(转载)
  16. 免杀技术有一套(免杀方法大集结)(Anti-AntiVirus)
  17. 用matlab绘制翼型,机翼翼型的Matlab编程
  18. 宿主机到虚拟机的端口映射
  19. 解决: ValueError: source code string cannot contain null bytes 问题
  20. 如何计算产生SPWM所需要的占空比

热门文章

  1. 《软件过程与项目管理》复习思考问题清单
  2. 二本双非一战中科大成功上岸-经验分享
  3. c++ string字符串详解
  4. Flask+Echarts搭建全国疫情可视化大屏
  5. 使用Python+小程序实现诗词大会的飞花令
  6. UWB高精度定位系统源码,商业级智慧工厂人员定位系统源码
  7. flutter 颜色值处理
  8. 缺少对象nbsp;WScriptnbsp;问题解决方法
  9. 线性代数 通俗的理解奇异值以及与特征值的区别
  10. 林肯公园让听众用Facebook相册创作新歌MV