最近在做微信小程序,發(fā)現(xiàn)很多頁面都有一種特點(diǎn):在onLoad里異步發(fā)送HTTP請(qǐng)求加載數(shù)據(jù)叭披。默認(rèn)的界面是wxml中定義好的模板寥殖,如果斷網(wǎng)或者網(wǎng)速較慢就會(huì)一直卡在這里玩讳,界面看起來不太友好。
所以需要加入一個(gè)加載中的提示嚼贡,成功加載后再切換回來熏纯。使用wx.showLoading等API無法完全遮擋后面突兀的模板,所以要在wxml中寫一些界面的代碼才可以完成這項(xiàng)需求粤策。
如果在每個(gè)page的wxml中都寫一次這種代碼樟澜,工作量非常大,后期重構(gòu)也不方便叮盘,所以本文提供了一種使用template的方式秩贰,復(fù)用這段代碼。需要切換狀態(tài)的時(shí)候直接在js中一行代碼pageState.xxx()
即可柔吼。
下面是演示圖片毒费,具體的內(nèi)容可以定制,比如做一個(gè)加載動(dòng)畫愈魏。
使用方法
在需要的page的wxml文件開頭加入兩行代碼:
<!--pages/xxxxxx.wxml-->
<import src="/utils/pageState/index.wxml" />
<template is="pageState" data="{{...pageState}}" />
<!-- 這里是原來頁面的內(nèi)容 -->
<!-- <view class="container"> -->
在需要的page的js文件中使用:
import pageState from '這里寫js文件的路徑'
Page({
// ...
getXXXXX(xxxxx) {
const pageState = pageState(this)
pageState.loading() // 切換為loading狀態(tài)
api.getXXXXX(xxxxx) // 異步請(qǐng)求
.then((res) => {
// 更新界面...
pageState.finish() // 切換為finish狀態(tài)
})
.catch(err => {
pageState.error() // 切換為error狀態(tài)
})
},
// ...
模板代碼
wxml
這里定義了模板觅玻,根據(jù)狀態(tài)判斷是否顯示以及顯示那種狀態(tài):
<!-- utils/pageState/index.wxml -->
<template name="pageState">
<view class="page-state-container" wx:if="{{state != 'finish'}}">
<view class="page-state-empty page-state-center" wx:if="{{state == 'empty'}}">
<icon type="info" size="70" />
<view class="message">{{message}}</view>
</view>
<view class="page-state-loading page-state-center" wx:if="{{state == 'loading'}}">
<icon type="waiting" size="70" />
<view class="message">{{message}}</view>
</view>
<view class="page-state-error page-state-center" wx:if="{{state == 'error'}}">
<icon type="warn" size="70" />
<view class="message">{{message}}</view>
<button class="retrybtn" type="warn" catchtap="onRetry">重試</button>
</view>
</view>
</template>
這里使用了兩個(gè)變量:state
和message
,表示當(dāng)前的狀態(tài)和提示信息培漏。
這里注意必須在使用此模板的page中定義onRetry溪厘,即異步加載數(shù)據(jù)的代碼,才可以使用重試按鈕牌柄。
wxss
接著定義樣式:
<!-- utils/pageState/index.wxss -->
.page-state-center {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
align-content: center;
height: 100%;
width: 100%;
}
.page-state-container {
animation: fadein 2s 1 ease-out;
height: 100%;
width: 100%;
}
.page-state-container~view {
display: none;
}
page {
height: 100%;
overflow-y: auto;
}
這里我設(shè)置了一個(gè)漸入的動(dòng)畫畸悬,刪掉也沒關(guān)系。注意最后一個(gè).page-state-container~view
這里是將class為page-state-container
之后的view
全部隱藏友鼻。如果模板之后想隱藏的不是view可以定義一個(gè)新class傻昙。我一般都用view作為container,所以這里就直接寫了view彩扔。為了使內(nèi)容豎直居中妆档,我將所有頁面都設(shè)置了最小高度為100%,暫時(shí)還沒發(fā)現(xiàn)什么副作用虫碉,發(fā)現(xiàn)的朋友可以在評(píng)論中指出贾惦。
最后把它導(dǎo)入到app.wxss中,以便在全局范圍內(nèi)使用敦捧。
/**app.wxss**/
@import 'utils/pageState/index.wxss';
js
// utils/pageState/index.js
const loading = (that) => {
return () => {
that.setData({
pageState: {
state: 'loading',
message: '加載中'
}
})
}
}
const error = (that, message) => {
return (message = '請(qǐng)檢查您的網(wǎng)絡(luò)連接') => {
that.setData({
pageState: {
state: 'error',
message
}
})
}
}
const empty = (that, message) => {
return (message = '空空如也') => {
that.setData({
pageState: {
state: 'empty',
message
}
})
}
}
const finish = (that) => {
return () => {
that.setData({
pageState: {
state: 'finish',
message: ''
}
})
}
}
export default (that) => {
return {
loading: loading(that),
error: error(that),
empty: empty(that),
finish: finish(that)
}
}