您好,登錄后才能下訂單哦!
之前開發了一個單頁面應用,按照深度,分為三層:目錄頁、一級子頁(標簽頁、故事頁等)、二級子頁(故事編輯頁)。
這三類頁面都共享一個完整的數據model,從上級頁面進入下一級頁面時,能夠加載相應數據;回到上一級時,數據有更新。舉個栗子,從故事頁點擊“編輯”按鈕,進入故事編輯頁則默認填充點擊的“編輯”按鈕所對應的故事數據;而當在故事編輯頁更新數據,返回到故事頁時,剛剛更新的信息也能在故事頁展示。
對于這項需求,我們需要解決如下幾個問題:
本文后面內容,將對如上問題一一提出解決方案。
共享數據
多個路由共享數據,可以使用vuex做數據中心,由于需求對數據處理并不復雜,為了簡便就使用window全局對象作為路由間傳遞數據的工具。
核心數據我們可以設計為如下結構,以故事為例:
window.profileData = { storyList: [{ content: 'xxx', type: 0, picList: [...], }, ...], description: {...}, // 其他字段數據 }
注意到,如果需要更新storyList,則應該使用能夠被檢測到的方法,如push, splice等。
數據更新與緩存
數據更新與緩存大致有兩種方案:
第一種,利用vue-router的導航守衛(見文檔:https://router.vuejs.org/zh/guide/advanced/navigation-guards.html),主要使用路由組件內導航 beforeRouteEnter 和 beforeRouteLeave;
第二種,在路由組件中監聽$route,每次路由變化就會調用其中方法加載數據,需要注意的是第一次進入路由組件$route的監聽不會觸發,我們需要在mounted方法中調用相同加載數據的方法;
我們在代碼中使用的是方法一,以故事列表進入到故事編輯頁為例,從列表傳遞index給編輯頁,利用beforeRouteEnter進入路由時就加載新的數據。
編輯頁中關鍵代碼,即加載數據、更新本地共享數據:
export default { // 編輯頁中, 進入路由前加載數據 beforeRouteEnter(to, from, next) { next(vm => { const index = vm.$route.params.storyIndex vm.storyIndex = index vm.storyData = window.profile.storyList[index] }) }, methods: { // 提交成功后,更新本地共享數據 submit() { Adapter.post('...').then(result => { window.profile.storyList.splice(this.storyIndex, 1, result) }) }, }, }
列表頁中關鍵代碼,即返回時更新數據:
export default { beforeRouteEnter(to, from, next) { next(vm => { vm.storyList = window.profileData.storyList }) }, }
這部分需要注意的有兩點:
保留瀏覽位置
從故事編輯頁回到故事列表頁,我們希望可以保存之前瀏覽的位置。思路也很簡單,進入編輯頁時保存scrollTop,返回時scrollTo即可。而且vue-router對象有屬性可以實現這個功能,這就簡潔多了。
由于我們過渡動畫中間,有將路由組件定位成fixed的操作,所以,動畫結束后再手動滾動到目標位置:
new VueRouter({ routes, scrollBehavior (to, from, savedPosition) { const y = savedPosition && savedPosition.y || 0 setTimeout(() => { window.scrollTo(0, y) }, 300) } })
總結
vue-router我們在偏B端的場景中經常用到,尤其是分步驟填寫表單的頁面。前期在使用過程中總是不太順暢,摸索幾次后,最終找到比較“舒適”的使用方法,索性就梳理成文。
當然,還有其他一些特殊場景的用法,這里暫時不說了,等項目中用過后再另起一文,繼續研究。
參考文獻
1. 《官方文檔》
2. 《滾動行為》
以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持億速云。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。