vue中的渲染函数h函数基本用法及原理
h函数、h渲染函数、vue中的h函数、vue中的h渲染函数、ctx.slots.default、ctx.emit、props、IProps、interface、Btn、onDbClick、template、tsx、jsx、h函数原理
Vue组件有几种写法?
- template
- jsx / tsx
- h
template写法示例:
<template>
<div>
<span>6</span>
</div>
</template>
jsx / tsx写法示例:
const renderDom = () => {
return (
<>
<button onClick={clickTap}>点击</button>
</>
)
}
const clickTap = () => {
console.log('click');
}
export default renderDom
使用 h 函数写法有什么好处?
- 比模板更加接近编译器
- 效率更高
比模版更加接近编辑器,这很容易理解,因为本身模版就是为了方便开发者而做的高度封装。
效率更高从何体现?
因为我们编写的代码转化为真正的dom时,首先会先转换为VNode,然后多个Vnode进行结合起来转化为VDOM,最后VDOM才渲染成真实的DOM,此时我们思考一个问题,如果我们直接编写生成vnode的代码,效率会更高,这里我们就是h()函数。h函数我们也可以称为createVnode函数。
模版转化为节点的流程
template ➡️ parser ➡️ ast ➡️ transform ➡️ js api ➡️ generate ➡️ render ➡️ vnode ➡️ node
我们编写的h函数就是直接生成vnode,省去了前面编译转换的繁琐流程,效率必然是高的。
h函数
h函数接收三个参数。
第一个参数:,可以为一个html标签,一个组件,一个异步组件,或者是一个函数式组件。
第二个参数:{ Object } Props,与attributes和props,以及事件对应的对象,我们可以在模板中使用,如果没有需要传入的属性,可以设置为null。
第三个参数:{String | Object |Array}可以是字符串Text文本或者是h函数构建的对象再者可以是有插槽的对象。
基本写法:
例如:
<template>
<div>
<span>123</span>
</div>
</template>
转化为:
let render = () => {
return h('div',{},[
h('span',{},'1')
])
}
说实话有点类似于 React 当中,createElement 的写法。
实战练习:使用h函数编写一个Button组件,可以通过type属性指定按钮的主题颜色,可以传入自定义事件,可以指定不同的按钮文案
<template>
<Btn @sendMessage="send" type="success">按钮1</Btn>
<Btn type="error">按钮2</Btn>
</template>
<script setup lang="ts">
import { h } from 'vue';
interface IProps {
type: string;
}
const Btn = (props: IProps, ctx: any) => {
console.log(props);
console.log(ctx);
return h(
'button',
{
style: {
color: props.type === 'success' ? 'green' : 'red',
border: '1px solid green',
borderRadius: '5px',
padding: '5px 10px'
},
onClick: () => {
console.log('我被点击');
},
// 双击时触发父组件的send方法
onDblclick: () => {
ctx.emit('sendMessage');
}
},
ctx.slots.default()
);
};
// 子组件触发sendMessage事件时执行的回调
const send = () => {
console.log('send');
};
</script>
<style scoped lang="less"></style>
效果:
魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。
更多推荐

所有评论(0)