❤️ 原文地址 ❤️
场景:A首页=> B列表页(需要缓存的页面)=> C详情页
由A到B到C再返回B的时候,B页面缓存,滚动到上次滚动的位置,如果由B返回到A,再进入B,B重新加载
根据业务逻辑需要实现部分页面缓存,且记住滚动位置,以及清部分缓存和全部缓存(如退出登录)
1、store 保存要缓存的页面
通过pinia
保存要缓存的页面, 来处理keep-alive include
缓存数据
keepAlive.ts
文件:
import { defineStore } from "pinia";
import { RouteRecordName } from "vue-router";
export const useKeepAlive = defineStore("keepAlive", {
state: () => {
return {
caches: [] as any,
};
},
getters: {},
actions: {
add(name: RouteRecordName| null | undefined) {
this.caches.push(name);
},
remove(name: RouteRecordName| null | undefined) {
this.caches = this.caches.filter((item: any) => item !== name);
},
clear() {
this.caches = [];
},
},
});
复制代码
2、根代码引入keep-alive
组件
APP.vue
根代码引入keep-alive
组件:
<template>
<router-view v-slot="{ Component }">
<keep-alive :include="keepAlive.caches">
<component :is="Component" :key="route.name" />
</keep-alive>
</router-view>
</template>
<script lang="ts" setup>
import { useRoute } from "vue-router";
import { useKeepAlive } from '@/storePinia/keepAlive';
const route = useRoute();
const keepAlive = useKeepAlive();
</script>
复制代码
keep-alive
include
必须要组件命名,对应要缓存的页面要添加:
<script lang="ts">
export default { name: 'list1' }; //name与路由name相同
</script>
复制代码
3、router 缓存、清除缓存
import {
createRouter,
createWebHashHistory,
RouteRecordRaw
} from 'vue-router';
import pinia from '@/store'
import { useKeepAlive } from '@/store/keepAlive';
const keepAlive = useKeepAlive(pinia);
const routes: Array<RouteRecordRaw> = [
。。。
]
const router = createRouter({
history: createWebHashHistory(),
routes,
})
router.beforeEach((to, from) => {
let routeFromTo=`${String(from.name)}>${String(to.name)}`;
console.log('路由',routeFromTo);
let addCacheArr=['home>list1','home>list2'];
let rmCacheArr=['list1>home','list2>home'];
if(addCacheArr.indexOf(routeFromTo)>-1){
//添加缓存
keepAlive.add(to.name)
return
}
if(rmCacheArr.indexOf(routeFromTo)>-1){
//删除缓存,清空缓存:keepAlive.clear()
keepAlive.remove(from.name)
}
})
export default router
复制代码
后面增加缓存页面,只需要在对应页面加上命名:export default { name: 'xxx' };
,然后,根据缓存需求修改router.ts
里对应的addCacheArr
、rmCacheArr
4、记住页面滚动位置
keepalive
缓存并没有缓存页面滚动位置,需要手动记录
可以在 layout
文件全局处理,在 keepalive
两个钩子函数中进行处理scroll
位置的缓存,onActivated
中获取缓存中的位置,onDeactivated
记录位置到缓存
<script setup lang="ts">
import { ref, onActivated, onDeactivated } from "vue";
const scrollTop = ref(0);
const handleScroll = () => {
// 记录滚动位置
scrollTop.value = document.getElementsByClassName("content")[0].scrollTop;
};
onActivated(() => {
console.log("onActivated");
if (scrollTop.value > 0) {
let body = document.getElementsByClassName("content")[0];
// 滚动到缓存的scroll值的位置
body.scrollTo(0, scrollTop.value);
scrollTop.value = 0;
}
window.addEventListener("scroll", handleScroll, true);
});
onDeactivated(() => {
console.log("onDeactivated");
// 页面退出时关闭事件,防止其他页面出现问题
window.removeEventListener("scroll", handleScroll, true);
});
</script>
复制代码