全局Loading插件

1,867 阅读2分钟

场景:我们在项目中会调用很多后台接口,但是有一些请求时间过长的接口需要一个过渡状态展示给客户,我们通常会给点击的那个按钮去设置一个loading或者disabled状态,所以我们可以在axios的请求拦截器和返回拦截器中直接设置全局loading状态

loading插件代码如下:

//loading.js
/*
* 可以自己找不同的loading图传入组件
* imagePath在main.js注册时候传入的loading动图
* 如:'./static/image/loading.gif'
* */
const install = ( Vue, imagePath ) => {
  Vue.$loading = Vue.prototype.$loading = {
    //loading状态显示方法
    show(){
      let loadingBox = document.getElementById('loading-box');
      //先判断是否有遮罩层,如果有直接插入loading图,没有则先插入遮罩层
      if (loadingBox) {
        loadingBox.style.display = 'flex';
        loadingBox.innerHTML = `
          <img src=${ imagePath } alt="">
        `;
      } else {
        let box = document.createElement('div');
        box.id = 'loading-box';
        document.getElementById('app').appendChild(box);
        loadingBox = document.getElementById('loading-box');
        if (loadingBox) {
          loadingBox.style.display = 'flex';
          loadingBox.innerHTML = `
          <img src=${ imagePath } alt="">
        `;
        }
      }
    },
    //loading状态隐藏方法
    hide(){
      let loadingBox = document.getElementById('loading-box');
      if (loadingBox) {
        loadingBox.parentNode.removeChild(loadingBox);
      }
    }
  };
};
/*
* 注:对外暴露的函数名必须为install,当用Vue.use全局引用注册的时候会默认调用install方法
* 也可以写成
* const Loading = {
*  install: (Vue, imagePath)=>{
*    Vue.$loading = Vue.prototype.$loading = {
*      //......
*    }
*   }
* };
* export default {
*   Loading
* }
* */
export default {
  install
}

写好插件方法后需要在main.js项目的入口文件中进行引入和注册,代码如下:

const myLoading = require('vue-axios-loading');
//loading图存储目录,依据打包后dist文件夹层级结构设置相对路径
const src = './static/image/loading.gif';
Vue.use(myLoading, src);

最后在main.css主样式表里设置loading遮罩层的样式,代码如下:

#loading-box {
  display: flex;
  justify-content: center;
  align-items: center;
  z-index: 99999;
  position: absolute;
  top: 0;
  background-color: rgba(0,0,0,0.2);
  height: 100%;
  width: 100%;
}

这里用了最简单的flex布局居中,如果项目中不使用flex布局,大家也可以自己写居中样式

最后调用,如果在组件中调用我们可以直接使用this.$loading.show()this.$loading.hide()进行调用,因为在组件中this指向默认为Vue实例本身,但是如果在axios拦截器中使用时需要先对Vue进行引入,然后new出一个实例,代码如下:

import Vue from 'vue'
const vm = new Vue();
//拦截器调用方法及位置
//在请求拦截器中开启loading
axios.interceptors.request.use(
  response => {
    //......项目业务处理代码
    vm.$loading.show();
    return response
  },
  err => {
    return Promise.reject(err)
  }
);
//响应拦截器中关闭loading
axios.interceptors.response.use(
  config => {
    //......项目业务处理代码
    vm.$loading.hide();
    return config
  },
  err => {
    //......项目业务处理代码
    vm.$loading.hide();
    return Promise.reject(err)
  }
);

附带一个loading图:

项目地址:github.com/Naruto0623/…

最后给大家分享两个免费的loading图下载地址:

1、loading图免费下载

2、在线制作loading图