在前端开发中很多中央都须要 loading, 上面咱们就看下如何在 vue 中实现一个全局的 loading 框,并且将其封装到 axios 中,实现发送申请时主动显示 loading 框,申请完结主动敞开 loading 框。
首先建一个 loading.vue 的页面
<template>
<div class="loadEffect _loadEffect">
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
<span></span>
</div>
</template>
<script>
export default {data() {return {};
}
};
</script>
<style lang=”scss” scoped>
.loadEffect {
width: 100px;
height: 100px;
position: relative;
margin: 0 auto;
top: -60%;
z-index: 9999;
span {
display: inline-block;
width: 20px;
height: 20px;
border-radius: 50%;
background: #Fa3;
position: absolute;
animation: load 1.04s ease infinite;
&:nth-child(1) {
left: 0;
top: 50%;
margin-top: -10px;
animation-delay: 0.13s;
}
&:nth-child(2) {
left: 14px;
top: 14px;
animation-delay: 0.26s;
}
&:nth-child(3) {
left: 50%;
top: 0;
margin-left: -10px;
animation-delay: 0.39s;
}
&:nth-child(4) {
top: 14px;
right: 14px;
animation-delay: 0.52s;
}
&:nth-child(5){
right: 0;
top: 50%;
margin-top: -10px;
animation-delay: 0.65s;
}
&:nth-child(6) {
right: 14px;
bottom:14px;
animation-delay: 0.78s;
}
&:nth-child(7) {
bottom: 0;
left: 50%;
margin-left: -10px;
animation-delay: 0.91s;
}
&:nth-child(8) {
bottom: 14px;
left: 14px;
animation-delay: 1.04s;
}
}
@keyframes load{
0% {transform: scale(1.2);
opacity: 1;
}
100% {transform: scale(.3);
opacity: 0.5;
}
}
}
</style>
为了不便调用,咱们须要把 loading 组件封装成可函数式调用的 API。
Vue.extend() 能够生成一个 Vue 的子类构造函数,因为 loading 组件自身是一个 vue 实例,将其作为参数生成一个子类构造函数,只有动静操作 loading 的挂载元素 el,便能够实现 loading 组件的函数式调用。创立 loading.js,实现如下:
import Vue from ‘vue’;
import loading from ‘./loading.vue’;
// 扩大实例结构器
const LoadingConstructor = Vue.extend(loading);
// 创立一个 vue 实例,挂载元素为新创建的 div
let initLoadingInstance = function () {
return new LoadingConstructor({el: document.createElement('div'),
});
}
// 删除 dom 节点
let removeDom = (node) => {if (node.parentNode) {
node.parentNode.removeChild(node);
}
};
let instance = initLoadingInstance();
// 敞开 loading
let closeLoading = () => {
removeDom(instance.$el)
};
// 展现 loading
let showLoading = function () {
document.body.appendChild(instance.$el);
}
export default {
showLoading,
closeLoading
}
这样只有通过调用函数 showLoading() 和 closeLoading() 就能够展现和敞开 loading 框了。实现了 loading 框的函数式调用,那么如何实现在申请发送开始时主动调用 loading 框,在申请完结主动敞开 loading 框呢,这就波及到申请和响应的拦挡。
axios 拦挡申请和响应
咱们应用 axios 作为 ajax 申请的解决框架,axios 反对申请的拦挡和响应,具体能够参见 axios 文档而后在 main.js 中引入 axios,在其申请拦截器中展现 loading 框,在响应拦截器中敞开 loading 框。代码如下:
// 引入 js
import loading from ‘./components/common/loading.js’
// 拦挡申请
axios.interceptors.request.use(function (config) {
// 在发送申请之前展现 loading
loading.showLoading()
console.log('申请拦挡')
return config;
}, function (error) {
// 对申请谬误做些解决
console.log('申请错误处理')
return Promise.reject(error);
});
// 拦挡响应
axios.interceptors.response.use(function (response) {
// 响应后敞开 loading
loading.closeLoading()
console.log('响应拦挡')
return response;
}, function (error) {
// 对响应谬误也要敞开 loading
loading.closeLoading()
console.log('响应谬误')
return Promise.reject(error);
});