date | tags |
---|---|
2019-05-23 |
javascript |
当项目大了再重点关注这个问题确实是失误。为了有更沉浸的体验,产品会把逻辑穿梭在不同的页面,越繁琐用户越容易迷路,我们应该知道如何不让用户迷路。不同平台的页面栈有自己的优势或局限性,提前更深入的理解,可以将风险提前抛出,引导产品在特定平台产出正确设计,研发可以让这件事更好。
h5和小程序都有页面栈的概念,要知道这些页面栈设计的特点,业务才会不坑,而且从学习的角度,再接触新平台更容易对比学习。
-
出栈的时机不同。小程序后退就清空,h5后退不清空,仍然可前进,也就是后退实际上是指针前移,访问新页面会清空该指针之后的栈元素。
-
栈的深度不同。h5可以有很深的栈,小程序的栈只有5层,爆栈会让用户无法向下跳转,从数据结构上讲,它不是一个双端队列,不会用更廉价的数据结构替代栈底的webview,这种设计偶尔会让产品设计变得受限,但也保护小程序的用户体验。
-
小程序支持修改栈内任意页面的数据,可以不动声色的影响其他页面,小程序本身可以理解为一个大单页应用,它有单页h5才能达到的能力。
-
小程序有个特殊的页面类型tabBar页面。特殊在使用
switchTab
的时候只清空非tabBar页面,意味着它优先级略高,我理解它从产品角度的定义是一组平行的入口页。tabBar最多可以有5个,够用了。
关于页面栈的操作,h5和小程序一致的地方。
- 小程序支持清空栈,使用
reLaunch
,h5则可以通过history.go(-history.length + 1)
到达栈顶(姑且认为没有前进的ui,算是逻辑意义上的清空)。 - 小程序支持替换栈顶页面,使用
redirectTo
,h5通过location.replace
,history.replaceState
也可以。
流程图很重要,它其实隐藏着一部分需求,除了流程更清晰,工作量更可视化,他也能帮我们发现产品中不合理的流程,以及尽早暴露业务上必须但技术上难实现的风险点。至于怎么画有更专业的解读,我也没必要献丑,找了个高票的,感兴趣可以看下。
在页面流程图中,研发还需要重点关注一下,哪些页面是平行关系,哪些页面是阅后即焚的(如登陆注册),确认前进和回退的逻辑。我先用一个简单的树状图表达页面的层级关系(层级,不是完整流程,但恰恰是主流程)。
从产品的归属关系上,可以把页面分层,这时更像是一个树,这样的好处是可以把跳转抽象&归类,对于研发来讲:
- 可以更清楚该如何调用api。
- 可以更清楚的跟产品表达跳转的逻辑风险,以及hack后的体验折损。
各个平台的api可能不一样,我用一组原语表示api控制流转,
forward(P)
前进到P
页面,back(N)
出栈N
个页面(回退),redirect(P)
替换栈顶为P
页面,restart(P)
清空栈并跳转到P
(以P作为入口重新预览)。通过forward
建栈,forward(A), forward(B)
之后的栈结构为[A, B]
。
假设上图没有其他边了,那么整个流程的前进&回退都是完整的。
A -> B -> C
。假设B
是一个说明页,体验上讲C
退回的时候最好直接到A
。那么B -> C
这一步跳转的api调用为redirect(C)
,B
页面阅后即焚了。
C -> A
。可能会有多个入口页,有可能是C -> A1
,C -> A2
,入口要单独分类的意义就在这,如果是回到入口页,那么在C
页面调用restart(A)
。
C -> D
。这一步跳转的api调用为redirect(D)
,算是在B
的子功能的沉浸式体验的做法。比如:
- 同一本小说的不同章节。
- 抖音和快手的列表对比(快手不够沉浸,每次回退出来)。
为了保持到F页面的时候。简单粗暴,重新建栈。
C -> F
。
back(1)
forward(E)
forward(F)
优化算法,因为有redirect
操作,利用平级跳转。
redirect(E)
forward(F)
F -> B
。因为B
是F
的祖先节点所以直接back
可保证B
的栈完整。
back(2)
多步操作有平台局限,如果平台支持的不好,对用户体验会有质的破坏。
back(1), forward(E), forward(F)
把原语对应到平台的操作,h5单页面或许很ok,但是在小程序里面交互却并不好,back
和forward
会有明显的时间延迟。而常见的react-router
实现,对于多步的同步路由操作有没有debounce
?这也是个需要看的问题。
具体情况具体分析,可以:
forward(F)
或许这样也行?
redirect(F)
总之怎样不奇怪就怎样来吧。
OUTER -> E
这时候栈是不完整的,要看具体需求定制回退效果:
- 回退直接退出。
- 回退到首页以触达用户使用(这种情况大多是海报页面,回首页,会有完整的体验)。
对于第二种,流程应该是这样OUTER -> A -> forward(E)
。这样可以满足需求。
泛客户端知识,值得思考。后续想写个lib支持一下,可以输出转化过程原语表述。