Learn vue3 by comparing the syntax of vue3 with that of vue2. Take a look at slot’s use in 2.x and 3.x.
2.x syntax
In 2.x, I mainly understand the usage of these two. , $slots, $scopedSlots
Vm.$slots template usage
• Type: {[name: string]:? Array
}
Default specifies that propsName is defined in $slots.propsname
// fahter
<template>
<Book>
<span>The default value</span>
<span slot="header">header</span>
<span slot="content">content1</span>
<span slot="content">content2</span>
</Book>
</template>
Copy the code
// child
<template>
<div>
<slot>default 1</slot>
<slot name="header">default 2</slot>
<slot name="content">default 3</slot>
</div>
</template>
Copy the code
- Slot the default
- Slot name Indicates a named slot. In this way, multiple slots can be specified and arranged arbitrarily to achieve layout requirements.
$slots is used in the vm.$slots rendering function
Let’s first look at the syntax of the render function
createElement('div',{//... data object},[ 'some text', createElement('h1'), createElement(MyComponent,{props:{someProp:'foobar'}}) ])Copy the code
Parameter 1: Book 2: components, parameters is of the first parameter {HTML tag | component} parameter Settings, the specific reference createElement method parameters, 3: Children VNodes {String | Array} can String, there is more than one using the form of an Array
render(h) {
return h(Book,{},[
h('span', {},'Default value'),
h('span', {slot:'header'},'header'),
h('span', {slot:'content'},'content1'),
h('span', {slot:'content'},'content2')])}Copy the code
Implement custom defaults
export default {
render(h) {
return h('div', {},this.$slots.default || 'default1'.this.$slots.header || 'default2'.this.$slots.content || 'default3'])}}Copy the code
Vm.$scopedSlots template usage
Type: { [name: string]: props => Array<VNode> | undefined }
The difference from $slots is that $scopedSlots passes data from within the component to the parent scope.
<template>
<div>
<Child>
<template v-slot:default="slotProps">
{{ slotProps.user.name }}
</template>
</Child>
</div>
</template>
Copy the code
<template>
<div>
<slot :user="user"></slot>
</div>
</template>
Copy the code
Vm.$scopedSlots is used in the rendering function
- $scopedslots. default is a function that passes data to the parent component
- The parent component uses scopedSlots to receive data from the child component as follows:
// fahter
render(h) {
return h(Book,{
scopedSlots: {
default:function(props){
return [
props.user.name,
<div>text</div>.'sdfsdf']}}})}Copy the code
// Book.vue
render(h) {
return h('div', {},this.$scopedSlots.default({
user:this.user
})
])
}
Copy the code
3.x syntax
• This.$slots now exposes slots as a function (2. X is an object) • Specify a function to define slot syntax for passing to child components :h(Component,{},{header ()=>Component), as follows:
// father
<script lang='ts'>
import { h } from 'vue';
import Child from './Child.vue'
export default {
components:{
Child
},
render() {
return h(Child,{},
{
header:(props:{year:number}) = >{
return h('div'.`this year is ${props.year}`)},title:() = > h('h1', {
innerHTML:'title'.onClick(){
console.log('Click on the title')},style: {color:'#f66'
}
})
}
)
}
}
</script>
Copy the code
// child
<script lang='ts'>
import { h } from 'vue';
export default {
render() {
return h('div'[this.$slots.title(),this.$slots.header({year:2021})])
}
}
</script>
Copy the code
• H is now imported globally instead of being passed as a parameter to the render function, see the official website for details. X defines a VNode directly,h(‘span’,{slot:’header’},’header’)
- H (Child,{},{header:Function}) uses scopedSlots. The third argument must be an object
- CreateElement method parameters for a third {String | Array}, guess there must be as the object is to think through propName to find the corresponding function to render we specify the header, the title VNode. If you have multiple child elements you can’t determine which one they are.
H render function
It is also important to note that in 3.x the syntax of the render function has changed as follows:
2. X syntax
In 2.x, domProps contains a nested list of VNode props:
// 2.x
{
class: ['button'.'is-outlined'].style: { color: '#34495E' },
attrs: { id: 'submit' },
domProps: { innerHTML: ' ' },
on: { click: submitForm },
key: 'submit-button'
}
Copy the code
3. X syntax
In 3.x, the entire VNode props structure is flat, using the example above, and here is what it looks like now
/ / 3. X syntax
{
class: ['button'.'is-outlined'].style: { color: '#34495E' },
id: 'submit'.innerHTML: ' '.onClick: submitForm,
key: 'submit-button'
}
Copy the code
reference
Chinese document