目錄
(1)調整Order父組件結構(解決Bug)
之前在Vue項目實戰:訂單確認頁面實現中關於訂單父組件結構封裝裏寫到:在order.vue中引入<order-header></order-header>
,然後通過路由判斷當前頁面屬於哪個,並展示不同內容。但現在發現那樣子做存在一個問題:
問題:
在使用微信支付完後跳轉到訂單列表頁面,但是訂單列表頁面中的<order-header></order-header>
的內容仍是訂單支付頁面中<order-header></order-header>
的內容,沒有變成<order-header></order-header>
對應的內容。但是如果跳轉完訂單列表頁面,在重新刷新一下頁面,那<order-header></order-header>
的內容就會改變。
原因:
訂單列表的路由是order的子路由,當我們從order路由跳轉到它的子路由時,並不會再次執行order.vue中的mounted()函數。此函數只有在頁面渲染時纔會執行。也就是說,如果想用之前的方法,那只有在第一次從別的路由(比如購物車路由)跳轉到訂單列表路由時,此前order頁面並沒有被渲染過,則可以出現相應的<order-header></order-header>
組件內容。如果是從訂單訂單確認跳轉到訂單列表的話,此時沒有重新渲染order頁面,那<order-header></order-header>
內容不會改變。
解決方法:
不用之前的第二種方法,刪去之前路由判斷的代碼,而用第一次,在每個頁面中引入<order-header></order-header>
。
如,在orderConfirm.vue:
<order-header title="訂單確認">
<template v-slot:tip>
<span>請認真填寫收貨地址</span>
</template>
</order-header>
<script>
import OrderHeader from "./../components/OrderHeader";
export default {
components: {
OrderHeader,
}
}
(2)訂單列表數據渲染
在orderList.vue中:
<!-- 省略不重要代碼,下面是如何判斷並展示訂單狀態 -->
<div class="good-state fr" v-if="order.status == 20">
<a href="javascript:;">{{order.statusDesc}}</a>
</div>
<div class="good-state fr" v-else>
<a href="javascript:;" @click="goPay(order.orderNo)">{{order.statusDesc}}</a>
</div>
<script>
export default{
data() {
return {
list: []
}
},
mounted() {
this.getOrderList();
},
methods: {
getOrderList() {
this.axios.get('/orders').then((res) => {
this.list = res.list;
})
},
goPay(orderNo) {
//三種路由跳轉方式
this.$router.push({
path: '/order/pay',
query: {
orderNo
}
})
/* this.$router.push({
name: 'order-pay',
query: {
orderNo
}
})
*/
//this.$router.push('/order/pay')
}
}
}
</script>
(3)Loading 和 NoData優化
-
在orderList.vue中引入並使用之前定義的Loading組件:
這個優化是針對請求發出來,響應還沒回來前做個loading處理。在請求時顯示,請求回來後不顯示。
<loading v-if="loading"></loading> //3.使用組件
<script>
import Loading from './../components/Loading'; //1.導入組件
export default{
components:{
Loading //2.註冊組件
},
data() {
return {
loading: true
}
},
methods: {
getOrderList() {
this.axios.get('/orders').then((res) => {
this.loading = false;
this.list = res.list;
}).catch(() => {
this.loading = false;
})
}
}
-
NoData優化:
在訂單列表無數據時,顯示NoData組件,給用戶訂單列表爲空提示。
在components文件夾中新建NoData.vue:
<template>
<div class="no-data">
<img src="/imgs/icon-no-data.png" alt="">
<p>當前暫無提交的訂單記錄.</p>
</div>
</template>
<!--此處省略樣式等不重要代碼-->
在orderList.vue中引入並使用NoData組件:
<no-data v-if="!loading && list.length == 0"></no-data>
<script>
import NoData from './../components/NoData';
export default{
components:{
NoData
},
data() {
return {
list: [],
loading: true
}
},
methods: {
getOrderList() {
this.axios.get('/orders').then((res) => {
this.loading = false;
this.list = [] || res.list;
}).catch(() => {
this.loading = false;
})
},
}
}
(4)訂單列表分頁 - 分頁器
在orderList.vue中使用ElementUI中的Pagination組件:
<el-pagination
class="pagination"
background
layout="pre, pager, next"
:pageSize="pageSize"
:total="total"
@current-change="handleChange"
></el-pagination>
<script>
import {Pagination} from 'element-ui';
export default{
components:{
[Pagination.name]: Pagination
},
data() {
return {
list: [],
loading: false,
pageSize: 10, //每頁幾條數據
pageNum: 1, //當前是第幾頁
total: 0 //總條數
};
},
mounted() {
this.getOrderList();
},
methods: {
getOrderList() {
this.axios
.get("/orders", {
params: {
pageNum: this.pageNum
}
})
.then(res => {
this.loading = false;
this.list = [] || res.list;
this.total = res.total;
})
.catch(() => {
this.loading = false;
});
},
handleChange(pageNum) {
this.pageNum = pageNum;
this.getOrderList();
}
}
};
</script>
(5)訂單列表分頁 - 加載更多
在orderList.vue中使用ElementUI中的Button組件:
<div class="load-more" v-if="showNextPage">
<el-button type="primary" :loading="loading" @click="loadMore">加載更多</el-button>
</div>
<script>
import {Button} from 'element-ui';
export default{
components:{
[Button.name]: Button
},
data() {
return {
list: [],
loading: false,
pageSize: 10,
pageNum: 1,
showNextPage: true, //是否顯示按鈕,但數據都加載完了,就不需要顯示“加載更多”按鈕。
};
},
methods: {
getOrderList() {
this.axios
.get("/orders", {
params: {
pageNum: 10,
pageNum: this.pageNum
}
})
.then(res => {
this.loading = false;
this.list = res.list.concat(res.list); //數據累加
this.showNextPage = res.hasNext
})
.catch(() => {
this.loading = false;
});
},
loadMore() {
this.pageNum++;
this.getOrderList();
}
}
};
</script>
(6)訂單列表分頁 - 滾動加載
-
安裝該插件:
npm install vue-infinite-scroll --save
-
在orderList.vue中使用Vue中的vue-infinite-scroll插件:
<div class="scroll-more"
v-infinite-scroll="scrollMore"
infinite-scroll-disabled = "busy"
infinite-scroll-distance="410"
>
<img src="/imgs/loading-svg/loading-spinning-bubbles.svg" alt="" v-show="loading">
</div>
<script>
// v-infinite-scroll="scrollMore" :滾動的時候會調用的方法
//infinite-scroll-disabled = "busy" : 控制滾動加載是否有效,在busy爲false:滾動纔有效,才能觸發loadMore函數,爲true時,滾動不會觸發函數。
//infinite-scroll-distance="410" : 不是距離底部410px時才觸發loadMore函數
import {Button} from 'element-ui';
export default{
directives: {infiniteScroll},
components:{
[Button.name]: Button
},
data() {
return {
list: [],
loading: false,
pageSize: 10,
pageNum: 1,
busy: false, //滾動加載,是否觸發
};
},
methods: {
getOrderList() {
this.loading = true;
this.busy = true;
this.axios
.get("/orders", {
params: {
pageNum: 10,
pageNum: this.pageNum
}
})
.then(res => {
this.loading = false;
this.list = res.list.concat(res.list); //數據累加
this.busy = false;
})
.catch(() => {
this.loading = false;
});
},
getList() {
this.loading = true;
this.busy = true;
this.axios
.get("/orders", {
params: {
pageNum: 10,
pageNum: this.pageNum
}
})
.then(res => {
this.list = res.list.concat(res.list); //數據累加
this.loading = false;
if(res.hasNextPage) {
this.busy = false;
} else {
this.busy = true;
}
})
},
scrollMore() {
this.busy= true;
setTimeout(() => {
this.pageNum++;
this.getList();
}, 500)
}
}
};
</script>