首页 > 其他分享 >Vue动态创建组件实例并挂载到body

Vue动态创建组件实例并挂载到body

时间:2023-08-24 19:33:13浏览次数:47  
标签:body Vue comp Component 动态创建 props 组件

方式一

import Vue from 'vue'

/**
 * @param Component 组件实例的选项对象
 * @param props 组件实例中的prop
 */
export function create(Component, props) {
  const comp = new (Vue.extend(Component))({ propsData: props }).$mount()
  
  document.body.appendChild(comp.$el)

  comp.remove = () => {
    document.body.removeChild(comp.$el)

    comp.$destroy()
  }

  return comp
}

方式二

import Vue from 'vue'

export function create(Component, props) {
  // 借鸡生蛋new Vue({render() {}}),在render中把Component作为根组件
  const vm = new Vue({
    // h是createElement函数,它可以返回虚拟dom
    render(h) {
      console.log(h(Component,{ props }));
      
      // 将Component作为根组件渲染出来
      // h(标签名称或组件配置对象,传递属性、事件等,孩子元素)
      return h(Component, { props })
    }
  }).$mount() // 挂载是为了把虚拟dom变成真实dom
  // 不挂载就没有真实dom
  // 手动追加至body
  // 挂载之后$el可以访问到真实dom
  document.body.appendChild(vm.$el)

  console.log(vm.$children);
  
  // 实例
  const comp = vm.$children[0]

  // 淘汰机制
  comp.remove = () => {
    // 删除dom
    document.body.removeChild(vm.$el)

    // 销毁组件
    vm.$destroy()
  }

  // 返回Component组件实例
  return comp
}

使用

  • A组件(要动态创建的组件)
<template>
  <div class="a">
    <h2>{{ title }}</h2>
    <p>{{ data }}</p>
  </div>
</template>

<script>
export default {
  props: {
    title: {
      type: String,
      default: "hello world!"
    },
    message: {
      type: String,
      default: "o(∩_∩)o 哈哈"
    },
    duration: {
      type: Number,
      default: 1000
    }
  },
  data() {
    return {
      data: "我是a组件",
    };
  },
  created() {
    let num = 1
    
    const timer = setInterval(() => {
      this.data = num++
    }, this.duration)

    this.$once("hook: beforeDestroy", () => clearInterval(timer))
  }
};
</script>

<style>
.a {
  position: fixed;
  width: 100%;
  top: 16px;
  left: 0;
  text-align: center;
  pointer-events: none;
  background-color: #fff;
  border: grey 3px solid;
  box-sizing: border-box;
}
</style>
  • B组件(操作动态创建组件的地方)
<template>
  <div class="b">
    <button @click="createA">创建</button>
  </div>
</template>

<script>
import A from "@/components/A.vue"
import { create } from "@/utils/create.js"
export default {

  components: {
    A,
  },
  methods: {
    createA() {
      // 创建A组件,并挂载到body上
      create(A, { title: "vue", message: "么么哒

标签:body,Vue,comp,Component,动态创建,props,组件
From: https://www.cnblogs.com/mmzuo-798/p/17654998.html

相关文章

  • VUE- elementUI使用quill富文本编辑器(编辑文本、上传图片)
    准备工作:安装 yarninstall vue-quill-editormain.js//编辑器importVueQuillEditorfrom'vue-quill-editor'//引入样式import'quill/dist/quill.core.css'import'quill/dist/quill.snow.css'import'quill/dist/quill.bubble.css'......
  • vue实现大文件上传下载
    ​ 以ASP.NETCoreWebAPI 作后端 API ,用 Vue 构建前端页面,用 Axios 从前端访问后端 API,包括文件的上传和下载。 准备文件上传的API #region 文件上传  可以带参数        [HttpPost("upload")]        publicJsonResultuploadProject(I......
  • vue中,一个参数是一个图片网络地址,当重新上传一个图片替换原来的图片后,地址没变,但是图
    这个问题可能是由于浏览器缓存导致的。为了解决这个问题,你可以向图片的URL地址中添加一个随机参数,以确保每次加载图片时都会从服务器获取最新的图片。你可以使用类似于以下方式来添加随机参数:<img:src="imageUrl+'?timestamp='+Date.now()"/>这样,每次你更新了图片后,URL中......
  • Vue组件缓存之keep-alive正确使用姿势
    先来看一个项目中的需求作为苦逼的前端开发者,我们无时无刻都要面对产品经理提的各种需求,比如下图这个场景场景:从首页的点击导航进入列表页,列表页点击列表进入该数据详情页从详情页返回,希望列表页缓存,不重新渲染数据,这样会提高用户体验。分析一下这样需求,如果是小程序......
  • Electron,VUEJS3,Vite,TypesSript 开发环境配置
    Electron,VUEJS3,Vite,TypesSript开发环境配置项目早期是vue3+vite开发的,后期由于运营需求,要修改为Win安装包。方案还是比较多的:1.WPF-Webview由于目前只需要兼容win,所以可以选择WPF,但WPF需要WebView的,还需要本地架设服务。整体部署比较复杂以及需要熟悉C#与WPF相关开发。2.......
  • vue3 使用 setup 语法糖时,keep-alive 缓存使用 include / exclude 获取组件名
    <template><router-viewv-slot="{Component,route}"><keep-alive:include="['ComponentName']"><component:is="Component":key="route.name"/></keep-alive>......
  • Vue【原创】数据可视化,复合数字形式展示
    做数据可视化的时候,经常碰到需要很灵活的数字形式展示。先上个效果图: 如图包括名称,数量,别名,单位,上升下降,环比等等的复合数据展示,并且需要支持样式灵活配置。此组件包括2个模块,父容器组件box-group,其中每一项的子组件box。 父组件box-group1<template>2<divcl......
  • vue3 报错:husky - pre-commit hook exited with code 1 (error)
    问题:git提交不上去解决方法:   "format":"prettier--write\"./**/*.{html,vue,ts,js,json,md}\"",......
  • 找不到模块“../view/Home.vue”或其相应的类型声明。
    环境:vue3+ts解决办法:在src目录里面添加env.d.ts文件,在文件里贴上declaremodule'*.vue'{importtype{DefineComponent}from'vue'constcomponent:ComponentOptions|ComponentOptions['setup']exportdefaultcomponent} ......
  • VUE input允许数字 且两位小数
    页面:<[email protected]="onlyNumber()"placeholder="请输入(整数或者小数)金额"v-model="form.ysje"></el-input>方法:onlyNumber(){this.form.ysje=this.onlyNumOnePoint(this.form.ysje);},onlyNumOnePoint(number_on......