vue spa中页面切换效果的思路以及如何保留列表页的浏览状态

要解决的业务场景:列表页点击进入详情页,添加切换效果。并且:详情页返回时,并不改变列表页当前的浏览状态,比如下拉的滚动高度等。

这个问题,看着简单,解决起来却各种小问题不断。经过几番思考,才整理出一个感觉可用的方案

页面切换的时候,为了和原生体验更接近,页面切换的时候一般会添加一些交互效果。本文以左右滑动为例,子页面从右划入,父页面从左划入。

官方推荐

官方推荐的思路是,监听路由,路由切换的时候判断两个路由之间的'/'层级。如果存在大小关系,则添加切换效果,不存在则不添加。处理逻辑如下:

码友总结的技巧

官方推荐的思路,虽然能解决部分问题,但是实际业务中的逻辑切换,缺并不能简单的按照'/'的层级去区分层级。所以网友总结出一个更灵活的思路,就是把层级写到mata里,层级自己定义,自己判断 这样控制起来会相对灵活一些。

上面的思路面临的问题

上面的两个思路,其实算是一种,只是下面那个去了一步巧。面对我的业务逻辑,他们都有一个很不友好的体验

一 当前页面浏览高度问题:

场景是这样的:我从列表页向下浏览了1000px的内容,当前浏览到第12条文章。我点击第12条文章进入详情页。这时,详情页要从上向下浏览,所以向下浏览高度变成了0。这时候返回列表页的时候, 虽然数据不会清空,内容还在,但是出现在我面前的是第一条文章,而不是第12条。面对这个问题,我就必须要向下滑动才能继续浏览。


最终的思路

我认为,vue的keep-alive 虽然是可以缓存数据,但是web访问的局限性,他无法真正做到app中将当前的activiy进行缓存,打开一个新的activity, 而只能所有页面都在使用一个窗口。所以只是将当前页面缓存并跳转到其他页面,就会有浏览高度体验不好的情况。最终,我的思路是 在列表页添加一个routerView,并且添加切换效果。然后将详情页写成fixed,占满全屏。 我的考虑如下:

  • 一:要用路由切换而不能单纯将页面作为组件引入进来。

    这主要是为了面对两个场景。1:用户在详情页点击返回按钮,必须返回到列表页。但如果没有路由变化,则会跳出列表页。2:用户刷新的时候,如果没有路由记录,当前浏览的详情页将会消失

  • 二:我的路由配置规则是将路径提取出来的。虽然配置路由的时候,每个列表页都必须要为此添加一个子路由,但也不需要重复的创建组件引入组件。勉强还可以接受。
  • 列表页切换出去之后,并不需要缓存,不然放出这么多router-view在缓存里,也是一个很不友好的方式

弊端

  • 一:每个列表页都要添加一个router-view。这是当前这个思路最大的一个问题。
    { // 资讯列表
        name: '列表',
        path: routerWeb.List,
        component: () => import('@/pages/List/List.vue'),
        meta: {
          keepAlive: false,
          deepIndex: 1
        },
        children: [
          {// 资讯详情
            name: '详情',
            path: routerWeb.ListDetail,
            component: () => import('@/pages/Detail/Detail.vue'),
            meta: {
              keepAlive: false,
              deepIndex: 1
            }
          }
        ]
      }

      /***********
      内容页切换效果
       */
      .slide-left-in-enter-active,
      .slide-left-in-leave-active {
        will-change: transform;
        transition: all 200ms;
        position: absolute;
      }
      .slide-left-in-enter {
        opacity: 0;
        transform: translate3d(100%, 0, 0);
      }
      .slide-left-in-leave-active {
        opacity: 0;
        transform: translate3d(100%, 0, 0);
      }

随机浏览