视频1 视频21 视频41 视频61 视频文章1 视频文章21 视频文章41 视频文章61 推荐1 推荐3 推荐5 推荐7 推荐9 推荐11 推荐13 推荐15 推荐17 推荐19 推荐21 推荐23 推荐25 推荐27 推荐29 推荐31 推荐33 推荐35 推荐37 推荐39 推荐41 推荐43 推荐45 推荐47 推荐49 关键词1 关键词101 关键词201 关键词301 关键词401 关键词501 关键词601 关键词701 关键词801 关键词901 关键词1001 关键词1101 关键词1201 关键词1301 关键词1401 关键词1501 关键词1601 关键词1701 关键词1801 关键词1901 视频扩展1 视频扩展6 视频扩展11 视频扩展16 文章1 文章201 文章401 文章601 文章801 文章1001 资讯1 资讯501 资讯1001 资讯1501 标签1 标签501 标签1001 关键词1 关键词501 关键词1001 关键词1501 专题2001
vue 自定义提示框(Toast)组件的实现代码
2020-11-27 22:09:41 责编:小采
文档


1.自定义 提示框 组件

src / components / Toast / index.js

/**
 * 自定义 提示框( Toast )组件
 */
var Toast = {};
var showToast = false, // 存储toast显示状态
 showLoad = false, // 存储loading显示状态
 toastVM = null, // 存储toast vm
 loadNode = null; // 存储loading节点元素
 
Toast.install = function (Vue, options) {
 // 参数
 var opt = {
 defaultType: 'bottom',
 duration: '2500',
 wordWrap: false
 };
 for (var property in options) {
 opt[property] = options[property];
 }
 
 Vue.prototype.$toast = function (tips, type) {
 
 var curType = type ? type : opt.defaultType;
 var wordWrap = opt.wordWrap ? 'lx-word-wrap' : '';
 var style = opt.width ? 'style="width: ' + opt.width + '"' : '';
 var tmp = '<div v-show="show" :class="type" class="lx-toast ' + wordWrap + '" ' + style + '>{{tip}}</div>';
 
 if (showToast) {
 // 如果toast还在,则不再执行
 return;
 }
 if (!toastVM) {
 var toastTpl = Vue.extend({
 data: function () {
 return {
 show: showToast,
 tip: tips,
 type: 'lx-toast-' + curType
 }
 },
 template: tmp
 });
 toastVM = new toastTpl()
 var tpl = toastVM.$mount().$el;
 document.body.appendChild(tpl);
 }
 toastVM.type = 'lx-toast-' + curType;
 toastVM.tip = tips;
 toastVM.show = showToast = true;
 
 setTimeout(function () {
 toastVM.show = showToast = false;
 }, opt.duration)
 };
 
 ['bottom', 'center', 'top'].forEach(function (type) {
 Vue.prototype.$toast[type] = function (tips) {
 return Vue.prototype.$toast(tips, type)
 }
 });
 
 Vue.prototype.$loading = function (tips, type) {
 if (type == 'close') {
 loadNode.show = showLoad = false;
 } else {
 if (showLoad) {
 // 如果loading还在,则不再执行
 return;
 }
 var loadTpl = Vue.extend({
 data: function () {
 return {
 show: showLoad
 }
 },
 template: '<div v-show="show" class="lx-load-mark"><div class="lx-load-box"><div class="lx-loading"><div class="loading_leaf loading_leaf_0"></div><div class="loading_leaf loading_leaf_1"></div><div class="loading_leaf loading_leaf_2"></div><div class="loading_leaf loading_leaf_3"></div><div class="loading_leaf loading_leaf_4"></div><div class="loading_leaf loading_leaf_5"></div><div class="loading_leaf loading_leaf_6"></div><div class="loading_leaf loading_leaf_7"></div><div class="loading_leaf loading_leaf_8"></div><div class="loading_leaf loading_leaf_9"></div><div class="loading_leaf loading_leaf_10"></div><div class="loading_leaf loading_leaf_11"></div></div><div class="lx-load-content">' + tips + '</div></div></div>'
 });
 loadNode = new loadTpl();
 var tpl = loadNode.$mount().$el;
 
 document.body.appendChild(tpl);
 loadNode.show = showLoad = true;
 }
 };
 
 ['open', 'close'].forEach(function (type) {
 Vue.prototype.$loading[type] = function (tips) {
 return Vue.prototype.$loading(tips, type)
 }
 });
}
 
// 向外暴露接口
module.exports = Toast;

src / components / Toast / toast.css

/**
 * Toast 样式
 */
.lx-toast {
 position: fixed;
 bottom: 100px;
 left: 50%;
 box-sizing: border-box;
 max-width: 80%;
 height: 40px;
 line-height: 20px;
 padding: 10px 20px;
 transform: translateX(-50%);
 -webkit-transform: translateX(-50%);
 text-align: center;
 z-index: 9999;
 font-size: 14px;
 color: #fff;
 border-radius: 5px;
 background: rgba(0, 0, 0, 0.7);
 animation: show-toast .5s;
 -webkit-animation: show-toast .5s;
 overflow: hidden;
 text-overflow: ellipsis;
 white-space: nowrap;
}
 
.lx-toast.lx-word-wrap {
 width: 80%;
 white-space: inherit;
 height: auto;
}
 
.lx-toast.lx-toast-top {
 top: 50px;
 bottom: inherit;
}
 
.lx-toast.lx-toast-center {
 top: 50%;
 margin-top: -20px;
 bottom: inherit;
}
 
@keyframes show-toast {
 from {
 opacity: 0;
 transform: translate(-50%, -10px);
 -webkit-transform: translate(-50%, -10px);
 }
 to {
 opacity: 1;
 transform: translate(-50%, 0);
 -webkit-transform: translate(-50%, 0);
 }
}
 
.lx-load-mark {
 position: fixed;
 left: 0;
 top: 0;
 width: 100%;
 height: 100%;
 z-index: 9999;
}
 
.lx-load-box {
 position: fixed;
 z-index: 3;
 width: 7.6em;
 min-height: 7.6em;
 top: 180px;
 left: 50%;
 margin-left: -3.8em;
 background: rgba(0, 0, 0, 0.7);
 text-align: center;
 border-radius: 5px;
 color: #FFFFFF;
}
 
.lx-load-content {
 margin-top: %;
 font-size: 14px;
}
 
.lx-loading {
 position: absolute;
 width: 0px;
 left: 50%;
 top: 38%;
}
 
.loading_leaf {
 position: absolute;
 top: -1px;
 opacity: 0.25;
}
 
.loading_leaf:before {
 content: " ";
 position: absolute;
 width: 9.14px;
 height: 3.08px;
 background: #d1d1d5;
 box-shadow: rgba(0, 0, 0, 0.0980392) 0px 0px 1px;
 border-radius: 1px;
 -webkit-transform-origin: left 50% 0px;
 transform-origin: left 50% 0px;
}
 
.loading_leaf_0 {
 -webkit-animation: opacity-0 1.25s linear infinite;
 animation: opacity-0 1.25s linear infinite;
}
 
.loading_leaf_0:before {
 -webkit-transform: rotate(0deg) translate(7.92px, 0px);
 transform: rotate(0deg) translate(7.92px, 0px);
}
 
.loading_leaf_1 {
 -webkit-animation: opacity-1 1.25s linear infinite;
 animation: opacity-1 1.25s linear infinite;
}
 
.loading_leaf_1:before {
 -webkit-transform: rotate(30deg) translate(7.92px, 0px);
 transform: rotate(30deg) translate(7.92px, 0px);
}
 
.loading_leaf_2 {
 -webkit-animation: opacity-2 1.25s linear infinite;
 animation: opacity-2 1.25s linear infinite;
}
 
.loading_leaf_2:before {
 -webkit-transform: rotate(60deg) translate(7.92px, 0px);
 transform: rotate(60deg) translate(7.92px, 0px);
}
 
.loading_leaf_3 {
 -webkit-animation: opacity-3 1.25s linear infinite;
 animation: opacity-3 1.25s linear infinite;
}
 
.loading_leaf_3:before {
 -webkit-transform: rotate(90deg) translate(7.92px, 0px);
 transform: rotate(90deg) translate(7.92px, 0px);
}
 
.loading_leaf_4 {
 -webkit-animation: opacity-4 1.25s linear infinite;
 animation: opacity-4 1.25s linear infinite;
}
 
.loading_leaf_4:before {
 -webkit-transform: rotate(120deg) translate(7.92px, 0px);
 transform: rotate(120deg) translate(7.92px, 0px);
}
 
.loading_leaf_5 {
 -webkit-animation: opacity-5 1.25s linear infinite;
 animation: opacity-5 1.25s linear infinite;
}
 
.loading_leaf_5:before {
 -webkit-transform: rotate(150deg) translate(7.92px, 0px);
 transform: rotate(150deg) translate(7.92px, 0px);
}
 
.loading_leaf_6 {
 -webkit-animation: opacity-6 1.25s linear infinite;
 animation: opacity-6 1.25s linear infinite;
}
 
.loading_leaf_6:before {
 -webkit-transform: rotate(180deg) translate(7.92px, 0px);
 transform: rotate(180deg) translate(7.92px, 0px);
}
 
.loading_leaf_7 {
 -webkit-animation: opacity-7 1.25s linear infinite;
 animation: opacity-7 1.25s linear infinite;
}
 
.loading_leaf_7:before {
 -webkit-transform: rotate(210deg) translate(7.92px, 0px);
 transform: rotate(210deg) translate(7.92px, 0px);
}
 
.loading_leaf_8 {
 -webkit-animation: opacity-8 1.25s linear infinite;
 animation: opacity-8 1.25s linear infinite;
}
 
.loading_leaf_8:before {
 -webkit-transform: rotate(240deg) translate(7.92px, 0px);
 transform: rotate(240deg) translate(7.92px, 0px);
}
 
.loading_leaf_9 {
 -webkit-animation: opacity-9 1.25s linear infinite;
 animation: opacity-9 1.25s linear infinite;
}
 
.loading_leaf_9:before {
 -webkit-transform: rotate(270deg) translate(7.92px, 0px);
 transform: rotate(270deg) translate(7.92px, 0px);
}
 
.loading_leaf_10 {
 -webkit-animation: opacity-10 1.25s linear infinite;
 animation: opacity-10 1.25s linear infinite;
}
 
.loading_leaf_10:before {
 -webkit-transform: rotate(300deg) translate(7.92px, 0px);
 transform: rotate(300deg) translate(7.92px, 0px);
}
 
.loading_leaf_11 {
 -webkit-animation: opacity-11 1.25s linear infinite;
 animation: opacity-11 1.25s linear infinite;
}
 
.loading_leaf_11:before {
 -webkit-transform: rotate(330deg) translate(7.92px, 0px);
 transform: rotate(330deg) translate(7.92px, 0px);
}
 
@-webkit-keyframes opacity-0 {
 0% {
 opacity: 0.25;
 }
 0.01% {
 opacity: 0.25;
 }
 0.02% {
 opacity: 1;
 }
 60.01% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.25;
 }
}
 
@-webkit-keyframes opacity-1 {
 0% {
 opacity: 0.25;
 }
 8.34333% {
 opacity: 0.25;
 }
 8.35333% {
 opacity: 1;
 }
 68.3433% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.25;
 }
}
 
@-webkit-keyframes opacity-2 {
 0% {
 opacity: 0.25;
 }
 16.6767% {
 opacity: 0.25;
 }
 16.6867% {
 opacity: 1;
 }
 76.6767% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.25;
 }
}
 
@-webkit-keyframes opacity-3 {
 0% {
 opacity: 0.25;
 }
 25.01% {
 opacity: 0.25;
 }
 25.02% {
 opacity: 1;
 }
 85.01% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.25;
 }
}
 
@-webkit-keyframes opacity-4 {
 0% {
 opacity: 0.25;
 }
 33.3433% {
 opacity: 0.25;
 }
 33.3533% {
 opacity: 1;
 }
 93.3433% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.25;
 }
}
 
@-webkit-keyframes opacity-5 {
 0% {
 opacity: 0.270958333333333;
 }
 41.6767% {
 opacity: 0.25;
 }
 41.6867% {
 opacity: 1;
 }
 1.67667% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.270958333333333;
 }
}
 
@-webkit-keyframes opacity-6 {
 0% {
 opacity: 0.375125;
 }
 50.01% {
 opacity: 0.25;
 }
 50.02% {
 opacity: 1;
 }
 10.01% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.375125;
 }
}
 
@-webkit-keyframes opacity-7 {
 0% {
 opacity: 0.479291666666667;
 }
 58.3433% {
 opacity: 0.25;
 }
 58.3533% {
 opacity: 1;
 }
 18.3433% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.479291666666667;
 }
}
 
@-webkit-keyframes opacity-8 {
 0% {
 opacity: 0.583458333333333;
 }
 66.6767% {
 opacity: 0.25;
 }
 66.6867% {
 opacity: 1;
 }
 26.6767% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.583458333333333;
 }
}
 
@-webkit-keyframes opacity-9 {
 0% {
 opacity: 0.687625;
 }
 75.01% {
 opacity: 0.25;
 }
 75.02% {
 opacity: 1;
 }
 35.01% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.687625;
 }
}
 
@-webkit-keyframes opacity-10 {
 0% {
 opacity: 0.791791666666667;
 }
 83.3433% {
 opacity: 0.25;
 }
 83.3533% {
 opacity: 1;
 }
 43.3433% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.791791666666667;
 }
}
 
@-webkit-keyframes opacity-11 {
 0% {
 opacity: 0.5958333333333;
 }
 91.6767% {
 opacity: 0.25;
 }
 91.6867% {
 opacity: 1;
 }
 51.6767% {
 opacity: 0.25;
 }
 100% {
 opacity: 0.5958333333333;
 }
}

2.全局引入

main.js

// 全局引入Toast
import './components/Toast/toast.css';
import Toast from './components/Toast/index';
Vue.use(Toast);

3.页面调用

Toast.vue

<!-- 提示框 -->

<template>

 <div>

 <!-- 标题栏 -->

 <mt-header title= "提示框" >

 <router-link to= "/" slot= "left" >

 <mt-button icon= "back" >返回</mt-button>

 </router-link>

 </mt-header>

 <!-- 内容 -->

 <button @click= "openTop()" >top</button>

 <button @click= "openCenter()" >center</button>

 <button @click= "openBottom()" >bottom</button>

 <button @click= "openLoading()" >loading</button>

 </div>

</template>

<script>

 export default {

 name: 'Toast' ,

 data(){

 return {

 //

 }

 },

 methods:{

 openTop(){

 this .$toast.top( 'top' );

 },

 openCenter(){

 this .$toast.center( 'center' );

 },

 openBottom(){

 this .$toast( 'bottom' ); // or this.$toast.bottom('bottom');

 },

 openLoading(){

 this .$loading( 'loading...' );

 let self = this ;

 setTimeout( function () {

 self.closeLoading()

 }, 2000)

 },

 closeLoading(){

 this .$loading.close();

 }

 }

 }

</script>

<style lang= "less" scoped>
 //
</style>

4.效果图

下载本文
显示全文
专题