深入理解vue-router之keep-alive


Posted in Javascript onAugust 31, 2017

本文基于 Vue2.0

keep-alive 简介

keep-alive 是 Vue 内置的一个组件,可以使被包含的组件保留状态,或避免重新渲染。

用法也很简单:

<keep-alive>
 <component>
  <!-- 该组件将被缓存! -->
 </component>
</keep-alive>

props

  • include - 字符串或正则表达,只有匹配的组件会被缓存
  • exclude - 字符串或正则表达式,任何匹配的组件都不会被缓存
// 组件 a
export default {
 name: 'a',
 data () {
  return {}
 }
}
<keep-alive include="a">
 <component>
  <!-- name 为 a 的组件将被缓存! -->
 </component>
</keep-alive>可以保留它的状态或避免重新渲染
<keep-alive exclude="a">
 <component>
  <!-- 除了 name 为 a 的组件都将被缓存! -->
 </component>
</keep-alive>可以保留它的状态或避免重新渲染

遇见 vue-router

router-view 也是一个组件,如果直接被包在 keep-alive 里面,所有路径匹配到的视图组件都会被缓存:

<keep-alive>
  <router-view>
    <!-- 所有路径匹配到的视图组件都会被缓存! -->
  </router-view>
</keep-alive>

然而产品汪总是要改需求,拦都拦不住...

问题

如果只想 router-view 里面某个组件被缓存,怎么办?

  • 使用 include/exclude
  • 增加 router.meta 属性

使用 include/exclude

// 组件 a
export default {
 name: 'a',
 data () {
  return {}
 }
}
<keep-alive include="a">
  <router-view>
    <!-- 只有路径匹配到的视图 a 组件会被缓存! -->
  </router-view>
</keep-alive>

exclude 例子类似。

缺点:需要知道组件的 name,项目复杂的时候不是很好的选择

增加 router.meta 属性

// routes 配置
export default [
 {
  path: '/',
  name: 'home',
  component: Home,
  meta: {
   keepAlive: true // 需要被缓存
  }
 }, {
  path: '/:id',
  name: 'edit',
  component: Edit,
  meta: {
   keepAlive: false // 不需要被缓存
  }
 }
]
<keep-alive>
  <router-view v-if="$route.meta.keepAlive">
    <!-- 这里是会被缓存的视图组件,比如 Home! -->
  </router-view>
</keep-alive>

<router-view v-if="!$route.meta.keepAlive">
  <!-- 这里是不被缓存的视图组件,比如 Edit! -->
</router-view>

优点:不需要例举出需要被缓存组件名称

【加盐】使用 router.meta 拓展

假设这里有 3 个路由: A、B、C。

需求:

  • 默认显示 A
  • B 跳到 A,A 不刷新
  • C 跳到 A,A 刷新

实现方式

在 A 路由里面设置 meta 属性:

{
  path: '/',
  name: 'A',
  component: A,
  meta: {
    keepAlive: true // 需要被缓存
  }
}

在 B 组件里面设置 beforeRouteLeave:

export default {
  data() {
    return {};
  },
  methods: {},
  beforeRouteLeave(to, from, next) {
     // 设置下一个路由的 meta
    to.meta.keepAlive = true; // 让 A 缓存,即不刷新
    next();
  }
};

在 C 组件里面设置 beforeRouteLeave:

export default {
  data() {
    return {};
  },
  methods: {},
  beforeRouteLeave(to, from, next) {
    // 设置下一个路由的 meta
    to.meta.keepAlive = false; // 让 A 不缓存,即刷新
    next();
  }
};

这样便能实现 B 回到 A,A 不刷新;而 C 回到 A 则刷新。

总结

路由大法不错,不需要关心哪个页面跳转过来的,只要 router.go(-1) 就能回去,不需要额外参数。

然而在非单页应用的时候,keep-alive 并不能有效的缓存了= =

参考

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
Firefox下提示illegal character并出现乱码的原因
Mar 25 Javascript
用jquery设置按钮的disabled属性的实现代码
Nov 28 Javascript
Jquery实现自定义窗口随意的拖拽
Mar 12 Javascript
自己封装的常用javascript函数分享
Jan 07 Javascript
js图片卷帘门导航菜单特效代码分享
Sep 10 Javascript
JS实现超精简响应鼠标显示二级菜单代码
Sep 12 Javascript
jquery转盘抽奖功能实现
Nov 13 Javascript
JS禁止查看网页源代码的实现方法
Oct 12 Javascript
使用纯JS代码判断字符串中有多少汉字的实现方法(超简单实用)
Nov 12 Javascript
js 取消页面可以选中文字的功能方法
Jan 02 Javascript
Vue实现验证码功能
Dec 03 Javascript
原生js实现html手机端城市列表索引选择城市
Jun 24 Javascript
vue-router 导航钩子的具体使用方法
Aug 31 #Javascript
浅谈express 中间件机制及实现原理
Aug 31 #Javascript
JavaScript 通过Ajax 动态加载CheckBox复选框
Aug 31 #Javascript
BootStrap下的弹出框加载select2框架失败的解决方法
Aug 31 #Javascript
Angular2 http jsonp的实例详解
Aug 31 #Javascript
BootStrap中Table隐藏后显示问题的实现代码
Aug 31 #Javascript
Cpage.js给组件绑定事件的实现代码
Aug 31 #Javascript
You might like
PHP4引用文件语句的对比
2006/10/09 PHP
php带密码功能并下载远程文件保存本地指定目录 修改加强版
2010/05/16 PHP
thinkphp3.2中Lite文件替换框架入口文件或应用入口文件的方法
2015/05/21 PHP
tp5(thinkPHP5)框架实现多数据库查询的方法
2019/01/10 PHP
Nigma vs Liquid BO3 第一场2.14
2021/03/10 DOTA
javascript下IE与FF兼容函数收集
2008/09/17 Javascript
js setTimeout opener的用法示例详解
2013/10/23 Javascript
深入理解javascript的执行顺序
2014/04/04 Javascript
javascript实现网页屏蔽Backspace事件,输入框不屏蔽
2015/07/21 Javascript
jQuery实现图片渐入渐出切换展示效果
2015/08/15 Javascript
AngularJS中的表单简单入门
2016/07/28 Javascript
jQuery给指定的table动态添加删除行的操作方法
2016/10/12 Javascript
ES6下React组件的写法示例代码
2017/05/04 Javascript
教你5分钟学会用requirejs(必看篇)
2017/07/25 Javascript
vue 怎么创建组件及组件使用方法
2017/07/27 Javascript
11行JS代码制作二维码生成功能
2018/03/09 Javascript
关于Vue源码vm.$watch()内部原理详解
2019/04/26 Javascript
highcharts.js数据绑定方式代码实例
2019/11/13 Javascript
[49:29]LGD vs Winstrike 2018国际邀请赛小组赛BO2 第一场 8.17
2018/08/18 DOTA
Python中的rfind()方法使用详解
2015/05/19 Python
Python实时获取cmd的输出
2015/12/13 Python
Tornado 多进程实现分析详解
2018/01/12 Python
python之拟合的实现
2019/07/19 Python
PyQt5基本控件使用之消息弹出、用户输入、文件对话框的使用方法
2019/08/06 Python
Pandas中DataFrame交换列顺序的方法实现
2020/12/14 Python
新加坡网上花店:FlowerAdvisor新加坡
2018/10/05 全球购物
蔻驰法国官网:COACH法国
2018/11/14 全球购物
求两个数的乘积和商数,该作用由宏定义来实现
2013/03/13 面试题
渡河少年教学反思
2014/02/12 职场文书
音乐兴趣小组活动总结
2014/07/07 职场文书
公务员爱岗敬业演讲稿
2014/08/26 职场文书
公司的门卫岗位职责
2014/09/09 职场文书
党员干部公开承诺书范文
2015/04/27 职场文书
python实现简单的名片管理系统
2021/04/26 Python
JavaScript实现简单计时器
2021/06/22 Javascript
Win11跳过联网界面创建本地管理账户的3种方法
2022/04/20 数码科技