轻松掌握 Vue render 函数:简单易懂的使用指南

最近在项目开发过程中,经常用到 UI 组件库中的 render 函数来渲染内容。今天来总结一下 render 的用法。

Render 函数

在 Vue 2 中,render 函数是一个用于创建 Vue 组件虚拟 DOM 的函数。它允许你以编程方式定义组件的结构,而不是使用模板语法。

render 函数接受一个 createElement 函数作为参数,并返回一个虚拟 DOM 节点。createElement 函数用于创建 Vue 的虚拟节点(VNode)。

基本结构

js 复制代码
render(createElement) {
  return createElement(
    'div',             // 标签名
    { class: 'my-class' },  // 属性对象
    [
      createElement('h1', 'Hello World'),  // 子节点
      createElement('p', 'This is a paragraph.')
    ]
  );
}

用途

  1. 复杂逻辑: 当模板语法无法满足复杂逻辑需求时,可以使用 render 函数编写更复杂的组件结构。
  2. 动态内容: render 函数可以用来创建动态的虚拟 DOM,允许更细粒度地控制组件的渲染。
  3. 性能优化: 在某些性能要求高的场景中,render 函数可能提供比模板更高效的渲染方式。

render 函数最常见的地方就是表格的 columns。

Render 写法

通过给 columns 数据的项,设置一个函数 render,可以自定义渲染当前列,包括渲染自定义组件,它基于 Vue 的 Render 函数

render 函数传入两个参数,第一个是 h,第二个是对象,包含 rowcolumnindex,分别指当前单元格数据,当前列数据,当前是第几行。
h 作为 createElement 的别名是 Vue 生态系统中的一个通用惯例,实际上也是 JSX 所要求的。从 Vue 的 Babel 插件的 3.4.0 版本开始,我们会在以 ES2015 语法声明的含有 JSX 的任何方法和 getter 中 (不是函数或箭头函数中) 自动注入 const h = this.$createElement,这样你就可以去掉 (h) 参数了。对于更早版本的插件,如果 h 在当前作用域中不可用,应用会抛错。-- v2.cn.vuejs.org/v2/guide/re...

基本语法

html 复制代码
<template>
  <Table :columns="columns" :data="data"></Table>
</template>

<script>
export default {
  data() {
    return {
      data: [
        { name: 'John', age: 30 },
        { name: 'Jane', age: 24 }
      ],
      columns: [
        {
          title: 'Name', // 列的标题为 'Name'
          key: 'name', // 数据中对应的键为 'name'
          render: (h, params) => {
            // render 函数,用于自定义渲染列的内容
            return h('div', [
              // 创建一个 <div> 元素
              h('Icon', {
                // 在 <div> 中创建一个 <Icon> 组件
                props: {
                  type: 'person' // 设置 <Icon> 组件的属性 'type' 为 'person'
                }
              }),
              h('strong', params.row.name)
              // 在 <div> 中创建一个 <strong> 元素,并显示当前行的数据中的 'name' 字段
            ]);
          }
        }
      ]
    };
  }
};
</script>

render 函数有两个参数, 最主要的是第一个参数 h 函数, 第二个参数是组件库自己封装的对外暴露的数据。

h 函数

在 Vue.js 中,h 函数通常是 createElement 的别名 ,用于创建虚拟 DOM 元素。在使用 Vue 的 render 函数时,h 函数是非常重要的,它可以创建任何你想要的 DOM 结构或组件。让我们详细解析 h 函数的用法和参数。

h 函数的三种用法

h 函数是 Vue 的 createElement 函数的缩写形式。它有三种主要的用法:

创建普通元素

创建了一个 div 元素,具有 class="my-class",并包含文本 "Hello World"。

js 复制代码
h('div', { class: 'my-class' }, 'Hello World')

创建组件

创建了一个 MyComponent 组件,并传递了 someProp 属性。

js 复制代码
h(MyComponent, { props: { someProp: 'value' } })

嵌套子节点

创建了一个 ul 元素,包含两个 li 子节点。

js 复制代码
h('ul', [
  h('li', 'Item 1'),
  h('li', 'Item 2')
])

h 函数的参数

h 函数通常接收三个参数:

  1. 标签名或组件(tag): 可以是一个字符串(表示 HTML 标签) 或者是一个组件对象。
  2. 数据对象(data):一个包含属性、事件、样式等信息的对象(可选)。
  3. 子节点(children):一个子节点、一个子节点数组或者是字符串(可选)。

只有两个参数的情况

当使用 Vue.js 的 h 函数(createElement)时,如果只提供两个参数,这两个参数通常是标签名或组件以及子节点。数据对象(第二个参数)是可选的,所以如果你只提供两个参数,Vue 会将第二个参数解释为子节点。

js 复制代码
h('div', 'Hello World')

到这里基本可以熟练的掌握用 h 函数来创建基本的虚拟 DOM 元素的了。

深入了解数据对象参数

下面主要来看一下数据对象(data) : 包含属性、事件、样式等信息的对象 的参数。下面是完整的数据对象声明参考。

常用项需要注意的几个点是:

  1. class 和 style 直接定义, HTML属性定义在 attrs 对象内
  2. 组件的 prop 定义在 props 中, DOM 属性定义在 domProps 中
  3. 组件事件在 on 中定义, 原生事件 在 nativeOn 中定义
  4. 作用域插槽在 scopedSlots 中定义
js 复制代码
{
  // 与 `v-bind:class` 的 API 相同,
  // 接受一个字符串、对象或字符串和对象组成的数组
  'class': {
    foo: true,
    bar: false
  },
  // 与 `v-bind:style` 的 API 相同,
  // 接受一个字符串、对象,或对象组成的数组
  style: {
    color: 'red',
    fontSize: '14px'
  },
  // 普通的 HTML attribute
  attrs: {
    id: 'foo'
  },
  // 组件 prop
  props: {
    myProp: 'bar'
  },
  // DOM property
  domProps: {
    innerHTML: 'baz'
  },
  // 事件监听器在 `on` 内,
  // 但不再支持如 `v-on:keyup.enter` 这样的修饰器。
  // 需要在处理函数中手动检查 keyCode。
  on: {
    click: this.clickHandler
  },
  // 仅用于组件,用于监听原生事件,而不是组件内部使用
  // `vm.$emit` 触发的事件。
  nativeOn: {
    click: this.nativeClickHandler
  },
  // 自定义指令。注意,你无法对 `binding` 中的 `oldValue`
  // 赋值,因为 Vue 已经自动为你进行了同步。
  directives: [
    {
      name: 'my-custom-directive',
      value: '2',
      expression: '1 + 1',
      arg: 'foo',
      modifiers: {
        bar: true
      }
    }
  ],
  // 作用域插槽的格式为
  // { name: props => VNode | Array<VNode> }
  scopedSlots: {
    default: props => createElement('span', props.text)
  },
  // 如果组件是其它组件的子组件,需为插槽指定名称
  slot: 'name-of-slot',
  // 其它特殊顶层 property
  key: 'myKey',
  ref: 'myRef',
  // 如果你在渲染函数中给多个元素都应用了相同的 ref 名,
  // 那么 `$refs.myRef` 会变成一个数组。
  refInFor: true
}

场景示例

渲染组件

js 复制代码
render: (h, {column,row,index}) => {
  return h('div', [
    h(
      'Button', {
        props: {
          type: 'primary'
        },
        on: {
          click: () => {
            this.handleClick(row.id)
          }
        }
      },
      '编辑'
    )])

渲染作用域插槽

js 复制代码
  render: (h, params) => {
    return h("i-switch", {
      props: {
        size: "large",
        trueValue: 1,
        falseValue: 0,
        value: params.row.status,
        disabled: !params.row.disbaled
      },
      scopedSlots: {
        open: () => h("span", "是"),
        close: () => h("span", "否")
      },
      on: {
        "on-change": value => {
          this.handleChange(value);
        }
      }
    });
  }
},

结语

在 Vue 2 中,render 函数是一个极具灵活性的工具,能够帮助我们创建复杂的组件结构和优化性能。本文详细探讨了 render 函数的基本概念、常见用法及其在实际开发中的应用场景。通过学习 render 函数,我们不仅可以应对复杂的业务需求,还能在构建动态内容和提升应用性能方面获得更多的选择和控制。

掌握 render 函数及其 h 函数的用法,将有助于你在 Vue 项目中实现更高效的组件开发。希望本文的总结对你有所帮助,也鼓励你在实际项目中灵活运用这些知识,探索 Vue 的更多高级功能。

参考资料

相关推荐
Mr_Xuhhh几秒前
重生之我在学环境变量
linux·运维·服务器·前端·chrome·算法
永乐春秋1 小时前
WEB攻防-通用漏洞&文件上传&js验证&mime&user.ini&语言特性
前端
鸽鸽程序猿1 小时前
【前端】CSS
前端·css
ggdpzhk1 小时前
VUE:基于MVVN的前端js框架
前端·javascript·vue.js
小曲曲2 小时前
接口上传视频和oss直传视频到阿里云组件
javascript·阿里云·音视频
学不会•3 小时前
css数据不固定情况下,循环加不同背景颜色
前端·javascript·html
EasyNTS4 小时前
H.264/H.265播放器EasyPlayer.js视频流媒体播放器关于websocket1006的异常断连
javascript·h.265·h.264
活宝小娜5 小时前
vue不刷新浏览器更新页面的方法
前端·javascript·vue.js
程序视点5 小时前
【Vue3新工具】Pinia.js:提升开发效率,更轻量、更高效的状态管理方案!
前端·javascript·vue.js·typescript·vue·ecmascript
coldriversnow5 小时前
在Vue中,vue document.onkeydown 无效
前端·javascript·vue.js