使用版本

        "vue": "2.5.10",
        "vue-router": "3.0.1",
         "vuex": "3.0.1",

        正如购物网站商品列表,点击商品查看详情,回退回商品列表,依然是之前看商品的位置。从其他页面进入商品列表,列表重新获取为初始状态。

        要完成这个功能,需要增加缓存,使用vue自带的keep-alive功能。在尝试了多种方式之后,实现需要的效果。


先上正确的解决方式:

 1、增加<keep-alive>

        理论:vuex增加维护缓存的state,根据当前路由判断是否缓存目标页面。

        路由维护增加<keep-alive>,使用include维护是否缓存组件。

        include是字符串或者正则表达式,跟组件的name对应。

注意组件的name一定要和include对应,之前由于没有设置组件的name,导致功能不生效。跟路由的name无关。

<template>
  <section class="app-main">
    <transition name="fade" mode="out-in">
      <div class="box-card" id="boxarea">
        <keep-alive :include="aliveRoutes">
          <router-view></router-view>
        </keep-alive>
      </div>
    </transition>
  </section>
</template>

<script>
import { mapGetters } from 'vuex'
export default {
  name: 'AppMain',
  computed: {
    ...mapGetters('cachedRoutes', ['aliveRoutes']),
  },
  data() {
    return {
    }
  },

}
</script>

2、vuex增加state

        cachedRouters.js

 这里aliveRoutes用一个数组维护,之前用字符串维护的,发现当是空串时,include也会匹配成功,故做此修改。

3、列表页面增加name,beforeRouteEnter,beforeRouteLeave

目的:当从列表页面进入详情,缓存字段增加组件名称,当从该列表页面进入其他页面,清除缓存,缓存字段去掉该组件名称。

当前仅一个列表页,就固定了值,多个字段维护同理。

和data、methods同级别

 beforeRouteEnter(to, from, next) {
    next((vm) => {
        vm.updateAliveRoutes('statistics')
    })
  },

  beforeRouteLeave(to, from, next) {
    if (to.name === 'statisticsContent') {
        this.updateAliveRoutes('statistics')
    } else {
      this.updateAliveRoutes('')
    }
    next()
  },

 至此,最简易式缓存维护生成且有效~~~ 2021.12.15


避坑说明:

也尝试过在列表组件的beforeRouteLeave时候,根据直接修改路由的meta的keepAlive属性,却无法清除缓存,后增加$destory()方法后,发现清除缓存了之后,再生成缓存却生成不上了。

最终还是需要增加全局状态来维护靠谱。

升级补充:

可放到路由守卫中统一管理

​​​​​​​

 

const cachedRoutes = {
  namespaced: true,
  state: {
    aliveRoutes: [''],
  },
  getters: {
    aliveRoutes: (state) => state.aliveRoutes,
  },
  mutations: {
    UPDATE_ALIVEROUTES: (state, data) => {
      state.aliveRoutes = data
    },
  },
  actions: {
    updateAliveRoutes({ commit }, payload) {
      // console.log('actions', payload)
      commit('UPDATE_ALIVEROUTES', payload)
    },
  },
}
export default cachedRoutes

一些keep-alive 知识:

Props

  • include - 字符串或正则表达式。只有名称匹配的组件会被缓存。
  • exclude - 字符串或正则表达式。任何名称匹配的组件都不会被缓存。
  • max - 数字。最多可以缓存多少组件实例。
  • activated 当 keep-alive 包含的组件再次渲染的时候触发
  • deactivated 当 keep-alive 包含的组件销毁的时候触发
// 所有路径匹配到的视图组件都会被缓存! 
<keep-alive>
    <router-view></router-view>
</keep-alive>

// 只缓存组件name为aa或者bb的组件
<keep-alive include="aa,bb"> 
  <component />
</keep-alive>

// 组件name为cc的组件不缓存
<keep-alive exclude="cc"> 
  <component />
</keep-alive>

// 如果同时使用include,exclude,那么exclude优先于include, 下面的例子只缓存aa组件
<keep-alive include="aa,bb" exclude="bb"> 
  <component />
</keep-alive>

// 如果缓存的组件超过了max设定的值3,那么将删除第一个缓存的组件
<keep-alive exclude="c" max="3"> 
  <component />
</keep-alive>

Logo

Vue社区为您提供最前沿的新闻资讯和知识内容

更多推荐