Vue2.5仿去哪兒——vuex 公共畫廊元件 導航欄的漸變出現
阿新 • • 發佈:2018-12-04
Vue2.5仿去哪兒app 實戰專案筆記
利用vuex實現跨頁面資料共享 公共畫廊元件 導航欄的漸變出現
利用vuex實現跨頁面資料共享
要同時改變兩個頁面的資料,但city.vue和home.vue之間沒有一個共同的父級元件,所以無法通過類似前面的父級元件進行資料中轉。所以可以用vuex來進行資料管理。
vuex就是通過把所有的公用資料放到一個公共的資料空間去儲存,某一個元件改變了這個公用資料,其他元件也能感知到並動態變化。
其中:
- state: 存放所有公用資料
- Actions: 非同步處理或者批量的同步操作
- Mutation: 對state進行最後的修改
整體來說,就是components呼叫acions,actions呼叫mutations,mutations改變state.
使用vuex
1、建立store資料夾和index.js
//store/index.js
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
export default new Vuex.Store({
state: {
city: '上海'
//這個資料分別被home.vue中的header元件,
//city.vue中的list元件所用
}
})
2、元件通過呼叫$store呼叫資料
在建立store後,即city資料由前端儲存和改變,代替掉原來通過ajax返回後端資料。
要使所有元件都能用公用資料,需在main.js中宣告store。
這樣,當在city.vue中改變當前城市,需要使得home.vue中的當前城市也一起動態變化。
<!--在list.vue和header.vue呼叫公共資料city-->
<div class="header-right">
{ {this.$store.state.city} }
<!--呼叫store中的公共資料-->
< span class="iconfont icon-down"></span>
</div>
3、在元件中改變公共資料
在city頁面中的list元件和search元件,通過點選實現當前城市的切換,用到vuex中的actions
changeCity (city) {
//this.$store.dispatch('changeCity', city)
this.$store.commit('changeCity', city)
this.$router.push('./')
//修改完當前城市後,自動跳轉回主頁
}
//store/index.js
/**可略過Actions,元件直接去呼叫mutations,修改資料。
action: {
changeCity(ctx, city) {
ctx.commit('changeCity',city)
}
},
**/
mutations: {
changeCity (state, city) {
state.city = city
}
}
})
公共畫廊元件
在詳情頁,需要用到一個公共畫廊元件。當點選詳情頁面中的圖片時,畫廊會跳出並覆蓋整個頁面,通過輪播圖模式可左右滑動。並且底部有pagination,顯示當前頁面位置。
其中畫廊中的圖片,通過父子元件傳值獲取。
//gallary.vue
//gallary.vue作為banner.vue的元件,與其實父子元件的關係
props: {
imgs: {
type: Array,
default () {
return []
}
}//從banner.vue獲取資料
},
data () {
return {
swiperOption: {
pagination: '.swiper-pagination',
paginationType: 'fraction',
observeParents: true,
observer: true
}
}
},
methods: {
turnGallary () {
this.$emit('close')
//在gallary.vue中向外(banner.vue)觸發事件,在banner.vue中處理
}
}
頂部導航欄的漸變出現
詳情頁首頁沒有導航欄,下拉詳情頁時,當下拉到一定畫素,頂部漸變出現導航欄。所以header.vue中包括兩個結構,用過v-show
指令控制其交替出現。
<div>
<router-link rag="div" to="/" class="header-abs" v-show="showABS">
<span class="iconfont"></span>
</router-link>
<div class="header-fixed" v-show="!showABS" :style="opacityStyle">
景點詳情
<router-link to='/'>
<span class="iconfont"></span>
</router-link>
</div>
</div>
data () {
return {
showABS: true,
opacityStyle: {
opacity: 0
//控制
}
}
},
methods: {
handleScroll () {
const top = document.documentElement.scrollTop
if (top > 60) {
//當下拉60畫素後,頂部漸變出現導航欄
let opacity = top / 140
opacity = opacity > 1 ? 1 : opacity
this.opacityStyle = { opacity }
this.showABS = false
} else {
this.showABS = true
}
}
},
mounted () {
window.addEventListener('scroll', this.handleScroll)
//獲取滾動條
}