Vue自定义实现Element-ui中Message组件

原文

创建message.vue文件

首先创建message.vue来规定message组件显示的内容

<template>
  <transition name="message-fade">
    <div v-if="visible"
         :class="wrapClasses">
      <img class="message_img"
           :src="typeImg" />
      <span>{{message}}</span>
    </div>
  </transition>
</template>
<script>
const prefixCls = 'message'
export default {
  name: 'message',
  data () {
    return {
      visible: false,
      type: 'info',
      message: '',
      duration: 3000
    }
  },
  computed: {
    typeImg () {
      return require(`../../assets/${this.type}.svg`);
    },
    wrapClasses () {
      return [
        `${prefixCls}`,
        `${prefixCls}-${this.type}`
      ]
    }
  },
  mounted () {
    // 挂载的时候就开始计时,3000ms后消失
    this.setTimer()
  },
  methods: {
    setTimer () {
      setTimeout(() => {
        // 3000ms之后调用关闭方法
        this.handleClose()
      }, this.duration)
    },
    handleClose () {
      this.visible = false
      // 从DOM里将这个组件移除  
      // visible只是控制了显示与隐藏  但是dom结构中还是存在组件  为了避免消耗内存必须销毁组件
      setTimeout(() => {
        this.$el.parentNode.removeChild(this.$el)
      }, 500)
    }
  },
}
</script>
<style>
.message-fade-enter-active,
.message-fade-leave-active {
  transition: all 0.3s ease;
}
.message-fade-enter, .message-fade-leave-to /* .fade-leave-active below version 2.1.8 */ {
  transform: translateY(-20px);
  opacity: 0;
}
.message {
  position: fixed;
  top: 30px;
  right: 39%;
  width: 22%;
  border-radius: 4px;
  padding: 13px 18px;
  color: #616060;
  font-size: 18px;
  line-height: 28px;
  display: flex;
  align-items: center;
}
.message_img {
  width: 18px;
  margin-right: 6px;
}
.message-success {
  background: #dcffefd3;
  color: rgb(48, 194, 104);
}
.message-info {
  background: #2db7f5;
}
.message-warning {
  background: #ffdec9;
  color: #ecae51;
}
.message-error {
  background: #ffe2e2;
  color: rgb(255, 108, 108);
}
</style>

创建message.js文件

在组件中没有props接收参数,那么如何给message组件传参,这就需要一个message.js文件去管理message.vue组件。

import Vue from 'vue'
// 直接将Vue组件作为Vue.extend的参数
const constructor = Vue.extend(require('./message.vue').default)

// import message from "./message.vue"
// const constructor = Vue.extend(message) 

let nId = 1

const Message = (options) => {
  let id = 'notice-' + nId++;
  options = options || {};

  console.log("options",options);

  // 如果只传入字符串,将其设置为显示的信息
  // 形如这种调用方式 this.$message("message")
  if (typeof options === 'string') {
    options = {
      // 这里的message就是message.vue中data中的message
      message: options
    };
  }

  // 创建实例 
  // this.$message({
  //   message: '警告哦,这是一条警告消息',
  //   type: 'warning'
  // });
  const instance = new constructor({
    data:options//重点:在这里将你传过来的参数匹配到message.vue组件的data
  }) 

  console.log("instance",instance);

  instance.id = id;
  instance.$mount(); // 挂载但是并未插入dom,是一个完整的Vue实例
  document.body.appendChild(instance.$el) // 将dom插入body
  instance.visible = true   //这里修改message.vue数据中的visible,这样message组件就显示出来

  return instance
};

//同element-ui一样,在给Message绑定四个方法,直接调用
['success', 'warning', 'info', 'error'].forEach(type => {
    Message[type] = options => {
      if (typeof options === 'string') {
        options = {
          message: options
        };
      }
      options.type = type;
      return Message(options);
    };
  });

export default  Message;

配置全局方法

在最后在入口文件main.js中引用message.js并添加Vue实例方法

import Message from './components/message/message.js'
Vue.prototype.$message = Message;

组件的使用方式

this.$message("message")
this.$message({
  message: '警告哦,这是一条警告消息',
  type: 'warning'
});

this.$message.success("success")
this.$message.info("info")
this.$message.error("error")
this.$message.warning("warning")
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值