vue 3 源码分析 第一版

90 阅读1分钟

vue3 原理解析,临时笔记

1、 vue2.0 是通过new vue() 3.0 通过createApp()

2、 实列真正创建者 readerer.createApp(options)

renderer = createReaderer(options) createReaderer 实列上挂在了一个 createApp = createAppApi()

3、 createAppApi 实列下面有 mount() 如果传就一个对象(这个对象是通过createApp(options) 得来的), 就会识别为一个组件, 最后mount 下面的 subtree()递归虚拟Vnode 树

1const Vue = {
	createApp(options){
    // 真正用来创建app实列的是 renderer
    	return renderer.createApp(options)
    }
}
2const renderer = createRenderer({
	createElement(tag){
    	return document.createElement(tag)    
    }
    insert(child,parent) {
    	parent.appendChild(child)
    }
})
3、
createRenderer = ({createElement,insert}) => {
	const render = (vnode,container) => {
      //解析vnode => dom
      //创建vnode 对应dom
      const child = createElement(vnode.tag)
      if(typeof vnode.children === 'string'){
      	//元素内部如果是文本
        child.textContent = vnode.children
      }
      // 这里如果有多个子元素的话, 
      //追加节点
      insert(child, container)
    }
	return {
    	render,
        createApp: createAppAPI(render)
    }
}
4、
createAppAPI = (render) => {
	return function createApp(rootComponent) {
    	//创建一个app , 定义mount
        //mount 后面会调用render,  将虚拟 vnode 转换真实的dom
        const app = {
            // rootContainer 是宿主元素, 当前实例即将要挂在的元素,类似 mount(#app) 
        	mount(rootContainer){
            	// 此处手写一个vnode ,实际上它应该是根组件render 函数的返回值
                const vnode = {
                	tag: 'div',
                    props: null,
                    children: rootContainer.data().count
                }
                // 把虚拟 vnode 挂在上去
                render(vnode,document.querySelector(rootContainer))
            }
        }
    }
}