手写Vue之Api-createApp()

Vue之Api-createApp()

1、认识

vue3中,我们经常使用createApp来创建一个vue应用实例,比如我们经常使用的项目

JS 复制代码
☞ App.vue 

<script setup lang="ts">
</script>
<template>
    <router-view></router-view>
</template>
<style scoped>
</style>


☞ main.ts

import { createApp } from 'vue'
import App from './App.vue'

const app = createApp(App)


app.use(SomePlugin);

// 可以进行一些全局配置,例如使用插件
... 

app.mount('#app')//挂载

2、官方使用

官方给我们的案例是

JS 复制代码
function createApp(rootComponent: Component, rootProps?: object): App

使用方式可以直接使用也可以从别处导入

  • 直接内联根组件
JS 复制代码
import { createApp } from 'vue'
const app = createApp({
  /* 根组件选项 */
})
  • 使用从别处导入的组件
JS 复制代码
import { createApp } from 'vue'
import App from './App.vue'
const app = createApp(App)

createApp 接收两个参数:

  • Component (组件,必选)
  • rootProps (参数,可选)

3、源码解析

那么在这个过程之中createApp进行了什么操作呢,我们可以把源码拿出来手写着试试看看

createApp 函数的源码位于 Vue 3 的核心库中,通常在 packages/runtime-core/src 目录下。主要实现文件为 app.ts

接下来我们手写一个createApp 函数的简化版源码,他应该是这样子的

JS 复制代码
// createRenderer: 负责创建 Vue 的渲染器,处理 DOM 操作更新,实现将Vue组件的状态映射到真实 DOM。
import { createRenderer } from './renderer';  

// createLifecycle: 管理组件的生命周期,包括组件的创建、挂载、更新和销毁等。
import { createLifecycle } from './lifecycle';

// initGlobalAPI: 初始化全局 API,比如全局组件、指令和配置等。通过这个 API,开发者可以在应用中使用全局功能。
import { initGlobalAPI } from './globalAPI';

export function createApp(rootComponent, rootProps = null) {
  const app = {
    // 应用实例的核心 API
    mount,
    // 一些内部属性
    _component: rootComponent,
    _props: rootProps,
    // 其他属性和方法
  };

  // 初始化全局 API
  initGlobalAPI(app);

  // 返回应用实例
  return app;
}

function mount(selector) {
  // 挂载逻辑
}

☞ 上面的mount函数挂载方法我们可以拆开分析看看,那么他很有可能就是这么写的

JS 复制代码
 // 挂载方法
mount(selector) {
  // 创建渲染器
  const renderer = createRenderer({
    createElement: (type) => document.createElement(type),
    insert: (el, container) => container.appendChild(el),
    patchProps: (el, props) => {
      Object.keys(props).forEach(key => {
        el.setAttribute(key, props[key]);
      });
    },
    render: () => rootComponent.render(rootProps), // 渲染函数
  });

  const container = document.querySelector(selector);
  renderer.mount(rootComponent, container);
},

上面的createApp函数涉及到的三个函数我们简单写一下大致就是这样子的

(1) createRenderer

写一下上面的renderer.js

整个createRenderer函数主要是负责将Vue组件渲染成真实的DOM元素,实现渲染逻辑和更新机制

简单分析一下: 其实就是渲染、挂载、更新

JS 复制代码
// renderer.js

export function createRenderer(options) {
  // 创建渲染器
  const { createElement, insert, patchProps, render } = options;

  return {
    render,
    // 挂载组件到 DOM
    mount(component, container) {
      const vnode = component.render(); // 生成虚拟节点
      const el = createElement(vnode.type); // 创建元素
      // 将节点插入容器
      insert(el, container);
      // 更新属性
      patchProps(el, vnode.props);
      return el;
    },
    // 更新组件的渲染
    update(component, container) {
      const vnode = component.render();
      // ... 更新逻辑
    }
  };
}

(2) createLifecycle

写一下上面的lifecycle.js

整个lifecycle函数主要用于管理Vue组件的生命周期,包括创建、更新和销毁的过程

简单分析一下: 其实就是管理Vue组件的生命周期

JS 复制代码
// lifecycle.js

export function createLifecycle() {
  return {
    // 组件挂载的生命周期钩子
    beforeMount() {
      // 在组件挂载前执行的逻辑
    },
    mounted() {
      // 在组件挂载后执行的逻辑
    },
    beforeUpdate() {
      // 在组件更新前执行的逻辑
    },
    updated() {
      // 在组件更新后执行的逻辑
    },
    beforeUnmount() {
      // 在组件卸载前执行的逻辑
    },
    unmounted() {
      // 在组件卸载后执行的逻辑
    },
  };
}

(3) initGlobalAPI

写一下上面的globalAPI.js

整个globalAPI主要用于初始化 Vue 应用的全局 API,比如全局组件和指令的注册

简单分析一下: 其实就是Vue的全局API、全局组件以及全局指令

JS 复制代码
// globalAPI.js
export function initGlobalAPI(app) {
  // 注册全局组件
  app.component = function(name, component) {
    // ... 注册逻辑
  };
  
  // 注册全局指令
  app.directive = function(name, directive) {
    // ... 注册逻辑
  };
  
  // 配置全局选项
  app.config = {
    // 一些配置选项
  };
}
相关推荐
毋若成42 分钟前
前端三大组件之CSS,三大选择器,游戏网页仿写
前端·css
红中马喽1 小时前
JS学习日记(webAPI—DOM)
开发语言·前端·javascript·笔记·vscode·学习
Black蜡笔小新2 小时前
网页直播/点播播放器EasyPlayer.js播放器OffscreenCanvas这个特性是否需要特殊的环境和硬件支持
前端·javascript·html
秦jh_3 小时前
【Linux】多线程(概念,控制)
linux·运维·前端
蜗牛快跑2133 小时前
面向对象编程 vs 函数式编程
前端·函数式编程·面向对象编程
Dread_lxy3 小时前
vue 依赖注入(Provide、Inject )和混入(mixins)
前端·javascript·vue.js
涔溪4 小时前
Ecmascript(ES)标准
前端·elasticsearch·ecmascript
榴莲千丞4 小时前
第8章利用CSS制作导航菜单
前端·css
奔跑草-4 小时前
【前端】深入浅出 - TypeScript 的详细讲解
前端·javascript·react.js·typescript
羡与4 小时前
echarts-gl 3D柱状图配置
前端·javascript·echarts