1. 程式人生 > 其它 >vue資料未載入完成前顯示loading遮罩

vue資料未載入完成前顯示loading遮罩

目的

在前後端分離專案中,由於頁面請求和資料請求並非同步,所以導致頁面和資料不能同時渲染,因此在實際過程中往往採用SSR即服務端渲染或者請求資料時採用遮罩(載入中)的方式提升使用者體驗。
下面我將使用loading遮罩的方式實現更加友好的資料載入

參考

https://codepen.io/bartezic/pen/ByqeNq

效果

程式碼

  1. 在App.vue中新增一個<div>
<div>
    <div id="appLoading">
      <div class='lmask'></div>
    </div>
<div id="app"> <router-view v-if="isRouterAlive"/> </div> </div>
  1. 以下是CSS樣式

.lmask {
  position: absolute;
  height: 100%;
  width: 100%;
  background-color: #000;
  bottom: 0;
  left: 0;
  right: 0;
  top: 0;
  z-index: 9999;;
  opacity: 0.4;
  &.fixed
{ position: fixed; } &:before { content: ''; background-color: rgba(0,0,0,0); border: 5px solid rgba(0,183,229,0.9); opacity: .9; border-right: 5px solid rgba(0,0,0,0); border-left: 5px solid rgba(0,0,0,0); border-radius: 50px; box-shadow: 0 0 35px #2187e7; width: 50px;
height: 50px; -moz-animation: spinPulse 1s infinite ease-in-out; -webkit-animation: spinPulse 1s infinite linear; margin: -25px 0 0 -25px; position: absolute; top: 50%; left: 50%; } &:after { content: ''; background-color: rgba(0,0,0,0); border: 5px solid rgba(0,183,229,0.9); opacity: .9; border-left: 5px solid rgba(0,0,0,0); border-right: 5px solid rgba(0,0,0,0); border-radius: 50px; box-shadow: 0 0 15px #2187e7; width: 30px; height: 30px; -moz-animation: spinoffPulse 1s infinite linear; -webkit-animation: spinoffPulse 1s infinite linear; margin: -15px 0 0 -15px; position: absolute; top: 50%; left: 50%; } } @-moz-keyframes spinPulse { 0% { -moz-transform:rotate(160deg); opacity: 0; box-shadow: 0 0 1px #2187e7; } 50% { -moz-transform: rotate(145deg); opacity: 1; } 100% { -moz-transform: rotate(-320deg); opacity: 0; } } @-moz-keyframes spinoffPulse { 0% { -moz-transform: rotate(0deg); } 100% { -moz-transform: rotate(360deg); } } @-webkit-keyframes spinPulse { 0% { -webkit-transform: rotate(160deg); opacity: 0; box-shadow: 0 0 1px #2187e7; } 50% { -webkit-transform: rotate(145deg); opacity: 1; } 100% { -webkit-transform: rotate(-320deg); opacity: 0; } } @-webkit-keyframes spinoffPulse { 0% { -webkit-transform: rotate(0deg); } 100% { -webkit-transform: rotate(360deg); } }
  1. 此時遮罩層顯示,我們需要當App載入完成後取消遮罩層,即display: none
	document.getElementById('app').style.display = 'block';
	document.getElementById('appLoading').style.display = 'none';
  1. 如何在我們需要的地方呼叫呢
    我採用的方法是寫一個loading和loaded函式,在分別在請求資料前和請求資料完成後呼叫,因為該功能可能會重複的使用,所以將其封裝成為一個可以複用的模組
    在App.vue中寫兩個方法:
	provide() {
	    return {
	      loading: this.loading,
	      loaded: this.loaded
	    }
	  },
	  methods: {
		loading() {
		      document.getElementById('app').style.display = 'block';
		      document.getElementById('appLoading').style.display = 'block';
		},
	    loaded() {
	      document.getElementById('app').style.display = 'block';
	      document.getElementById('appLoading').style.display = 'none';
	    }
	  }
	

上面將這兩個函式給暴露了出來,在我們需要的地方inject就好
5. 在需要使用的地方呼叫

export default {
  inject: ['loading', 'loaded'],
  name: "index",
  created() {
    this.getData()
  },
  methods: {
    getData() {
      this.loading()
      getUserInfo().then(res => {
        this.userInfo = res.data
      }).finally(() => {
        this.loaded()
      })
    }
  }
}
  1. 完成

總結

實現思路非常簡單,就是請求資料之前將遮罩顯示,載入資料完成後將遮罩隱藏,解決這個問題肯定有非常多的辦法,如果你有更好的方法,請在評論區留言。