vue中前进刷新、后退缓存用户浏览数据和浏览位置的实例讲解


Posted in Javascript onSeptember 21, 2018

vue中,我们所要实现的一个场景就是:

1.搜索页面==>到搜索结果页时,搜索结果页面要重新获取数据,

2.搜索结果页面==>点击进入详情页==>从详情页返回列表页时,要保存上次已经加载的数据和自动还原上次的浏览位置。

最近在项目中遇到这个问题,思考了几套方案,总是不太完善。百度搜到的方案也基本都只能满足一些很简单的需求。对于复杂一些的情况,还是有些不完善的地方。以下是个人对于这种场景的一个摸索,也参考了百度。如有更好的方案,欢迎指出。

缓存组件,vue2中提供了keep-alive。首先在我们的app.vue中定义keep-alive:

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

这里是根据路由中的meta源信息中的keepAlive字段来判断当前路由组件是否需要缓存。这里的meta的keepAlive是我们自定义的,当然你也可以叫别的名字。

下面在router/index.js即我们的路由文件中,定义meta信息:

// list是我们的搜索结果页面
{  
 path: '/list', 
 name: 'List',  
 component: resolve => require(['@/pages/list'], resolve), 
 meta: {  
  isUseCache: false, // 这个字段的意思稍后再说  
  keepAlive: true // 通过此字段判断是否需要缓存当前组件 
 } 
},

上面的component: resolve => require(['@/pages/list'], resolve)这里的组件引入方式可能和大家平时写的有些不一样,这里是为了路由的懒加载用的,大家可以忽略。按照正常的import引入也可以,这个和本次的主题无关。如此一来,vue的路由会帮我们去缓存list页面。

刷新数据or缓存数据的实现:

说这之前,先简单说一下和缓存相关的vue钩子函数。

设置了keepAlive缓存的组件:

第一次进入:beforeRouterEnter ->created->…->activated->…->deactivated

后续进入时:beforeRouterEnter ->activated->deactivated

可以看出,只有第一次进入该组件时,才会走created钩子,而需要缓存的组件中activated是每次都会走的钩子函数。所以,我们要在这个钩子里面去判断,当前组件是需要使用缓存的数据还是重新刷新获取数据。思路有了,下面我们来实现:

// list组价的activated钩子
 activated() {
 // isUseCache为false时才重新刷新获取数据
 // 因为对list使用keep-alive来缓存组件,所以默认是会使用缓存数据的   
 if(!this.$route.meta.isUseCache){   
  this.list = []; // 清空原有数据
  this.onLoad(); // 这是我们获取数据的函数
 } 
},

这里的isUseCache 其实就是我们用来判断是否需要使用缓存数据的字段,我们在list的路由的meta中已经默认设置为false,所以第一次进入list时是获取数据的。

当我们从详情页返回时,我们把list页面路由的isUseCache设置成true,这样我们在返回list页面时会使用缓存数据:

// 详情页面的beforeRouteLeave钩子函数
beforeRouteLeave (to, from, next) {  
 if (to.name == 'List') {
  to.meta.isUseCache = true; 
 }  
 next();
},

我们这里是在即将离开detail页面前判断是否返回的列表页。如果是返回list页面,则把list页面路由的isUseCache字段设置成true。为什么这样设置呢?因为我们对list组件使用的keep-alive进行缓存组件,其默认就是使用缓存的。而我们又在list组件的actived钩子函数中进行了判断:只有在list页面的isUseCache==false时才会清空原有数据并重新获取数据。所以此处设置isUseCache为true,此时返会list页面是不会重新获取数据的,而是使用的缓存数据。

detail返回list可以缓存数据了,那么search前往list页面时怎么让list页面不使用缓存数据而是获取新数据呢?我们重新回到list的activated钩子中:

// list组价的activated钩子
 activated() {
 // isUseCache为false时才重新刷新获取数据
 // 因为对list使用keep-alive来缓存组件,所以默认是会使用缓存数据的   
 if(!this.$route.meta.isUseCache){   
  this.list = []; // 清空原有数据
  this.onLoad(); // 这是我们获取数据的函数
  this.$route.meta.isUseCache = false; } 
},

我们加了一行this.$route.meta.isUseCache=false;也就是从detail返回list后,将list的isUseCache字段为false,而从detail返回list前,我们设置了list的isUseCache为true。所以,只有从detail返回list才使用缓存数据,而其他页面进入list是重新刷新数据的。

至此,一个前进刷新、后退返回的功能基本完成了。

如果场景再复杂一丢丢,比如,如果这个详情页是个订单详情,那么在订单详情页可能会有删除订单的操作。那么删除订单操作后会返回订单列表页,是需要列表页重新刷新的。那么我们需要此时在订单详情页进行是否要刷新的判断。简单改造一下详情页:

data () { 
 return {
  isDel: false // 是否进行了删除订单的操作  
 }
},
beforeRouteLeave (to, from, next) {  
 if (to.name == 'List') {
  // 根据是否删除了订单的状态,进行判断list是否需要使用缓存数据
  to.meta.isUseCache = !this.isDel;    
 }  
 next(); 
},
methods: {  
 deleteOrder () {  
  // 这里是一些删除订单的操作
 
  // 将状态变为已删除订单
  // 所以beforeRouteLeave钩子中就会将list组件路由的isUseCache设置为false 
  // 所以此时再返回list时,list是会重新刷新数据的 
  this.isDel = true; 
  this.$router.go(-1)
 }
}

至此,算是解决了我的vue项目中的这个前进刷新、后退缓存数据和浏览位置的问题。

最后再提一下,页面滚动位置的问题。

问题1:我们知道,在vue这种单页应用中,如果你在a页面滚动了一段距离后,此时前往b页面后,b页面也会停留在a页面的滚动位置。这个问题的解决,我们可以利用router本身提供的功能来解决:

routes: [ 
 {  
  path: '/detail',  
  name: 'Detail',  
  component: resolve => require(['@/pages/detail'], resolve) 
 } 
],
scrollBehavior (to, from, savedPosition) {
 if (savedPosition) {  
   return savedPosition 
 } else {  
   if (from.meta.keepAlive) {  
    from.meta.savedPosition = document.body.scrollTop;  
   }  
   return { x: 0, y: to.meta.savedPosition || 0 } 
 } 
}

scrollBehavior是路由提供的基础功能,这段函数写的是:

1.如果通过浏览器自带的前进后退按钮切换的路由,那么会自动使用浏览默认的回滚上次页面的浏览位置。

2.如果是通过vue路由进行的页面切换。例如a前往b,首先判断a是不是通过keep-alive缓存的组件,如果是,则在a路由的meta中添加一个savedPosition字段,并且值为a的滚动位置。最后return的是页面需要回滚的位置。如此一来,如果打开一个页面,该页面的组件路由中meta.savedPosition为undefined的话,则页面滚动到(0,0)的位置,这样解决了问题1。那么如果打开一个页面,它的路由的meta.savedPosition有值的话,则滚动到上次浏览的位置,因为meta.savedPosition保存的就是上次浏览的位置。

以上这篇vue中前进刷新、后退缓存用户浏览数据和浏览位置的实例讲解就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
filters.revealTrans.Transition使用方法小结
Aug 19 Javascript
网页右下角弹出窗体实现代码
Jun 05 Javascript
jQuery插件pagination实现分页特效
Apr 12 Javascript
更高效的使用JQuery 这里总结了8个小技巧
Apr 13 Javascript
JavaScript使用delete删除数组元素用法示例【数组长度不变】
Jan 17 Javascript
Bootstrap导航中表单简单实现代码
Mar 06 Javascript
JS实现的简单拖拽功能示例
Mar 13 Javascript
详解微信小程序与内嵌网页交互实现支付功能
Oct 22 Javascript
Angular2 自定义表单验证器的实现方法
Dec 14 Javascript
解决IOS端微信H5页面软键盘弹起后页面下方留白的问题
Jun 05 Javascript
Js通过AES加密后PHP用Openssl解密的方法
Jul 12 Javascript
BootStrap表单验证中的非Submit类型按钮点击时触发验证的坑
Sep 05 Javascript
vue单页面应用打开新窗口显示跳转页面的实例
Sep 21 #Javascript
详解Vue改变数组中对象的属性不重新渲染View的解决方案
Sep 21 #Javascript
默认浏览器设置及vue自动打开页面的方法
Sep 21 #Javascript
详解Vue中数组和对象更改后视图不刷新的问题
Sep 21 #Javascript
详解vue 数组和对象渲染问题
Sep 21 #Javascript
vue 2.8.2版本配置刚进入时候的默认页面方法
Sep 21 #Javascript
Puppeteer环境搭建的详细步骤
Sep 21 #Javascript
You might like
Windows下的PHP5.0安装配制详解
2006/09/05 PHP
PHP中调用C/C++制作的动态链接库的教程
2016/03/10 PHP
PDO::lastInsertId讲解
2019/01/29 PHP
项目实践之javascript技巧
2007/12/06 Javascript
JS 自动安装exe程序
2008/11/30 Javascript
javascript开发中因空格引发的错误
2010/11/08 Javascript
浅析jQuery的链式调用之each函数
2010/12/03 Javascript
裁剪字符串trim()自定义改进版
2013/04/10 Javascript
jQuery中校验时间格式的正则表达式小结
2013/09/22 Javascript
JS烟花背景效果实现方法
2015/03/03 Javascript
jQuery 监控键盘一段时间没输入
2016/04/22 Javascript
使用JS和canvas实现gif动图的停止和播放代码
2017/09/01 Javascript
vue+axios+mock.js环境搭建的方法步骤
2018/08/28 Javascript
react同构实践之实现自己的同构模板
2019/03/13 Javascript
如何利用vue+vue-router+elementUI实现简易通讯录
2019/05/13 Javascript
详解element-ui动态限定的日期范围选择器代码片段
2020/07/03 Javascript
vue-router为激活的路由设置样式操作
2020/07/18 Javascript
详解Vue中Axios封装API接口的思路及方法
2020/10/10 Javascript
分析Python中解析构建数据知识
2018/01/20 Python
Python编程深度学习绘图库之matplotlib
2018/12/28 Python
Python使用paramiko操作linux的方法讲解
2019/02/25 Python
Django框架静态文件使用/中间件/禁用ip功能实例详解
2019/07/22 Python
Python的互斥锁与信号量详解
2019/09/12 Python
HTML5中微数据概述及在搜索引擎中的使用举例
2013/02/07 HTML / CSS
Myprotein蛋白粉美国官网:欧洲畅销运动营养品牌
2016/11/15 全球购物
慕尼黑山地运动、户外服装和体育用品专家:Sporthaus Schuster
2019/08/27 全球购物
意大利领先的奢侈品在线时装零售商:MCLABELS
2020/10/13 全球购物
大学生的四年学习自我评价
2013/12/13 职场文书
《和我们一样享受春天》教学反思
2014/02/07 职场文书
2014年中班元旦活动方案
2014/02/14 职场文书
元旦晚会策划方案
2014/02/18 职场文书
创业大赛策划书
2014/03/01 职场文书
毕业评语大全
2014/05/04 职场文书
对领导班子的意见和建议
2015/06/08 职场文书
2016三八妇女节校园广播稿
2015/12/17 职场文书
Python基本数据类型之字符串str
2021/07/21 Python