vue3中渲染函数的非兼容变更
渲染函数API变更
此更改不会影响到<template>
用户
h
当初全局导入,而非作为参数传递给渲染函数- 渲染函数参数更改为在有状态组件和函数组件之间更加统一
- vnode当初又一个扁平的prop构造
Render函数参数
// 2.0 渲染函数export default { render(h) { return h('div') }}// 3.x语法export default { render() { return h('div') }}
渲染函数签名更改
// 2.xexport default { render(h) { return h('div') }}// 3.ximport { h, reactive } from 'vue'export default { setup(prop, {slots, attrs, emit}) { const state = reactive({ count: 0 }) function increment() { state.count++ } // 返回render函数 return () => h( 'div', { onClick: increment }, state.count ) }}
VNode Props 格式化
// 2.x{ class: ['button', 'is-outlined'], style: {color: '#fffff'}, attr: {id: 'submit'}, domProps: {innerHTML: ''}, on: {click: submitForm}, key: 'submit-button'}// 3.x VNode的构造是扁平的{ class: ['button', 'is-outlined'], style: { color: '#34495E' }, id: 'submit', innerHTML: '', onClick: submitForm, key: 'submit-button'}
slot对立
更改了一般slot和作用域slot
this.$slots
当初将slots作为函数公开- 移除
this.$scopedSlots
// 2.xh(LayoutComponent, [ h('div', {slot: 'header'}, this.header), h('div', {slot: 'header'}, this.header)])// 作用域slot:// 3.xh(LayoutComponent, {}, { header: () => h('div', this.header), content: () => h('div', this.content)})// 须要以编程形式引入作用域slot时,他们当初被对立在了$slots选项中// 2.x的作用域slotthis.$scopedSlots.header// 3.x的写法this.$slots.header
移除$listeners
$listeners
对象在vue3中曾经移除,当初事件监听器是$attrs
的一部分
在vue2中,能够应用this.$attrs和this.$listeners别离拜访传递给组件的attribute和工夫监听器,联合inheritAttrs: false,开发者能够将这些attribute和监听器利用到其余元素,而不是根元素
<template><label> <input type="text" v-bind="$attrs" v-on="$listeners"></label></template><script> export default { inheritAttrs: false }</script>
在vue的虚构DOM中,事件监听器当初只是以on为前缀的attribute,这样就成了$attrs对象的一部分,这样$listeners就被移除了
<template> <label> <input type="text" v-bind="$attrs" /> </label></template><script>export default { inheritAttrs: false}// 如果这个组件接管一个 id attribute 和一个 v-on:close 监听器,那么 $attrs 对象当初将如下所示{ id: 'my-input', onClose: () => console.log('close Event Triggered')}</script>
$attrs当初包含class和style
当初的$attr蕴含所有的attribute,包含class和style
在2.x中,虚构dom会对class和style进行非凡解决,所以他们不包含在$attr中
在应用inheritAttr: false的时候会产生副作用
- $attrs 中的 attribute 不再主动增加到根元素中,而是由开发者决定在哪增加。
- 然而 class 和 style 不属于 $attrs,依然会利用到组件的根元素:
<template> <label> <input type="text" v-bind="$attrs" /> </label></template><script>export default { inheritAttrs: false}</script><!-- 写入 --><my-component id="my-id" class="my-class"></my-component><!-- vue2 将生成 --><label class="my-class"> <input type="text" id="my-id" /></label><!-- vue3 将生成 --><label> <input type="text" id="my-id" class="my-class" /></label>