vue keep-alive緩存問題

場景:
list頁面(要緩存),跳轉(zhuǎn)到details頁面,
需求:
1 從details頁面返回后 list頁面不刷新,并保持離開時(shí)的位置.
2 從其他任意頁面進(jìn)入list頁面,正常刷新

方案:
1 使用keep-alive包裹router-view

<div id="app">
        <keep-alive>
            <router-view v-if="$route.meta.keepAlive"></router-view>
        </keep-alive>

        <!-- 這里不會被keepalive -->
        <router-view v-if="!$route.meta.keepAlive"></router-view>
</div>

2 路由注冊,添加meta

 {
      path: '/list',
      name: 'List',
      component: () => import('@/pages/list.vue'),
      meta: {
        keepAlive: true
      }
},

3 list.vue中使用beforeRouteLeave鉤子

beforeRouteLeave(to, from, next) {
        if (to.name == "details") {
            from.meta.keepAlive = true
        } else {
            from.meta.keepAlive = false
        }
        next()
},

4 在組件中記錄scroll滑動的距離

this.scrollTop = document.querySelector(  ".scroll-box"  ).scrollTop

keep-alive緩存組件重新激活時(shí)會觸發(fā)activated周期函數(shù),在此函數(shù)中做滾動,回到跳轉(zhuǎn)details.vue前的位置

activated() {
       document.querySelector(".scroll-box").scrollTop = this.scrollTop 
},

問題:
list頁面會由于數(shù)據(jù)的不同,重復(fù)緩存,details返回后的頁面不是它的真正的上級頁面
場景還原:
點(diǎn)擊/list?id=01 下的01-item 前往01-item-details,返回后為/list?id=01下的頁面,正常
再點(diǎn)擊/list?id=02 下的02-item 前往02-item-details,返回后仍為/list?id=01下的頁面,異常
原因:第二次返回list?id=02時(shí)返回的是keep-alive已緩存的組件(即第一次緩存的list組件)

解決問題:
手動銷毀已緩存的list組件,使其每次進(jìn)入list都重新緩存新的頁面;
1 使用keep-aliveexclude屬性(任何名稱匹配的組件都不會被緩存)

<keep-alive :exclude="exclude" >
      <router-view v-if="$route.meta.keepAlive"></router-view>
</keep-alive>
data() {
    return {
      exclude: this.$exclude,
    }
  },

2 對list.vue中的beforeRouteLeave鉤子函數(shù)做修改

beforeRouteLeave(to, from, next) {
        // 離開list頁面且進(jìn)入的不是details頁面
        if (to.name != "details") {
          // exclude添加匹配后,會自動銷毀已緩存的組件
            this.$exclude.push(this.$options.name) 
          // 緩存組件銷毀后要把exclude中的匹配刪除,不然下次進(jìn)去頁面不會緩存當(dāng)前組件
            setTimeout(() => {
                for (let i = 0; i < this.$exclude.length; i++) {
                    if (this.$exclude[i] == this.$options.name) {
                        this.$exclude.splice(i, 1)
                        break
                    }
                }
            }, 0)
        }
        next()
    },
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容