首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >vue 自定义MessageBox 消息框组件

vue 自定义MessageBox 消息框组件

作者头像
用户9914333
发布2022-07-22 15:01:33
发布2022-07-22 15:01:33
2.5K0
举报
文章被收录于专栏:bug收集bug收集

封装一个类似elementui 的message ;

通过js this.$message() , 能显示一个消息组件 ; 所需知识点:

1. Vue.extend() 2. render函数,h函数 3. install 方法,及use() 方法 一、Vue.extend()

可以使用Vue.extend 创建一个构造器,extend 创建的是Vue 构造器,而不是我们平时常写的组件实例。 代码如下:

代码语言:javascript
复制
// 创建构造器
var Profile = Vue.extend({  
template: '<p>pw_firstName pw_lastName aka pw_alias</p>',  
data: function () {
return {
      firstName: 'Walter',
      lastName: 'White',
       alias: 'Heisenberg'    
      }  
 }
 })

 // 创建 Profile 实例,并挂载到一个元素上。
 new Profile().$mount('#mount-point')

需要通过 new Profile().$mount('#mount-point') 来挂载到指定的元素上。或者 new Profile( {el: "#app" })

总结: Vue.extend 的作用,就是基于 Vue 构造器,创建一个‘ 子类 ',它的参数跟new Vue的基本一样,但data要跟组件一样,是个函数,再配合$mount,就可以渲染组件,并且挂载到任意指定的节点上 二、render函数,h函数 vue2.0新增了render方法,官方案例写的是:

代码语言:javascript
复制
render: h=>h(app)

其中 h 是由 createElement 方法演变而来

代码语言:javascript
复制
render: function(createElement){
    return createElement(app)
}

用 es6 的写法就是:(只有一个个return语句,可以省略return和{})

代码语言:javascript
复制
render: createElement=>createElement(app)

将createElement改成 h 就是官方写法。

使用 h 的理由,官方解释是:

It comes from the term “hyperscript”, which is commonly used in many virtual-dom implementations. “Hyperscript” itself stands for “script that generates HTML structures” because HTML is the acronym for “hyper-text markup language”.

它来自单词 hyperscript,这个单词通常用在 virtual-dom 的实现中。Hyperscript 本身是指 生成HTML 结构的 script 脚本,因为 HTML 是 hyper-text markup language 的缩写(超文本标记语言)

createElement 用来生成 HTML DOM 元素,也就是上文中的 generate HTML structures,也就是 Hyperscript,所以用 h 替代了 createElement 。 三、install() 方法与use() 方法 vue提供install可供我们开发新的插件及全局注册组件等 install 方法第一个参数是vue的构造器,第二个参数是可选的选项对象

代码语言:javascript
复制
export default {
    install(Vue,option){
        组件
        指令
        混入
        挂载vue原型
    }
}

示例:全局注册组件

代码语言:javascript
复制
import PageTools from '@/components/PageTools/pageTools.vue'
import update from './update/index.vue'
import ImageUpload from './ImageUpload/ImageUpload.vue'

export default {

  install(Vue) {
    Vue.component('PageTools', PageTools)
    Vue.component('update', update)
    Vue.component('ImageUpload', ImageUpload)
  }
}

在main.js中直接用引用并Vue.use进行注册

代码语言:javascript
复制
import Component from '@/components'
Vue.use(Component)

当调用Vue.use()方法时,就会执行install() 这个方法

四、 messageBox 代码解析

1. MessageBox 组件代码 , MessageBox.vue

template内容

代码语言:javascript
复制
<template>
    <div :class="['message-box',type]">
        <div class="inner">
            <header class="header">
                <h1 class="title">{{ title }}</h1>
                <span class="close-btn" @click="$messageBox.hide()">x</span>
            </header>
            <div class="content">
               {{ content }}
            </div>
        </div>
    </div>
</template>

script 内容

代码语言:javascript
复制
<script>
    export default {
        name: "MessageBox",
        props:{
            title:{
                type:String,
                default:"This is TITLE"
            },
            content:{
                type:String,
                default:"This is CONTENT"
            },
            type:{
                type:String,
                default:'primary',
                validator(value) {
                    return [
                        'primary',
                        'success',
                        'warn',
                        'danger'
                    ].includes(value);
                }
            }
        }
    }
</script>

style 样式代码就不公布了; 2. 暴露messageBox的 index.js 代码,最主要的核心代码

代码语言:javascript
复制
import _MessageBox from "./MessageBox";
export default {
    install(Vue){
        let messageBox = null; //保证只创建一个messageBox
        // 注册组件
        Vue.component(_MessageBox.name,_MessageBox);
        // 原型上添加方法
        Vue.prototype.$messageBox = {
            show,
            hide,
            primary,
            success,
            warn,
            danger
        }
        function show(props,callback) {
          if(!messageBox){
              const MessageBox = Vue.extend({
                  render(h){
                      return h('message-box',{props})
                  }
              })
              messageBox = new MessageBox();
              this.vm = messageBox.$mount(); //挂载方法会返回一个MessageBox实例对象
              document.body.appendChild(this.vm.$el);
              callback && callback();
          }
        }
        function hide() {
           document.body.removeChild(this.vm.$el);
           messageBox.$destroy();
           messageBox=null;
           this.vm = null;
        }
        function primary(props,callback){
            this.show({...props,type:'primary'},callback)
        }
        function success(props,callback){
            this.show({...props,type:'success'},callback)
        }
        function warn(props,callback){
            this.show({...props,type:'warn'},callback)
        }
        function danger(props,callback){
            this.show({...props,type:'danger'},callback)
        }
    }
};

3. 导出所有组件的接口文件

代码语言:javascript
复制
import store from './store'
import {MessageBox} from './components/MyUI';
Vue.config.productionTip = false
Vue.use(MessageBox); //当调用Vue.use()方法时,就会执行install() 这个方法
new Vue({
  router,
  store,
  render: h => h(App)
}).$mount('#app')

4. main.js 引用

代码语言:javascript
复制
import store from './store'
import {MessageBox} from './components/MyUI';
Vue.config.productionTip = false
Vue.use(MessageBox); //当调用Vue.use()方法时,就会执行install() 这个方法
new Vue({
  router,
  store,
  render: h => h(App)
}).$mount('#app')

5. 组件中,使用 使用 this.$messageBox调用对应的方法,即可以显示对应的组件;

代码语言:javascript
复制
<template>
  <div id="app">
    <div>
      <button @click="show">show</button>
      <button @click="primary">primary</button>
      <button @click="danger">danger</button>
      <button @click="warn">warn</button>
      <button @click="success">success</button>
    </div>
  </div>
</template>
<script>
  export default {
    name:"App",
    methods:{
      show(){
        this.$messageBox.show({
          type:'primary'
        })
      },
      primary(){
        this.$messageBox.primary({
          title:"doubleyong",
          content:"content"
        })
      },
      danger(){
        this.$messageBox.danger({
          title:'doubleyong',
          content:'下班了'
        })
      },
      warn(){
        this.$messageBox.warn({
          title:'doubleyong',
          content:'下班了'
        })
      },
      success(){
        this.$messageBox.success({
          title:'doubleyong',
          content:'下班了'
        })
      }
    }
  }
</script>

代码下载:

http://bugshouji.com/zhuopingweb/t1571

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2022-06-09,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 bug收集 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档