前面寫過一次loading組件的js組件使用:
elementUI提供了loading組件的簡便使用:
1、在table等組件上綁定指令:v-loading="loading",然后通過控制變量loading的值為true或false,切換顯示和隱藏
<el-table v-loading="loading">
2、在使用指令的基礎上,自定義加載文案、圖標和背景色:
<el-table v-loading="loading" element-loading-text="拼命加載中" element-loading-spinner="el-icon-loading" element-loading-background="rgba(0, 0, 0, 0.8)" :data="tableData">
3、以上都是給單個的組件添加loading條,如果要給整頁進行加載:fullscreen修飾符將遮罩插入到body上,lock修飾符鎖定屏幕滾動
<el-button v-loading.fullscreen.lock="fullscreenLoading">指令方式</el-button>
4、整頁加載可以使用服務的方式,遮罩默認為全屏,不需要額外設置修飾符fullscreen:
<el-button @click="handleClick">服務方式</el-button>
handleClick() { const loading = this.$loading({ lock: true, text: 'Loading', spinner: 'el-icon-loading', background: 'rgba(0, 0, 0, 0.7)' }); setTimeout(() => { loading.close(); }, 2000); }
5、配合axios做全局的設置:
實際項目中發現,如果某個頁面請求多個接口,且每個接口都返回很慢的話,實際看到的效果是雖然Loading會出現,但是當第一個接口返回值以后后面的Loading都不會出現了,就會出現頁面數據從無到有的過濾,用戶體驗較差。
原來,是因為elementUI的全屏Loading是單例的:如果前一個Loading關閉之前再次調用了下一個Loading並不會創建一個新的實例,返回的仍然是當前這個Loading實例;同理,當調用任意一個close()方法都會關閉這個Loading實例。因為這幾個接口都是同一時間請求的,也就是說當前頁面幾個Loading實例其實都是同一個,所以關閉后也就都關閉了。
import axios from 'axios' import { Message, Loading } from 'element-ui' let instance = axios.create({ baseURL: '', timeout: 60000 }) /* 當頁面有兩個接口時,第一個接口loading的close事件會直接將第二個接口的loading實例也close */ let loadingInstance = null function startLoading () { loadingInstance = Loading.service({ fullscreen: true, text: '拼命加載中...', background: 'rgba(0, 0, 0, 0.8)' }) } function endLoading () { loadingInstance.close() } let needLoadingRequestCount = 0 function showFullScreenLoading () { if (needLoadingRequestCount === 0) { startLoading() } needLoadingRequestCount++ } function tryHideFullScreenLoading () { if (needLoadingRequestCount <= 0) return needLoadingRequestCount-- if (needLoadingRequestCount === 0) { endLoading() } } // 請求攔截 instance.interceptors.request.use((config) => { showFullScreenLoading() return config }, (error) => { tryHideFullScreenLoading() Message.error({message: '請求超時!'}) return Promise.reject(error) }) // 響應攔截 instance.interceptors.response.use((response) => { tryHideFullScreenLoading() if (response.data && response.data.code && response.data.code === 200) { return response.data } else { Message({ message: response.data.msg || '接口錯誤', type: 'error' }) } }, (error) => { tryHideFullScreenLoading() return Promise.reject(error) }) export default instance
每次創建Loading實例的時候判斷當前是否存在,如果當前還沒有Loading實例就創建一個,如果有就不會再創建而是計數;每次關閉的時候判斷當前的計數,如果是0了就關閉,否則也計數減一,直到為0的時候表示當前所有頁面所有接口都返回結束了,此時執行關閉Loading.close()操作關閉菊花。
service()中沒有參數對象時,

有參數對象時,
loadingInstance = Loading.service({ fullscreen: true, text: '拼命加載中...', background: 'rgba(0, 0, 0, 0.8)' })